feat: import leftover student fields into notes and show them on the roster
Store leftover CSV columns on hidden student notes, move catalog import to /events/import, and persist Students index columns from Chapter Settings. Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
@@ -1,4 +1,5 @@
|
||||
using System.Text.Json;
|
||||
using System.Text.Json.Nodes;
|
||||
using WebApp.Models;
|
||||
|
||||
namespace WebApp.Services;
|
||||
@@ -8,6 +9,11 @@ namespace WebApp.Services;
|
||||
/// </summary>
|
||||
public class ChapterSettingsWriter : IChapterSettingsWriter
|
||||
{
|
||||
private static readonly JsonSerializerOptions JsonOptions = new()
|
||||
{
|
||||
WriteIndented = true
|
||||
};
|
||||
|
||||
private readonly IWebHostEnvironment _environment;
|
||||
private readonly IConfiguration _configuration;
|
||||
private readonly ILogger<ChapterSettingsWriter> _logger;
|
||||
@@ -29,35 +35,41 @@ public class ChapterSettingsWriter : IChapterSettingsWriter
|
||||
var appSettingsPath = GetAppSettingsPath();
|
||||
var dataDir = Path.GetDirectoryName(appSettingsPath);
|
||||
if (dataDir != null && !Directory.Exists(dataDir))
|
||||
{
|
||||
Directory.CreateDirectory(dataDir);
|
||||
}
|
||||
|
||||
Dictionary<string, object?> root;
|
||||
JsonObject root;
|
||||
if (File.Exists(appSettingsPath))
|
||||
{
|
||||
var existingJson = await File.ReadAllTextAsync(appSettingsPath, cancellationToken);
|
||||
root = JsonSerializer.Deserialize<Dictionary<string, object?>>(existingJson)
|
||||
?? [];
|
||||
root = JsonNode.Parse(existingJson) as JsonObject ?? [];
|
||||
}
|
||||
else
|
||||
{
|
||||
root = [];
|
||||
}
|
||||
|
||||
root["ChapterSettings"] = settings;
|
||||
var incoming = JsonSerializer.SerializeToNode(settings, JsonOptions) as JsonObject ?? [];
|
||||
if (root["ChapterSettings"] is JsonObject existing)
|
||||
{
|
||||
foreach (var property in incoming)
|
||||
existing[property.Key] = property.Value?.DeepClone();
|
||||
}
|
||||
else
|
||||
{
|
||||
root["ChapterSettings"] = incoming;
|
||||
}
|
||||
|
||||
var options = new JsonSerializerOptions { WriteIndented = true };
|
||||
var json = JsonSerializer.Serialize(root, options);
|
||||
await File.WriteAllTextAsync(appSettingsPath, json, cancellationToken);
|
||||
await File.WriteAllTextAsync(appSettingsPath, root.ToJsonString(JsonOptions), cancellationToken);
|
||||
|
||||
if (_configuration is IConfigurationRoot configurationRoot)
|
||||
configurationRoot.Reload();
|
||||
|
||||
_logger.LogInformation("Chapter settings written to {Path}", appSettingsPath);
|
||||
}
|
||||
|
||||
public async Task UpdateCompetitionYearAsync(string competitionYear, CancellationToken cancellationToken = default)
|
||||
{
|
||||
var settings = _configuration.GetSection("ChapterSettings").Get<ChapterSettings>()
|
||||
?? new ChapterSettings();
|
||||
var settings = ChapterSettings.FromConfiguration(_configuration);
|
||||
settings.CompetitionYear = competitionYear;
|
||||
await WriteAsync(settings, cancellationToken);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user