using Nettention.Proud; using Newtonsoft.Json; using ServerCommon; using ServerCommon.Cache; using ServerCore; using ServerBase; using System; using System.Collections.Concurrent; using System.Collections.Generic; using System.Linq; using System.Text; using System.Threading.Tasks; namespace GameServer; public class FriendAgentAction : EntityActionBase { private ConcurrentDictionary m_friends = new(); public FriendAgentAction(Player owner) : base(owner) { } public override async Task onInit() { await Task.CompletedTask; var result = new Result(); return result; } public override void onClear() { m_friends.Clear(); } public async Task loadFriends() { var owner = getOwner() as Player; NullReferenceCheckHelper.throwIfNull(owner, () => $"owner is null !!!"); var server_logic = GameServerApp.getServerLogic(); var batch = new QueryBatchEx(owner, LogActionType.None, server_logic.getDynamoDbClient()); { batch.addQuery(new DBQFriendsReadAll(owner.getUserGuid())); } var result = await QueryHelper.sendQueryAndBusinessLog(batch); return result; } public async Task setFriendsFromDoc(FriendDoc doc) { var result = new Result(); var owner = getOwner(); Friend friend = new Friend(owner); var attribute = friend.getEntityAttribute(); if (attribute is null) { var err_msg = $"Fail to get FriendAttribute"; result.setFail(ServerErrorCode.EntityAttributeNotFound, err_msg); Log.getLogger().error(result.toBasicString()); return result; } if (false == doc.getAttribWrappers().TryGetValue(typeof(FriendAttrib), out var to_copy_doc_attrib)) { var err_msg = $"Fail to get FriendAttrib"; result.setFail(ServerErrorCode.EntityAttributeNotFound, err_msg); Log.getLogger().error(result.toBasicString()); return result; } var attrib_base = to_copy_doc_attrib.getAttribBase(); var doc_attrib = attrib_base as FriendAttrib; if (doc_attrib is null) { var err_msg = $"Fail to get FriendAttrib"; result.setFail(ServerErrorCode.EntityAttributeNotFound, err_msg); Log.getLogger().error(result.toBasicString()); return result; } var player = owner as Player; NullReferenceCheckHelper.throwIfNull(player, () => $"player is null !!!"); attribute.UserGuid = player.getUserGuid(); attribute.FriendGuid = doc_attrib.FriendGuid; attribute.CreateTime = doc_attrib.CreateTime; attribute.FolderName = doc_attrib.FolderName; attribute.IsNew = doc_attrib.IsNew; if (doc_attrib.FriendGuid.Equals(string.Empty)) { var err_msg = $"FriendGuid is Empty, {toBasicString()}"; result.setFail(ServerErrorCode.FriendInfoNotExist, err_msg); Log.getLogger().error(result.toBasicString()); return result; } if (doc_attrib.FriendGuid.Equals(attribute.UserGuid)) { var err_msg = $"FriendGuid and UserGuid is Equals, {toBasicString()}"; result.setFail(ServerErrorCode.FriendInfoNotExist, err_msg); Log.getLogger().error(result.toBasicString()); return result; } (result, var nickname_attrib) = await NicknameDoc.findNicknameFromGuid(doc_attrib.FriendGuid); if(result.isFail()) { return result; } NullReferenceCheckHelper.throwIfNull(nickname_attrib, () => $"nickname_attrib is null !!!"); attribute.Nickname = nickname_attrib.Nickname; m_friends.AddOrUpdate(doc_attrib.FriendGuid, friend, (key, oldValue) => friend); return result; } public async Task> getFriendsInfo() { return await convertFriendsToProtoFriendInfo(); } public async Task> convertFriendsToProtoFriendInfo() { List friend_infos = new(); foreach (var friend in m_friends) { FriendInfo info = new(); (var result, var friend_attibute) = getFriendAttribFromAttribute(friend.Value); if (result.isFail()) { continue; } NullReferenceCheckHelper.throwIfNull(friend_attibute, () => $"friend_attibute is null !!!"); info.Guid = friend_attibute.FriendGuid; info.FolderName = friend_attibute.FolderName; info.IsNew = friend_attibute.IsNew; info.NickName = await getFriendNickname(friend_attibute.FriendGuid); friend_infos.Add(info); } return friend_infos; } private async Task getFriendNickname(string friendGuid) { var (result, attrib) = await NicknameDoc.findNicknameFromGuid(friendGuid); if (result.isFail()) { Log.getLogger().error($"User : {friendGuid} has not Exist NicknameDoc"); return "notexistnickname"; } NullReferenceCheckHelper.throwIfNull(attrib, () => $"attrib is null !!!"); return attrib.Nickname; } private (Result, FriendAttribute?) getFriendAttribFromAttribute(Friend friend) { var result = new Result(); var attribute = friend.getEntityAttribute(); if (attribute is null) { var err_msg = $"Fail to get FriendAttribute, owner : {getOwner().toBasicString()}"; result.setFail(ServerErrorCode.EntityAttributeNotFound, err_msg); Log.getLogger().error(result.toBasicString()); return (result, null); } return (result, attribute); } public async Task<(Result, FriendRequestCache?)> sendedRequestExistCheck(FriendReqCacheRequest cache, string friendGuid) { var result = new Result(); var owner = getOwner() as Player; NullReferenceCheckHelper.throwIfNull(owner, () => $"owner is null !!!"); var received_requests = await cache.getSendedFriendRequests(); var send_friend_action = owner.getEntityAction(); NullReferenceCheckHelper.throwIfNull(send_friend_action, () => $"send_friend_action is null !!! - {owner.toBasicString()}"); //내가 요청 보낸 정보가 없으면 리턴.. (var is_sended, var req_cache) = send_friend_action.isSendedRequest(received_requests, friendGuid); if (false == is_sended) { string err_msg = $"requeat info not exist send guid : {owner.getUserGuid()}, friend_guid : {friendGuid}, {toBasicString()}"; result.setFail(ServerErrorCode.FriendRequestNotExistInfo, err_msg); Log.getLogger().error(result.toBasicString()); return (result, null); } return (result, req_cache); } public async Task<(Result, FriendRequestCache?)> receivedRquestsExitstCheck(FriendReqCacheRequest cache, string friendGuid) { var result = new Result(); var owner = getOwner() as Player; NullReferenceCheckHelper.throwIfNull(owner, () => $"owner is null !!!"); var received_requests = await cache.getReceivedFriendRequests(); var send_friend_action = owner.getEntityAction(); NullReferenceCheckHelper.throwIfNull(send_friend_action, () => $"send_friend_action is null !!! - {owner.toBasicString()}"); //요청 받은 정보가 없으면 리턴.. //상대방이 먼저 취소한경우 여기에 해당 (var is_received, var req_cache) = send_friend_action.isReceivedRequest(received_requests, friendGuid); if (false == is_received) { string err_msg = $"requeat info not exist receive guid : {owner.getUserGuid()}, friend_guid : {friendGuid}, {toBasicString()}"; result.setFail(ServerErrorCode.FriendRequestNotExistInfo, err_msg); Log.getLogger().error(result.toBasicString()); return (result, null); } return (result, req_cache); } public Result friendMaxCountCheck() { var result = new Result(); if (MetaHelper.GameConfigMeta.MaxFriendsNum <= m_friends.Values.Count) { var err_msg = $"my friend count already max count owner : {getOwner().toBasicString()}, friendCount : {m_friends.Values.Count}"; result.setFail(ServerErrorCode.FriendInfoMyCountAlreadyMaxCount, err_msg); Log.getLogger().error(result.toBasicString()); return result; } return result; } public Result raiseErrorIfExistFriend(string friendGuid) { var result = new Result(); if (m_friends.ContainsKey(friendGuid)) { var err_msg = $"already exist friend : {friendGuid}, friendGuids : {JsonConvert.SerializeObject(m_friends.Keys)}, owner : {getOwner().toBasicString()}"; result.setFail(ServerErrorCode.FriendRequestAlreadyFriend, err_msg); Log.getLogger().error(result.toBasicString()); return result; } return result; } public bool isFriend(string friendGuid) { return m_friends.ContainsKey(friendGuid); } public ConcurrentDictionary getFriends() => m_friends; public FriendAttribute? getFriendAttribute(string friendGuid) { if (!m_friends.TryGetValue(friendGuid, out var friend)) return null; var friend_attribute = friend.getEntityAttribute(); return friend_attribute; } public Friend? getFriend(string friendGuid) { m_friends.TryGetValue(friendGuid, out var friend); return friend; } public static FriendErrorMember makeFriendMemberError(ServerErrorCode errorCode, string guid) { FriendErrorMember errormember = new(); errormember.ErrorCode = errorCode; errormember.Guid = guid; return errormember; } public void deleteFriend(string friendGuid) { m_friends.TryRemove(friendGuid, out _); } }