/* Forward message to MQTT server */ func ConnectToMQTTServer(MQTTServerAddress string) (*client.Client, error) { defer func() { if err := recover(); err != nil { utils.Log.Println(err) debug.PrintStack() } }() cli := client.New(&client.Options{ ErrorHandler: func(err error) { utils.Log.Println("MQTT Client error:", err) }, }) var err error RandomID := utils.MakeRandomID() err = cli.Connect(&client.ConnectOptions{ Network: "tcp", Address: MQTTServerAddress, ClientID: []byte(RandomID), CleanSession: true, PINGRESPTimeout: 5 * time.Second, KeepAlive: 5, }) if err != nil { return nil, err } return cli, nil }
// 处理POST消息 func MessagePostHandler(w http.ResponseWriter, req *http.Request) { var channel_name string var ok bool var channel *Channel var err error var buf []byte vars := mux.Vars(req) if channel_name, ok = vars["channel"]; !ok { utils.Log.Printf("[%s] channel name not in url\n", req.RemoteAddr) http.Error(w, "channel name not in url", 400) return } // use byte pool buffer := byte_pool.Checkout() defer buffer.Close() buffer.ReadFrom(req.Body) body := buffer.Bytes() post_message := post_message_pool.Get().(*PostMessage) err = json.Unmarshal(body, post_message) if err != nil { utils.Log.Printf("[%s] Unmarshal json failed: [%s], channel: [%s]\n", req.RemoteAddr, err, channel_name) w.WriteHeader(http.StatusBadRequest) return } channel, err = GetChannel(channel_name) if err != nil { utils.Log.Printf("[%s] GetChannel failed: [%s], channel: [%s]\n", req.RemoteAddr, err, channel_name) w.WriteHeader(http.StatusBadRequest) return } message_id := utils.MakeRandomID() post_message.MessageID = message_id if post_message.ToUser == "" { channel.MultiCastChan <- post_message } post_reply := post_reply_pool.Get().(*PostReply) post_reply.Result = 0 post_reply.MessageID = message_id buf, err = json.Marshal(*post_reply) if err != nil { utils.Log.Printf("[%s] Marshal JSON failed: [%s], channel: [%s]\n", req.RemoteAddr, err, channel_name) w.WriteHeader(http.StatusBadRequest) return } if ServerDebug { utils.Log.Printf("Got message from [%s], message: [%s], message_id: [%s], channel: [%s]\n", req.RemoteAddr, string(body), message_id, channel_name) } w.Header().Set("Content-Type", "application/json") w.Write(buf) post_reply_pool.Put(post_reply) }
// 处理POST消息 func MessagePostHandler(w http.ResponseWriter, req *http.Request) { defer func() { if err := recover(); err != nil { utils.Log.Println(err) debug.PrintStack() } }() var channel_name string var channel *Channel var err error var buf []byte w.Header().Set("Access-Control-Allow-Origin", "*") w.Header().Set("Access-Control-Allow-Methods", "GET, POST, PUT, DELETE, OPTIONS") w.Header().Set("Access-Control-Allow-Headers", "channel, tourid, tag") w.Header().Set("Access-Control-Allow-Credentials", "true") channel_name = req.Header.Get("channel") if channel_name == "" { utils.Log.Printf("[%s] channel name not in header\n", req.RemoteAddr) http.Error(w, "channel name not in header", 400) return } // use byte pool buffer := byte_pool.Checkout() defer buffer.Close() buffer.ReadFrom(req.Body) body := buffer.Bytes() channel = GetChannel(channel_name) //post_message := channel.PostMessagePool.Get().(*lib.PostMessage) post_message := new(lib.PostMessage) err = ffjson.Unmarshal(body, post_message) if err != nil { utils.Log.Printf("[%s] Unmarshal json failed: [%s], channel: [%s]\n", req.RemoteAddr, err, channel_name) http.Error(w, "Unmarshal json failed", 500) return } if channel.PrepareClose == true { utils.Log.Printf("[%s] Channel: [%s] will be closed.\n", req.RemoteAddr, channel_name) http.Error(w, "channel will be closed or not exists", 500) return } message_id := utils.MakeRandomID() post_message.MessageID = message_id send_finished := false if post_message.Delay == 0 { send_finished = PostMessage(channel, post_message) } else { go PostMessage(channel, post_message) send_finished = true } post_reply := channel.PostReplyPool.Get().(*lib.PostReply) if send_finished { post_reply.Result = 0 post_reply.MessageID = message_id } else { post_reply.Result = 1 post_reply.MessageID = "message buffer of channel is full." } buf, err = ffjson.Marshal(*post_reply) if err != nil { utils.Log.Printf("[%s] Marshal JSON failed: [%s], channel: [%s]\n", req.RemoteAddr, err, channel_name) http.Error(w, "Marshal json failed", 500) return } if ServerDebug { utils.Log.Printf("Got message from [%s], message: [%s], message_id: [%s], channel: [%s]\n", req.RemoteAddr, string(body), message_id, channel_name) } w.Header().Set("Content-Type", "application/json") w.Write(buf) channel.PostReplyPool.Put(post_reply) ffjson.Pool(buf) }