using System; using System.Collections.Generic; using System.Collections.Immutable; using System.Text.RegularExpressions; using ChaosBot.Repositories; using Microsoft.Extensions.Configuration; namespace ChaosBot { public class Configuration { private readonly IConfiguration _appSettingsWrapper; private static readonly Dictionary ConfigurationFlags = new Dictionary { {"Bot:Name", typeof(string)}, {"Bot:Version", typeof(string)}, {"WebServer:Port", typeof(int)}, {"WebServer:Debug", typeof(bool)}, {"Discord:Prefix", typeof(string)}, {"Discord:Token", typeof(string)}, {"Discord:BaseUri", typeof(string)}, {"Discord:ClientId", typeof(string)}, {"Discord:ClientSecret", typeof(string)}, {"Lodestone:ChaosBotApi:ApiToken", typeof(string)}, {"Lodestone:ChaosBotApi:Url", typeof(string)}, {"Database:Host", typeof(string)}, {"Database:Port", typeof(int)}, {"Database:User", typeof(string)}, {"Database:Pass", typeof(string)}, {"Database:Name", typeof(string)}, }; public Configuration() { _appSettingsWrapper = Program.AppSettingsHandler; if (_appSettingsWrapper == null) throw new NullReferenceException("Program.AppSettingsHandler is unset"); } /** * Gets the configuration value associated with a key in an optional guild * Configuration key does not exist * Configuration key does not have the provided type * Configuration value */ public T GetValue(string key, T defaultValue, ulong? guildId = null) { bool keyExists = TryGetKeyFromRegexMatch(key, out string realKey); if (!keyExists) throw new ArgumentException($"Configuration does not contain key '{key}'"); if (!(ConfigurationFlags[realKey] == typeof(T))) throw new ArgumentException($"Configuration flag '{realKey}<{ConfigurationFlags[realKey]}>' does not have type '{typeof(T)}'"); if (guildId.HasValue) return ConfigurationRepository.GetValue(realKey, guildId.Value, defaultValue); return _appSettingsWrapper.GetValue(realKey, defaultValue); } public T GetValue(string key) { return GetValue(key, default); } public IConfigurationSection GetSection(string key) { return _appSettingsWrapper.GetSection(key); } /** * Get the available configuration flags * Immutable dictionary of config-key/type pairs */ public ImmutableDictionary GetConfigurationFlags() { return ConfigurationFlags.ToImmutableDictionary(); } private bool TryGetKeyFromRegexMatch(string key, out string realKey) { if (ConfigurationFlags.ContainsKey(key)) { realKey = key; return true; } foreach (string configurationFlagsKey in ConfigurationFlags.Keys) { if (new Regex(configurationFlagsKey).IsMatch(key)) { realKey = key; return true; } } realKey = null; return false; } } }