package server import ( "context" "encoding/json" "git.pyer.club/kingecg/goemitter" "git.pyer.club/kingecg/gotunnelserver/util" "github.com/gorilla/websocket" ) type Session struct { Id string Name string conn *websocket.Conn ctx context.Context cancel context.CancelFunc *goemitter.EventEmitter } type Command struct { Type int `json:"type"` Payload map[string]string `json:"payload"` } func (s *Session) Send(cmd *Command) (err error) { return s.conn.WriteJSON(cmd) } func (s *Session) Close() { _ = s.conn.Close() s.Emit("Close") } func (s *Session) Start() { s.ctx, s.cancel = context.WithCancel(context.Background()) go func() { defer s.conn.Close() for { var cmd Command err := s.conn.ReadJSON(&cmd) if err != nil { return } if cmd.Type == util.NewConnection { s.Emit("NewConnection", cmd.Payload) } select { case <-s.ctx.Done(): return default: continue } } }() } func (s *Session) Stop() { s.cancel() } func NewSession(conn *websocket.Conn) *Session { return &Session{ conn: conn, Id: util.GenRandomstring(16), EventEmitter: goemitter.NewEmitter(), } } func NewCommand(t int, p map[string]string) *Command { return &Command{ Type: t, Payload: p, } } func NcmdSession(sessionId string) *Command { return NewCommand(util.NewSession, map[string]string{"sessionId": sessionId}) } func NewErrorResponse(err string, cmd *Command) *Command { payload := map[string]string{ "error": err, // "originalcmd": strconv.Itoa(cmd.Type), } if cmd != nil { originalCmd, _ := json.Marshal(cmd) payload["originalcmd"] = string(originalCmd) } return NewCommand(util.ErrorCmd, payload) } func NcmdConnectionInited(sessionId string) *Command { return NewCommand(util.ConnectInited, map[string]string{"sessionId": sessionId}) } func NcmdConnectionReady(sessionId string) *Command { return NewCommand(util.ConnectionReady, map[string]string{"sessionId": sessionId}) }