diff --git a/DiscordBotCore.PluginManagement.Loading/PluginLoader.cs b/DiscordBotCore.PluginManagement.Loading/PluginLoader.cs index 76e80d0..5ce855d 100644 --- a/DiscordBotCore.PluginManagement.Loading/PluginLoader.cs +++ b/DiscordBotCore.PluginManagement.Loading/PluginLoader.cs @@ -38,9 +38,9 @@ public class PluginLoader : IPluginLoader public void SetDiscordClient(DiscordSocketClient discordSocketClient) { - if (_DiscordClient is not null) + if (_DiscordClient is not null && discordSocketClient == _DiscordClient) { - _Logger.Log("A client is already set. Please set the client only once.", this, LogType.Error); + _Logger.Log("A client is already set. Please set the client only once.", this, LogType.Warning); return; } diff --git a/WebUI/Components/Pages/Home.razor b/WebUI/Components/Pages/Home.razor index 9001e0b..58c37b6 100644 --- a/WebUI/Components/Pages/Home.razor +++ b/WebUI/Components/Pages/Home.razor @@ -1,7 +1,122 @@ @page "/" +@using DiscordBotCore.Bot +@using DiscordBotCore.PluginManagement.Loading +@inject IDiscordBotApplication DiscordBotApplication +@inject IPluginLoader PluginLoader +@inject DiscordBotCore.Logging.ILogger Logger +@inject IJSRuntime JS +@rendermode InteractiveServer +

Console Log Viewer

-Home +
+
+
+

Console Log

+
+ @foreach (var line in Logs) + { +
@line
+ } +
+
-

Hello, world!

+
+

Controls

+ + + +
+
+
-Welcome to your new app. + + + +@code { + private bool IsRunning { get; set; } + private List Logs { get; set; } = new(); + private Timer? _logTimer; + private int _lastLogCount = 0; + private readonly object _logLock = new(); + + protected override void OnInitialized() + { + IsRunning = DiscordBotApplication.IsReady; + + _logTimer = new Timer(async _ => await RefreshLogsAsync(), null, 0, 2000); + } + + private async Task StartApplication() + { + if (!DiscordBotApplication.IsReady) + { + await DiscordBotApplication.StartAsync(); + Logger.Log("Application started", this); + } + IsRunning = DiscordBotApplication.IsReady; + } + + private async Task StopApplication() + { + if (DiscordBotApplication.IsReady) + { + await DiscordBotApplication.StopAsync(); + Logger.Log("Application stopped", this); + } + IsRunning = DiscordBotApplication.IsReady; + } + + private async Task LoadPlugins() + { + Logger.Log("Loading plugins", this); + await PluginLoader.LoadPlugins(); + Logger.Log("Plugins loaded", this); + } + + private string GetLogStyle(string line) + { + if (line.Contains("[Error]")) return "color: #ff4d4d;"; + if (line.Contains("[Warning]")) return "color: #ffa500;"; + if (line.Contains("[Debug]")) return "color: #88f;"; + return ""; + } + + private async Task RefreshLogsAsync() + { + try + { + var logText = Logger.GetLogsHistory(); + var newLogs = logText.Split(Environment.NewLine, StringSplitOptions.RemoveEmptyEntries); + + if (newLogs.Length != _lastLogCount) + { + lock (_logLock) + { + Logs = newLogs.ToList(); + _lastLogCount = newLogs.Length; + } + await InvokeAsync(async () => + { + StateHasChanged(); + await JS.InvokeVoidAsync("scrollToBottom", "consoleLog"); + }); + } + } + catch (Exception ex) + { + + } + } + + public void Dispose() + { + _logTimer?.Dispose(); + } +} diff --git a/WebUI/Components/Pages/Settings.razor b/WebUI/Components/Pages/Settings.razor new file mode 100644 index 0000000..f23f08a --- /dev/null +++ b/WebUI/Components/Pages/Settings.razor @@ -0,0 +1,115 @@ +@page "/settings" +@using System.ComponentModel.DataAnnotations +@using DiscordBotCore.Configuration +@using DiscordBotCore.Logging + +@inject NavigationManager Navigation + +@rendermode InteractiveServer + +@if (_settingsViewModel is not null) +{ + + + + +
+ + +
+ +
+ + +
+ +
+ + +
+ + +
+} +@code { + [Inject] + public ILogger Logger { get; set; } + + [Inject] + public IConfiguration Configuration { get; set; } + + private SettingsViewModel? _settingsViewModel; + + protected override void OnInitialized() + { + var token = Configuration.Get("token"); + var prefix = Configuration.Get("prefix"); + var serverIds = Configuration.GetList("ServerIds", new List()); + if(token == null || prefix == null) + { + Logger.Log("Token or Prefix is not set in the configuration.", this); + _settingsViewModel = new SettingsViewModel + { + Token = "", + Prefix = "", + ServerIds = "" + }; + + return; + } + + + _settingsViewModel = new SettingsViewModel + { + Token = token, + Prefix = prefix, + ServerIds = string.Join(",", serverIds) + }; + + StateHasChanged(); + } + + private async Task HandleSubmitTask() + { + if (_settingsViewModel is null) + { + return; + } + + var token = _settingsViewModel.Token; + var prefix = _settingsViewModel.Prefix; + var serverIds = _settingsViewModel.ServerIds + .Split(new[] { ',' }, StringSplitOptions.RemoveEmptyEntries) + .Select(id => ulong.TryParse(id.Trim(), out var result) ? result : 0) + .Where(id => id != 0) + .ToList(); + + if (string.IsNullOrWhiteSpace(token) || string.IsNullOrWhiteSpace(prefix)) + { + return; + } + + Configuration.Set("token", token); + Configuration.Set("prefix", prefix); + Configuration.Set("ServerIds", serverIds); + + await Configuration.SaveToFile(); + Logger.Log("Settings saved successfully.", this); + + Navigation.NavigateTo($"/"); + } + + + private class SettingsViewModel + { + [Required(ErrorMessage = "Token is required.")] + public string Token { get; set; } + + [Required(ErrorMessage = "Prefix is required.")] + public string Prefix { get; set; } + + [Required(ErrorMessage = "Server IDs are required.")] + public string ServerIds { get; set; } + } + +} \ No newline at end of file