func (h *handler) handleWebsocket(rw http.ResponseWriter, req *http.Request) { // conn, err := websocket.Upgrade(rw, req, nil, WebSocketReadBufSize, WebSocketWriteBufSize) req.ParseForm() sid := req.Form.Get("sid") // , _ := h.parseSessionID(req.URL) if sid == "" { sid = uuid.NewRandom().String() } rw.Header().Add("sid", sid) conn, err := wsUpgrader.Upgrade(rw, req, nil) if _, ok := err.(websocket.HandshakeError); ok { http.Error(rw, `Can "Upgrade" only to "WebSocket".`, http.StatusBadRequest) return } else if err != nil { rw.WriteHeader(http.StatusInternalServerError) return } path := req.RequestURI sess := newSession(sid, h.options.DisconnectDelay, h.options.HeartbeatDelay, path) if h.handlerFunc != nil { go h.handlerFunc(sess) } receiver := newWsReceiver(conn) sess.attachReceiver(receiver) readCloseCh := make(chan struct{}) go func() { for { // todo: refactor needed // kind of silly to be doing all this // read > accept > encode > decode > yada lark // can just do.. c.ws.ReadJSON(&msg) t, m, err := conn.ReadMessage() if err != nil { log.Println("error reading message, calling close", err) close(readCloseCh) return } if t != websocket.TextMessage { log.Println("only accept text messages, closing") close(readCloseCh) return } sess.accept(string(m)) } }() select { case <-readCloseCh: case <-receiver.doneNotify(): } sess.close() conn.Close() }
func (s *server) newSocket(session Session, path string) *socket { log.Println("new socket %s with path: %s", session.ID(), path) id := uuid.NewRandom().String() sock := &socket{ id: id, session: session, path: path, presense: make(map[string]string), server: s, } return sock }
func New(opts *Options) PubSub { // todo: this should return PubSub iface ps := &pubsub{ opts: opts, sublist: sublist.New(), subs: make(map[Subscriber]*set.Set), topics: make(map[string]*set.Set), } // set to random id if not set if opts.PubSubNodeId == "" { log.Println("pub sub node id not set, setting to uuid") // todo: truncate this to say 16 chars? opts.PubSubNodeId = uuid.NewRandom().String() } log.Println("pub sub node id:", opts.PubSubNodeId) if opts.PubSubMode != PubSubModeNormal && opts.PubSubMode != PubSubModeFirehose { log.Println("pub sub mode not set using normal mode") opts.PubSubMode = PubSubModeNormal } // Ensure interface compliance var _ PubSub = ps return ps }
func newId() string { return uuid.NewRandom().String() }