Utopia-Canteen-System/Services/ClientConfigService.cs

182 lines
7.3 KiB
C#

using System.IO;
using System.Text.Json;
using UtopiaCanteenSystem.Data;
using UtopiaCanteenSystem.Models;
namespace UtopiaCanteenSystem.Services;
/// <summary>
/// Scanner frontend configuration: backend URL, device/site, admin UI. No HRMS/production credentials.
/// </summary>
public sealed class ClientConfigService : IConfigService
{
private readonly string _configPath;
private ClientAppConfig _config;
public ClientConfigService()
{
DatabasePath.UseClientStorage();
_configPath = DatabasePath.GetConfigPath();
_config = LoadConfig();
}
public string GetSyncApiEndpoint() => string.Empty;
public void SetSyncApiEndpoint(string endpoint) { }
public bool GetSyncServiceEnabled() => false;
public void SetSyncServiceEnabled(bool enabled) { }
public bool GetScannerConnected() => _config.ScannerConnected;
public void SetScannerConnected(bool connected)
{
_config.ScannerConnected = connected;
SaveConfig();
}
public int GetScanIntervalDays() => Math.Clamp(_config.ScanIntervalDays, 0, 365);
public void SetScanIntervalDays(int value) { _config.ScanIntervalDays = Math.Clamp(value, 0, 365); SaveConfig(); }
public int GetScanIntervalHours() => Math.Clamp(_config.ScanIntervalHours, 0, 23);
public void SetScanIntervalHours(int value) { _config.ScanIntervalHours = Math.Clamp(value, 0, 23); SaveConfig(); }
public int GetScanIntervalMinutes() => Math.Clamp(_config.ScanIntervalMinutes, 0, 59);
public void SetScanIntervalMinutes(int value) { _config.ScanIntervalMinutes = Math.Clamp(value, 0, 59); SaveConfig(); }
public int GetScanIntervalSeconds() => Math.Clamp(_config.ScanIntervalSeconds, 0, 59);
public void SetScanIntervalSeconds(int value) { _config.ScanIntervalSeconds = Math.Clamp(value, 0, 59); SaveConfig(); }
public TimeSpan GetScanInterval()
{
var ts = TimeSpan.FromDays(GetScanIntervalDays()) + TimeSpan.FromHours(GetScanIntervalHours())
+ TimeSpan.FromMinutes(GetScanIntervalMinutes()) + TimeSpan.FromSeconds(GetScanIntervalSeconds());
return ts > TimeSpan.Zero ? ts : TimeSpan.FromMinutes(1);
}
public string GetAdminCardId() => _config.AdminCardId ?? "ADMIN";
public void SetAdminCardId(string cardId) { _config.AdminCardId = cardId ?? string.Empty; SaveConfig(); }
public string GetSiteId() => _config.SiteId ?? string.Empty;
public void SetSiteId(string siteId) { _config.SiteId = siteId ?? string.Empty; SaveConfig(); }
public void ApplyLocationSiteIdFromAuth(string? locationSiteId)
{
if (string.IsNullOrWhiteSpace(locationSiteId))
return;
var digits = new string(locationSiteId.Where(char.IsDigit).ToArray());
if (string.IsNullOrEmpty(digits))
return;
_config.SiteId = $"SITE : {digits}";
SaveConfig();
}
public string GetDeviceId() => _config.DeviceId ?? string.Empty;
public void SetDeviceId(string deviceId) { _config.DeviceId = deviceId ?? string.Empty; SaveConfig(); }
public bool GetRememberAdminCredentials() => _config.RememberAdminCredentials;
public void SetRememberAdminCredentials(bool remember) { _config.RememberAdminCredentials = remember; SaveConfig(); }
public string GetSavedAdminUsername() => _config.SavedAdminUsername ?? string.Empty;
public void SetSavedAdminUsername(string username) { _config.SavedAdminUsername = username ?? string.Empty; SaveConfig(); }
public string GetSavedAdminPassword() => DecryptPassword(_config.SavedAdminPasswordProtected ?? string.Empty);
public void SetSavedAdminPassword(string password) { _config.SavedAdminPasswordProtected = EncryptPassword(password ?? string.Empty); SaveConfig(); }
public string GetMySqlConnectionString() => string.Empty;
public void SetMySqlConnectionString(string connectionString) { }
public string GetHrmsLookupConnectionString() => string.Empty;
public void SetHrmsLookupConnectionString(string connectionString) { }
public DateTime? GetLastEmployeeRfidCacheSyncUtc() => null;
public void SetLastEmployeeRfidCacheSyncUtc(DateTime utc) { }
public DateTime? GetLastMealMenuCacheSyncUtc() => null;
public void SetLastMealMenuCacheSyncUtc(DateTime utc) { }
public AppMode GetAppMode() => AppMode.Client;
public void SetAppMode(AppMode mode) { }
public string GetCentralServerBaseUrl() => GetBackendBaseUrl();
public void SetCentralServerBaseUrl(string url) => SetBackendBaseUrl(url);
public string GetBackendBaseUrl() => (_config.BackendBaseUrl ?? string.Empty).TrimEnd('/');
public void SetBackendBaseUrl(string url)
{
_config.BackendBaseUrl = (url ?? string.Empty).Trim().TrimEnd('/');
SaveConfig();
}
public string GetLocalServerListenUrls() => string.Empty;
public void SetLocalServerListenUrls(string urls) { }
private ClientAppConfig LoadConfig()
{
try
{
if (!File.Exists(_configPath))
return new ClientAppConfig { BackendBaseUrl = "http://localhost:5000" };
var json = File.ReadAllText(_configPath);
return JsonSerializer.Deserialize<ClientAppConfig>(json) ?? new ClientAppConfig();
}
catch
{
return new ClientAppConfig();
}
}
private void SaveConfig()
{
try
{
var json = JsonSerializer.Serialize(_config, new JsonSerializerOptions { WriteIndented = true });
File.WriteAllText(_configPath, json);
}
catch (Exception ex)
{
Logger.Log(ex, "ClientConfigService.SaveConfig");
}
}
private static string EncryptPassword(string plain)
{
if (string.IsNullOrEmpty(plain)) return string.Empty;
try
{
var bytes = System.Text.Encoding.UTF8.GetBytes(plain);
var protectedBytes = System.Security.Cryptography.ProtectedData.Protect(bytes, null, System.Security.Cryptography.DataProtectionScope.CurrentUser);
return Convert.ToBase64String(protectedBytes);
}
catch
{
return string.Empty;
}
}
private static string DecryptPassword(string protectedBase64)
{
if (string.IsNullOrEmpty(protectedBase64)) return string.Empty;
try
{
var protectedBytes = Convert.FromBase64String(protectedBase64);
var bytes = System.Security.Cryptography.ProtectedData.Unprotect(protectedBytes, null, System.Security.Cryptography.DataProtectionScope.CurrentUser);
return System.Text.Encoding.UTF8.GetString(bytes);
}
catch
{
return string.Empty;
}
}
private sealed class ClientAppConfig
{
public string? BackendBaseUrl { get; set; }
public bool ScannerConnected { get; set; }
public int ScanIntervalDays { get; set; }
public int ScanIntervalHours { get; set; }
public int ScanIntervalMinutes { get; set; }
public int ScanIntervalSeconds { get; set; } = 5;
public string? AdminCardId { get; set; }
public string? SiteId { get; set; }
public string? DeviceId { get; set; }
public bool RememberAdminCredentials { get; set; }
public string? SavedAdminUsername { get; set; }
public string? SavedAdminPasswordProtected { get; set; }
}
}