func main() { logger.Info("Go router running \r\n") //init logger logger.GetLogger().SetLogLevel(5, 5) logger.GetLogger().SetOutputDir(`c:\`) logger.GetLogger().Init("testlog") //init tcp server logger.Info("Go run TCPServer \r\n") tcpServer := server.NewTCPServer("tcp", ":9093") //setup handler tcpServer.GetRouter().SetConnHandler(&ConnHandlerImpl{}) tcpServer.GetRouter().SetDisconHandler(&DisconHandlerImpl{}) //register handler tcpServer.GetRouter().SetTcpHandler(map[uint8]router.Handler{ 0x0: &MyHandlerImpl{}, }) //register Ipc handler tcpServer.GetRouter().SetIpcHandler(map[string]router.IpcHandler{}) //startup tcpServer.Run() <-exitChan }
func (this *ConnHandlerImpl) Handle(client *client.Client, ch chan []byte) *client.Client { go util.TraceCrashStack() logger.Info("TODO: i am the conn handler \n") select { case res := <-ch: //it handle the data like flash sandbox and other logger.Info("TODO: ConnHandlerImpl first data %v \n", string(res)) case <-time.After(time.Second * 60): logger.Info("when somebody connect but no packs to send , this operation will disconnect it\n") //client.GetConn().Close() } return nil }
func (this *WsUserHandlerImpl) Handle(client *client.Client, command string, data string) *client.Client { logger.Info("TODO: WsUserHandlerImpl data = %v \n", data) switch command { case "echo": //TODO: logger.Info("echo server \n") client.WsSend("user", "echo", data) break default: //TODO: break } return nil }
func (this *Connection) serveWsHandle() { defer util.TraceCrashStackAndHandle(func() { this.Conn.Close() }) logger.Info("Websocket handle looping tcp \n") defer this.Conn.Close() client := client.NewClient(this.Conn) //serve when connect go router.GetRouter().ConnHandler.Handle(client, this.FirstDataChan) //loop recv protocol for { select { case wp, _ := <-this.WsChan: //get handler logger.Info("handle module:%v command:%v data:%v \n", wp.Module, wp.Command, string(wp.Data)) h := router.GetRouter().GetWsHandler()[wp.Module] if h != nil { c := h.Handle(client, string(wp.Data)) if c != nil { client = c } } case data, ok := <-this.IpcChan: logger.Info("IPCHandler %v %v\r\n", data.Data, ok) h := router.GetRouter().GetIpcHandler()[data.ModuleId] if h != nil { c := h.Handle(client, data.CommandId, data.Data) if c != nil { client = c } } break case data, ok := <-this.ExitChan: logger.Info("ExitHandler %v %v\r\n", data, ok) router.GetRouter().GetDisconHandler().Handle(client) return } } fmt.Printf("ServeHandle ending \n") }
// into the handler func (this *Connection) serveHandle() { logger.Info("TCPHandle looping tcp \n") defer this.Conn.Close() client := client.NewClient(this.Conn) defer util.TraceCrashStackAndHandle(func() { logger.Critial("serveHandle goroutine crash!\n") this.Conn.Close() }) defer router.GetRouter().GetDisconHandler().Handle(client) //serve when connect go router.GetRouter().ConnHandler.Handle(client, this.FirstDataChan) //loop recv protocol for { select { case <-this.ExitChan: logger.Debug("Serve Handle Goroutine Exit !!! \r\n") router.GetRouter().GetDisconHandler().Handle(client) return case data, _ := <-this.TcpChan: logger.Debug("TCPHandler %v %v\r\n", data) h := router.GetRouter().GetTcpHandler()[data.ModuleId] if h != nil { c := h.Handle(client, &data) if c != nil { client = c } } case data, _ := <-this.IpcChan: logger.Info("IPCHandler %v %v\r\n", data.Data) h := router.GetRouter().GetIpcHandler()[data.ModuleId] if h != nil { c := h.Handle(client, data.CommandId, data.Data) if c != nil { client = c } } } // end select } //end for }
// recving the data from socket func (this *Connection) serveLoop() { //prevent crash other goroutines defer util.TraceCrashStackAndHandle(func() { this.Conn.Close() }) //release the goroutine and connection defer func() { GetConnectionManager().Release(this) logger.Info("Serve Loop Goroutine End !!!\n") }() var fristPack = true for this.Running == true { //looping to recv the client buf := make([]byte, 4096) this.Conn.SetReadDeadline(time.Now().Add(60 * time.Second)) n, err := this.Conn.Read(buf) if err != nil { logger.Info("Client Read Buffer Failed %v %v\r\n", err, n) return } //when the user connected,the first data will not parse to protocol //it will send to the ConnHandler for modify if fristPack { maxSize := 1024 if n > maxSize { this.FirstDataChan <- buf[0:maxSize] } else { this.FirstDataChan <- buf[0:n] } fristPack = false } //end first pack //make the protocal this.PacketChan <- buf[0:n] //logger.Info("make protocal complete\n") } //end for{} }
// for handling the packet interrupt func (this *Connection) servePacket() { defer util.TraceCrashStackAndHandle(func() { this.Conn.Close() }) const packsize = 20480 bigBuffer := simplebuffer.NewSimpleBuffer("BigEndian") for { select { case data, _ := <-this.ExitChan: logger.Info("Serve Packet Goroutine End !!! %v \r\n", data) return case data, _ := <-this.PacketChan: // construct the protocal packet if len(bigBuffer.Data())+len(data) > packsize { //block this pack } else { bigBuffer.WriteData(data) } //construct the protocol and send it to the handler proto := protocol.NewProtocal() ps, err := proto.PraseFromSimpleBuffer(bigBuffer) if err != nil { logger.Info("BigBuffer remain %v \n", bigBuffer.Data()) logger.Info("Data Parse failed \n") logger.Info("Buffer : %v\n\n\n", bigBuffer.Data()) continue } //### parse success ! reset all ### //bigBuffer = simplebuffer.NewSimpleBufferBySize("bigEndian",packsize) // 2 Mb for _, v := range ps { this.SendTcpChan(v) } // Packget goroutine no need Ipc /* case data, ok := <-this.IpcChan: logger.Info("ExitHandler %v %v\r\n", data, ok) break */ } } }
//specify websocket func (this *Connection) WSServe() { defer util.TraceCrashStackAndHandle(func() { this.Conn.Close() }) // init handle go this.serveWsHandle() var firstPack = true // parse data const packsize = 8192 for { var padding []byte buf := make([]byte, packsize) //no heartbeat after 60s will disconnect this.Conn.SetReadDeadline(time.Now().Add(60 * time.Second)) n, err := this.Conn.Read(buf) // error handle if err != nil { this.ExitChan <- err.Error() return } // pack handle if n >= packsize { tmpBuff := make([]byte, 20480) tn, _ := this.Conn.Read(tmpBuff) if tn > 20480 { continue } padding = make([]byte, tn+n) copy(padding[0:], buf) copy(padding[n:], tmpBuff) n = n + tn } else { padding = buf } logger.Info("websocket read size %v data %v\n", n, padding[0:n]) if err != nil { return } //parse data in jso wp, err := protocol.NewWsProtocolFromData(padding[0:n]) if err != nil { continue } //first pack channel if firstPack { this.FirstDataChan <- wp.ToBytes() firstPack = false } //pass value to handle goroutine this.WsChan <- *wp } }
func (this *MyHandlerImpl) Handle(client *client.Client, data *protocol.Protocol) *client.Client { logger.Info("TODO: MyHandlerImpl data = %v \n", data) switch data.Command { case 0: //TODO: client.Send(data.ModuleId, data.Command, data.Data) break default: //TODO: break } return nil }
func main() { logger.Info("Go router running \r\n") //init logger logger.GetLogger().SetLogLevel(5, 5) logger.GetLogger().SetOutputDir(`c:\`) logger.GetLogger().Init("testlog") logger.Info("Go run WSServer \r\n") wsServer := server.NewWSServer(":9092") //register handler wsServer.GetRouter().SetWsHandler(map[string]router.WSHandler{ "system": &WsUserHandlerImpl{}, "user": &WsUserHandlerImpl{}, "chat": &WsUserHandlerImpl{}, }) //startup wsServer.Run() <-exitChan }
func NewWsProtocolFromData(data []byte) (*WsProtocol, error) { json, err := simplejson.NewJson(data) if err != nil { logger.Info("Parsing data error:%v\n", err) return nil, err } m := json.Get("module").MustString() c := json.Get("command").MustString() d, _ := json.Get("data").MarshalJSON() wp := NewWsProtocol() wp.Module = m wp.Command = c wp.Data = d return wp, nil }
// Echo the data received on the WebSocket. func WsServerProc(ws *websocket.Conn) { logger.Info("wsserver connection \n") // conn starting network.GetConnectionManager(). Produce(socket.NewBaseSocket(ws)).WSServe() }
func (this *DisconHandlerImpl) Handle(client *client.Client) { logger.Info("TODO: i am the handler \n") }
func (this *MyHandlerImpl) Init() { logger.Info("LoginHandleImple loaded \n") }