Golang加头和尾部来解决tcp粘包问题.代码片段示例
发布时间:2020-12-16 18:33:17 所属栏目:大数据 来源:网络整理
导读:package mainimport ("bufio""encoding/binary""fmt""io""net")var empty []bytefunc main() {lis,_ := net.Listen("tcp",":1789")for {con,err := lis.Accept()if err != nil {continue}//当建立连接的时候交给registerConn来处理这个链接.//想自定义就可以
package main import ( "bufio" "encoding/binary" "fmt" "io" "net" ) var empty []byte func main() { lis,_ := net.Listen("tcp",":1789") for { con,err := lis.Accept() if err != nil { continue } //当建立连接的时候交给registerConn来处理这个链接. //想自定义就可以把这个函数重写. go registerConn(con) } } type ConnectionInfo struct { Conn net.Conn Buf *bufio.Reader Authfunc func(msg []byte) bool } type ConnResolve interface { OnceRead() ([]byte,error) StillRead() Close() error AuthFuncation(msg []byte) bool } func (self *ConnectionInfo) OnceRead() ([]byte,error) { return reader(self.Buf) } func (self *ConnectionInfo) AuthFuncation(msg []byte) bool { return self.Authfunc(msg) } func (self *ConnectionInfo) Close() error { return self.Conn.Close() } func (self *ConnectionInfo) StillRead() { for { msg,err := reader(self.Buf) if err != nil { if err == io.EOF { continue } return } fmt.Printf("收到的信息: %sn",string(msg)) } } func registerConn(conn net.Conn) { defer conn.Close() //这里返回的是一个接口,可以自定义消息处理机制. reg := NewconnectionInfo(conn,nil) //接入的时候第一次读取认证信息,然后 msg,err := reg.OnceRead() if err != nil { return } if !reg.AuthFuncation(msg) { return } reg.StillRead() } func NewconnectionInfo(conn net.Conn,authfunc func(msg []byte) bool) ConnResolve { if authfunc == nil { authfunc = DefaultAuthFunc } return &ConnectionInfo{conn,bufio.NewReader(conn),authfunc} } func DefaultAuthFunc(msg []byte) bool { fmt.Println("开始校验认证信息: ",string(msg)) return true } //reader方法是用来定义读取的流的逻辑的,可以自己按找自己的逻辑定义. func reader(buf *bufio.Reader) ([]byte,error) { head := make([]byte,5) _,err := buf.Read(head) if err != nil { return empty,err } bodyLen,_ := binary.Uvarint(head) line,err := buf.ReadSlice('n') if err != nil { return empty,err } if uint64(len(line)-1) != bodyLen { return empty,io.EOF } return line[:bodyLen],nil } func writer(conn net.Conn,msg []byte) (int,error) { mgslen := len(msg) head := make([]byte,5+mgslen+1) binary.PutUvarint(head,uint64(mgslen)) copy(head[5:],msg) head[mgslen] = 'n' return conn.Write(head) } (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |