package rest_websocket import ( "context" "log" "time" "git.ali33.ru/fcg-xvii/go-tools/json" "git.ali33.ru/fcg-xvii/rest" ) func NewSocketServer(socket *Socket, appConf *appConfig) *SocketServer { res := &SocketServer{ socket: socket, appConf: appConf, auth: json.Map{}, chIn: make(chan rest.IRequestIn, 1), clientData: make(map[string]any), } go res.work() return res } type SocketServer struct { socket *Socket appConf *appConfig auth json.Map chIn chan rest.IRequestIn clientData json.Map } func (s *SocketServer) ClientData(key string) (any, bool) { res, check := s.clientData[key] return res, check } func (s *SocketServer) SetClientData(key string, data any) { s.clientData[key] = data } func (s *SocketServer) Auth() json.Map { return s.auth } func (s *SocketServer) SetAuth(auth json.Map) { s.auth = auth } func (s *SocketServer) In() <-chan rest.IRequestIn { return s.chIn } func (s *SocketServer) IsStream() bool { return true } func (s *SocketServer) Context() context.Context { return s.socket.Context() } func (s *SocketServer) Close() { s.socket.Close() } func (s *SocketServer) SendMessage(req rest.IRequestOut) (<-chan *rest.RequestStream, error) { var request *rest.RequestStream if rreq, check := req.(*rest.RequestStream); check { request = rreq } else { request = &rest.RequestStream{ Request: &rest.Request{ Type: req.RType(), Command: req.RCommand(), Data: req.RData(), Files: req.RFiles(), }, Timeout: time.Now().Add(time.Second * 10), } } return s.socket.SendMessage(request) } func (s *SocketServer) work() { loop: for { select { case <-s.socket.Context().Done(): return case req := <-s.socket.MessagesIn(): reqIn := &RequestIn{ RequestStream: req, owner: s, core: s.appConf.core, } var reqOut rest.IRequestOut command, check := s.appConf.app.Executer(reqIn) if !check { reqOut = reqIn.OutError(rest.ErrorMessage("ErrNotFound", "command is not found")) } else { // serialize if err := rest.Serialize(reqIn.RData(), command); err != nil { //s.socket.Close() reqOut = reqIn.OutError(err) if _, err := s.SendMessage(reqOut); err != nil { log.Println("socket send error", err) } reqOut.RClose() continue loop } // validate if validator, check := command.(rest.IValidator); check { reqOut = validator.Validate(reqIn) if reqOut != nil { if _, err := s.SendMessage(reqOut); err != nil { log.Println("socket send error", err) } reqOut.RClose() continue loop } } reqOut = command.Execute(reqIn) } s.SendMessage(reqOut) reqOut.RClose() //s.chIn <- reqIn } } }