void CDBServConn::_HandleMsgData(CImPdu *pPdu) { IM::Message::IMMsgData msg; CHECK_PB_PARSE_MSG(msg.ParseFromArray(pPdu->GetBodyData(), pPdu->GetBodyLength())); if (CHECK_MSG_TYPE_GROUP(msg.msg_type())) { s_group_chat->HandleGroupMessage(pPdu); return; } uint32_t from_user_id = msg.from_user_id(); uint32_t to_user_id = msg.to_session_id(); uint32_t msg_id = msg.msg_id(); if (msg_id == 0) { log("HandleMsgData, write db failed, %u->%u.", from_user_id, to_user_id); return; } uint8_t msg_type = msg.msg_type(); CDbAttachData attach_data((uchar_t*)msg.attach_data().c_str(), msg.attach_data().length()); uint32_t handle = attach_data.GetHandle(); log("HandleMsgData, from_user_id=%u, to_user_id=%u, msg_id=%u.", from_user_id, to_user_id, msg_id); CMsgConn* pMsgConn = CImUserManager::GetInstance()->GetMsgConnByHandle(from_user_id, attach_data.GetHandle()); if (pMsgConn) { IM::Message::IMMsgDataAck msg2; msg2.set_user_id(from_user_id); msg2.set_msg_id(msg_id); msg2.set_session_id(to_user_id); msg2.set_session_type(::IM::BaseDefine::SESSION_TYPE_SINGLE); pMsgConn->SendPdu(SID_MSG, CID_MSG_DATA_ACK, msg2); } CRouteServConn* pRouteConn = get_route_serv_conn(); if (pRouteConn) { pRouteConn->SendPdu(pPdu); } msg.clear_attach_data(); pPdu->SetPBMsg(&msg); CImUser* pFromImUser = CImUserManager::GetInstance()->GetImUserById(from_user_id); CImUser* pToImUser = CImUserManager::GetInstance()->GetImUserById(to_user_id); pPdu->SetSeqNum(0); if (pFromImUser) { pFromImUser->BroadcastClientMsgData(pPdu, msg_id, pMsgConn, from_user_id); } if (pToImUser) { pToImUser->BroadcastClientMsgData(pPdu, msg_id, NULL, from_user_id); } IM::Server::IMGetDeviceTokenReq msg3; msg3.add_user_id(to_user_id); msg3.set_attach_data(pPdu->GetBodyData(), pPdu->GetBodyLength()); SendPdu(SID_OTHER, CID_OTHER_GET_DEVICE_TOKEN_REQ, msg3); }
void send_to_all_route_server(CImPdu* pPdu) { CRouteServConn* pConn = NULL; for (uint32_t i = 0; i < g_route_server_count; i++) { pConn = (CRouteServConn*)g_route_server_list[i].serv_conn; if (pConn && pConn->IsOpen()) { pConn->SendPdu(pPdu); } } }
void CGroupChat::HandleGroupChangeMemberResponse(CImPdu* pPdu) { IM::Group::IMGroupChangeMemberRsp msg; CHECK_PB_PARSE_MSG(msg.ParseFromArray(pPdu->GetBodyData(), pPdu->GetBodyLength())); uint32_t change_type = msg.change_type(); uint32_t user_id = msg.user_id(); uint32_t result = msg.result_code(); uint32_t group_id = msg.group_id(); uint32_t chg_user_cnt = msg.chg_user_id_list_size(); uint32_t cur_user_cnt = msg.cur_user_id_list_size(); log("HandleChangeMemberResp, change_type=%u, req_id=%u, group_id=%u, result=%u, chg_usr_cnt=%u, cur_user_cnt=%u. ", change_type, user_id, group_id, result, chg_user_cnt, cur_user_cnt); CDbAttachData attach_data((uchar_t*)msg.attach_data().c_str(), msg.attach_data().length()); CMsgConn* pFromConn = CImUserManager::GetInstance()->GetMsgConnByHandle(user_id, attach_data.GetHandle()); if (pFromConn) { msg.clear_attach_data(); pPdu->SetPBMsg(&msg); pFromConn->SendPdu(pPdu); } if (!result) { IM::Group::IMGroupChangeMemberNotify msg2; msg2.set_user_id(user_id); msg2.set_change_type((::IM::BaseDefine::GroupModifyType)change_type); msg2.set_group_id(group_id); for (uint32_t i = 0; i < chg_user_cnt; i++) { msg2.add_chg_user_id_list(msg.chg_user_id_list(i)); } for (uint32_t i = 0; i < cur_user_cnt; i++) { msg2.add_cur_user_id_list(msg.cur_user_id_list(i)); } CImPdu pdu; pdu.SetPBMsg(&msg2); pdu.SetServiceId(SID_GROUP); pdu.SetCommandId(CID_GROUP_CHANGE_MEMBER_NOTIFY); CRouteServConn* pRouteConn = get_route_serv_conn(); if (pRouteConn) { pRouteConn->SendPdu(&pdu); } for (uint32_t i = 0; i < chg_user_cnt; i++) { uint32_t to_user_id = msg.chg_user_id_list(i); _SendPduToUser(&pdu, to_user_id, pFromConn); } for (uint32_t i = 0; i < cur_user_cnt; i++) { uint32_t to_user_id = msg.cur_user_id_list(i); _SendPduToUser(&pdu, to_user_id, pFromConn); } } }
void CFileHandler::HandleClientFileRequest(CMsgConn* pMsgConn, CImPduClientFileRequest* pPdu) { string from_id_url(pPdu->GetFromId(), pPdu->GetFromIdLen()); uint32_t from_id = urltoid(from_id_url.c_str()); string to_id_url(pPdu->GetToId(), pPdu->GetToIdLen()); uint32_t to_id = urltoid(to_id_url.c_str()); string file_name(pPdu->GetFileName(), pPdu->GetFileNameLen()); uint32_t file_size = pPdu->GetFileSize(); log("HandleClientFileRequest, %u->%u, fileName: %s\n", from_id, to_id, file_name.c_str()); CPduAttachData attach(ATTACH_TYPE_HANDLE, pMsgConn->GetHandle(), 0, NULL, 0); CImUser* pUser = CImUserManager::GetInstance()->GetImUserById(to_id); if (pUser) { uint32_t client_type_flag = pUser->GetClientTypeFlag(); //to_user has pc_client in this msg_server if ((client_type_flag & CLIENT_TYPE_FLAG_BOTH) == CLIENT_TYPE_FLAG_PC) { CFileServConn* pFileConn = get_random_file_serv_conn(); if (pFileConn) { CImPduMsgFileTransferReq pdu(from_id, to_id, file_name.c_str(), file_size, FILE_TYPE_ONLINE, attach.GetLength(), attach.GetBuffer()); pdu.SetReserved(pPdu->GetReserved()); pFileConn->SendPdu(&pdu); } else { log("HandleClientFileRequest, no file server.\n"); CImPduClientFileResponse pdu2(REFUSE_REASON_NO_FILE_SERVER, from_id_url.c_str(), to_id_url.c_str(), file_name.c_str(), NULL, NULL, 0); pdu2.SetReserved(pPdu->GetReserved()); pMsgConn->SendPdu(&pdu2); } return; } } else { //no pc_client in this msg_server, check it from route_server CRouteServConn* pConn = get_route_serv_conn(); CPduAttachData pduAttachData(ATTACH_TYPE_HANDLE_AND_PDU, pMsgConn->GetHandle(), pPdu->GetLength(), pPdu->GetBuffer()); CImPduUserClientTypeRequest pdu3(to_id, pduAttachData.GetLength(), pduAttachData.GetBuffer()); pdu3.SetReserved(pPdu->GetReserved()); pConn->SendPdu(&pdu3); } }
void CGroupChat::HandleGroupMessage(CImPdu* pPdu) { IM::Message::IMMsgData msg; CHECK_PB_PARSE_MSG(msg.ParseFromArray(pPdu->GetBodyData(), pPdu->GetBodyLength())); uint32_t from_user_id = msg.from_user_id(); uint32_t to_group_id = msg.to_session_id(); string msg_data = msg.msg_data(); uint32_t msg_id = msg.msg_id(); if (msg_id == 0) { log("HandleGroupMsg, write db failed, %u->%u. ", from_user_id, to_group_id); return; } uint8_t msg_type = msg.msg_type(); CDbAttachData attach_data((uchar_t*)msg.attach_data().c_str(), msg.attach_data().length()); log("HandleGroupMsg, %u->%u, msg id=%u. ", from_user_id, to_group_id, msg_id); CMsgConn* pFromConn = CImUserManager::GetInstance()->GetMsgConnByHandle(from_user_id, attach_data.GetHandle()); if (pFromConn) { //接收反馈 IM::Message::IMMsgDataAck msg2; msg2.set_user_id(from_user_id); msg2.set_session_id(to_group_id); msg2.set_msg_id(msg_id); msg2.set_session_type(::IM::BaseDefine::SESSION_TYPE_GROUP); CImPdu pdu; pdu.SetPBMsg(&msg2); pdu.SetServiceId(SID_MSG); pdu.SetCommandId(CID_MSG_DATA_ACK); pdu.SetSeqNum(pPdu->GetSeqNum()); pFromConn->SendPdu(&pdu); } CRouteServConn* pRouteConn = get_route_serv_conn(); if (pRouteConn) { pRouteConn->SendPdu(pPdu); } // 服务器没有群的信息,向DB服务器请求群信息,并带上消息作为附件,返回时在发送该消息给其他群成员 //IM::BaseDefine::GroupVersionInfo group_version_info; CPduAttachData pduAttachData(ATTACH_TYPE_HANDLE_AND_PDU, attach_data.GetHandle(), pPdu->GetBodyLength(), pPdu->GetBodyData()); IM::Group::IMGroupInfoListReq msg3; msg3.set_user_id(from_user_id); IM::BaseDefine::GroupVersionInfo* group_version_info = msg3.add_group_version_list(); group_version_info->set_group_id(to_group_id); group_version_info->set_version(0); msg3.set_attach_data(pduAttachData.GetBuffer(), pduAttachData.GetLength()); CImPdu pdu; pdu.SetPBMsg(&msg3); pdu.SetServiceId(SID_GROUP); pdu.SetCommandId(CID_GROUP_INFO_REQUEST); CDBServConn* pDbConn = get_db_serv_conn(); if(pDbConn) { pDbConn->SendPdu(&pdu); } }
void CDBServConn::_HandleValidateResponse(CImPduValidateResponse* pPdu) { string user_name(pPdu->GetUserName(), pPdu->GetUserNameLen()); uint32_t result = pPdu->GetResult(); CDbAttachData attach_data(pPdu->GetAttachData(), pPdu->GetAttachLen()); log("HandleValidateResp, user_name=%s, result=%d\n", user_name.c_str(), result); CImUser* pImUser = CImUserManager::GetInstance()->GetImUserByName(user_name); CMsgConn* pMsgConn = NULL; if (!pImUser) { // can not find the client connection, // maybe the client is closed before the DB response arrived // do nothing log("ImUser for user_name=%s not exist\n", user_name.c_str()); return; } else { pMsgConn = pImUser->GetUnValidateMsgConn(attach_data.GetHandle()); if (!pMsgConn || pMsgConn->IsOpen()) { log("no such connection or is validated, user_name=%s\n", user_name.c_str()); return; } } if (result != 0) { result = REFUSE_REASON_DB_VALIDATE_FAILED; } // validate OK, set client validate past, and send FriendListRequest to db storage server // else close the client connection if (result == 0) { user_info_t* user = pPdu->GetUserInfo(); pImUser->SetUser(user); pImUser->SetValidated(); uint32_t user_id = user->user_id; CImUserManager::GetInstance()->AddImUserById(user_id, pImUser); pImUser->KickOutSameClientType(pMsgConn->GetClientType(), pMsgConn); CRouteServConn* pRouteConn = get_route_serv_conn(); if (pRouteConn) { CImPduServerKickUser kickPdu(user_id, pMsgConn->GetClientType(), KICK_REASON_DUPLICATE_USER); pRouteConn->SendPdu(&kickPdu); } string token = create_uuid(); log("user_name: %s, uid: %d, token:%s\n", user_name.c_str(), user->user_id, token.c_str()); pMsgConn->SetToken(token); pMsgConn->SetOpen(); pMsgConn->SendUserActionLog(USER_ACTION_TYPE_LOGIN); pMsgConn->SendUserStatusUpdate(USER_STATUS_ONLINE); pImUser->ValidateMsgConn(token, pMsgConn); CImPduLoginResponse pduLR(result, pImUser->GetIMOnlineStatus(), user, (char*)token.c_str()); pduLR.SetReserved(pPdu->GetReserved()); pMsgConn->SendPdu(&pduLR); } else { CImPduLoginResponse pduLR(result); pduLR.SetReserved(pPdu->GetReserved()); pMsgConn->SendPdu(&pduLR); //pMsgConn->Close(); } }
void CDBServConn::_HandleValidateResponse(CImPdu* pPdu) { IM::Server::IMValidateRsp msg; CHECK_PB_PARSE_MSG(msg.ParseFromArray(pPdu->GetBodyData(), pPdu->GetBodyLength())); string login_name = msg.user_name(); uint32_t result = msg.result_code(); string result_string = msg.result_string(); CDbAttachData attach_data((uchar_t*)msg.attach_data().c_str(), msg.attach_data().length()); log("HandleValidateResp, user_name=%s, result=%d", login_name.c_str(), result); CImUser* pImUser = CImUserManager::GetInstance()->GetImUserByLoginName(login_name); CMsgConn* pMsgConn = NULL; if (!pImUser) { log("ImUser for user_name=%s not exist", login_name.c_str()); return; } else { pMsgConn = pImUser->GetUnValidateMsgConn(attach_data.GetHandle()); if (!pMsgConn || pMsgConn->IsOpen()) { log("no such conn is validated, user_name=%s", login_name.c_str()); return; } } if (result != 0) { result = IM::BaseDefine::REFUSE_REASON_DB_VALIDATE_FAILED; } if (result == 0) { IM::BaseDefine::UserInfo user_info = msg.user_info(); uint32_t user_id = user_info.user_id(); CImUser* pUser = CImUserManager::GetInstance()->GetImUserById(user_id); if (pUser) { pUser->AddUnValidateMsgConn(pMsgConn); pImUser->DelUnValidateMsgConn(pMsgConn); if (pImUser->IsMsgConnEmpty()) { CImUserManager::GetInstance()->RemoveImUserByLoginName(login_name); delete pImUser; } } else { pUser = pImUser; } pUser->SetUserId(user_id); pUser->SetNickName(user_info.user_nick_name()); pUser->SetValidated(); //帐号验证通过 CImUserManager::GetInstance()->AddImUserById(user_id, pUser); pUser->KickOutSameClientType(pMsgConn->GetClientType(), IM::BaseDefine::KICK_REASON_DUPLICATE_USER, pMsgConn); CRouteServConn* pRouteConn = get_route_serv_conn(); if (pRouteConn) { IM::Server::IMServerKickUser msg2; msg2.set_user_id(user_id); msg2.set_client_type((::IM::BaseDefine::ClientType)pMsgConn->GetClientType()); msg2.set_reason(1); //1是什么鬼 pRouteConn->SendPdu(SID_OTHER, CID_OTHER_SERVER_KICK_USER, msg2); } log("user_name: %s, uid: %d", login_name.c_str(), user_id); pMsgConn->SetUserId(user_id); pMsgConn->SetOpen(); pMsgConn->SendUserStatusUpdate(IM::BaseDefine::USER_STATUS_ONLINE); pUser->ValidateMsgConn(pMsgConn->GetHandle(), pMsgConn); IM::Login::IMLoginRes msg3; msg3.set_server_time(time(NULL)); msg3.set_result_code(IM::BaseDefine::REFUSE_REASON_NONE); msg3.set_result_string(result_string); msg3.set_online_status((IM::BaseDefine::UserStatType)pMsgConn->GetOnlineStatus()); IM::BaseDefine::UserInfo* user_info_tmp = msg3.mutable_user_info(); user_info_tmp->set_user_id(user_info.user_id()); user_info_tmp->set_user_gender(user_info.user_gender()); user_info_tmp->set_user_nick_name(user_info.user_nick_name()); user_info_tmp->set_avatar_url(user_info.avatar_url()); user_info_tmp->set_sign_info(user_info.sign_info()); user_info_tmp->set_department_id(user_info.department_id()); user_info_tmp->set_email(user_info.email()); user_info_tmp->set_user_real_name(user_info.user_real_name()); user_info_tmp->set_user_tel(user_info.user_tel()); user_info_tmp->set_user_domain(user_info.user_domain()); user_info_tmp->set_status(user_info.status()); pMsgConn->SendPdu(SID_LOGIN, CID_LOGIN_RES_USERLOGIN, msg3); } else { IM::Login::IMLoginRes msg4; msg4.set_server_time(time(NULL)); msg4.set_result_code((IM::BaseDefine::ResultType)result); msg4.set_result_string(result_string); pMsgConn->SendPdu(SID_LOGIN, CID_LOGIN_RES_USERLOGIN, msg4); pMsgConn->Close(); } }
void CDBServConn::_HandleValidateResponse(CImPdu* pPdu) { IM::Server::IMValidateRsp msg; CHECK_PB_PARSE_MSG(msg.ParseFromArray(pPdu->GetBodyData(), pPdu->GetBodyLength())); string login_name = msg.user_name(); uint32_t result = msg.result_code(); string result_string = msg.result_string(); CDbAttachData attach_data((uchar_t*)msg.attach_data().c_str(), msg.attach_data().length()); struct timeval now; gettimeofday(&now, NULL); uint32_t rand_num = rand(); string strKey = int2string(now.tv_usec % 10000) + int2string(now.tv_sec) + int2string(rand_num); strKey += strKey; uint32_t nKeyLen = strKey.length(); if (nKeyLen < 32) { for (uint32_t i=nKeyLen; i<32; i++) strKey += '0'; } else { strKey = strKey.substr(0, 32); } log("HandleValidateResp, user_name=%s, result=%d, key=%s", login_name.c_str(), result, strKey.c_str()); CImUser* pImUser = CImUserManager::GetInstance()->GetImUserByLoginName(login_name); CMsgConn* pMsgConn = NULL; if (!pImUser) { log("ImUser for user_name=%s not exist", login_name.c_str()); return; } else { pMsgConn = pImUser->GetUnValidateMsgConn(attach_data.GetHandle()); if (!pMsgConn || pMsgConn->IsOpen()) { log("no such conn is validated, user_name=%s", login_name.c_str()); return; } log("_HandleValidateResponse, user=%s(%p) conn=%p", login_name.c_str(), pImUser, pMsgConn); } if (result != 0) { result = IM::BaseDefine::REFUSE_REASON_DB_VALIDATE_FAILED; } log("_HandleValidateResponse, login_user=%s key=%s %p ", login_name.c_str(), strKey.c_str(), pMsgConn); total_users++; switch(pMsgConn->GetClientType()) { case IM::BaseDefine::CLIENT_TYPE_WINDOWS: case IM::BaseDefine::CLIENT_TYPE_MAC: pc_total_users++; break; case IM::BaseDefine::CLIENT_TYPE_ANDROID: android_total_users++; break; case IM::BaseDefine::CLIENT_TYPE_IOS: ios_total_users++; break; case IM::BaseDefine::CLIENT_TYPE_WEB: web_total_users++; break; } if (result == 0) { IM::BaseDefine::UserInfo user_info = msg.user_info(); uint32_t user_id = user_info.user_id(); CImUser* pUser = CImUserManager::GetInstance()->GetImUserById(user_id); if (pUser) { log("_HandleValidateResponse, get user %u(%p) key=%s %p", user_id, pUser, strKey.c_str(), pMsgConn); pUser->AddUnValidateMsgConn(pMsgConn); pImUser->DelUnValidateMsgConn(pMsgConn); if (pImUser->IsMsgConnEmpty()) { CImUserManager::GetInstance()->RemoveImUserByLoginName(login_name); delete pImUser; } } else { pUser = pImUser; log("_HandleValidateResponse, use login user %u(%p) key=%s %p", user_id, pUser, strKey.c_str(), pMsgConn); } pUser->SetUserId(user_id); pUser->SetNickName(user_info.user_nick_name()); pUser->SetValidated(); CImUserManager::GetInstance()->AddImUserById(user_id, pUser); log("user_name: %s, uid: %d(%p)", login_name.c_str(), user_id, pMsgConn); pMsgConn->SetKey(strKey); pMsgConn->SetUserId(user_id); pMsgConn->SetOpen(); pMsgConn->SendUserStatusUpdate(IM::BaseDefine::USER_STATUS_ONLINE); CRouteServConn* pRouteConn = get_route_serv_conn(); if (pRouteConn) { IM::Server::IMServerKickUser msg2; msg2.set_user_id(user_id); msg2.set_client_type((::IM::BaseDefine::ClientType)pMsgConn->GetClientType()); msg2.set_reason(1); CImPdu pdu; pdu.SetPBMsg(&msg2); pdu.SetServiceId(SID_OTHER); pdu.SetCommandId(CID_OTHER_SERVER_KICK_USER); pRouteConn->SendPdu(&pdu); } pUser->ValidateMsgConn(pMsgConn->GetHandle(), pMsgConn); //pUser->KickOutSameClientType(pMsgConn->GetClientType(), IM::BaseDefine::KICK_REASON_DUPLICATE_USER, user_id); pUser->KickOutSameClientType(pMsgConn->GetClientType(), IM::BaseDefine::KICK_REASON_DUPLICATE_USER, pMsgConn); IM::Login::IMLoginRes msg3; msg3.set_server_time(time(NULL)); msg3.set_result_code(IM::BaseDefine::REFUSE_REASON_NONE); msg3.set_result_string(result_string); msg3.set_online_status((IM::BaseDefine::UserStatType)pMsgConn->GetOnlineStatus()); msg3.set_client_key(strKey); IM::BaseDefine::UserInfo* user_info_tmp = msg3.mutable_user_info(); user_info_tmp->set_user_id(user_info.user_id()); user_info_tmp->set_user_gender(user_info.user_gender()); user_info_tmp->set_user_nick_name(user_info.user_nick_name()); user_info_tmp->set_avatar_url(user_info.avatar_url()); user_info_tmp->set_sign_info(user_info.sign_info()); user_info_tmp->set_department_id(user_info.department_id()); user_info_tmp->set_email(user_info.email()); user_info_tmp->set_user_real_name(user_info.user_real_name()); user_info_tmp->set_user_tel(user_info.user_tel()); user_info_tmp->set_user_domain(user_info.user_domain()); user_info_tmp->set_status(user_info.status()); user_info_tmp->set_user_type(user_info.user_type()); log("id:%u gender:%u nick:%s avatar:%s sign:%s depid:%u email:%s name:%s tel:%s uname:%s status:%u type:%u", user_info.user_id(), user_info.user_gender(), user_info.user_nick_name().c_str(), user_info.avatar_url().c_str(), user_info.sign_info().c_str(), user_info.department_id(), user_info.email().c_str(), user_info.user_real_name().c_str(), user_info.user_tel().c_str(), user_info.user_domain().c_str(), user_info.status(), user_info.user_type()); CImPdu pdu2; pdu2.SetPBMsg(&msg3); pdu2.SetServiceId(SID_LOGIN); pdu2.SetCommandId(CID_LOGIN_RES_USERLOGIN); pdu2.SetSeqNum(pPdu->GetSeqNum()); pMsgConn->SendPdu(&pdu2); } else { fail_users++; IM::Login::IMLoginRes msg4; msg4.set_server_time(time(NULL)); msg4.set_result_code((IM::BaseDefine::ResultType)result); msg4.set_result_string(result_string); CImPdu pdu3; pdu3.SetPBMsg(&msg4); pdu3.SetServiceId(SID_LOGIN); pdu3.SetCommandId(CID_LOGIN_RES_USERLOGIN); pdu3.SetSeqNum(pPdu->GetSeqNum()); pMsgConn->SendPdu(&pdu3); pMsgConn->Close(); } }