package im import ( "encoding/json" "github.com/go-netty/go-netty" redis2 "github.com/go-redis/redis" "github.com/qit-team/snow-core/redis" "go.mongodb.org/mongo-driver/bson" "snow-im/app/constants/common" "snow-im/app/constants/errorcode" "snow-im/app/constants/msgid" "snow-im/app/http/controllers" "snow-im/app/http/entities" "snow-im/app/models" "snow-im/app/utils" common2 "snow-im/app/utils/common" "snow-im/app/utils/mq" "snow-im/app/utils/netool" "snow-im/app/utils/serialize" "snow-im/config" "strconv" "strings" "time" ) var ImRouter netool.Router func init() { ImRouter = netool.Router{} ImRouter.AddRouter(msgid.SINGLE_MSG, SendMsgtoUser) ImRouter.AddRouter(msgid.GROUP_MSG, SendMsgtoGroup) ImRouter.AddRouter(msgid.MULT_MSG, SendMsgtoMultUser) ImRouter.AddRouter(msgid.HEART_BEAT, HeartBeat) ImRouter.AddRouter(msgid.AUTH, Auth) ImRouter.AddRouter(msgid.ACK_MSG, Ack) } func getRsp(err error) entities.ImRsp { var rsp entities.ImRsp if err == nil { rsp = entities.ImRsp{ Code: errorcode.Success, Msg: errorcode.GetMsg(errorcode.Success, ""), } } else { rsp = entities.ImRsp{ Code: errorcode.SystemError, Msg: errorcode.GetMsg(errorcode.SystemError, ""), } utils.Log(nil, "err", err) } return rsp } //验证 func Auth(msg []byte, connect netty.InboundContext) error { var authReq entities.AuthReq err := serialize.SerializeTool.UnSerialize(config.GetConf().Serialize,msg,&authReq) if err == nil { err = controllers.Validate(authReq) if err == nil { uid, _ := redis.GetRedis().Get(utils.GetRealKey(common.TOKEN_PRE) + authReq.AppId + ":" + authReq.Token) if uid != "" { netool.GetConnManagger().SaveConnection(uid, connect.Channel()) } } } return err } //单聊 func SendMsgtoUser(msg []byte, connect netty.InboundContext) error { var singReq entities.SingTalkReq utils.Log(nil, string(msg)) err := serialize.SerializeTool.UnSerialize(config.GetConf().Serialize,msg,&singReq) if err == nil { err = controllers.Validate(singReq) if err == nil { singReq.Id = utils.GenUniqId(singReq.SenderId) singReq.Timestamp = time.Now().Unix() var uid, _ = strconv.Atoi(singReq.To) var msgFrom = common2.CacheHelper.GetCache(utils.GetRealKey(common.USER)+singReq.SenderId,false).(map[string]interface{}) singReq.Avatar = msgFrom["avatar"].(string) singReq.SenderName = msgFrom["nick_name"].(string) utils.Log(nil, "err", utils.GetUnderLineKey(common.SINGLE_TALK)+strconv.Itoa(uid%config.GetConf().Im.ImworkNum)) err = rabbitmq.MqManager.GetMqByName(common.MQ_KFK).Produce(utils.GetUnderLineKey(common.SINGLE_TALK)+strconv.Itoa(uid%config.GetConf().Im.ImworkNum), singReq, 0) //生成会话 var msgData,_ = json.Marshal(singReq) if err == nil { var msg = models.Msg{} msg.ParseFromParam(singReq.Msg) msg.Conversion = utils.SortKeys([]string{singReq.SenderId,singReq.To}) msg.SaveMsg() if singReq.RoomId == ""{ //优化管道操作 var pipline = common2.PikaTool.GetPipe() var to = redis2.Z{ Score: float64(singReq.Timestamp), Member: singReq.SenderId, } var from = redis2.Z{ Score: float64(singReq.Timestamp), Member: singReq.SenderId, } pipline.ZAdd(utils.GetRealKey(common.CONVERSION)+singReq.To, to,from) var msgFrom = common2.CacheHelper.GetCache(utils.GetRealKey(common.USER)+singReq.To,false).(map[string]interface{}) singReq.Avatar = msgFrom["avatar"].(string) singReq.SenderName = msgFrom["nick_name"].(string) msgDataFrom,_ := json.Marshal(singReq) pipline.MSet(utils.GetRealKey(common.CONVERSION)+singReq.To+":"+singReq.SenderId, msgData,utils.GetRealKey(common.CONVERSION)+singReq.SenderId+":"+singReq.To, msgDataFrom) pipline.Incr(utils.GetRealKey(common.CONVERSION)+singReq.To+":"+singReq.SenderId+":num") pipline.Incr(utils.GetRealKey(common.CONVERSION)+singReq.SenderId+":"+singReq.To+":num") pipline.Exec() } } } } return err } //群聊 func SendMsgtoGroup(msg []byte, connect netty.InboundContext) error { var singReq entities.SingTalkReq err := serialize.SerializeTool.UnSerialize(config.GetConf().Serialize,msg,&singReq) if err == nil { err = controllers.Validate(singReq) if err == nil { singReq.Id = utils.GenUniqId(singReq.SenderId) singReq.Timestamp = time.Now().Unix() var userInfo map[string]interface{} var rs = common2.CacheHelper.GetCache(utils.GetRealKey(common.USER)+singReq.SenderId,false) userInfo = rs.(map[string]interface{}) var room = models.Room{} room = room.GetRoom(bson.M{"_id":singReq.RoomId}) singReq.SenderName = userInfo["nick_name"].(string) singReq.Avatar = userInfo["avatar"].(string) singReq.RoomAvatar = room.Avatar singReq.RoomName = room.Name var uid, _ = strconv.Atoi(singReq.RoomId) err = rabbitmq.MqManager.GetMqByName(common.MQ_KFK).Produce(utils.GetUnderLineKey(common.GROUP_TALK)+strconv.Itoa(uid%config.GetConf().Im.ImGroupNum), singReq, 0) if err == nil { var msg = models.Msg{} msg.ParseFromParam(singReq.Msg) msg.Conversion = singReq.RoomId msg.SaveMsg() var pipie = common2.PikaTool.GetPipe() var roomMembers = common2.PikaTool.SetGet(utils.GetRealKey(common.ROOM) + singReq.RoomId) for _,v := range roomMembers{ var msgData,_ = json.Marshal(singReq) var member =redis2.Z{ Member:singReq.RoomId, Score:float64(singReq.Timestamp), } pipie.ZAdd(utils.GetRealKey(common.CONVERSION)+v, member) pipie.Set(utils.GetRealKey(common.CONVERSION)+v+":"+singReq.RoomId,msgData, 0) } _,err = pipie.Exec() } } } return err } //组聊 func SendMsgtoMultUser(msg []byte, connect netty.InboundContext) error { var singReq entities.SingTalkReq err := serialize.SerializeTool.UnSerialize(config.GetConf().Serialize,msg,&singReq) if err == nil { err = controllers.Validate(singReq) if err == nil { singReq.Id = utils.GenUniqId(singReq.SenderId) var userInfo map[string]string json.Unmarshal([]byte(common2.PikaTool.HashGet(utils.GetRealKey("user_info"), singReq.SenderId)), &userInfo) singReq.SenderName = userInfo["nick_name"] singReq.Avatar = userInfo["avatar"] var uids = strings.Split(singReq.To, ",") var pipie = common2.PikaTool.GetPipe() for _, v := range uids { var uid, _ = strconv.Atoi(v) singReq.To = v err = rabbitmq.MqManager.GetMqByName(common.MQ_KFK).Produce(utils.GetUnderLineKey(common.SINGLE_TALK)+strconv.Itoa(uid%config.GetConf().Im.ImworkNum), singReq, 0) //生成会话 if err == nil { var member =redis2.Z{ Member:singReq.RoomId, Score:float64(singReq.Timestamp), } pipie.ZAdd(utils.GetRealKey(common.CONVERSION)+v, member) pipie.Set(utils.GetRealKey(common.CONVERSION)+singReq.To+":"+singReq.RoomId, msg,0) } _,err = pipie.Exec() } } } return err } //消息ack func Ack(msg []byte, connect netty.InboundContext) error { var req entities.MsgId err := json.Unmarshal(msg, &req) if err == nil { } return err } //心跳 func HeartBeat(msg []byte, connect netty.InboundContext) error { if connect.Channel().IsActive() { netool.GetConnManagger().SetBeat(connect.Channel().ID()) connect.Write(utils.PackMsg([]byte("Ping"), msgid.HEART_BEAT)) } return nil }