//-------------------------------------------------------------------------------------------------------------------------- //供外部通过QueueAction调用的方法,实际执行线程是DataCacheThread。 //-------------------------------------------------------------------------------------------------------------------------- internal void LoadAccount(string accountId) { Msg_LD_Load msg = new Msg_LD_Load(); msg.MsgId = (int)DataEnum.TableAccount; msg.PrimaryKeys.Add(accountId); Msg_LD_SingleLoadRequest reqAccount = new Msg_LD_SingleLoadRequest(); reqAccount.MsgId = (int)DataEnum.TableAccount; reqAccount.LoadType = Msg_LD_SingleLoadRequest.LoadTypeEnum.LoadSingle; reqAccount.Keys.Add(accountId); msg.LoadRequests.Add(reqAccount); RequestLoad(msg, (ret) => { KeyString primaryKey = KeyString.Wrap(ret.PrimaryKeys); if (Msg_DL_LoadResult.ErrorNoEnum.Success == ret.ErrorNo) { LogSys.Log(LOG_TYPE.INFO, ConsoleColor.Green, "DataCache Load Success: Msg:{0}, Key:{1}", "Account", primaryKey); } else if (Msg_DL_LoadResult.ErrorNoEnum.NotFound == ret.ErrorNo) { LogSys.Log(LOG_TYPE.INFO, ConsoleColor.Yellow, "DataCache Load NotFound: Msg:{0}, Key:{1}", "Account", primaryKey); } else { LogSys.Log(LOG_TYPE.ERROR, ConsoleColor.Red, "DataCache Load Failed: Msg:{0}, Key:{1}, ERROR:{2}", "Account", primaryKey, ret.ErrorInfo); } UserProcessScheduler dataProcessScheduler = UserServer.Instance.UserProcessScheduler; dataProcessScheduler.DefaultUserThread.QueueAction(dataProcessScheduler.LoadAccountCallback, accountId, ret); }); }
internal void DeleteMail(ulong userGuid, ulong mailGuid) { UserProcessScheduler dataProcess = UserServer.Instance.UserProcessScheduler; UserInfo user = dataProcess.GetUserInfo(userGuid); if (null != user) { List<MailInfo> mails; if (m_UserMails.TryGetValue(userGuid, out mails)) { if (null != mails) { MailInfo info = null; int ct = mails.Count; int index = 0; for (; index < ct; ++index) { if (mails[index].m_MailGuid == mailGuid) { info = mails[index]; break; } } if (null != info) { mails.RemoveAt(index); } } } MailStateInfo mailStateInfo = user.MailStateInfo; if (!mailStateInfo.IsAlreadyReceived(mailGuid)) { int wholeCt = m_WholeMails.Count; for (int index = 0; index < wholeCt; ++index) { MailInfo info = m_WholeMails[index]; if (info.m_MailGuid == mailGuid) { mailStateInfo.DeleteMail(mailGuid); } } } } }
private void HandleQueryUserStateResult(Msg_BL_QueryUserStateResult msg_, PBChannel channel, int src, uint session) { UserProcessScheduler dataProcess = UserServer.Instance.UserProcessScheduler; UserInfo user = dataProcess.GetUserInfo(msg_.Guid); if (user != null && user.CurrentState == UserState.Room) { user.CurrentState = UserState.Online; } }
private void HandleUserChangeScene(Msg_BL_UserChangeScene msg_, PBChannel channel, int src, uint session) { UserProcessScheduler dataProcess = UserServer.Instance.UserProcessScheduler; UserInfo user = dataProcess.GetUserInfo(msg_.Guid); if (user != null) { user.SceneId = msg_.SceneId; } }
private void HandleUserOffline(Msg_BL_UserOffline msg_, PBChannel channel, int src, uint session) { UserProcessScheduler dataProcess = UserServer.Instance.UserProcessScheduler; UserInfo user = dataProcess.GetUserInfo(msg_.Guid); if (user != null && user.CurrentState == UserState.Room) { user.CurrentState = UserState.Online; user.LeftLife = 0; } }
private void ExtractMailAttachment(MailInfo info, ulong userGuid) { UserProcessScheduler dataProcess = UserServer.Instance.UserProcessScheduler; UserThread userThread = dataProcess.GetUserThread(userGuid); userThread.QueueAction(userThread.AddAssets, userGuid, info.m_Money, info.m_Gold); int itemCt = info.m_Items.Count; for (int itemIx = 0; itemIx < itemCt; ++itemIx) { MailItem item = info.m_Items[itemIx]; userThread.QueueAction(userThread.AddItem, userGuid, item.m_ItemId, item.m_ItemNum); } }
internal void ReceiveMail(ulong userGuid, ulong mailGuid) { UserProcessScheduler dataProcess = UserServer.Instance.UserProcessScheduler; UserInfo user = dataProcess.GetUserInfo(userGuid); if (null != user) { List <TableMailInfoWrap> mails; if (m_UserMails.TryGetValue((long)userGuid, out mails)) { if (null != mails) { TableMailInfoWrap info = null; int ct = mails.Count; int index = 0; for (; index < ct; ++index) { if (mails[index].Guid == mailGuid) { info = mails[index]; break; } } if (null != info && CheckBagCapacity(user, info)) { mails.RemoveAt(index); ExtractMailAttachment(info, userGuid); } } } MailStateInfo mailStateInfo = user.MailStateInfo; if (!mailStateInfo.IsAlreadyReceived(mailGuid)) { int wholeCt = m_WholeMails.Count; for (int index = 0; index < wholeCt; ++index) { TableMailInfoWrap info = m_WholeMails[index]; if (info.Guid == mailGuid) { if (CheckBagCapacity(user, info)) { mailStateInfo.ReceiveMail(mailGuid); if (info.LevelDemand <= user.Level && info.SendDate >= user.CreateTime && info.ExpiryDate >= DateTime.Now) { ExtractMailAttachment(info, userGuid); } } } } } } }
private void HandleUserQuit(Msg_RL_UserQuit msg_, PBChannel channel, int src, uint session) { UserProcessScheduler dataProcess = UserServer.Instance.UserProcessScheduler; UserThread userThread = dataProcess.GetUserThread(msg_.UserGuid); if (null != userThread) { userThread.QueueAction(userThread.HandleUserQuit, msg_); } else { dataProcess.DefaultUserThread.QueueAction(dataProcess.DefaultUserThread.HandleUserQuit, msg_); } }
internal void LoadUser(ulong userGuid, string accountId, string nickname) { string key = userGuid.ToString(); Msg_LD_Load msg = new Msg_LD_Load(); msg.MsgId = (int)DataEnum.TableUserInfo; msg.PrimaryKeys.Add(key); Msg_LD_SingleLoadRequest reqUser = new Msg_LD_SingleLoadRequest(); reqUser.MsgId = (int)DataEnum.TableUserInfo; reqUser.LoadType = Msg_LD_SingleLoadRequest.LoadTypeEnum.LoadSingle; reqUser.Keys.Add(key); msg.LoadRequests.Add(reqUser); Msg_LD_SingleLoadRequest reqMember = new Msg_LD_SingleLoadRequest(); reqMember.MsgId = (int)DataEnum.TableMemberInfo; reqMember.LoadType = Msg_LD_SingleLoadRequest.LoadTypeEnum.LoadMulti; reqMember.Keys.Add(key); msg.LoadRequests.Add(reqMember); Msg_LD_SingleLoadRequest reqItem = new Msg_LD_SingleLoadRequest(); reqItem.MsgId = (int)DataEnum.TableItemInfo; reqItem.LoadType = Msg_LD_SingleLoadRequest.LoadTypeEnum.LoadMulti; reqItem.Keys.Add(key); msg.LoadRequests.Add(reqItem); Msg_LD_SingleLoadRequest reqFriend = new Msg_LD_SingleLoadRequest(); reqFriend.MsgId = (int)DataEnum.TableFriendInfo; reqFriend.LoadType = Msg_LD_SingleLoadRequest.LoadTypeEnum.LoadMulti; reqFriend.Keys.Add(key); msg.LoadRequests.Add(reqFriend); RequestLoad(msg, (ret) => { KeyString primaryKey = KeyString.Wrap(ret.PrimaryKeys); if (Msg_DL_LoadResult.ErrorNoEnum.Success == ret.ErrorNo) { LogSys.Log(LOG_TYPE.INFO, "DataCache Load Success: Msg:{0}, Key:{1}", "UserInfo", primaryKey); } else if (Msg_DL_LoadResult.ErrorNoEnum.NotFound == ret.ErrorNo) { LogSys.Log(LOG_TYPE.INFO, ConsoleColor.Yellow, "DataCache Load NotFound: Msg:{0}, Key:{1}", "UserInfo", primaryKey); } else { LogSys.Log(LOG_TYPE.ERROR, "DataCache Load Failed: Msg:{0}, Key:{1}, ERROR:{2}", "UserInfo", primaryKey, ret.ErrorInfo); } UserProcessScheduler dataProcessScheduler = UserServer.Instance.UserProcessScheduler; dataProcessScheduler.DefaultUserThread.QueueAction(dataProcessScheduler.LoadUserCallback, ret, accountId, nickname); }); }
internal void SendWholeMail(MailInfo wholeMail, int validityPeriod) { wholeMail.m_MailGuid = GenMailGuid(); wholeMail.m_SendTime = DateTime.Now; wholeMail.m_ExpiryDate = wholeMail.m_SendTime.AddDays(validityPeriod); m_WholeMails.Add(wholeMail); NodeMessage newMailMsg = new NodeMessage(LobbyMessageDefine.Msg_LC_NotifyNewMail); NodeMessageWithGuid headerData = new NodeMessageWithGuid(); newMailMsg.m_NodeHeader = headerData; UserProcessScheduler dataProcess = UserServer.Instance.UserProcessScheduler; dataProcess.VisitUsers((UserInfo userInfo) => { headerData.m_Guid = userInfo.Guid; NodeMessageDispatcher.SendNodeMessage(userInfo.NodeName, newMailMsg); }); }
internal void SendUserMail(MailInfo userMail, int validityPeriod) { userMail.m_MailGuid = GenMailGuid(); userMail.m_SendTime = DateTime.Now; userMail.m_ExpiryDate = userMail.m_SendTime.AddDays(validityPeriod); List<MailInfo> mails = null; if (!m_UserMails.TryGetValue(userMail.m_Receiver, out mails)) { mails = new List<MailInfo>(); m_UserMails.Add(userMail.m_Receiver, mails); } mails.Add(userMail); UserProcessScheduler dataProcess = UserServer.Instance.UserProcessScheduler; UserInfo user = dataProcess.GetUserInfo(userMail.m_Receiver); if (null != user && user.CurrentState != UserState.DropOrOffline) { NodeMessage newMailMsg = new NodeMessage(LobbyMessageDefine.Msg_LC_NotifyNewMail, userMail.m_Receiver); NodeMessageDispatcher.SendNodeMessage(user.NodeName, newMailMsg); } }
//------------------------------------------------------------------------------------------------------ private void ObserveEnterSceneResult(NodeMessage msg, int handle, uint seq) { if (handle != 0) { return; } GameFrameworkMessage.NodeMessageWithGuid headerMsg = msg.m_NodeHeader as GameFrameworkMessage.NodeMessageWithGuid; if (null != headerMsg) { GameFrameworkMessage.EnterSceneResult protoMsg = msg.m_ProtoData as GameFrameworkMessage.EnterSceneResult; if (null != protoMsg) { UserProcessScheduler dataProcess = UserServer.Instance.UserProcessScheduler; UserInfo user = dataProcess.GetUserInfo(headerMsg.m_Guid); if (user != null && protoMsg.result == 0) { user.CurrentState = UserState.Room; user.SceneId = protoMsg.scene_type; } } } }
internal void ReadMail(ulong userGuid, ulong mailGuid) { UserProcessScheduler dataProcess = UserServer.Instance.UserProcessScheduler; UserInfo user = dataProcess.GetUserInfo(userGuid); if (null != user) { List <TableMailInfoWrap> mails; if (m_UserMails.TryGetValue((long)userGuid, out mails)) { if (null != mails) { int ct = mails.Count; int index = 0; for (; index < ct; ++index) { if (mails[index].Guid == mailGuid) { TableMailInfoWrap info = mails[index]; info.IsRead = true; break; } } } } MailStateInfo mailStateInfo = user.MailStateInfo; int wholeCt = m_WholeMails.Count; for (int index = 0; index < wholeCt; ++index) { TableMailInfoWrap info = m_WholeMails[index]; if (info.Guid == mailGuid) { mailStateInfo.ReadMail(mailGuid); break; } } } }
private void HandleEnterScene(NodeMessage msg, int handle, uint seq) { GameFrameworkMessage.NodeMessageWithGuid headerMsg = msg.m_NodeHeader as GameFrameworkMessage.NodeMessageWithGuid; if (null != headerMsg) { GameFrameworkMessage.EnterScene protoMsg = msg.m_ProtoData as GameFrameworkMessage.EnterScene; if (null != protoMsg) { ulong guid = headerMsg.m_Guid; int sceneId = protoMsg.m_SceneId; int wantRoomId = protoMsg.m_RoomId; UserProcessScheduler dataProcess = UserServer.Instance.UserProcessScheduler; UserInfo user = dataProcess.GetUserInfo(guid); if (user != null) { Msg_LB_RequestEnterScene builder = new Msg_LB_RequestEnterScene(); Msg_LB_BigworldUserBaseInfo baseInfoBuilder = new Msg_LB_BigworldUserBaseInfo(); baseInfoBuilder.AccountId = user.AccountId; baseInfoBuilder.NodeName = user.NodeName; baseInfoBuilder.WorldId = UserServerConfig.WorldId; baseInfoBuilder.ClientInfo = user.ClientInfo; baseInfoBuilder.StartServerTime = UserServerConfig.StartServerTime; baseInfoBuilder.SceneId = user.SceneId; builder.BaseInfo = baseInfoBuilder; builder.User = UserThread.BuildRoomUserInfo(user, 0, 0); builder.SceneId = sceneId; builder.WantRoomId = wantRoomId; builder.FromSceneId = user.SceneId; UserServer.Instance.BigworldChannel.Send(builder); } } } }
protected override void OnTick() { long curTime = TimeUtility.GetLocalMilliseconds(); if (m_LastTickTime != 0) { long elapsedTickTime = curTime - m_LastTickTime; if (elapsedTickTime > c_WarningTickTime) { LogSys.Log(LOG_TYPE.MONITOR, "QueueingThread Tick:{0}", elapsedTickTime); } } m_LastTickTime = curTime; if (m_LastLogTime + 60000 < curTime) { m_LastLogTime = curTime; DebugPoolCount((string msg) => { LogSys.Log(LOG_TYPE.INFO, "QueueingThread.ActionQueue {0}", msg); }); LogSys.Log(LOG_TYPE.MONITOR, "QueueingThread.ActionQueue Current Action {0}", this.CurActionNum); } const int c_MaxIterationPerTick = 10; if (IsLobbyFull() || GetTotalQueueingCount() <= 0) { //大厅已经满或者没有排队的玩家,多休息1秒 System.Threading.Thread.Sleep(1000); } else { UserProcessScheduler dataProcess = UserServer.Instance.UserProcessScheduler; for (int i = 0; i < c_MaxIterationPerTick; ++i) { if (m_QueueingAccounts.Count > 0 && null != m_QueueingAccounts.First && CanEnter()) { string accountId = m_QueueingAccounts.First.Value; m_QueueingAccounts.RemoveFirst(); m_LogoutQueueingAccounts.Remove(accountId); IncEnterCount(); LoginInfo info; if (m_QueueingInfos.TryRemove(accountId, out info)) { dataProcess.DefaultUserThread.QueueAction(dataProcess.DoAccountLoginWithoutQueueing, accountId, info.Password, info.ClientInfo, info.NodeName); ++i; } } } if (m_LastCleanTickTime + c_CleanTickInterval < curTime) { m_LastCleanTickTime = curTime; if (m_QueueingAccounts.Count > 0) { int ct = 0; int removeCount = 0; for (LinkedListNode <string> node = m_QueueingAccounts.First; null != node && m_QueueingAccounts.Count > 0;) { ++ct; if (ct > m_MaxQueueingCount) { LogSys.Log(LOG_TYPE.WARN, "QueueingThread.Tick maybe deadlock {0}", m_QueueingAccounts.Count); break; } string accountId = node.Value; LoginInfo info; if (m_LogoutQueueingAccounts.Contains(accountId)) { m_LogoutQueueingAccounts.Remove(accountId); m_QueueingInfos.TryRemove(accountId, out info); ++removeCount; LinkedListNode <string> delNode = node; node = node.Next; m_QueueingAccounts.Remove(delNode); } else if (m_QueueingInfos.TryGetValue(accountId, out info)) { info.QueueingNum -= removeCount; node = node.Next; } } } } } }
internal void GetMailList(ulong userGuid) { UserProcessScheduler dataProcess = UserServer.Instance.UserProcessScheduler; UserInfo user = dataProcess.GetUserInfo(userGuid); if (null != user) { List<MailInfoForMessage> mailList = new List<MailInfoForMessage>(); List<MailInfo> mails; if (m_UserMails.TryGetValue(userGuid, out mails)) { int ct = mails.Count; for (int ix = 0; ix < ct; ++ix) { MailInfo mailInfo = mails[ix]; if (mailInfo.m_ExpiryDate >= DateTime.Now) { MailInfoForMessage mailInfoForMsg = new MailInfoForMessage(); mailInfoForMsg.m_AlreadyRead = mailInfo.m_AlreadyRead; mailInfoForMsg.m_MailGuid = mailInfo.m_MailGuid; mailInfoForMsg.m_Title = mailInfo.m_Title; mailInfoForMsg.m_Sender = mailInfo.m_Sender; mailInfoForMsg.m_SendTime = mailInfo.m_SendTime.ToString("yyyyMMddHHmmss"); mailInfoForMsg.m_Text = mailInfo.m_Text; mailInfoForMsg.m_Money = mailInfo.m_Money; mailInfoForMsg.m_Gold = mailInfo.m_Gold; int itemCt = mailInfo.m_Items.Count; if (itemCt > 0) { for (int index = 0; index < itemCt; ++index) { MailItemForMessage mailItem = new MailItemForMessage(); mailItem.m_ItemId = mailInfo.m_Items[index].m_ItemId; mailItem.m_ItemNum = mailInfo.m_Items[index].m_ItemNum; mailInfoForMsg.m_Items.Add(mailItem); } } mailList.Add(mailInfoForMsg); } } } MailStateInfo mailStateInfo = user.MailStateInfo; //这里不对用户数据加锁,因为用户的邮件状态的改变都在这个线程完成(除上线时的数据加载) int wholeMailCt = m_WholeMails.Count; for (int ix = 0; ix < wholeMailCt; ++ix) { MailInfo mailInfo = m_WholeMails[ix]; if (mailInfo.m_LevelDemand <= user.Level && mailInfo.m_SendTime >= user.CreateTime && mailInfo.m_ExpiryDate >= DateTime.Now && !mailStateInfo.IsAlreadyReceived(mailInfo.m_MailGuid)) { if (!mailStateInfo.HaveMail(mailInfo.m_MailGuid)) { mailStateInfo.AddMail(mailInfo.m_MailGuid, mailInfo.m_ExpiryDate); } MailInfoForMessage mailInfoForMsg = new MailInfoForMessage(); mailInfoForMsg.m_AlreadyRead = mailStateInfo.IsAlreadyRead(mailInfo.m_MailGuid); mailInfoForMsg.m_MailGuid = mailInfo.m_MailGuid; mailInfoForMsg.m_Title = mailInfo.m_Title; mailInfoForMsg.m_Sender = mailInfo.m_Sender; mailInfoForMsg.m_SendTime = mailInfo.m_SendTime.ToString("yyyyMMddHHmmss"); mailInfoForMsg.m_Text = mailInfo.m_Text; mailInfoForMsg.m_Money = mailInfo.m_Money; mailInfoForMsg.m_Gold = mailInfo.m_Gold; int itemCt = mailInfo.m_Items.Count; if (itemCt > 0) { for (int index = 0; index < itemCt; ++index) { MailItemForMessage mailItem = new MailItemForMessage(); mailItem.m_ItemId = mailInfo.m_Items[index].m_ItemId; mailItem.m_ItemNum = mailInfo.m_Items[index].m_ItemNum; mailInfoForMsg.m_Items.Add(mailItem); } } mailList.Add(mailInfoForMsg); } } NodeMessage syncMailListMsg = new NodeMessage(LobbyMessageDefine.Msg_LC_SyncMailList, userGuid); GameFrameworkMessage.Msg_LC_SyncMailList protoMsg = new Msg_LC_SyncMailList(); protoMsg.m_Mails.AddRange(mailList); syncMailListMsg.m_ProtoData = protoMsg; NodeMessageDispatcher.SendNodeMessage(user.NodeName, syncMailListMsg); } }