package tcp import ( "fmt" "go.uber.org/zap" "net" "server/dao" "server/global" "time" ) var ( Devices = make(map[string]*Device) // 存储连接的全局 map ) type Device struct { Info dao.Screens Conn net.Conn IsLogin bool LastTime time.Time } // 实例所有设备 func InitDevices() { //// 将数据库中的设备全部离线 //screens, _ := dao.QueryAllScreens() //for _, screen := range screens { // Devices[screen.Sn] = &Device{Info: screen} //} } func (s *Device) Start(conn net.Conn) { s.Conn = conn go s.Process() } func (s *Device) Process() { // 函数执行完之后关闭连接 defer s.Conn.Close() for { buf := make([]byte, 256) // 将tcp连接读取到的数据读取到byte数组中, 返回读取到的byte的数目 n, err := s.Conn.Read(buf) if err != nil { // 从客户端读取数据的过程中发生错误 这里如果没读到可以视为设备离线了 global.GVA_LOG.Error("read err,dev offLine") break } data := string(buf[:n]) fmt.Println("读取", string(buf[:n])) if data[2:7] == "login" { s.Conn.Write([]byte("login:successful")) } if data[2:11] == "heartbeat" { //默认一分钟发一次心跳 s.LastTime = time.Now() if !s.IsLogin { screen, _ := dao.QueryScreensBySn(data[20:44]) s.Info = screen s.IsLogin = true Devices[data[20:44]] = s _ = dao.UpdateScreensStatusBySn(s.Info.Sn, 1) } //更新上次发送心跳时间 global.GVA_LOG.Info("设备心跳", zap.String("ScreensName", s.Info.ScreensName)) } } } func IsOnline() { t := time.NewTicker(1 * time.Minute) //每分钟 for { select { case <-t.C: for _, device := range Devices { //符合条件 if time.Now().Add(-2*time.Minute).After(device.LastTime) || device.LastTime.IsZero() { state := 0 err := dao.UpdateScreensStatusBySn(device.Info.Sn, state) delete(Devices, device.Info.Sn) if err != nil { continue } device.Info.Status = 0 global.GVA_LOG.Info("设备离线了", zap.String("ScreensName", device.Info.ScreensName)) } } } } }