// GetServer2 handle for server get. func GetServer2(w http.ResponseWriter, r *http.Request) { if r.Method != "GET" { http.Error(w, "Method Not Allowed", 405) return } params := r.URL.Query() key := params.Get("k") callback := params.Get("cb") protoStr := params.Get("p") res := map[string]interface{}{"ret": OK} defer retWrite(w, r, res, callback, time.Now()) if key == "" { res["ret"] = ParamErr return } // Match a push-server with the value computed through ketama algorithm node := myrpc.GetComet(key) if node == nil { res["ret"] = NotFoundServer return } addrs, ret := getProtoAddr(node, protoStr) if ret != OK { res["ret"] = ret return } // give client a addr list, client do the best choice res["data"] = map[string]interface{}{"server": addrs} return }
// PushPrivate handle for push private message. func PushPrivate(w http.ResponseWriter, r *http.Request) { if r.Method != "POST" { http.Error(w, "Method Not Allowed", 405) return } body := "" res := map[string]interface{}{"ret": OK} defer retPWrite(w, r, res, &body, time.Now()) // param bodyBytes, err := ioutil.ReadAll(r.Body) if err != nil { res["ret"] = ParamErr glog.Errorf("ioutil.ReadAll() failed (%s)", err.Error()) return } body = string(bodyBytes) params := r.URL.Query() key := params.Get("key") expireStr := params.Get("expire") if key == "" { res["ret"] = ParamErr return } expire, err := strconv.ParseUint(expireStr, 10, 32) if err != nil { res["ret"] = ParamErr glog.Errorf("strconv.ParseUint(\"%s\", 10, 32) error(%v)", expireStr, err) return } node := myrpc.GetComet(key) if node == nil || node.CometRPC == nil { res["ret"] = NotFoundServer return } client := node.CometRPC.Get() if client == nil { res["ret"] = NotFoundServer return } rm := json.RawMessage(bodyBytes) msg, err := rm.MarshalJSON() if err != nil { res["ret"] = ParamErr glog.Errorf("json.RawMessage(\"%s\").MarshalJSON() error(%v)", body, err) return } args := &myrpc.CometPushPrivateArgs{Msg: json.RawMessage(msg), Expire: uint(expire), Key: key} ret := 0 if err := client.Call(myrpc.CometServicePushPrivate, args, &ret); err != nil { glog.Errorf("client.Call(\"%s\", \"%s\", &ret) error(%v)", myrpc.CometServicePushPrivate, args.Key, err) res["ret"] = InternalErr return } return }
// GetServer handle for server get func GetServer(w http.ResponseWriter, r *http.Request) { if r.Method != "GET" { http.Error(w, "Method Not Allowed", 405) return } params := r.URL.Query() key := params.Get("k") callback := params.Get("cb") protoStr := params.Get("p") res := map[string]interface{}{"ret": OK} defer retWrite(w, r, res, callback, time.Now()) if key == "" { res["ret"] = ParamErr return } proto, err := strconv.Atoi(protoStr) if err != nil { glog.Errorf("strconv.Atoi(\"%s\") error(%v)", protoStr, err) res["ret"] = ParamErr return } // Match a push-server with the value computed through ketama algorithm node := myrpc.GetComet(key) if node == nil { res["ret"] = NotFoundServer return } addrs := node.Addr[proto] if addrs == nil || len(addrs) == 0 { res["ret"] = NotFoundServer return } server := "" // Select the best ip if Conf.Router != "" { var ips []string for _, addr := range addrs { ips = append(ips, addr.Addr) } server = routerCN.SelectBest(r.RemoteAddr, ips) glog.V(1).Infof("select the best ip:\"%s\" match with remoteAddr:\"%s\" , from ip list:\"%v\"", server, r.RemoteAddr, ips) } if server == "" { glog.V(1).Infof("remote addr: \"%s\" chose the ip: \"%s\"", r.RemoteAddr, addrs[0].Addr) server = addrs[0].Addr } res["data"] = map[string]interface{}{"server": server} return }
// PushMultiPrivate handle for push multiple private messages. // Because of it`s going asynchronously in this method, so it won`t return a InternalErr to caller. func PushMultiPrivate(w http.ResponseWriter, r *http.Request) { if r.Method != "POST" { http.Error(w, "Method Not Allowed", 405) return } body := "" res := map[string]interface{}{"ret": OK} defer retPWrite(w, r, res, &body, time.Now()) // post param bodyBytes, err := ioutil.ReadAll(r.Body) if err != nil { res["ret"] = InternalErr log.Error("ioutil.ReadAll() failed (%v)", err) return } body = string(bodyBytes) msgBytes, keys, ret := parseMultiPrivate(bodyBytes) if ret != OK { res["ret"] = ret return } rm := json.RawMessage(msgBytes) msg, err := rm.MarshalJSON() if err != nil { res["ret"] = ParamErr log.Error("json.RawMessage(\"%s\").MarshalJSON() error(%v)", string(msg), err) return } // url param params := r.URL.Query() expire, err := strconv.ParseUint(params.Get("expire"), 10, 32) if err != nil { res["ret"] = ParamErr log.Error("strconv.ParseUint(\"%s\", 10, 32) error(%v)", params.Get("expire"), err) return } // match nodes nodes := map[*myrpc.CometNodeInfo]*[]string{} for i := 0; i < len(keys); i++ { node := myrpc.GetComet(keys[i]) if node == nil || node.Rpc == nil { res["ret"] = NotFoundServer return } keysTmp, ok := nodes[node] if ok { *keysTmp = append(*keysTmp, keys[i]) } else { nodes[node] = &([]string{keys[i]}) } } var fKeys []string //push to every node for cometInfo, ks := range nodes { client := cometInfo.Rpc.Get() if client == nil { log.Error("cannot get comet rpc client") fKeys = append(fKeys, *ks...) continue } args := &myrpc.CometPushPrivatesArgs{Msg: json.RawMessage(msg), Expire: uint(expire), Keys: *ks} resp := myrpc.CometPushPrivatesResp{} if err := client.Call(myrpc.CometServicePushPrivates, args, &resp); err != nil { log.Error("client.Call(\"%s\", \"%v\", &ret) error(%v)", myrpc.CometServicePushPrivates, args.Keys, err) fKeys = append(fKeys, *ks...) continue } log.Debug("fkeys len(%d) addr:%v", len(resp.FKeys), cometInfo.RpcAddr) fKeys = append(fKeys, resp.FKeys...) } res["ret"] = OK if len(fKeys) != 0 { res["data"] = map[string]interface{}{"fk": fKeys} } return }