feat: add /configure-channels command
This commit is contained in:
parent
110edd34b4
commit
4db09346e2
7 changed files with 588 additions and 25 deletions
224
Catalogger.Backend/Bot/Commands/ChannelCommands.cs
Normal file
224
Catalogger.Backend/Bot/Commands/ChannelCommands.cs
Normal file
|
|
@ -0,0 +1,224 @@
|
|||
using System.ComponentModel;
|
||||
using Catalogger.Backend.Cache;
|
||||
using Catalogger.Backend.Database;
|
||||
using Catalogger.Backend.Database.Queries;
|
||||
using Catalogger.Backend.Extensions;
|
||||
using Catalogger.Backend.Services;
|
||||
using Remora.Commands.Attributes;
|
||||
using Remora.Commands.Groups;
|
||||
using Remora.Discord.API.Abstractions.Objects;
|
||||
using Remora.Discord.API.Objects;
|
||||
using Remora.Discord.Commands.Attributes;
|
||||
using Remora.Discord.Commands.Contexts;
|
||||
using Remora.Discord.Commands.Extensions;
|
||||
using Remora.Discord.Commands.Feedback.Messages;
|
||||
using Remora.Discord.Commands.Feedback.Services;
|
||||
using Remora.Discord.Commands.Services;
|
||||
using Remora.Discord.Interactivity;
|
||||
using Remora.Discord.Interactivity.Services;
|
||||
using Remora.Rest.Core;
|
||||
using Remora.Results;
|
||||
using DbGuild = Catalogger.Backend.Database.Models.Guild;
|
||||
using IResult = Remora.Results.IResult;
|
||||
|
||||
namespace Catalogger.Backend.Bot.Commands;
|
||||
|
||||
public class ChannelCommands(
|
||||
ILogger logger,
|
||||
DatabaseContext db,
|
||||
GuildCacheService guildCache,
|
||||
ChannelCacheService channelCache,
|
||||
IFeedbackService feedbackService,
|
||||
ContextInjectionService contextInjection,
|
||||
InMemoryDataService<Snowflake, ChannelCommandData> dataService) : CommandGroup
|
||||
{
|
||||
private readonly ILogger _logger = logger.ForContext<ChannelCommands>();
|
||||
|
||||
[Command("configure-channels")]
|
||||
[Description("Configure log channels for this server.")]
|
||||
[DiscordDefaultMemberPermissions(DiscordPermission.ManageGuild)]
|
||||
public async Task<IResult> ConfigureChannelsAsync()
|
||||
{
|
||||
if (contextInjection.Context is not IInteractionCommandContext ctx) throw new CataloggerError("No context");
|
||||
if (!ctx.TryGetUserID(out var userId)) throw new CataloggerError("No user ID in context");
|
||||
if (!ctx.TryGetGuildID(out var guildId)) throw new CataloggerError("No guild ID in context");
|
||||
if (!guildCache.TryGet(guildId, out var guild)) throw new CataloggerError("Guild not in cache");
|
||||
var guildChannels = channelCache.GuildChannels(guildId).ToList();
|
||||
var guildConfig = await db.GetGuildAsync(guildId);
|
||||
|
||||
var (embeds, components) = BuildRootMenu(guildChannels, guild, guildConfig);
|
||||
|
||||
var msg = await feedbackService.SendContextualAsync(embeds: embeds,
|
||||
options: new FeedbackMessageOptions(MessageComponents: components)).GetOrThrow();
|
||||
|
||||
dataService.TryAddData(msg.ID, new ChannelCommandData(userId, CurrentPage: null));
|
||||
|
||||
return Result.Success;
|
||||
}
|
||||
|
||||
public static (List<IEmbed>, List<IMessageComponent>) BuildRootMenu(List<IChannel> guildChannels, IGuild guild,
|
||||
DbGuild guildConfig)
|
||||
{
|
||||
List<IEmbed> embeds =
|
||||
[
|
||||
new Embed(
|
||||
Title: $"Log channels for {guild.Name}",
|
||||
Description: "Press one of the buttons below to change the channel for that log type.",
|
||||
Colour: DiscordUtils.Purple,
|
||||
Fields: new[]
|
||||
{
|
||||
new EmbedField("Server changes", PrettyChannelString(guildConfig.Channels.GuildUpdate), true),
|
||||
new EmbedField("Emoji changes", PrettyChannelString(guildConfig.Channels.GuildEmojisUpdate), true),
|
||||
new EmbedField("New roles", PrettyChannelString(guildConfig.Channels.GuildRoleCreate), true),
|
||||
new EmbedField("Edited roles", PrettyChannelString(guildConfig.Channels.GuildRoleUpdate), true),
|
||||
new EmbedField("Deleted roles", PrettyChannelString(guildConfig.Channels.GuildRoleDelete), true),
|
||||
|
||||
new EmbedField("New channels", PrettyChannelString(guildConfig.Channels.ChannelCreate), true),
|
||||
new EmbedField("Edited channels", PrettyChannelString(guildConfig.Channels.ChannelUpdate), true),
|
||||
new EmbedField("Deleted channels", PrettyChannelString(guildConfig.Channels.ChannelDelete), true),
|
||||
new EmbedField("Members joining", PrettyChannelString(guildConfig.Channels.GuildMemberAdd), true),
|
||||
new EmbedField("Members leaving", PrettyChannelString(guildConfig.Channels.GuildMemberRemove),
|
||||
true),
|
||||
|
||||
new EmbedField("Member role changes", PrettyChannelString(guildConfig.Channels.GuildMemberUpdate),
|
||||
true),
|
||||
new EmbedField("Key role changes", PrettyChannelString(guildConfig.Channels.GuildKeyRoleUpdate),
|
||||
true),
|
||||
new EmbedField("Member name changes",
|
||||
PrettyChannelString(guildConfig.Channels.GuildMemberNickUpdate),
|
||||
true),
|
||||
new EmbedField("Member avatar changes",
|
||||
PrettyChannelString(guildConfig.Channels.GuildMemberAvatarUpdate), true),
|
||||
new EmbedField("Kicks", PrettyChannelString(guildConfig.Channels.GuildMemberKick), true),
|
||||
|
||||
new EmbedField("Bans", PrettyChannelString(guildConfig.Channels.GuildBanAdd), true),
|
||||
new EmbedField("Unbans", PrettyChannelString(guildConfig.Channels.GuildBanRemove), true),
|
||||
new EmbedField("New invites", PrettyChannelString(guildConfig.Channels.InviteCreate), true),
|
||||
new EmbedField("Deleted invites", PrettyChannelString(guildConfig.Channels.InviteDelete), true),
|
||||
new EmbedField("Edited messages", PrettyChannelString(guildConfig.Channels.MessageUpdate), true),
|
||||
|
||||
new EmbedField("Deleted messages", PrettyChannelString(guildConfig.Channels.MessageDelete), true),
|
||||
new EmbedField("Bulk deleted messages", PrettyChannelString(guildConfig.Channels.MessageDeleteBulk),
|
||||
true),
|
||||
})
|
||||
];
|
||||
|
||||
List<IMessageComponent> components =
|
||||
[
|
||||
new ActionRowComponent([
|
||||
new ButtonComponent(ButtonComponentStyle.Primary, Label: "Server changes",
|
||||
CustomID: CustomIDHelpers.CreateButtonIDWithState("config-channels",
|
||||
nameof(LogChannelType.GuildUpdate))),
|
||||
new ButtonComponent(ButtonComponentStyle.Primary, Label: "Emoji changes",
|
||||
CustomID: CustomIDHelpers.CreateButtonIDWithState("config-channels",
|
||||
nameof(LogChannelType.GuildEmojisUpdate))),
|
||||
new ButtonComponent(ButtonComponentStyle.Primary, Label: "New roles",
|
||||
CustomID: CustomIDHelpers.CreateButtonIDWithState("config-channels",
|
||||
nameof(LogChannelType.GuildRoleCreate))),
|
||||
new ButtonComponent(ButtonComponentStyle.Primary, Label: "Edited roles",
|
||||
CustomID: CustomIDHelpers.CreateButtonIDWithState("config-channels",
|
||||
nameof(LogChannelType.GuildRoleUpdate))),
|
||||
new ButtonComponent(ButtonComponentStyle.Primary, Label: "Deleted roles",
|
||||
CustomID: CustomIDHelpers.CreateButtonIDWithState("config-channels",
|
||||
nameof(LogChannelType.GuildRoleDelete))),
|
||||
]),
|
||||
new ActionRowComponent([
|
||||
new ButtonComponent(ButtonComponentStyle.Primary, Label: "New channels",
|
||||
CustomID: CustomIDHelpers.CreateButtonIDWithState("config-channels",
|
||||
nameof(LogChannelType.ChannelCreate))),
|
||||
new ButtonComponent(ButtonComponentStyle.Primary, Label: "Edited channels",
|
||||
CustomID: CustomIDHelpers.CreateButtonIDWithState("config-channels",
|
||||
nameof(LogChannelType.ChannelUpdate))),
|
||||
new ButtonComponent(ButtonComponentStyle.Primary, Label: "Deleted channels",
|
||||
CustomID: CustomIDHelpers.CreateButtonIDWithState("config-channels",
|
||||
nameof(LogChannelType.ChannelDelete))),
|
||||
new ButtonComponent(ButtonComponentStyle.Primary, Label: "Members joining",
|
||||
CustomID: CustomIDHelpers.CreateButtonIDWithState("config-channels",
|
||||
nameof(LogChannelType.GuildMemberAdd))),
|
||||
new ButtonComponent(ButtonComponentStyle.Primary, Label: "Members leaving",
|
||||
CustomID: CustomIDHelpers.CreateButtonIDWithState("config-channels",
|
||||
nameof(LogChannelType.GuildMemberRemove))),
|
||||
]),
|
||||
new ActionRowComponent([
|
||||
new ButtonComponent(ButtonComponentStyle.Primary, Label: "Member role changes",
|
||||
CustomID: CustomIDHelpers.CreateButtonIDWithState("config-channels",
|
||||
nameof(LogChannelType.GuildMemberUpdate))),
|
||||
new ButtonComponent(ButtonComponentStyle.Primary, Label: "Key role changes",
|
||||
CustomID: CustomIDHelpers.CreateButtonIDWithState("config-channels",
|
||||
nameof(LogChannelType.GuildKeyRoleUpdate))),
|
||||
new ButtonComponent(ButtonComponentStyle.Primary, Label: "Member name changes",
|
||||
CustomID: CustomIDHelpers.CreateButtonIDWithState("config-channels",
|
||||
nameof(LogChannelType.GuildMemberNickUpdate))),
|
||||
new ButtonComponent(ButtonComponentStyle.Primary, Label: "Members avatar changes",
|
||||
CustomID: CustomIDHelpers.CreateButtonIDWithState("config-channels",
|
||||
nameof(LogChannelType.GuildMemberAvatarUpdate))),
|
||||
new ButtonComponent(ButtonComponentStyle.Primary, Label: "Kicks",
|
||||
CustomID: CustomIDHelpers.CreateButtonIDWithState("config-channels",
|
||||
nameof(LogChannelType.GuildMemberKick))),
|
||||
]),
|
||||
new ActionRowComponent([
|
||||
new ButtonComponent(ButtonComponentStyle.Primary, Label: "Bans",
|
||||
CustomID: CustomIDHelpers.CreateButtonIDWithState("config-channels",
|
||||
nameof(LogChannelType.GuildBanAdd))),
|
||||
new ButtonComponent(ButtonComponentStyle.Primary, Label: "Unbans",
|
||||
CustomID: CustomIDHelpers.CreateButtonIDWithState("config-channels",
|
||||
nameof(LogChannelType.GuildBanRemove))),
|
||||
new ButtonComponent(ButtonComponentStyle.Primary, Label: "New invites",
|
||||
CustomID: CustomIDHelpers.CreateButtonIDWithState("config-channels",
|
||||
nameof(LogChannelType.InviteCreate))),
|
||||
new ButtonComponent(ButtonComponentStyle.Primary, Label: "Deleted invites",
|
||||
CustomID: CustomIDHelpers.CreateButtonIDWithState("config-channels",
|
||||
nameof(LogChannelType.InviteDelete))),
|
||||
new ButtonComponent(ButtonComponentStyle.Primary, Label: "Edited messages",
|
||||
CustomID: CustomIDHelpers.CreateButtonIDWithState("config-channels",
|
||||
nameof(LogChannelType.MessageUpdate))),
|
||||
]),
|
||||
new ActionRowComponent([
|
||||
new ButtonComponent(ButtonComponentStyle.Primary, Label: "Deleted messages",
|
||||
CustomID: CustomIDHelpers.CreateButtonIDWithState("config-channels",
|
||||
nameof(LogChannelType.MessageDelete))),
|
||||
new ButtonComponent(ButtonComponentStyle.Primary, Label: "Bulk deleted messages",
|
||||
CustomID: CustomIDHelpers.CreateButtonIDWithState("config-channels",
|
||||
nameof(LogChannelType.MessageDeleteBulk))),
|
||||
new ButtonComponent(ButtonComponentStyle.Secondary, Label: "Close",
|
||||
CustomID: CustomIDHelpers.CreateButtonIDWithState("config-channels", "close")),
|
||||
]),
|
||||
];
|
||||
|
||||
return (embeds, components);
|
||||
|
||||
string PrettyChannelString(ulong id)
|
||||
{
|
||||
if (id == 0) return "Not set";
|
||||
if (guildChannels.All(c => c.ID != id)) return $"unknown channel {id}";
|
||||
return $"<#{id}>";
|
||||
}
|
||||
}
|
||||
|
||||
public static string PrettyLogTypeName(LogChannelType type) => type switch
|
||||
{
|
||||
LogChannelType.GuildUpdate => "Server changes",
|
||||
LogChannelType.GuildEmojisUpdate => "Emoji changes",
|
||||
LogChannelType.GuildRoleCreate => "New roles",
|
||||
LogChannelType.GuildRoleUpdate => "Edited roles",
|
||||
LogChannelType.GuildRoleDelete => "Deleted roles",
|
||||
LogChannelType.ChannelCreate => "New channels",
|
||||
LogChannelType.ChannelUpdate => "Edited channels",
|
||||
LogChannelType.ChannelDelete => "Deleted channels",
|
||||
LogChannelType.GuildMemberAdd => "Members joining",
|
||||
LogChannelType.GuildMemberUpdate => "Members leaving",
|
||||
LogChannelType.GuildKeyRoleUpdate => "Key role changes",
|
||||
LogChannelType.GuildMemberNickUpdate => "Member name changes",
|
||||
LogChannelType.GuildMemberAvatarUpdate => "Member avatar changes",
|
||||
LogChannelType.GuildMemberRemove => "Members leaving",
|
||||
LogChannelType.GuildMemberKick => "Kicks",
|
||||
LogChannelType.GuildBanAdd => "Bans",
|
||||
LogChannelType.GuildBanRemove => "Unbans",
|
||||
LogChannelType.InviteCreate => "New invites",
|
||||
LogChannelType.InviteDelete => "Deleted invites",
|
||||
LogChannelType.MessageUpdate => "Edited messages",
|
||||
LogChannelType.MessageDelete => "Deleted messages",
|
||||
LogChannelType.MessageDeleteBulk => "Bulk deleted messages",
|
||||
_ => throw new ArgumentOutOfRangeException(nameof(type), type, "Invalid LogChannelType value")
|
||||
};
|
||||
}
|
||||
Loading…
Add table
Add a link
Reference in a new issue