Prepares RioJoy.Core for the net40 (Windows XP) target, which has no System.Memory, ValueTask, or System.Text.Json: - IRioTransport and the whole protocol/framing layer now use byte[] + Task (RioPacket.Payload, PacketParser/Builder, RioChecksum, replies, AnalogReport, RioHidReport). At 9600 baud Span bought nothing; the SerialPortTransport bridge copies disappear entirely. - ConfigStore/OverlayTemplateStore switch to Newtonsoft 13 with the same conventions (indented, PascalCase, string enums, null-skipping); verified against the real STJ-written config.json and regions.json (load + round-trip). System.Memory and System.Text.Json packages dropped. 275 tests green. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
56 lines
2.3 KiB
C#
56 lines
2.3 KiB
C#
using Newtonsoft.Json;
|
|
using Newtonsoft.Json.Converters;
|
|
|
|
namespace RioJoy.Core.Profiles;
|
|
|
|
/// <summary>
|
|
/// Loads and saves <see cref="AppConfig"/> as JSON. Replaces the legacy
|
|
/// SimpleIni single-file config with a profile library (see docs/PLAN.md).
|
|
/// Newtonsoft rather than System.Text.Json so the net40 (Windows XP) flavor
|
|
/// shares one serializer — and one on-disk format — with net48 (PLAN.md §8A).
|
|
/// Conventions match the original STJ settings: indented, PascalCase names,
|
|
/// enums as strings, nulls skipped — existing config.json files parse as-is.
|
|
/// </summary>
|
|
public static class ConfigStore
|
|
{
|
|
private static readonly JsonSerializerSettings Options = new()
|
|
{
|
|
Formatting = Formatting.Indented,
|
|
NullValueHandling = NullValueHandling.Ignore,
|
|
Converters = { new StringEnumConverter() },
|
|
};
|
|
|
|
public static string Serialize(AppConfig config)
|
|
{
|
|
if (config is null) throw new ArgumentNullException(nameof(config));
|
|
return JsonConvert.SerializeObject(config, Options);
|
|
}
|
|
|
|
public static AppConfig Deserialize(string json)
|
|
{
|
|
if (string.IsNullOrWhiteSpace(json)) throw new ArgumentException("Value cannot be null or whitespace.", nameof(json));
|
|
return JsonConvert.DeserializeObject<AppConfig>(json, Options)
|
|
?? throw new JsonSerializationException("Config JSON deserialized to null.");
|
|
}
|
|
|
|
/// <summary>Save the config to <paramref name="path"/> (creating directories).</summary>
|
|
public static void Save(AppConfig config, string path)
|
|
{
|
|
if (string.IsNullOrWhiteSpace(path)) throw new ArgumentException("Value cannot be null or whitespace.", nameof(path));
|
|
string? dir = Path.GetDirectoryName(Path.GetFullPath(path));
|
|
if (!string.IsNullOrEmpty(dir))
|
|
Directory.CreateDirectory(dir);
|
|
File.WriteAllText(path, Serialize(config));
|
|
}
|
|
|
|
/// <summary>
|
|
/// Load the config from <paramref name="path"/>, or return a fresh default
|
|
/// <see cref="AppConfig"/> if the file does not exist.
|
|
/// </summary>
|
|
public static AppConfig Load(string path)
|
|
{
|
|
if (string.IsNullOrWhiteSpace(path)) throw new ArgumentException("Value cannot be null or whitespace.", nameof(path));
|
|
return File.Exists(path) ? Deserialize(File.ReadAllText(path)) : new AppConfig();
|
|
}
|
|
}
|