Refactored a bunch of things

Added Notes Module + Data Structure
Added Config Module + Data Structure
Added Role Buttons Module + Data Structure
This commit is contained in:
pan.codes 2024-04-12 02:25:32 +02:00
parent aab1fad4e2
commit 7f08d72ef8
23 changed files with 638 additions and 83 deletions

View file

@ -0,0 +1,31 @@
using Discord.Interactions;
using Discord;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Xml.Serialization;
using Orpticon.Wrappers;
using SMSModLogOutputAnalyzer.Modules;
namespace SMSModLogOutputAnalyzer.Data
{
public partial class Config
{
public static ITextChannel NotesLogChannel { get => (ITextChannel)Program.Client.GetChannel(Instance.notesLogChannel); set => Instance.notesLogChannel = value.Id; }
[XmlAttribute] public ulong notesLogChannel { get; set; }
public static void Load()
{
Instance = SerializerXML.DeserializeFromFileOrDefault<Config>("Config.xml");
}
public static void Save()
{
SerializerXML.SerializeToFile(Instance, "Config.xml");
}
public static Config Instance { get; set; }
}
}

View file

@ -0,0 +1,24 @@
using Discord;
using System.Reactive;
using System.Xml.Serialization;
using static SMSModLogOutputAnalyzer.Data.NotesDataObject;
namespace SMSModLogOutputAnalyzer.Data
{
public partial class NotesDataObject
{
public class Note
{
[XmlAttribute] public string Text { get; set; }
[XmlAttribute] public ulong CreatorID { get; set; }
[XmlAttribute] public DateTime CreationTime { get; set; }
[XmlAttribute] public int Id { get; set; }
public EmbedFieldBuilder ToField()
{
var unix = ((DateTimeOffset)CreationTime).ToUnixTimeSeconds();
// "Note " + Id, "`" + Text + "`\nCreated by <@" + CreatorID + "> at <t:" + unix + ":f>"
return new EmbedFieldBuilder().WithName(Text).WithValue("ID: `" + Id + "`\nCreated by <@" + CreatorID + "> at <t:" + unix + ":f>");
}
}
}
}

View file

@ -0,0 +1,14 @@
using System.Xml.Serialization;
namespace SMSModLogOutputAnalyzer.Data
{
public partial class NotesDataObject
{
public class UserNotes
{
[XmlAttribute] public ulong Id { get; set; }
[XmlAttribute] public int Counter { get; set; } = 0;
[XmlElement("Note")] public List<Note> Notes { get; set; } = new();
}
}
}

View file

@ -0,0 +1,42 @@
using Discord;
using Orpticon.Custom;
using Orpticon.Wrappers;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Xml.Serialization;
namespace SMSModLogOutputAnalyzer.Data
{
public partial class NotesDataObject
{
[XmlElement("Notes")] public List<UserNotes> List { get; set; } = new();
[XmlIgnore] public UserNotes this[IUser user] => this[user.Id];
[XmlIgnore]
public UserNotes this[ulong id]
{
get
{
var notes = List.Find(x => x.Id == id);
if(notes == null)
{
notes = new() { Id = id };
List.Add(notes);
}
return notes;
}
}
public void Save()
{
SerializerXML.SerializeToFile(this, "NotesData.xml");
}
public static NotesDataObject Load()
{
var obj = SerializerXML.DeserializeFromFileOrDefault<NotesDataObject>("NotesData.xml");
return obj;
}
}
}

View file

@ -0,0 +1,14 @@
using System.Xml.Serialization;
namespace SMSModLogOutputAnalyzer.Data
{
public partial class RoleButtonsDataObject
{
public class RoleButton
{
[XmlAttribute] public int Id { get; set; }
[XmlAttribute] public ulong Role { get; set; }
[XmlAttribute] public ulong RequiredRole { get; set; }
}
}
}

View file

@ -0,0 +1,27 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using static SMSModLogOutputAnalyzer.Data.NotesDataObject;
using System.Xml.Serialization;
using Orpticon.Wrappers;
namespace SMSModLogOutputAnalyzer.Data
{
public partial class RoleButtonsDataObject
{
public void Save()
{
SerializerXML.SerializeToFile(this, "RoleButtons.xml");
}
public static RoleButtonsDataObject Load()
{
var obj = SerializerXML.DeserializeFromFileOrDefault<RoleButtonsDataObject>("RoleButtons.xml");
return obj;
}
[XmlElement("Button")] public List<RoleButton> List { get; set; } = new();
[XmlAttribute] public int Counter { get; set; }
public RoleButton this[int id] => List.Find(x => x.Id == id);
}
}

View file

@ -0,0 +1,42 @@
using Discord;
using Discord.Interactions;
namespace SMSModLogOutputAnalyzer.Modules
{
public class AskForLogFileModule : InteractionModuleBase
{
[MessageCommand("Ask for Log file")]
public async Task AskForLog(IMessage message)
{
string title = "Please submit Log File";
string descr = "In order to assist you further, we are going to need your `BepInEx/LogOutput.log` file.";
if (message.Channel.Id == 1220431757266915400)
{
title = "Merci d'envoyer le fichier journal";
descr = "Afin de t'aider davantage, nous allons avoir besoin de ton fichier `BepInEx/LogOutput.log`.";
}
if (message.Channel.Id == 1220476339883216977)
{
title = "Bitte schick uns deine Log-Datei.";
descr = "Um dir weiterhelfen zu können, benötigen wir deine `BepInEx/LogOutput.log` Datei.";
}
if (message.Channel.Id == 1220488093124005909)
{
title = "Envía el archivo de registro";
descr = "Para poder ayudarte mejor, vamos a necesitar tu archivo `BepInEx/LogOutput.log`.";
}
if (message.Channel.Id == 1221180784598188082)
{
title = "Prześlij plik dziennika";
descr = "Aby pomóc Ci dalej, będziemy potrzebować Twojego pliku `BepInEx/LogOutput.log`.";
}
if (message.Channel.Id == 1225150931306549330)
{
title = "Por favor, envia o ficheiro de registo";
descr = "Para te podermos ajudar mais, vamos precisar do teu ficheiro `BepInEx/LogOutput.log`.";
}
var stream = new MemoryStream(Properties.Resources.LogOutput);
await RespondWithFileAsync(new FileAttachment(stream, "LogOutput.jpg"), "<@" + message.Author.Id + ">", embed: new EmbedBuilder().WithTitle(title).WithDescription(descr).WithImageUrl("attachment://LogOutput.jpg").WithDefaults().Build());
}
}
}

View file

@ -0,0 +1,25 @@
using Discord;
using Discord.Interactions;
using SMSModLogOutputAnalyzer.Data;
namespace SMSModLogOutputAnalyzer.Modules
{
public partial class ConfigModule
{
public partial class Commands
{
[Group("set", "Setter Commands")]
public class Setters : InteractionModuleBase
{
[SlashCommand("notes_log_channel", "What channel to log note creations into.")]
[RequireUserPermission(ChannelPermission.ManageChannels)]
public async Task NotesLogChannel(ITextChannel channel)
{
Config.NotesLogChannel = channel;
Config.Save();
await RespondAsync(embed: new EmbedBuilder().WithDescription("Config value `NotesLogChannel` set to `" + channel.Id + "`.").WithDefaults().Build());
}
}
}
}
}

View file

@ -0,0 +1,12 @@
using Discord.Interactions;
namespace SMSModLogOutputAnalyzer.Modules
{
public partial class ConfigModule
{
[Group("config", "Config Commands")]
public partial class Commands : InteractionModuleBase
{
}
}
}

View file

@ -0,0 +1,14 @@
using Discord.Interactions;
using Orpticon.Wrappers;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace SMSModLogOutputAnalyzer.Modules
{
public partial class ConfigModule : InteractionModuleBase
{
}
}

View file

@ -1,6 +1,6 @@
namespace SMSModLogOutputAnalyzer
namespace SMSModLogOutputAnalyzer.Modules
{
public partial class CommandModule
public partial class LogAnalyzeModule
{
public struct FoundLine
{

View file

@ -2,9 +2,9 @@
using Discord.Interactions;
using System.Text.RegularExpressions;
namespace SMSModLogOutputAnalyzer
namespace SMSModLogOutputAnalyzer.Modules
{
public partial class CommandModule : InteractionModuleBase
public partial class LogAnalyzeModule : InteractionModuleBase
{
public static List<string> KnownMelonLoaderMods = new List<string>
{
@ -35,39 +35,6 @@ namespace SMSModLogOutputAnalyzer
{
Console.WriteLine("Building module");
}
[MessageCommand("Ask for Log file")]
public async Task AskForLog(IMessage message)
{
string title = "Please submit Log File";
string descr = "In order to assist you further, we are going to need your `BepInEx/LogOutput.log` file.";
if(message.Channel.Id == 1220431757266915400)
{
title = "Merci d'envoyer le fichier journal";
descr = "Afin de t'aider davantage, nous allons avoir besoin de ton fichier `BepInEx/LogOutput.log`.";
}
if(message.Channel.Id == 1220476339883216977)
{
title = "Bitte schick uns deine Log-Datei.";
descr = "Um dir weiterhelfen zu können, benötigen wir deine `BepInEx/LogOutput.log` Datei.";
}
if (message.Channel.Id == 1220488093124005909)
{
title = "Envía el archivo de registro";
descr = "Para poder ayudarte mejor, vamos a necesitar tu archivo `BepInEx/LogOutput.log`.";
}
if (message.Channel.Id == 1221180784598188082)
{
title = "Prześlij plik dziennika";
descr = "Aby pomóc Ci dalej, będziemy potrzebować Twojego pliku `BepInEx/LogOutput.log`.";
}
if (message.Channel.Id == 1225150931306549330)
{
title = "Por favor, envia o ficheiro de registo";
descr = "Para te podermos ajudar mais, vamos precisar do teu ficheiro `BepInEx/LogOutput.log`.";
}
var stream = new MemoryStream(Properties.Resources.LogOutput);
await RespondWithFileAsync(new FileAttachment(stream, "LogOutput.jpg"), "<@" + message.Author.Id + ">", embed: new EmbedBuilder().WithTitle(title).WithDescription(descr).WithImageUrl("attachment://LogOutput.jpg").Build());
}
[MessageCommand("Analyze Log")]
public async Task Analyze(IMessage message)
{
@ -76,7 +43,7 @@ namespace SMSModLogOutputAnalyzer
await Upload((Attachment)message.Attachments.First());
} else
{
await RespondAsync("Message has no attachment.", ephemeral: true);
await RespondAsync(embed: new EmbedBuilder().WithDescription("Message has no attachment.").WithDefaults().Build(), ephemeral: true);
}
}
[SlashCommand("upload", "Upload a LogOutput.log file for analysis.")]
@ -89,7 +56,7 @@ namespace SMSModLogOutputAnalyzer
var text = await http.GetStringAsync(file.Url);
if(Program.AnalysisCache.ContainsKey(text))
{
await RespondAsync(ephemeral: true, text: "This log file has already been analysed [here](" + Program.AnalysisCache[text].GetJumpUrl() + ").");
await RespondAsync(ephemeral: true, embed: new EmbedBuilder().WithDescription("This log file has already been analysed [here](" + Program.AnalysisCache[text].GetJumpUrl() + ").").WithDefaults().Build());
return;
}
await DeferAsync();
@ -97,7 +64,6 @@ namespace SMSModLogOutputAnalyzer
var textLines = text.Split('\n').Select(x => x.Trim()).ToArray();
var embedBuilder = new EmbedBuilder();
embedBuilder.WithAuthor(Context.User);
embedBuilder.WithFooter(Program.Footer);
Dictionary<string, List<string>> values = new();
var lines = FindLines(textLines,
@ -209,7 +175,7 @@ namespace SMSModLogOutputAnalyzer
foreach (var field in fields) Log(field.Name + ", " + field.Value);
embedBuilder.WithFields(fields);
embedBuilder.WithColor(Color.DarkBlue);
embedBuilder.WithDefaults();
var embed = embedBuilder.Build();
var message = await ModifyOriginalResponseAsync(func => { func.Embeds = new[] { embed }; func.Components = downloadButton.Build(); });
Program.AnalysisCache.Add(text, message);
@ -236,33 +202,5 @@ namespace SMSModLogOutputAnalyzer
}
return results;
}
[SlashCommand("troubleshoot", "Starts the troubleshooting assistant.")]
[RequireUserPermission(GuildPermission.ManageChannels)]
public async Task Troubleshoot()
{
await RespondAsync("Posting", ephemeral: true);
await Context.Channel.SendMessageAsync(embed: new EmbedBuilder()
.WithTitle("Troubleshooting Assistant")
.WithDescription("Press the button below to be guided through our troubleshooting assistant. Hopefully it can help you with getting mods working.")
.WithFooter(Program.Footer)
.Build(),
components: new ComponentBuilder()
.WithButton("Start", "troubleshoot:root", ButtonStyle.Success)
.Build());
}
[ComponentInteraction("troubleshoot:*")]
public async Task TroubleshootButton(string node)
{
Flowchart.FlowchartNode fcnode = Program.Troubleshooting.Nodes.Find(x => x.Name == node);
if (fcnode == null) return;
var connections = Program.Troubleshooting.Connections.Where(x => x.FromName == node);
var cmpb = new ComponentBuilder();
foreach (var conn in connections) cmpb.WithButton(conn.Text, "troubleshoot:" + conn.ToName, conn.Text == "Yes" ? ButtonStyle.Success : conn.Text == "No" ? ButtonStyle.Danger : ButtonStyle.Primary);
await RespondAsync(embed: new EmbedBuilder()
.WithTitle(fcnode.Text)
.WithDescription(fcnode.Description)
.WithFooter(Program.Footer)
.Build(), components: cmpb.Build(), ephemeral: true);
}
}
}

View file

@ -0,0 +1,23 @@
using Discord;
using Discord.Interactions;
namespace SMSModLogOutputAnalyzer.Modules
{
public partial class NotesModule
{
public partial class Commands
{
/// <summary>
/// Currently unused because I can't figure out how to get modals to work
/// </summary>
public class AddNoteModal : IModal
{
public string Title => "Add Note";
[RequiredInput(true)]
[InputLabel("Note Text")]
[ModalTextInput("note_text", TextInputStyle.Paragraph, "stinky")]
public string Note { get; set; }
}
}
}
}

View file

@ -0,0 +1,108 @@
using Discord;
using Discord.Interactions;
using SMSModLogOutputAnalyzer.Data;
namespace SMSModLogOutputAnalyzer.Modules
{
public partial class NotesModule
{
[Group("notes", "Various commands related to notes.")]
public partial class Commands : InteractionModuleBase
{
[SlashCommand("view", "View notes that have been added to a user.")]
[RequireUserPermission(GuildPermission.ManageRoles)]
public async Task View(IUser user, [Summary(description: "How many notes to skip (used for pagination)")] int offset = 0)
{
EmbedBuilder embedBuilder = new EmbedBuilder();
var notes = Data[user].Notes.Skip(offset).Take(25).ToArray();
bool addNextPageButton = Data[user].Notes.Count > offset + 25;
if (notes.Length == 0)
{
await RespondAsync(embed: new EmbedBuilder().WithDefaults().WithDescription("No " + (offset > 0 ? "more " : "") + "notes have been added to this user.").Build(), ephemeral: true);
return;
}
embedBuilder.WithAuthor(user);
embedBuilder.WithDefaults();
foreach (var note in notes)
{
embedBuilder.AddField(note.ToField());
}
var embed = embedBuilder.Build();
var button = new ComponentBuilder().WithButton("Next Page", "view_notes:" + user.Id + ":" + (offset + 25)).Build();
if (addNextPageButton)
{
await RespondAsync(embed: embed, components: button, ephemeral: true);
}
else
{
await RespondAsync(embed: embed, ephemeral: true);
}
}
[SlashCommand("add", "Add a note to a user.")]
[RequireUserPermission(GuildPermission.ManageRoles)]
public async Task Add(IUser user, [Summary("note")] string text)
{
if (string.IsNullOrEmpty(text))
{
Console.WriteLine("Sending modal");
await Context.Interaction.RespondWithModalAsync<AddNoteModal>("add_note:" + user.Id);
return;
}
NotesDataObject.Note note = new();
note.Text = text;
note.CreatorID = Context.User.Id;
note.CreationTime = DateTime.Now;
note.Id = ++Data[user].Counter;
Data[user].Notes.Add(note);
Data.Save();
string error = "";
var field = note.ToField();
try
{
await Config.NotesLogChannel.SendMessageAsync(embed: new EmbedBuilder().WithDefaults().WithAuthor(user.Username + " - New Note", user.GetDisplayAvatarUrl()).WithTitle(field.Name).WithDescription((string)field.Value).Build());
} catch (Exception e)
{
error = "\n\n:x: Logging failed";
}
await RespondAsync(embed: new EmbedBuilder().WithDescription("Note **" + note.Id + "** added." + error).WithDefaults().Build(), ephemeral: true);
}
[SlashCommand("remove", "Removes a note from a user.")]
[RequireUserPermission(GuildPermission.ManageRoles)]
public async Task Remove(IUser user, int note_id)
{
int num = Data[user].Notes.RemoveAll(x => x.Id == note_id);
Data.Save();
if (num > 0) await RespondAsync(embed: new EmbedBuilder().WithDescription("Note **" + note_id + "** removed.").WithDefaults().Build(), ephemeral: true);
else await RespondAsync(embed: new EmbedBuilder().WithDescription("Note **" + note_id + "** was not found.").WithDefaults().Build(), ephemeral: true);
}
[SlashCommand("clear", "Removes all notes from a user.")]
[RequireUserPermission(GuildPermission.ManageRoles)]
public async Task Clear(IUser user)
{
int num = Data[user].Notes.RemoveAll(x => true);
Data.Save();
await RespondAsync(embed: new EmbedBuilder().WithDescription("**" + num + "** notes were removed.").WithDefaults().Build(), ephemeral: true);
}
[ModalInteraction("add_note:*", true)]
[RequireUserPermission(ChannelPermission.ManageRoles)]
public async Task AddModal(AddNoteModal modal, string user) => await Add(await Context.Client.GetUserAsync(ulong.Parse(user)), modal.Note);
[ComponentInteraction("view_notes:*:*", true)]
[RequireUserPermission(ChannelPermission.ManageRoles)]
public async Task ViewButton(string user, string offset) => await View(await Context.Client.GetUserAsync(ulong.Parse(user)), int.Parse(offset));
[MessageCommand("View Notes")]
[RequireUserPermission(ChannelPermission.ManageRoles)]
public async Task UserView(IMessage message) => await View(message.Author);
}
}
}

View file

@ -0,0 +1,15 @@
using Discord.Interactions;
using SMSModLogOutputAnalyzer.Data;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace SMSModLogOutputAnalyzer.Modules
{
public partial class NotesModule : InteractionModuleBase
{
public static NotesDataObject Data { get; set; }
}
}

View file

@ -0,0 +1,131 @@
using Discord;
using Discord.Interactions;
using Discord.WebSocket;
using System.Drawing;
using System.Globalization;
using static SMSModLogOutputAnalyzer.Data.RoleButtonsDataObject;
namespace SMSModLogOutputAnalyzer.Modules
{
public partial class RoleButtonModule
{
[Group("role", "Role Button Commands")]
public class Commands : InteractionModuleBase
{
[Group("button", "Role Button Commands")]
public class Subcommands : InteractionModuleBase
{
[SlashCommand("create", "Creates a new role button.")]
[RequireUserPermission(ChannelPermission.ManageRoles)]
public async Task Create([Summary(description: "What role the button should give")] IRole role,
[Summary(description: "What title the embed should have")] string title,
[Summary(description: "What description the embed should have")] string description,
[Summary(description: "What text the button should have")] string button_text,
[Summary(description: "What emote the button should have")] string button_emote = "",
[Summary(description: "What style the button should have")] ButtonStyle style = ButtonStyle.Primary,
[Summary(description: "What role should the user already need to have")] IRole required_role = null,
[Summary(description: "Embed color (hex code)")] string embed_color = "206694")
{
try
{
RoleButton button = new RoleButton();
button.Id = Data.Counter++;
button.Role = role.Id;
if (required_role != null) button.RequiredRole = required_role.Id;
Data.List.Add(button);
Data.Save();
EmbedBuilder embedBuilder = new EmbedBuilder();
embedBuilder.WithTitle(title);
embedBuilder.WithDescription(description);
embedBuilder.WithColor(Program.ConvertColor(embed_color));
ComponentBuilder componentBuilder = new ComponentBuilder();
var buttonBuilder = new ButtonBuilder().WithLabel(button_text).WithStyle(style).WithCustomId("role_button:" + button.Id);
if (Emote.TryParse(button_emote, out Emote emote))
{
buttonBuilder.WithEmote(emote);
}
if (Emoji.TryParse(button_emote, out Emoji emote2))
{
buttonBuilder.WithEmote(emote2);
}
componentBuilder.WithButton(buttonBuilder);
try
{
await Context.Channel.SendMessageAsync(embed: embedBuilder.Build(), components: componentBuilder.Build());
}
catch (Exception e)
{
Console.WriteLine(e);
await RespondAsync(embed: new EmbedBuilder().WithDefaults().WithDescription(":x: Message Sending failed. Ensure the bot has sufficient permissions to send in this channel.").Build(), ephemeral: true);
return;
}
await RespondAsync(embed: new EmbedBuilder().WithDefaults().WithDescription(":white_check_mark: Role Button Created").Build(), ephemeral: true);
}
catch (Exception e)
{
Console.WriteLine(e);
}
}
[ComponentInteraction("role_button:*", true)]
public async Task RoleButton(string id)
{
var button = Data[int.Parse(id)];
if (Context.User is SocketGuildUser user)
{
if (user.Roles.Any(x => x.Id == button.Role))
{
await RemoveRole(button.Role);
}
else
{
if (button.RequiredRole == 0)
{
await AddRole(button.Role);
}
else
{
if (user.Roles.Any(x => x.Id == button.RequiredRole))
{
await AddRole(button.Role);
}
else
{
await RespondAsync(embed: new EmbedBuilder().WithDefaults().WithDescription("You need the role <@&" + button.RequiredRole + "> to be allowed to get this role.").Build(), ephemeral: true);
}
}
}
}
}
private async Task AddRole(ulong role)
{
try
{
if (Context.User is SocketGuildUser user)
{
await user.AddRoleAsync(role);
await RespondAsync(embed: new EmbedBuilder().WithDefaults().WithDescription(":white_check_mark: Role Added: <@&" + role + ">").Build(), ephemeral: true);
}
} catch (Exception e)
{
Console.WriteLine(e);
}
}
private async Task RemoveRole(ulong role)
{
if (Context.User is SocketGuildUser user)
{
await user.RemoveRoleAsync(role);
await RespondAsync(embed: new EmbedBuilder().WithDefaults().WithDescription(":x: Role Removed: <@&" + role + ">").Build(), ephemeral: true);
}
}
}
}
}
}

View file

@ -0,0 +1,15 @@
using Discord.Interactions;
using SMSModLogOutputAnalyzer.Data;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace SMSModLogOutputAnalyzer.Modules
{
public partial class RoleButtonModule : InteractionModuleBase
{
public static RoleButtonsDataObject Data { get; set; }
}
}

View file

@ -0,0 +1,37 @@
using Discord;
using Discord.Interactions;
namespace SMSModLogOutputAnalyzer.Modules
{
public class TroubleshootingModule : InteractionModuleBase
{
[SlashCommand("troubleshoot", "Starts the troubleshooting assistant.")]
[RequireUserPermission(GuildPermission.ManageChannels)]
public async Task Troubleshoot()
{
await RespondAsync("Posting", ephemeral: true);
await Context.Channel.SendMessageAsync(embed: new EmbedBuilder()
.WithTitle("Troubleshooting Assistant")
.WithDescription("Press the button below to be guided through our troubleshooting assistant. Hopefully it can help you with getting mods working.")
.WithFooter(Program.Footer)
.Build(),
components: new ComponentBuilder()
.WithButton("Start", "troubleshoot:root", ButtonStyle.Success)
.Build());
}
[ComponentInteraction("troubleshoot:*")]
public async Task TroubleshootButton(string node)
{
Flowchart.FlowchartNode fcnode = Program.Troubleshooting.Nodes.Find(x => x.Name == node);
if (fcnode == null) return;
var connections = Program.Troubleshooting.Connections.Where(x => x.FromName == node);
var cmpb = new ComponentBuilder();
foreach (var conn in connections) cmpb.WithButton(conn.Text, "troubleshoot:" + conn.ToName, conn.Text == "Yes" ? ButtonStyle.Success : conn.Text == "No" ? ButtonStyle.Danger : ButtonStyle.Primary);
await RespondAsync(embed: new EmbedBuilder()
.WithTitle(fcnode.Text)
.WithDescription(fcnode.Description)
.WithFooter(Program.Footer)
.Build(), components: cmpb.Build(), ephemeral: true);
}
}
}

View file

@ -1,37 +1,60 @@
using Discord.WebSocket;
using Discord;
using Discord.Interactions;
using System.Reflection;
using System;
using SMSModLogOutputAnalyzer.Modules;
using SMSModLogOutputAnalyzer.Data;
using SMSModLogOutputAnalyzer.Modules;
using System.Globalization;
namespace SMSModLogOutputAnalyzer
{
internal static class Program
{
private static DiscordSocketClient _client;
public static DiscordSocketClient Client;
public static Flowchart Troubleshooting;
public const string Footer = "SMS Mods Bot • Made by BratPfanneTV, for Modded Supermarket Simulator (Unofficial)";
public static Color Color = Color.DarkBlue;
public static Dictionary<string, IMessage> AnalysisCache = new();
public static EmbedBuilder WithDefaults(this EmbedBuilder builder)
{
return builder.WithFooter(Footer).WithColor(Color);
}
public static Color ConvertColor(string hex)
{
string colorcode = hex;
colorcode = colorcode.TrimStart('#');
return new Color(
int.Parse(colorcode.Substring(0, 2), NumberStyles.HexNumber),
int.Parse(colorcode.Substring(2, 2), NumberStyles.HexNumber),
int.Parse(colorcode.Substring(4, 2), NumberStyles.HexNumber));
}
public static bool TryParseEmote(string str, out IEmote iemote)
{
if (Emote.TryParse(str, out Emote emote)) iemote = emote;
else if (Emoji.TryParse(str, out Emoji emoji)) iemote = emoji;
else iemote = null;
return iemote != null;
}
public static async Task Main()
{
Troubleshooting = Flowchart.Parse(Properties.Resources.Flowchart);
_client = new DiscordSocketClient(new DiscordSocketConfig { LogLevel = LogSeverity.Debug });
Client = new DiscordSocketClient(new DiscordSocketConfig { LogLevel = LogSeverity.Debug });
_client.Log += Log;
Client.Log += Log;
// You can assign your bot token to a string, and pass that in to connect.
// This is, however, insecure, particularly if you plan to have your code hosted in a public repository.
var token = File.ReadAllText("token.txt");
_client.Ready += _client_Ready;
Client.Ready += _client_Ready;
// Some alternative options would be to keep your token in an Environment Variable or a standalone file.
// var token = Environment.GetEnvironmentVariable("NameOfYourEnvironmentVariable");
// var token = File.ReadAllText("token.txt");
// var token = JsonConvert.DeserializeObject<AConfigurationClass>(File.ReadAllText("config.json")).Token;
await _client.LoginAsync(TokenType.Bot, token);
await _client.StartAsync();
await Client.LoginAsync(TokenType.Bot, token);
await Client.StartAsync();
// Block this task until the program is closed.
await Task.Delay(-1);
@ -39,14 +62,22 @@ namespace SMSModLogOutputAnalyzer
private static async Task _client_Ready()
{
var server = (ulong)652484929950842881;
var _interactionService = new InteractionService(_client.Rest);
var module = await _interactionService.AddModuleAsync<CommandModule>(null);
await _interactionService.AddModulesGloballyAsync(true, module);
NotesModule.Data = NotesDataObject.Load();
RoleButtonModule.Data = RoleButtonsDataObject.Load();
Config.Load();
_client.InteractionCreated += async (x) =>
var _interactionService = new InteractionService(Client.Rest);
await _interactionService.AddModulesGloballyAsync(true,
await _interactionService.AddModuleAsync<AskForLogFileModule>(null),
await _interactionService.AddModuleAsync<ConfigModule>(null),
await _interactionService.AddModuleAsync<RoleButtonModule>(null),
await _interactionService.AddModuleAsync<LogAnalyzeModule>(null),
await _interactionService.AddModuleAsync<NotesModule>(null),
await _interactionService.AddModuleAsync<TroubleshootingModule>(null));
Client.InteractionCreated += async (x) =>
{
var ctx = new SocketInteractionContext(_client, x);
var ctx = new SocketInteractionContext(Client, x);
await _interactionService.ExecuteCommandAsync(ctx, null);
};
}

View file

@ -7,10 +7,22 @@
<Nullable>enable</Nullable>
</PropertyGroup>
<ItemGroup>
<Compile Remove="Modules\NewFolder\**" />
<EmbeddedResource Remove="Modules\NewFolder\**" />
<None Remove="Modules\NewFolder\**" />
</ItemGroup>
<ItemGroup>
<PackageReference Include="Discord.Net" Version="3.14.1" />
</ItemGroup>
<ItemGroup>
<Reference Include="Orpticon">
<HintPath>..\..\OrpticonDLL\bin\Debug\Orpticon.dll</HintPath>
</Reference>
</ItemGroup>
<ItemGroup>
<Compile Update="Properties\Resources.Designer.cs">
<DesignTime>True</DesignTime>