Beispiel #1
0
func (self *Router) handleMsgServerClient(msc *libnet.Session) {
	msc.Process(func(msg *libnet.InBuffer) error {
		log.Info("msg_server", msc.Conn().RemoteAddr().String(), " say: ", string(msg.Data))
		var c protocol.CmdInternal
		pp := NewProtoProc(self)
		err := json.Unmarshal(msg.Data, &c)
		if err != nil {
			log.Error("error:", err)
			return err
		}
		switch c.GetCmdName() {
		case protocol.REQ_SEND_P2P_MSG_CMD:
			err := pp.procSendMsgP2P(&c, msc)
			if err != nil {
				log.Warning(err.Error())
			}

		case protocol.IND_ACK_P2P_STATUS_CMD:
			err := pp.procAckP2pStatus(&c, msc)
			if err != nil {
				log.Warning(err.Error())
			}

		case protocol.REQ_SEND_TOPIC_MSG_CMD:
			err := pp.procSendMsgTopic(&c, msc)
			if err != nil {
				log.Warning(err.Error())
			}

		}
		return nil
	})
}
func (self *ProtoProc) procClientID(cmd protocol.Cmd, session *libnet.Session) error {
	glog.Info("procClientID")
	var err error
	ID := cmd.GetArgs()[0]
	sessionStoreData := storage.NewSessionStoreData(cmd.GetArgs()[0], session.Conn().RemoteAddr().String(),
		self.msgServer.cfg.LocalIP, strconv.FormatUint(session.Id(), 10))

	glog.Info(sessionStoreData)
	args := make([]string, 0)
	args = append(args, cmd.GetArgs()[0])
	CCmd := protocol.NewCmdInternal(protocol.STORE_SESSION_CMD, args, sessionStoreData)

	glog.Info(CCmd)

	if self.msgServer.channels[protocol.SYSCTRL_CLIENT_STATUS] != nil {
		_, err = self.msgServer.channels[protocol.SYSCTRL_CLIENT_STATUS].Channel.Broadcast(libnet.Json(CCmd))
		if err != nil {
			glog.Error(err.Error())
			return err
		}
	}

	self.msgServer.sessions[cmd.GetArgs()[0]] = session
	self.msgServer.sessions[cmd.GetArgs()[0]].State = base.NewSessionState(true, cmd.GetArgs()[0])

	err = self.procOfflineMsg(session, ID)
	if err != nil {
		glog.Error(err.Error())
		return err
	}
	return nil
}
Beispiel #3
0
func (self *Manager) handleMsgServerClient(msc *libnet.Session) {
	msc.Process(func(msg *libnet.InBuffer) error {
		log.Info("msg_server", msc.Conn().RemoteAddr().String(), "say:", string(msg.Data))

		self.parseProtocol(msg.Data, msc)

		return nil
	})
}
Beispiel #4
0
func (self *ProtoProc) procLogin(cmd protocol.Cmd, session *libnet.Session) error {
	//log.Info("procLogin")
	var err error
	var uuid string
	var msgServer string

	ClientID := cmd.GetArgs()[0]
	ClientType := cmd.GetArgs()[1]
	ClientPwd := ""
	if len(cmd.GetArgs()) == 3 {
		ClientPwd = cmd.GetArgs()[2]
	}

	// get the session cache
	sessionCacheData, err := self.gateway.sessionCache.Get(ClientID)
	if sessionCacheData != nil {
		log.Warningf("ID %s already login", ClientID)

		msgServer = sessionCacheData.MsgServerAddr
		uuid = sessionCacheData.ID
	} else {
		// choose msg server and allocate UUID
		msgServer = self.procGetMinLoadMsgServer()
		uuid = common.NewV4().String()
		// get the session store to check whether registered
		sessionStoreData, _ := self.gateway.mongoStore.GetSessionFromCid(ClientID)
		if sessionStoreData == nil {
			log.Warningf("ID %s not registered", ClientID)

			// for store data
			sessionStoreData = mongo_store.NewSessionStoreData(ClientID, ClientPwd, ClientType)
			log.Info(sessionStoreData)
			common.StoreData(self.gateway.mongoStore, sessionStoreData)
		}
		// for cache data, MsgServer MUST update local & remote addr.
		sessionCacheData = redis_store.NewSessionCacheData(sessionStoreData, session.Conn().RemoteAddr().String(), msgServer, uuid)
		log.Info(sessionCacheData)
		self.gateway.sessionCache.Set(sessionCacheData)
	}
	//
	resp := protocol.NewCmdSimple(protocol.RSP_LOGIN_CMD)
	resp.AddArg(protocol.RSP_SUCCESS)
	resp.AddArg(uuid)
	resp.AddArg(msgServer)

	log.Info("Resp | ", resp)

	if session != nil {
		err = session.Send(libnet.Json(resp))
		if err != nil {
			log.Error(err.Error())
		}
		session.Close()
		log.Info("client ", session.Conn().RemoteAddr().String(), " | close")
	}
	return nil
}
Beispiel #5
0
func (self *Monitor) handleMsgServerClient(msc *libnet.Session) {
	msc.Process(func(msg *libnet.InBuffer) error {
		glog.Info("msg_server", msc.Conn().RemoteAddr().String(), " say: ", string(msg.Data))
		var c protocol.CmdMonitor

		err := json.Unmarshal(msg.Data, &c)
		if err != nil {
			glog.Error("error:", err)
			return err
		}

		return nil
	})
}
func (self *ProtoProc) procReqMsgServer(cmd protocol.Cmd, session *libnet.Session) error {
	//log.Info("procReqMsgServer")
	var err error
	msgServer := common.SelectServer(self.gateway.cfg.MsgServerList, self.gateway.cfg.MsgServerNum)

	resp := protocol.NewCmdSimple(protocol.SELECT_MSG_SERVER_FOR_CLIENT_CMD)
	resp.AddArg(msgServer)

	log.Info("Resp | ", resp)

	if session != nil {
		err = session.Send(libnet.Json(resp))
		if err != nil {
			log.Error(err.Error())
		}
		session.Close()
		log.Info("client ", session.Conn().RemoteAddr().String(), " | close")
	}
	return nil
}
Beispiel #7
0
/*
   MsgServer -> Router
       REQ_SEND_P2P_MSG_CMD
       arg0: Sent2ID       //接收方用户ID
       arg1: Msg           //消息内容
       arg2: FromID        //发送方用户ID
       arg3: uuid          //MsgServer分配的消息uuid
*/
func (self *ProtoProc) procSendMsgP2P(cmd protocol.Cmd, session *libnet.Session) error {
	log.Info("procSendMsgP2P")
	var err error
	send2ID := cmd.GetArgs()[0]
	send2Msg := cmd.GetArgs()[1]
	log.Info(send2Msg)

	self.Router.readMutex.Lock()
	defer self.Router.readMutex.Unlock()
	cacheSession, err := self.Router.sessionCache.Get(send2ID)
	if cacheSession == nil || cacheSession.Alive == false {
		storeSession, err := self.Router.mongoStore.GetSessionFromCid(send2ID)
		if err != nil {
			log.Warningf("ID %s not registered, msg dropped", send2ID)
			return err
		}
		log.Info(storeSession)
		log.Warningf("ID registered but offline: %s", send2ID)

		cmd.ChangeCmdName(protocol.ROUTE_SEND_P2P_MSG_CMD)
		//ms := self.Router.cfg.MsgServerList[0]
		ms := session.Conn().RemoteAddr().String()
		err = self.Router.msgServerClientMap[ms].Send(libnet.Json(cmd))
		if err != nil {
			log.Error("error:", err)
			return err
		}
	} else {
		log.Info(cacheSession.MsgServerAddr)

		cmd.ChangeCmdName(protocol.ROUTE_SEND_P2P_MSG_CMD)
		log.Info(cmd)
		err = self.Router.msgServerClientMap[cacheSession.MsgServerAddr].Send(libnet.Json(cmd))
		if err != nil {
			log.Error("error:", err)
			return err
		}
	}

	return nil
}
Beispiel #8
0
/*
   Router -> MsgServer
       ROUTE_SEND_TOPIC_MSG_CMD
       arg0: ClientID      //发送方用户ID
       arg1: ClientType    //发送方终端类型,是client还是device
       arg2: Msg           //消息内容
       arg3: TopicName     //群组名, device无须提供
*/
func (self *ProtoProc) procSendMsgTopic(cmd protocol.Cmd, session *libnet.Session) error {
	log.Info("procSendMsgTopic")
	var err error
	ms := session.Conn().RemoteAddr().String()

	//send2Msg := cmd.GetArgs()[0]
	topicName := cmd.GetArgs()[1]
	//fromID := cmd.GetArgs()[2]
	//fromType := cmd.GetArgs()[3]

	// check whether the topic exist
	topicCacheData, err := self.Router.topicCache.Get(topicName)
	if topicCacheData == nil {
		log.Warningf("TOPIC %s not exist: %s", topicName, err.Error())
		return err
	}

	cmd.ChangeCmdName(protocol.ROUTE_SEND_TOPIC_MSG_CMD)
	log.Info(protocol.ROUTE_SEND_TOPIC_MSG_CMD)
	log.Info(cmd)

	for ip, num := range topicCacheData.AliveMemberNumMap {
		if num > 0 {
			log.Warningf("topic %s has %d member(s) in ip %s", topicName, num, ip)
			if ip != ms {
				// not in this server, routing it
				err = self.Router.msgServerClientMap[ip].Send(libnet.Json(cmd))
				if err != nil {
					log.Error("error:", err)
					return err
				}
			}
		}
	}

	return nil
}
Beispiel #9
0
func (self *Router) handleMsgServerClient(msc *libnet.Session) {
	msc.Process(func(msg *libnet.InBuffer) error {
		log.Info("msg_server", msc.Conn().RemoteAddr().String(), " say: ", string(msg.Data))
		var c protocol.CmdInternal
		pp := NewProtoProc(self)
		err := json.Unmarshal(msg.Data, &c)
		if err != nil {
			log.Error("error:", err)
			return err
		}
		switch c.GetCmdName() {
		case protocol.SEND_MESSAGE_P2P_CMD:
			err := pp.procSendMsgP2P(c, msc)
			if err != nil {
				log.Warning(err.Error())
			}
		case protocol.CREATE_TOPIC_CMD:
			err := pp.procCreateTopic(c, msc)
			if err != nil {
				log.Warning(err.Error())
			}
		case protocol.JOIN_TOPIC_CMD:
			err := pp.procJoinTopic(c, msc)
			if err != nil {
				log.Warning(err.Error())
			}
		case protocol.SEND_MESSAGE_TOPIC_CMD:
			err := pp.procSendMsgTopic(c, msc)
			if err != nil {
				log.Warning(err.Error())
			}

		}
		return nil
	})
}
Beispiel #10
0
func (self *ProtoProc) procLogin(cmd protocol.Cmd, session *libnet.Session) error {
	log.Info("procLogin")
	var err error
	ClientID := cmd.GetArgs()[0]
	uuid := cmd.GetArgs()[1]
	resp := protocol.NewCmdSimple(protocol.RSP_LOGIN_CMD)

	// for cache data
	sessionCacheData, err := self.msgServer.sessionCache.Get(ClientID)
	if err != nil {
		log.Warningf("no ID : %s", ClientID)
	} else if sessionCacheData.ID != uuid {
		log.Warningf("ID(%s) & uuid(%s) not matched", ClientID, uuid)
		err = common.NOT_LOGIN
	}
	if err == nil {
		resp.AddArg(protocol.RSP_SUCCESS)
	} else {
		resp.AddArg(protocol.RSP_ERROR)
	}
	err2 := session.Send(libnet.Json(resp))
	if err2 != nil {
		log.Error(err2.Error())
		return err2
	}
	if err != nil {
		return err
	}
	// update the session cache
	sessionCacheData.ClientAddr = session.Conn().RemoteAddr().String()
	sessionCacheData.MsgServerAddr = self.msgServer.cfg.LocalIP
	sessionCacheData.Alive = true
	self.msgServer.sessionCache.Set(sessionCacheData)

	log.Info(sessionCacheData)

	self.msgServer.procOffline(ClientID)
	self.msgServer.procOnline(ClientID)

	/*
		args := make([]string, 0)
		args = append(args, cmd.GetArgs()[0])
		CCmd := protocol.NewCmdInternal(protocol.CACHE_SESSION_CMD, args, sessionCacheData)

		log.Info(CCmd)

		if self.msgServer.channels[protocol.SYSCTRL_CLIENT_STATUS] != nil {
			_, err = self.msgServer.channels[protocol.SYSCTRL_CLIENT_STATUS].Channel.Broadcast(libnet.Json(CCmd))
			if err != nil {
				log.Error(err.Error())
				return err
			}
		}

		// for store data
		sessionStoreData := mongo_store.SessionStoreData{ID, session.Conn().RemoteAddr().String(),
			self.msgServer.cfg.LocalIP, true}

		log.Info(sessionStoreData)
		args = make([]string, 0)
		args = append(args, cmd.GetArgs()[0])
		CCmd = protocol.NewCmdInternal(protocol.STORE_SESSION_CMD, args, sessionStoreData)

		log.Info(CCmd)

		if self.msgServer.channels[protocol.STORE_CLIENT_INFO] != nil {
			_, err = self.msgServer.channels[protocol.STORE_CLIENT_INFO].Channel.Broadcast(libnet.Json(CCmd))
			if err != nil {
				log.Error(err.Error())
				return err
			}
		}
	*/

	self.msgServer.sessions[ClientID] = session
	self.msgServer.sessions[ClientID].State = base.NewSessionState(true, ClientID, sessionCacheData.ClientType)

	err = self.procOfflineMsg(session, ClientID)
	if err != nil {
		log.Error(err.Error())
		return err
	}
	return nil
}
Beispiel #11
0
func (self *MsgServer) parseProtocol(cmd []byte, session *libnet.Session) error {
	var c protocol.CmdSimple

	// receive msg, that means client alive
	if session.State != nil {
		self.scanSessionMutex.Lock()
		session.State.(*base.SessionState).Alive = true
		self.scanSessionMutex.Unlock()
	}
	err := json.Unmarshal(cmd, &c)
	if err != nil {
		log.Error("error:", err)
		return err
	}

	pp := NewProtoProc(self)

	self.readMutex.Lock()
	defer self.readMutex.Unlock()

	log.Infof("[%s]->[%s]", session.Conn().RemoteAddr().String(), self.cfg.LocalIP)
	log.Info(c)
	switch c.GetCmdName() {
	case protocol.SEND_PING_CMD:
		err = pp.procPing(&c, session)
		if err != nil {
			log.Error("error:", err)
			return err
		}
	case protocol.SUBSCRIBE_CHANNEL_CMD:
		pp.procSubscribeChannel(&c, session)

	case protocol.REQ_LOGIN_CMD:
		err = pp.procLogin(&c, session)
		if err != nil {
			log.Error("error:", err)
			return err
		}

	case protocol.REQ_LOGOUT_CMD:
		err = pp.procLogout(&c, session)
		if err != nil {
			log.Error("error:", err)
			return err
		}

	case protocol.REQ_SEND_P2P_MSG_CMD:
		err = pp.procSendMessageP2P(&c, session)
		if err != nil {
			log.Error("error:", err)
			return err
		}
	case protocol.ROUTE_SEND_P2P_MSG_CMD:
		err = pp.procRouteMessageP2P(&c, session)
		if err != nil {
			log.Error("error:", err)
			return err
		}

	// p2p ack
	case protocol.IND_ACK_P2P_STATUS_CMD:
		err = pp.procP2pAck(&c, session)
		if err != nil {
			log.Error("error:", err)
			return err
		}
	// p2p ack
	case protocol.ROUTE_ACK_P2P_STATUS_CMD:
		err = pp.procP2pAck(&c, session)
		if err != nil {
			log.Error("error:", err)
			return err
		}

	case protocol.REQ_SEND_TOPIC_MSG_CMD:
		err = pp.procSendTopicMsg(&c, session)
		if err != nil {
			log.Error("error:", err)
			return err
		}
	case protocol.ROUTE_SEND_TOPIC_MSG_CMD:
		err = pp.procRouteTopicMsg(&c, session)
		if err != nil {
			log.Error("error:", err)
			return err
		}

	case protocol.REQ_CREATE_TOPIC_CMD:
		err = pp.procCreateTopic(&c, session)
		if err != nil {
			log.Error("error:", err)
			return err
		}

	case protocol.REQ_ADD_2_TOPIC_CMD:
		err = pp.procAdd2Topic(&c, session)
		if err != nil {
			log.Error("error:", err)
			return err
		}

	case protocol.REQ_KICK_TOPIC_CMD:
		err = pp.procKickTopic(&c, session)
		if err != nil {
			log.Error("error:", err)
			return err
		}

	case protocol.REQ_JOIN_TOPIC_CMD:
		err = pp.procJoinTopic(&c, session)
		if err != nil {
			log.Error("error:", err)
			return err
		}

	case protocol.REQ_QUIT_TOPIC_CMD:
		err = pp.procQuitTopic(&c, session)
		if err != nil {
			log.Error("error:", err)
			return err
		}

	case protocol.REQ_GET_TOPIC_LIST_CMD:
		err = pp.procGetTopicList(&c, session)
		if err != nil {
			log.Error("error:", err)
			return err
		}

	case protocol.REQ_GET_TOPIC_PROFILE_CMD:
		err = pp.procGetTopicProfile(&c, session)
		if err != nil {
			log.Error("error:", err)
			return err
		}
	}

	return err
}