From b419fe7679d1cebdca4c2253f57f3fe150730fa0 Mon Sep 17 00:00:00 2001 From: Timerix Date: Sun, 20 Sep 2026 21:08:19 +0200 Subject: [PATCH] replaced dtsod with json --- ParadoxSaveParser.CLI/Program.cs | 130 +++++++++++++++------------- ParadoxSaveParser.WebAPI/Config.cs | 38 ++++---- ParadoxSaveParser.WebAPI/Program.cs | 35 +++++--- 3 files changed, 113 insertions(+), 90 deletions(-) diff --git a/ParadoxSaveParser.CLI/Program.cs b/ParadoxSaveParser.CLI/Program.cs index d990211..61bd99b 100644 --- a/ParadoxSaveParser.CLI/Program.cs +++ b/ParadoxSaveParser.CLI/Program.cs @@ -4,67 +4,77 @@ global using DTLib.Demystifier; global using DTLib.Filesystem; global using Directory = DTLib.Filesystem.Directory; global using File = DTLib.Filesystem.File; -using ParadoxSaveParser.CLI; -try +namespace ParadoxSaveParser.CLI; + +internal class Program { - Mode mode = Mode.Unset; - IOPath? inputPath = null; - IOPath? outputPath = null; - string? searchQuery = null; - - new LaunchArgumentParser( - new LaunchArgument(["i", "input"], - "Set input file path", - s => inputPath = s, - "gamestate or zip file"), - - new LaunchArgument(["o", "output"], - "Set output file path", - s => outputPath = s, - "json file [default=stdout]"), - - new LaunchArgument(["s", "search"], - "Search in input file", - s => - { - searchQuery = s; - mode = Mode.Search; - }, - "search expression") - ) - .AllowNoArguments() - .ParseAndHandle(args); - - if (args.Length == 0) - mode = Mode.Interactive; - - switch (mode) + public static int Main(string[] args) { - default: - throw new ArgumentOutOfRangeException(nameof(mode)); - case Mode.Unset: - throw new Exception("No action specified"); - case Mode.Search: - if (string.IsNullOrEmpty(searchQuery)) - throw new ArgumentException("Search expression is required"); - if (inputPath is null) - throw new ArgumentException("Input file path is required"); - Modes.Search(searchQuery, inputPath.Value, outputPath); - break; - case Mode.Interactive: - Modes.Interactive(); - break; + try + { + Mode mode = Mode.Unset; + IOPath? inputPath = null; + IOPath? outputPath = null; + string? searchQuery = null; + + new LaunchArgumentParser( + new LaunchArgument(["i", "input"], + "Set input file path", + s => inputPath = s, + "gamestate or zip file"), + + new LaunchArgument(["o", "output"], + "Set output file path", + s => outputPath = s, + "json file [default=stdout]"), + + new LaunchArgument(["s", "search"], + "Search in input file", + s => + { + searchQuery = s; + mode = Mode.Search; + }, + "search expression") + ) + .AllowNoArguments() + .ParseAndHandle(args); + + if (args.Length == 0) + mode = Mode.Interactive; + + switch (mode) + { + default: + throw new ArgumentOutOfRangeException(nameof(mode)); + case Mode.Unset: + throw new Exception("No action specified"); + case Mode.Search: + if (string.IsNullOrEmpty(searchQuery)) + throw new ArgumentException("Search expression is required"); + if (inputPath is null) + throw new ArgumentException("Input file path is required"); + Modes.Search(searchQuery, inputPath.Value, outputPath); + break; + case Mode.Interactive: + Modes.Interactive(); + break; + } + } + catch (LaunchArgumentParser.ExitAfterHelpException) + { + // this exception is throwed after -h argument to close the program + } + catch (Exception ex) + { + ColoredConsole.WriteLine(ex.ToStringDemystified(), ConsoleColor.Red); + return 1; + } + finally + { + Console.ResetColor(); + } + return 0; } -} -catch (LaunchArgumentParser.ExitAfterHelpException) -{ - // this exception is throwed after -h argument to close the program -} -catch (Exception ex) -{ - ColoredConsole.WriteLine(ex.ToStringDemystified(), ConsoleColor.Red); - Console.ResetColor(); - Environment.Exit(1); -} -Console.ResetColor(); \ No newline at end of file +} \ No newline at end of file diff --git a/ParadoxSaveParser.WebAPI/Config.cs b/ParadoxSaveParser.WebAPI/Config.cs index 492a759..3520554 100644 --- a/ParadoxSaveParser.WebAPI/Config.cs +++ b/ParadoxSaveParser.WebAPI/Config.cs @@ -1,21 +1,27 @@ -using DTLib.Dtsod; +using System.Text.Json.Serialization; namespace ParadoxSaveParser.WebAPI; public class Config { + [JsonIgnore] public const int ActualVersion = 1; - public string BaseUrl = "http://127.0.0.1:5226/"; + public int Version { get; set; } = ActualVersion; + public string BaseUrl { get; set; } = "http://127.0.0.1:5226/"; + public int UploadLifetimeDays { get; set; } = 30; + public string DbPath { get; set; } = "database.sqlite"; - public int Version = ActualVersion; - - public static Config FromDtsod(DtsodV23 d) + public static JsonSerializerOptions JsonOptions = new() { - var cfg = new Config - { - Version = d["version"], - BaseUrl = d["baseUrl"] - }; + WriteIndented = false, + MaxDepth = 1024, + DefaultIgnoreCondition = JsonIgnoreCondition.WhenWritingNull, + }; + + public static Config Load(IOPath configPath) + { + var cfg = JsonSerializer.Deserialize(File.ReadAllText(configPath)) + ?? throw new Exception("Could not parse config file"); if (cfg.Version < ActualVersion) throw new Exception($"config is obsolete (config v{cfg.Version} < program v{ActualVersion})"); if (cfg.Version > ActualVersion) @@ -23,12 +29,10 @@ public class Config return cfg; } - public DtsodV23 ToDtsod() - => new() - { - { "version", Version }, - { "baseUrl", BaseUrl } - }; + public override string ToString() => JsonSerializer.Serialize(this, JsonOptions); - public override string ToString() => ToDtsod().ToString(); + public void Save(IOPath configPath) + { + File.WriteAllText(configPath, ToString()); + } } \ No newline at end of file diff --git a/ParadoxSaveParser.WebAPI/Program.cs b/ParadoxSaveParser.WebAPI/Program.cs index 50db454..c9bb035 100644 --- a/ParadoxSaveParser.WebAPI/Program.cs +++ b/ParadoxSaveParser.WebAPI/Program.cs @@ -12,7 +12,6 @@ global using Directory = DTLib.Filesystem.Directory; global using File = DTLib.Filesystem.File; global using Path = DTLib.Filesystem.Path; using DTLib.Console; -using DTLib.Dtsod; using DTLib.Web; using DTLib.Web.Routes; using ParadoxSaveParser.WebAPI.BackgroundTasks; @@ -29,7 +28,7 @@ public static class Program internal static DatabaseConnector DB = null!; - public static async Task Main(string[] args) + public static async Task Main(string[] args) { Console.InputEncoding = Encoding.UTF8; Console.OutputEncoding = Encoding.UTF8; @@ -43,7 +42,8 @@ public static class Program new LaunchArgument(["d", "debug"], "enables debug log output to console", () => IsDebug = true) - ).AllowNoArguments().ParseAndHandle(args); + ) + .AllowNoArguments().ParseAndHandle(args); var loggerRoot = new CompositeLogger( new ConsoleLogger @@ -68,23 +68,22 @@ public static class Program try { // config - IOPath configPath = "./config.dtsod"; + IOPath configPath = "config.json"; Config config; if (File.Exists(configPath)) { - config = Config.FromDtsod(new DtsodV23(File.ReadAllText(configPath))); + config = Config.Load(configPath); } else { - loggerMain.LogWarn("config file not found."); - config = new(); - File.WriteAllText(configPath, config.ToString()); - loggerMain.LogWarn($"created default at {configPath}."); + loggerMain.LogWarn($"Config file not found. Creating default config at {configPath}."); + config = new Config(); + config.Save(configPath); } - + PathHelper.CreateProgramDirectories(); PathHelper.CleanTempDirectory(); - DB = new("database.sqlite", 30, loggerRoot); + DB = new DatabaseConnector(config.DbPath, config.UploadLifetimeDays, loggerRoot); await DB.InitializeAsync(); await DB.DeleteInvalidData(); @@ -93,10 +92,10 @@ public static class Program { { Game.EU4, new SaveDataFilterEU4() }, }; - + // http server var router = new SimpleRouter(loggerRoot); - router.DefaultRoute = new SimpleRouter.RouteWithMethod(HttpMethod.GET, + router.DefaultRoute = new SimpleRouter.RouteWithMethod(HttpMethod.GET, new ServeFilesRouteHandler(PathHelper.PUBLIC_DIR)); router.MapRoute("/uploadSave", HttpMethod.POST, new UploadSaveHandler(mainCancel.Token, bgJobManager, saveFilters)); @@ -108,6 +107,10 @@ public static class Program var app = new WebApp(config.BaseUrl, loggerRoot, router, mainCancel.Token); await app.Run(); } + catch (LaunchArgumentParser.ExitAfterHelpException) + { + // this exception is throwed after -h argument to close the program + } catch (OperationCanceledException ex) { loggerMain.LogWarn($"catched OperationCanceledException from {ex.Source}"); @@ -115,6 +118,12 @@ public static class Program catch (Exception ex) { loggerMain.LogError(ex.ToStringDemystified()); + return 1; } + finally + { + Console.ResetColor(); + } + return 0; } } \ No newline at end of file