kbengine 登录login过程

kbengine 登录login过程

服务端部分:
1:服务端loginapp.cpp中“void Loginapp::login(Network::Channel* pChannel, MemoryStream& s)”被触发, 这个函数进行了一系列的检查,
确定合法后向dbmgr发送一个登陆请求包“(*pBundle).newMessage(DbmgrInterface::onAccountLogin);”, dbmgr也会进行一系列的检查并将登陆结果返回到loginapp。

  1. void Loginapp::login(Network::Channel* pChannel, MemoryStream& s)
  2. {
  3. ...
  4. ...
  5. if(loginName.size() > ACCOUNT_NAME_MAX_LENGTH)
  6. {
  7. INFO_MSG(fmt::format("Loginapp::login: loginName is too long, size={}, limit={}.\n",
  8. loginName.size(), ACCOUNT_NAME_MAX_LENGTH));
  9. _loginFailed(pChannel, loginName, SERVER_ERR_NAME, datas, true);
  10. s.done();
  11. return;
  12. }
  13. if(password.size() > ACCOUNT_PASSWD_MAX_LENGTH)
  14. {
  15. INFO_MSG(fmt::format("Loginapp::login: password is too long, size={}, limit={}.\n",
  16. password.size(), ACCOUNT_PASSWD_MAX_LENGTH));
  17. ...
  18. ...
  19. ...
  20. // 向dbmgr查询用户合法性
  21. Network::Bundle* pBundle = Network::Bundle::ObjPool().createObject();
  22. (*pBundle).newMessage(DbmgrInterface::onAccountLogin);
  23. (*pBundle) << loginName << password;
  24. (*pBundle).appendBlob(datas);
  25. dbmgrinfos->pChannel->send(pBundle);
  26. }

复制代码

1.1: loginapp得到dbmgr的登录合法结果后向baseappmgr发送了分配网关(baseapp)请求(registerPendingAccountToBaseapp), 通常是负载较低的一个baseapp进程.

  1. void Loginapp::onLoginAccountQueryResultFromDbmgr(Network::Channel* pChannel, MemoryStream& s)
  2. {
  3. ...
  4. ...
  5. ...
  6. // 如果大于0则说明当前账号仍然存活于某个baseapp上
  7. if(componentID > 0)
  8. {
  9. Network::Bundle* pBundle = Network::Bundle::ObjPool().createObject();
  10. (*pBundle).newMessage(BaseappmgrInterface::registerPendingAccountToBaseappAddr);
  11. (*pBundle) << componentID << loginName << accountName << password << entityID << dbid << flags << deadline << infos->ctype;
  12. baseappmgrinfos->pChannel->send(pBundle);
  13. return;
  14. }
  15. else
  16. {
  17. // 注册到baseapp并且获取baseapp的地址
  18. Network::Bundle* pBundle = Network::Bundle::ObjPool().createObject();
  19. (*pBundle).newMessage(BaseappmgrInterface::registerPendingAccountToBaseapp);
  20. (*pBundle) << loginName;
  21. (*pBundle) << accountName;
  22. (*pBundle) << password;
  23. (*pBundle) << dbid;
  24. (*pBundle) << flags;
  25. (*pBundle) << deadline;
  26. (*pBundle) << infos->ctype;
  27. baseappmgrinfos->pChannel->send(pBundle);
  28. }
  29. }

复制代码

1.2:baseappmgr最终返回所分配的baseapp的ip地址等信息,loginapp将其转发给客户端(登录成功协议onLoginSuccessfully,包含baseapp的ip和端口信息)

  1. void Loginapp::onLoginAccountQueryBaseappAddrFromBaseappmgr(Network::Channel* pChannel, std::string& loginName,
  2. std::string& accountName, std::string& addr, uint16 port)
  3. {
  4. ...
  5. ...
  6. ...
  7. Network::Bundle* pBundle = Network::Bundle::ObjPool().createObject();
  8. (*pBundle).newMessage(ClientInterface::onLoginSuccessfully);
  9. uint16 fport = ntohs(port);
  10. (*pBundle) << accountName;
  11. (*pBundle) << addr;
  12. (*pBundle) << fport;
  13. (*pBundle).appendBlob(infos->datas);
  14. pClientChannel->send(pBundle);
  15. SAFE_RELEASE(infos);
  16. }

复制代码

2: 客户端插件得到返回结果后调用KBEngineApp.cs->login_baseapp()函数开始正式登录到baseapp。

3:baseapp收到登录请求

  1. void Baseapp::loginGateway(Network::Channel* pChannel,
  2. std::string& accountName,
  3. std::string& password)

复制代码

进行了一系列的检查,包括:账号是否已经在线,是否可以在这里登录等等。
当检查合法后,向dbmgr发送了一个查询账号信息的请求“DbmgrInterface::queryAccount”,dbmgr将查询到的账号数据(包括属性等)返回到baseapp, Baseapp::onQueryAccountCBFromDbmgr
当函数结果为合法时,根据配置中定义的账号实体脚本名称“g_serverConfig.getDBMgr().dbAccountEntityScriptType”创建了Account实体, 同时还创建了一个clientMailbox,账号实体中调用clientMailbox->方法()即可与客户端通讯了。
Account实体被创建后, 首先__init__被调用, 接着onEntitiesEnabled被调用, 此时实体正式可用了。

账号登陆成功后, 客户端Account.cs中会调用__init__() -> baseCall("reqAvatarList");来请求获得角色列表,
UI.cs中onReqAvatarList得到结果