Klassenbucheinträge abgleich und poll

This commit is contained in:
2026-08-25 09:31:41 +02:00
parent 87a7badb44
commit 7fa8a93c82
14 changed files with 584 additions and 9 deletions
@@ -0,0 +1,53 @@
using System.Globalization;
namespace LehrerApp.WebUntis;
public static class WebUntisClassRegisterEventReportParser
{
public static IReadOnlyList<UntisClassRegisterEventReportEntry> Parse(string content)
{
var rows = TabSeparatedTextReader.ParseRows(content, '\t');
if (rows.Count == 0) return [];
var headers = rows[0]
.Select((header, index) => (index == 0 ? header.TrimStart('\uFEFF') : header).Trim())
.ToArray();
var result = new List<UntisClassRegisterEventReportEntry>();
foreach (var row in rows.Skip(1))
{
if (row.All(string.IsNullOrWhiteSpace)) continue;
var values = new Dictionary<string, string?>(StringComparer.Ordinal);
for (var index = 0; index < headers.Length; index++)
values[headers[index]] = index < row.Count ? row[index].Trim() : null;
result.Add(new UntisClassRegisterEventReportEntry(
Get(values, "Klasse")?.Trim() ?? "",
GermanShortDate(Get(values, "Datum")) ?? throw new InvalidDataException(
"Ungültiges Datum in Spalte \"Datum\"."),
Optional(Get(values, "Fach")),
Get(values, "Name")?.Trim() ?? "",
Optional(Get(values, "Benutzer")),
Optional(Get(values, "Eintragskategorie")),
Optional(Get(values, "Kategoriegruppe")),
Optional(Get(values, "Text"))));
}
return result;
}
private static string? Get(IReadOnlyDictionary<string, string?> values, string key) =>
values.TryGetValue(key, out var value) ? value : null;
private static string? Optional(string? value) =>
string.IsNullOrWhiteSpace(value) ? null : value.Trim();
private static int? GermanShortDate(string? value)
{
if (!DateOnly.TryParseExact(value?.Trim(), "dd.MM.yy", CultureInfo.InvariantCulture,
DateTimeStyles.None, out var date))
return null;
return date.Year * 10_000 + date.Month * 100 + date.Day;
}
}