From a7c8cdff56d0f03e44d199ed33d506d054334edd Mon Sep 17 00:00:00 2001 From: ca45382 Date: Mon, 9 Aug 2021 20:02:26 +0900 Subject: [PATCH] =?UTF-8?q?=E4=BA=88=E7=B4=84=E3=82=92=E3=82=B3=E3=83=9E?= =?UTF-8?q?=E3=83=B3=E3=83=89=E3=81=AB=E8=BF=BD=E5=8A=A0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- DataType/WarningType.cs | 15 + .../Shiori/DatabaseReservationController.cs | 72 ++-- Define/TimeDefine.cs | 1 + Script/ClanBattle/BattleDeclaration.cs | 16 +- Script/ClanBattle/BattleReservation.cs | 370 +++--------------- Script/ClanBattle/BattleReservationSummary.cs | 155 ++++++++ Script/ClanBattle/UpdateDate.cs | 2 +- Script/Commands.cs | 63 +++ Script/ReceiveInteractionController.cs | 7 +- 9 files changed, 332 insertions(+), 369 deletions(-) create mode 100644 DataType/WarningType.cs create mode 100644 Script/ClanBattle/BattleReservationSummary.cs diff --git a/DataType/WarningType.cs b/DataType/WarningType.cs new file mode 100644 index 00000000..0ced3198 --- /dev/null +++ b/DataType/WarningType.cs @@ -0,0 +1,15 @@ +using System; +using System.Collections.Generic; +using System.ComponentModel; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace PriconneBotConsoleApp.DataType +{ + public enum WarningType + { + [Description("コメントが長いので切り取られました。\n 問題がある場合は予約削除をして再度予約してください。") ] + LongComment, + } +} diff --git a/Database/Shiori/DatabaseReservationController.cs b/Database/Shiori/DatabaseReservationController.cs index f644d435..5e09cb5f 100644 --- a/Database/Shiori/DatabaseReservationController.cs +++ b/Database/Shiori/DatabaseReservationController.cs @@ -1,4 +1,5 @@ -using System.Collections.Generic; +using System; +using System.Collections.Generic; using System.Linq; using Microsoft.EntityFrameworkCore; using PriconneBotConsoleApp.DataModel; @@ -35,17 +36,15 @@ public static List LoadReservationData(ClanData clanData) public static List LoadReservationData(PlayerData playerData) { - if (playerData == null) + if (playerData == null|| playerData.PlayerID == 0) { return null; } using var databaseConnector = new DatabaseConnector(); - var playerID = LoadPlayerID(databaseConnector.PlayerData, playerData); - return databaseConnector.ReservationData.AsQueryable() - .Where(b => b.PlayerID == playerID && !b.DeleteFlag) + .Where(b => b.PlayerID == playerData.PlayerID && !b.DeleteFlag) .OrderBy(o => o.BattleLap).ThenBy(d => d.BossNumber) .ToList(); } @@ -96,28 +95,24 @@ public static List LoadBossLapReservationData(ClanData clanData /// public static void CreateReservationData(ReservationData reservationData) { - var playerData = reservationData.PlayerData; - using var databaseConnector = new DatabaseConnector(); - var transaction = databaseConnector.Database.BeginTransaction(); - var playerID = LoadPlayerID(databaseConnector.PlayerData, playerData); - - if (playerID == 0) + if (reservationData.PlayerID == 0) { - transaction.Rollback(); return; } - databaseConnector.ReservationData.Add( - new ReservationData() - { - PlayerID = playerID, - BattleLap = reservationData.BattleLap, - BossNumber = reservationData.BossNumber, - CommentData = reservationData.CommentData - }); + using var databaseConnector = new DatabaseConnector(); + var transaction = databaseConnector.Database.BeginTransaction(); - databaseConnector.SaveChanges(); - transaction.Commit(); + databaseConnector.ReservationData.Add(reservationData); + try + { + databaseConnector.SaveChanges(); + transaction.Commit(); + } + catch (Exception e) + { + Console.WriteLine(e.Message); + } } /// @@ -126,30 +121,21 @@ public static void CreateReservationData(ReservationData reservationData) /// public static void UpdateReservationData(ReservationData reservationData) { - var playerData = reservationData.PlayerData; using var databaseConnector = new DatabaseConnector(); var transaction = databaseConnector.Database.BeginTransaction(); - var playerID = LoadPlayerID(databaseConnector.PlayerData, playerData); + var updateData = databaseConnector.ReservationData + .FirstOrDefault(x => x.ReserveID == reservationData.ReserveID); - if (playerID == 0) + try { - transaction.Rollback(); - return; + updateData.CommentData = reservationData.CommentData; + databaseConnector.SaveChanges(); + transaction.Commit(); } - - var updateData = databaseConnector.ReservationData - .FirstOrDefault(d => d.PlayerID == playerID && d.BattleLap == reservationData.BattleLap - && d.BossNumber == reservationData.BossNumber && !d.DeleteFlag); - - if (updateData == null) + catch { transaction.Rollback(); - return; } - - updateData.CommentData = reservationData.CommentData; - databaseConnector.SaveChanges(); - transaction.Commit(); } public static void DeleteReservationData(ReservationData reservationData) @@ -176,15 +162,5 @@ public static void DeleteReservationData(IEnumerable reservatio databaseConnector.SaveChanges(); transaction.Commit(); } - - private static ulong LoadPlayerID(IQueryable queryable, PlayerData playerData) - { - return queryable - .Include(b => b.ClanData) - .FirstOrDefault(b => b.ClanData.ServerID == playerData.ClanData.ServerID - && b.ClanData.ClanRoleID == playerData.ClanData.ClanRoleID - && b.UserID == playerData.UserID) - ?.PlayerID ?? 0; - } } } diff --git a/Define/TimeDefine.cs b/Define/TimeDefine.cs index 0fcb6dc1..8bb0a977 100644 --- a/Define/TimeDefine.cs +++ b/Define/TimeDefine.cs @@ -8,6 +8,7 @@ public static class TimeDefine public readonly static TimeSpan DailyRefreshTime = new(5, 0, 30); public readonly static TimeSpan ErrorMessageDisplayTime = new(0, 0, 5); + public readonly static TimeSpan WarningMessageDisplayTime = new(0, 0, 20); public readonly static TimeSpan SuccessMessageDisplayTime = new(0, 0, 30); } } diff --git a/Script/ClanBattle/BattleDeclaration.cs b/Script/ClanBattle/BattleDeclaration.cs index 7d72d56e..582bc32f 100644 --- a/Script/ClanBattle/BattleDeclaration.cs +++ b/Script/ClanBattle/BattleDeclaration.cs @@ -80,9 +80,9 @@ public async Task RunDeclarationCommandByMessage() if (m_UserMessage.Content.StartsWith("!call")) { await DeclarationCallCommand(); - var battleReservation = new BattleReservation(m_UserRole); - battleReservation.DeleteUnusedData(m_BossNumber); - await battleReservation.UpdateSystemMessage(); + var battleReservationSummary = new BattleReservationSummary(m_UserRole); + battleReservationSummary.DeleteUnusedData(m_BossNumber); + await battleReservationSummary.UpdateMessage(); } } @@ -119,7 +119,7 @@ public async Task RunByInteraction() case ButtonType.SubdueBoss: await NextBossCommand(); - await new BattleReservation(m_UserRole).UpdateSystemMessage(); + await new BattleReservationSummary(m_UserRole).UpdateMessage(); return; case ButtonType.CancelBattle: @@ -128,7 +128,7 @@ public async Task RunByInteraction() } await UpdateDeclarationBotMessage(); - await new BattleReservation(m_UserRole).UpdateSystemMessage(); + await new BattleReservationSummary(m_UserRole).UpdateMessage(); } /// @@ -307,9 +307,9 @@ private async Task NextBossCommand() m_UserClanData.SetBossLap(m_BossNumber, nextBattleLap); DatabaseClanDataController.UpdateClanData(m_UserClanData); - var battleReservation = new BattleReservation(m_UserRole); - battleReservation.DeleteUnusedData(m_BossNumber); - await Task.WhenAll(SendDeclarationBotMessage(), battleReservation.UpdateSystemMessage()); + var battleReservationSummary = new BattleReservationSummary(m_UserRole); + battleReservationSummary.DeleteUnusedData(m_BossNumber); + await Task.WhenAll(SendDeclarationBotMessage(), battleReservationSummary.UpdateMessage()); } /// diff --git a/Script/ClanBattle/BattleReservation.cs b/Script/ClanBattle/BattleReservation.cs index 32bbaf87..b477bc63 100644 --- a/Script/ClanBattle/BattleReservation.cs +++ b/Script/ClanBattle/BattleReservation.cs @@ -1,17 +1,15 @@ using System; +using System.Collections.Generic; using System.Linq; using System.Text; using System.Threading.Tasks; -using System.Reflection; -using System.ComponentModel; using Discord; using Discord.WebSocket; +using PriconneBotConsoleApp.Database; using PriconneBotConsoleApp.DataModel; using PriconneBotConsoleApp.DataType; -using PriconneBotConsoleApp.Database; -using PriconneBotConsoleApp.Extension; -using System.Collections.Generic; using PriconneBotConsoleApp.Define; +using PriconneBotConsoleApp.Extension; namespace PriconneBotConsoleApp.Script { @@ -19,232 +17,87 @@ public class BattleReservation { private const int MaxCommentLength = 30; - private readonly ClanData m_UserClanData; - private readonly SocketRole m_UserRole; - private readonly SocketUserMessage m_UserMessage; - private readonly SocketInteraction m_UserInteraction; - - private BattleReservation( - ClanData userClanData, - ISocketMessageChannel channel, - SocketUserMessage userMessage = null, - SocketInteraction userInterction = null) - { - m_UserClanData = userClanData; - m_UserRole = (channel as SocketGuildChannel)?.Guild.GetRole(m_UserClanData.ClanRoleID); - m_UserMessage = userMessage; - m_UserInteraction = userInterction; - } + private readonly CommandEventArgs m_CommandEventArgs; - public BattleReservation(ClanData userClanData, SocketUserMessage message) - : this(userClanData, message.Channel, userMessage: message) + public BattleReservation(CommandEventArgs commandEventArgs) { + m_CommandEventArgs = commandEventArgs; } - public BattleReservation(ClanData userClanData, SocketInteraction interaction) - : this(userClanData, interaction.Channel, userInterction: interaction) - { - } - - public BattleReservation(SocketRole userRole) + /// + /// 個人の予約一覧を表示する。引数は無し。 + /// + public void PlayerReserveList() { - m_UserRole = userRole; - m_UserClanData = DatabaseClanDataController.LoadClanData(userRole); + _ = m_CommandEventArgs.Channel.SendMessageAsync( + CreateUserReservationDataMessage(m_CommandEventArgs.PlayerData)); } - public async Task RunReservationCommand() + public void RegisterReserveData() { - var userMessage = m_UserMessage; - - if (userMessage == null) + if (!IsReservationAllowTime()) { + _ = m_CommandEventArgs.Channel.SendTimedMessageAsync( + TimeDefine.ErrorMessageDisplayTime, + string.Format(ErrorType.OutOfReservationTime.ToLabel(), + $"{m_CommandEventArgs.ClanData.ReservationStartTime.Hours}:00", + $"{m_CommandEventArgs.ClanData.ReservationEndTime.Hours}:00") + ); return; } - var messageContents = userMessage.Content; - - if (messageContents.StartsWith("予約")) - { - switch (messageContents) - { - case "予約": - case "予約確認": - case "予約状況": - Console.WriteLine("予約確認"); - await userMessage.Channel.SendMessageAsync(CreateUserReservationDataMessage()); - return; - } - - if (!IsReservationAllowTime()) - { - await SendErrorMessage(ErrorType.OutOfReservationTime, - $"{m_UserClanData.ReservationStartTime.Hours}:00", $"{m_UserClanData.ReservationEndTime.Hours}:00"); - return; - } - - var reservationData = MessageToReservationData(); - - if (reservationData is null) - { - await SendErrorMessage(ErrorType.FailedReservation); - return; - } - - var allowReservationLap = m_UserClanData.ReservationLap == 0 - ? ClanBattleDefine.MaxLapNumber : (m_UserClanData.ReservationLap + m_UserClanData.GetMinBossLap()); - - if (reservationData.BattleLap > allowReservationLap) - { - await SendErrorMessage(ErrorType.OutOfReservationBossLaps, allowReservationLap.ToString()); - return; - } - - RegisterReservationData(reservationData); - await SuccessAddEmoji(); - await UpdateSystemMessage(); - - if (m_UserClanData.GetBossLap(reservationData.BossNumber) == reservationData.BattleLap) - { - await new BattleDeclaration(m_UserRole, (BossNumberType)reservationData.BossNumber).UpdateDeclarationBotMessage(); - } - } - else if (messageContents.StartsWith("削除")) - { - var deleteReservationData = MessageToReservationData(); - - if (deleteReservationData is null) - { - // await FailedToRegisterMessage(); - return; - } + var reservationData = MessageToReservationData(); - if (DeleteUserReservationData(deleteReservationData)) - { - await SuccessAddEmoji(); - await UpdateSystemMessage(); - } - } - else if (messageContents.StartsWith("!rm")) - { - var userReservationData = MessageToUserReservationData(); - - if (userReservationData == null || !DeleteUserReservationData(userReservationData)) - { - return; - } - - await SuccessAddEmoji(); - await UpdateSystemMessage(); - - if (m_UserClanData.GetBossLap(userReservationData.BossNumber) == userReservationData.BattleLap) - { - await new BattleDeclaration(m_UserRole, (BossNumberType)userReservationData.BossNumber).UpdateDeclarationBotMessage(); - } - } - } - - - public async Task RunReservationResultCommand() - { - if (m_UserMessage.Content.StartsWith("!start")) - { - await SendSystemMessage(); - } - } - - public async Task RunResultInteraction() - { - if (m_UserInteraction == null) + if (reservationData is null) { + _ = m_CommandEventArgs.Channel.SendTimedMessageAsync( + TimeDefine.ErrorMessageDisplayTime, + ErrorType.FailedReservation.ToLabel() + ); return; } - var messageComponent = (SocketMessageComponent)m_UserInteraction; + var allowReservationLap = m_CommandEventArgs.ClanData.ReservationLap == 0 + ? ClanBattleDefine.MaxLapNumber : (m_CommandEventArgs.ClanData.ReservationLap + m_CommandEventArgs.ClanData.GetMinBossLap()); - if (!Enum.TryParse(messageComponent.Data.CustomId, out var buttonType)) + if (reservationData.BattleLap > allowReservationLap) { + _ = m_CommandEventArgs.Channel.SendTimedMessageAsync( + TimeDefine.ErrorMessageDisplayTime, + string.Format(ErrorType.OutOfReservationBossLaps.ToLabel(), allowReservationLap.ToString()) + ); return; } - switch (buttonType) - { - case ButtonType.Reload: - await UpdateSystemMessage(); - break; - } - } + RegisterReservationData(reservationData); + _ = m_CommandEventArgs.SocketUserMessage.AddReactionAsync(ReactionType.Success.ToEmoji()); + _ = new BattleReservationSummary(m_CommandEventArgs.Role, m_CommandEventArgs.ClanData).UpdateMessage(); - /// - /// 凸予約一覧チャンネルにメッセージを送信する。 - /// - /// - public async Task SendSystemMessage() - { - var embedData = CreateAllReservationDataMessage(); - var componentData = CreateSystemMessageComponent(); - var reservationResultChannelID = m_UserClanData.ChannelData - .GetChannelID(m_UserClanData.ClanID, ChannelFeatureType.ReserveResultID); - - if (reservationResultChannelID == 0) + if (m_CommandEventArgs.ClanData.GetBossLap(reservationData.BossNumber) == reservationData.BattleLap) { - return; + _ = new BattleDeclaration(m_CommandEventArgs.Role, (BossNumberType)reservationData.BossNumber).UpdateDeclarationBotMessage(); } - - var resultChannel = m_UserRole.Guild - .GetTextChannel(reservationResultChannelID); - - var sendedMessageData = await resultChannel.SendMessageAsync(embed: embedData, component: componentData); - DatabaseMessageDataController.UpdateMessageID(m_UserClanData, sendedMessageData.Id, MessageFeatureType.ReserveResultID); } - public async Task UpdateSystemMessage() + public void DeleteReserveData() { - var reservationMessageID = m_UserClanData.MessageData - .GetMessageID(m_UserClanData.ClanID, MessageFeatureType.ReserveResultID); - var reservationResultChannelID = m_UserClanData.ChannelData - .GetChannelID(m_UserClanData.ClanID, ChannelFeatureType.ReserveResultID); + var deleteReservationData = MessageToReservationData(); - if (reservationResultChannelID == 0 || reservationMessageID == 0) + if (deleteReservationData is null) { return; } - var guildChannel = m_UserRole.Guild - .GetChannel(reservationResultChannelID) as SocketTextChannel; - var socketMessage = guildChannel.GetCachedMessage(reservationMessageID); - - if (socketMessage == null || !(socketMessage is SocketUserMessage)) + if (DeleteUserReservationData(deleteReservationData)) { - var message = await guildChannel.GetMessageAsync(reservationMessageID); + _ = m_CommandEventArgs.SocketUserMessage.AddReactionAsync(ReactionType.Success.ToEmoji()); + _ = new BattleReservationSummary(m_CommandEventArgs.Role, m_CommandEventArgs.ClanData).UpdateMessage(); - if (message != null) + if (m_CommandEventArgs.ClanData.GetBossLap(deleteReservationData.BossNumber) == deleteReservationData.BattleLap) { - await guildChannel.DeleteMessageAsync(message); - await SendSystemMessage(); + _ = new BattleDeclaration(m_CommandEventArgs.Role, (BossNumberType)deleteReservationData.BossNumber).UpdateDeclarationBotMessage(); } - - return; } - - var serverMessage = socketMessage as SocketUserMessage; - var embedData = CreateAllReservationDataMessage(); - await serverMessage.ModifyAsync(x => x.Embed = embedData); - } - - public void DeleteUnusedData(byte bossNumber) - { - var clanReservationData = DatabaseReservationController.LoadReservationData(m_UserClanData, bossNumber); - var bossLap = m_UserClanData.GetBossLap(bossNumber); - var deleteData = clanReservationData.Where(x => x.BattleLap < bossLap); - DatabaseReservationController.DeleteReservationData(deleteData); - } - - private MessageComponent CreateSystemMessageComponent() - { - ComponentBuilder componentBuilder = new(); - componentBuilder.WithButton( - ButtonType.Reload.ToLongLabel(), ButtonType.Reload.ToString(), ButtonStyle.Secondary, ButtonType.Reload.ToEmoji()); - return componentBuilder.Build(); } /// @@ -255,80 +108,47 @@ private MessageComponent CreateSystemMessageComponent() /// private ReservationData MessageToReservationData() { - var splitMessageContent = m_UserMessage.Content.ZenToHan().Split(' ', StringSplitOptions.RemoveEmptyEntries); - - if (splitMessageContent.Length < 3 - || !(byte.TryParse(splitMessageContent[1], out byte battleLap) && battleLap > 0) - || !(byte.TryParse(splitMessageContent[2], out byte bossNumber) && bossNumber <= CommonDefine.MaxBossNumber && bossNumber >= CommonDefine.MinBossNumber) - || battleLap < m_UserClanData.GetBossLap(bossNumber)) + if (!Enum.TryParse(m_CommandEventArgs.Arguments[1], out var bossNumber) + || !(byte.TryParse(m_CommandEventArgs.Arguments[0], out var battleLap) && battleLap > m_CommandEventArgs.ClanData.GetBossLap(bossNumber))) { return null; } - var commentData = string.Join(' ', splitMessageContent.Skip(3)); + + var commentData = string.Join(' ', m_CommandEventArgs.Arguments.Skip(2)); if (commentData.Length > MaxCommentLength) { commentData = commentData.Substring(0, MaxCommentLength); - m_UserMessage.Channel.SendMessageAsync($"コメントが長いので切り取られました。\n 問題がある場合は予約削除をして再度予約してください。"); + _ = m_CommandEventArgs.Channel.SendTimedMessageAsync(TimeDefine.WarningMessageDisplayTime, WarningType.LongComment.ToLabel()); } return new ReservationData() { - PlayerData = new PlayerData - { - ClanData = m_UserClanData, - UserID = m_UserMessage.Author.Id, - }, + PlayerID = m_CommandEventArgs.PlayerData.PlayerID, BattleLap = battleLap, - BossNumber = bossNumber, + BossNumber = (byte)bossNumber, CommentData = commentData, }; } private void RegisterReservationData(ReservationData reservationData) { - var allSqlReservationData = DatabaseReservationController.LoadReservationData(reservationData.PlayerData); + var allSqlReservationData = DatabaseReservationController.LoadReservationData(m_CommandEventArgs.PlayerData); - var doesExistReservationData = allSqlReservationData - .Any(x => x.BossNumber == reservationData.BossNumber && x.BattleLap == reservationData.BattleLap); + var DatabaseReservationData = allSqlReservationData + .FirstOrDefault(x => x.BossNumber == reservationData.BossNumber && x.BattleLap == reservationData.BattleLap); - if (!doesExistReservationData) + if (DatabaseReservationData == null) { DatabaseReservationController.CreateReservationData(reservationData); } else { + reservationData.ReserveID = DatabaseReservationData.ReserveID; DatabaseReservationController.UpdateReservationData(reservationData); } } - /// - /// 個人が予約しているデータの取得 - /// - /// - private ReservationData MessageToUserReservationData() - { - var splitMessageContent = m_UserMessage.Content.ZenToHan().Split(' ', StringSplitOptions.RemoveEmptyEntries); - - if (splitMessageContent.Length != 4 - || !ulong.TryParse(splitMessageContent[1], out ulong userID) - || !(byte.TryParse(splitMessageContent[2], out byte battleLap) && battleLap > 0) - || !(byte.TryParse(splitMessageContent[3], out byte bossNumber) && bossNumber <= CommonDefine.MaxBossNumber && bossNumber >= CommonDefine.MinBossNumber)) - { - return null; - } - - var playerData = DatabasePlayerDataController.LoadPlayerData(m_UserRole, userID); - - if (playerData == null) - { - return null; - } - - return DatabaseReservationController.LoadReservationData(playerData) - .FirstOrDefault(d => d.BattleLap == battleLap && d.BossNumber == bossNumber); - } - private bool DeleteUserReservationData(ReservationData reservationData) { var userReservationDataList = DatabaseReservationController.LoadReservationData(reservationData.PlayerData); @@ -347,11 +167,6 @@ private bool DeleteUserReservationData(ReservationData reservationData) return true; } - private string CreateUserReservationDataMessage() - => CreateUserReservationDataMessage( - DatabasePlayerDataController.LoadPlayerData(m_UserRole, m_UserMessage.Author.Id) - ); - private string CreateUserReservationDataMessage(PlayerData playerData) { var reservationDataSet = DatabaseReservationController.LoadReservationData(playerData); @@ -377,82 +192,19 @@ private string CreateUserReservationDataMessage(PlayerData playerData) return messageData.ToString(); } - /// - /// 予約メッセージを作成する - /// - /// - /// - private Embed CreateAllReservationDataMessage() - { - var reservationDataSet = DatabaseReservationController.LoadReservationData(m_UserClanData); - List> reservationDataList = new(); - - for (var i = 0; i < CommonDefine.MaxBossNumber; i++) - { - reservationDataList.Add(new List()); - } - - reservationDataSet.ForEach(x => reservationDataList[x.BossNumber - 1].Add(x)); - EmbedBuilder embedBuilder = new(); - - for (var i = 0; i < CommonDefine.MaxBossNumber; i++) - { - EmbedFieldBuilder fieldBuilder = new(); - - if (!reservationDataList[i].Any()) - { - // 何かの空白代入して空行を生成している。 - fieldBuilder.Value = "\n\u200b"; - } - else - { - StringBuilder messageData = new(); - messageData.AppendLine("```python"); - reservationDataList[i].ForEach(x => messageData.AppendLine($"{x.BattleLap,2}周目 {x.PlayerData.GuildUserName} {x.CommentData}")); - messageData.AppendLine("```"); - fieldBuilder.Value = messageData.ToString(); - } - - fieldBuilder.Name = $"{i + 1}ボス({reservationDataList[i].Count}件)"; - embedBuilder.AddField(fieldBuilder); - } - - embedBuilder.Title = $"現在の予約状況:計{reservationDataSet.Count}件"; - - return embedBuilder.Build(); - } - - private async Task SendErrorMessage(ErrorType type, params string[] parameters) - { - var descriptionString = type.GetDescription(); - var sendMessage = string.Empty; - if (descriptionString == null) - { - sendMessage = type.ToString(); - } - else - { - sendMessage = string.Format(descriptionString, parameters); - } - await m_UserMessage.Channel.SendMessageAsync(sendMessage); - } - - private async Task SuccessAddEmoji() - => await m_UserMessage.AddReactionAsync(new Emoji(ReactionType.Success.GetDescription())); - /// /// 予約できる時間かどうか判断する。 /// /// private bool IsReservationAllowTime() { - if (m_UserClanData == null) + if (m_CommandEventArgs.ClanData == null) { return false; } - var startTime = m_UserClanData.ReservationStartTime; - var endTime = m_UserClanData.ReservationEndTime; + var startTime = m_CommandEventArgs.ClanData.ReservationStartTime; + var endTime = m_CommandEventArgs.ClanData.ReservationEndTime; var nowTime = DateTime.Now.TimeOfDay; if (startTime.Hours == 0 && endTime.Hours == 0) diff --git a/Script/ClanBattle/BattleReservationSummary.cs b/Script/ClanBattle/BattleReservationSummary.cs new file mode 100644 index 00000000..1b0e1874 --- /dev/null +++ b/Script/ClanBattle/BattleReservationSummary.cs @@ -0,0 +1,155 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using Discord; +using Discord.WebSocket; +using PriconneBotConsoleApp.Database; +using PriconneBotConsoleApp.DataModel; +using PriconneBotConsoleApp.DataType; +using PriconneBotConsoleApp.Define; + +namespace PriconneBotConsoleApp.Script +{ + public class BattleReservationSummary + { + private readonly ClanData m_ClanData; + private readonly SocketRole m_Role; + private readonly SocketTextChannel m_SocketTextChannel; + + public BattleReservationSummary(SocketRole role, ClanData clanData = null) + { + m_Role = role; + if (clanData == null) + { + m_ClanData = DatabaseClanDataController.LoadClanData(m_Role); + } + else + { + m_ClanData = clanData; + } + m_SocketTextChannel = m_Role.Guild.GetChannel(m_ClanData.GetChannelID(ChannelFeatureType.ReserveResultID)) + as SocketTextChannel; + } + + public async Task RunInteraction(SocketInteraction socketInteraction) + { + var messageComponent = (SocketMessageComponent)socketInteraction; + + if (!Enum.TryParse(messageComponent.Data.CustomId, out var buttonType)) + { + return; + } + + switch (buttonType) + { + case ButtonType.Reload: + await UpdateMessage(); + break; + } + } + + /// + /// 凸予約一覧チャンネルにメッセージを送信する。 + /// + /// + public async Task SendMessage() + { + var embedData = CreateEmbed(); + var componentData = CreateComponent(); + var sendedMessageData = await m_SocketTextChannel.SendMessageAsync(embed: embedData, component: componentData); + DatabaseMessageDataController.UpdateMessageID(m_ClanData, sendedMessageData.Id, MessageFeatureType.ReserveResultID); + } + + public async Task UpdateMessage() + { + if (m_SocketTextChannel == null) + { + return; + } + + var reservationMessageID = m_ClanData.GetMessageID(MessageFeatureType.ReserveResultID); + var cachedMessage = m_SocketTextChannel.GetCachedMessage(reservationMessageID); + var embedData = CreateEmbed(); + var componentData = CreateComponent(); + + if (cachedMessage is SocketUserMessage serverMessage) + { + await serverMessage.ModifyAsync(x => x.Embed = embedData); + } + else + { + var message = await m_SocketTextChannel.GetMessageAsync(reservationMessageID); + await SendMessage(); + + if (message != null) + { + await m_SocketTextChannel.DeleteMessageAsync(message); + } + } + } + + public void DeleteUnusedData(byte bossNumber) + { + var clanReservationData = DatabaseReservationController.LoadReservationData(m_ClanData, bossNumber); + var bossLap = m_ClanData.GetBossLap(bossNumber); + var deleteData = clanReservationData.Where(x => x.BattleLap < bossLap); + DatabaseReservationController.DeleteReservationData(deleteData); + } + + /// + /// 予約メッセージを作成する + /// + /// + /// + private Embed CreateEmbed() + { + var reservationDataSet = DatabaseReservationController.LoadReservationData(m_ClanData); + List> reservationDataList = new(); + + for (var i = 0; i < CommonDefine.MaxBossNumber; i++) + { + reservationDataList.Add(new List()); + } + + reservationDataSet.ForEach(x => reservationDataList[x.BossNumber - 1].Add(x)); + EmbedBuilder embedBuilder = new(); + + for (var i = 0; i < CommonDefine.MaxBossNumber; i++) + { + EmbedFieldBuilder fieldBuilder = new(); + + if (!reservationDataList[i].Any()) + { + // 何かの空白代入して空行を生成している。 + fieldBuilder.Value = "\n\u200b"; + } + else + { + StringBuilder messageData = new(); + messageData.AppendLine("```python"); + reservationDataList[i].ForEach(x => messageData.AppendLine($"{x.BattleLap,2}周目 {x.PlayerData.GuildUserName} {x.CommentData}")); + messageData.AppendLine("```"); + fieldBuilder.Value = messageData.ToString(); + } + + fieldBuilder.Name = $"{i + 1}ボス({reservationDataList[i].Count}件)"; + embedBuilder.AddField(fieldBuilder); + } + + embedBuilder.Title = $"現在の予約状況:計{reservationDataSet.Count}件"; + + return embedBuilder.Build(); + } + + private MessageComponent CreateComponent() + { + ComponentBuilder componentBuilder = new(); + componentBuilder.WithButton( + ButtonType.Reload.ToLongLabel(), ButtonType.Reload.ToString(), ButtonStyle.Secondary, ButtonType.Reload.ToEmoji()); + return componentBuilder.Build(); + } + + } +} diff --git a/Script/ClanBattle/UpdateDate.cs b/Script/ClanBattle/UpdateDate.cs index da5b09ef..190f3dbb 100644 --- a/Script/ClanBattle/UpdateDate.cs +++ b/Script/ClanBattle/UpdateDate.cs @@ -55,7 +55,7 @@ public async Task DeleteYesterdayData() } taskList.Add(new BattleTaskKill(clanRole).SyncTaskKillData()); - taskList.Add(new BattleReservation(clanRole).UpdateSystemMessage()); + taskList.Add(new BattleReservationSummary(clanRole).UpdateMessage()); for (int i = 0; i < CommonDefine.MaxBossNumber; i++) { diff --git a/Script/Commands.cs b/Script/Commands.cs index be2c8252..d91b10b0 100644 --- a/Script/Commands.cs +++ b/Script/Commands.cs @@ -307,5 +307,68 @@ public static Task RegisterReportData(CommandEventArgs commandEventArgs) new BattleReport(commandEventArgs).RegisterReportData(); return Task.CompletedTask; } + + [Command("予約", 0, compatibleChannels: ChannelFeatureType.ReserveID)] + public static Task ReservationCommand(CommandEventArgs commandEventArgs) + { + BattleReservation battleReservation = new(commandEventArgs); + + if (commandEventArgs.Arguments.Count == 0) + { + battleReservation.PlayerReserveList(); + } + else + { + battleReservation.RegisterReserveData(); + } + + return Task.CompletedTask; + } + + [Command(new[] { "予約一覧, 予約確認, 予約状況, !list" }, 0, 0, ChannelFeatureType.ReserveID)] + public static Task ListReservation(CommandEventArgs commandEventArgs) + { + new BattleReservation(commandEventArgs).PlayerReserveList(); + return Task.CompletedTask; + } + + [Command(new[] { "削除", "!rm" }, 2, 2, ChannelFeatureType.ReserveID)] + public static Task DeleteReserveData(CommandEventArgs commandEventArgs) + { + new BattleReservation(commandEventArgs).DeleteReserveData(); + return Task.CompletedTask; + } + + [Command("!start", 0, 0, ChannelFeatureType.ReserveResultID)] + public static async Task SendReserveSummary(CommandEventArgs commandEventArgs) + => await new BattleReservationSummary(commandEventArgs.Role, commandEventArgs.ClanData).SendMessage(); + + [Command(compatibleChannels: new[] + { + ChannelFeatureType.DeclareBoss1ID, + ChannelFeatureType.DeclareBoss2ID, + ChannelFeatureType.DeclareBoss3ID, + ChannelFeatureType.DeclareBoss4ID, + ChannelFeatureType.DeclareBoss5ID, + })] + public static async Task StartDeclare(CommandEventArgs commandEventArgs) + { + var BossNumber = commandEventArgs.ChannelFeatureType switch + { + ChannelFeatureType.DeclareBoss1ID => BossNumberType.Boss1Number, + ChannelFeatureType.DeclareBoss2ID => BossNumberType.Boss2Number, + ChannelFeatureType.DeclareBoss3ID => BossNumberType.Boss3Number, + ChannelFeatureType.DeclareBoss4ID => BossNumberType.Boss4Number, + ChannelFeatureType.DeclareBoss5ID => BossNumberType.Boss5Number, + _ => BossNumberType.Unknown, + }; + + if (BossNumber == BossNumberType.Unknown) + { + return; + } + + await new BattleDeclaration(commandEventArgs.ClanData, commandEventArgs.SocketUserMessage, BossNumber).RunDeclarationCommandByMessage(); + } } } diff --git a/Script/ReceiveInteractionController.cs b/Script/ReceiveInteractionController.cs index f29da2a2..80289aa8 100644 --- a/Script/ReceiveInteractionController.cs +++ b/Script/ReceiveInteractionController.cs @@ -13,6 +13,7 @@ public class ReceiveInteractionController private readonly SocketTextChannel m_TextChannel; private readonly PlayerData m_PlayerData; private readonly ClanData m_ClanData; + private readonly SocketRole m_Role; public ReceiveInteractionController(SocketInteraction interaction) { @@ -25,8 +26,8 @@ public ReceiveInteractionController(SocketInteraction interaction) return; } - var playerRole = m_TextChannel.Guild.GetRole(m_PlayerData.ClanData.ClanRoleID); - m_ClanData = DatabaseClanDataController.LoadClanData(playerRole); + m_Role = m_TextChannel.Guild.GetRole(m_PlayerData.ClanData.ClanRoleID); + m_ClanData = DatabaseClanDataController.LoadClanData(m_Role); } public async Task Run() @@ -42,7 +43,7 @@ public async Task Run() if (channelFeatureID == (int)ChannelFeatureType.ReserveResultID) { - await new BattleReservation(m_ClanData, m_Interaction).RunResultInteraction(); + await new BattleReservationSummary(m_Role, m_ClanData).RunInteraction(m_Interaction); } BattleDeclaration battleDeclaration = channelFeatureID switch