Stufe 4c (#764): Kommentare in C#, WebUI-Skripten, CSS und HTML auf Englisch
Rund 2.600 Kommentarblöcke in 310 C#-Dateien übersetzt, Begründungen vollständig erhalten: blockweise gleiche Anzahl wie vorher, kein Block unter 60 % seiner Länge, der Code außerhalb der Kommentare per Tokenizer byte-identisch geprüft. Zitate deutscher Oberflächentexte und Testdaten bleiben deutsch. WebUI: Kommentare in JS/CSS/HTML übersetzt, JSDoc-@param an die in 4b umbenannten Parameter angeglichen. Dabei behoben: - 4b hatte "tag" (HTML-Tag) als deutsches "Tag" gelesen und zu "dayValue" gemacht (makeElement, svg, Tagesübersicht) - zurück auf tag/day. - Aufgaben "InProgress" bekamen die Plakettenart "laufend", für die es nie eine CSS-Klasse gab - jetzt "success" wie laufende Instanzen. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
co-authored by
Claude Opus 5.5
parent
da4ceac7d5
commit
837a634a22
@@ -7,9 +7,9 @@ using Shouldly;
|
||||
namespace ClawdDotNet.Core.Tests.Tasks;
|
||||
|
||||
/// <summary>
|
||||
/// Der Scanner-Kern — der in der Roadmap für Opus 5/Fable markierte heikle Teil. Getestet
|
||||
/// gegen echte SQLite (das atomare Claiming ist der Punkt) mit einer Attrappe für die
|
||||
/// Ausführung, damit keine Engine nötig ist. Die drei Invarianten stehen im Mittelpunkt.
|
||||
/// The scanner core — the delicate part marked in the roadmap for Opus 5/Fable. Tested
|
||||
/// against real SQLite (atomic claiming is the point) with a fake for the
|
||||
/// execution, so no engine is needed. The three invariants are at the center.
|
||||
/// </summary>
|
||||
public sealed class TaskScannerTests : IDisposable
|
||||
{
|
||||
@@ -29,13 +29,13 @@ public sealed class TaskScannerTests : IDisposable
|
||||
{
|
||||
ClawdDotNet.Core.Storage.SqliteStorage.ReleasePooledConnections(_directory);
|
||||
try { Directory.Delete(_directory, recursive: true); }
|
||||
catch { /* Aufräumen ist Nebensache */ }
|
||||
catch { /* Cleaning up is secondary */ }
|
||||
}
|
||||
|
||||
private TaskScanner Scanner(ITaskDispatcher dispatcher, IMarketCalendar? market = null)
|
||||
=> new(_repo, dispatcher, NullLoggerFactory.Instance, market, _clock);
|
||||
|
||||
/// <summary>Eine sofort fällige Aufgabe (kein Termin, nie gelaufen).</summary>
|
||||
/// <summary>A task due immediately (no schedule, never run).</summary>
|
||||
private Task<TaskItem> SeedDue(
|
||||
string id, string assignee = "@new",
|
||||
TaskItemStatus status = TaskItemStatus.Todo,
|
||||
@@ -52,7 +52,7 @@ public sealed class TaskScannerTests : IDisposable
|
||||
OnlyWhenMarketOpen = onlyWhenMarketOpen
|
||||
}, default);
|
||||
|
||||
// ─── Grundfluss ───
|
||||
// ─── Basic flow ───
|
||||
|
||||
[Fact]
|
||||
public async Task Eine_faellige_Aufgabe_wird_ausgefuehrt_und_abgeschlossen()
|
||||
@@ -87,12 +87,12 @@ public sealed class TaskScannerTests : IDisposable
|
||||
await scanner.ScanOnceAsync(default);
|
||||
(await _repo.GetAsync("t-1", default))!.Status.ShouldBe(TaskItemStatus.Todo);
|
||||
|
||||
// Zweiter Takt: der Marker ist gesetzt, derselbe Termin läuft nicht erneut.
|
||||
// Second tick: the marker is set, the same occurrence does not run again.
|
||||
await scanner.ScanOnceAsync(default);
|
||||
dispatcher.Dispatched.Count.ShouldBe(1, "kein Retry-Sturm für denselben Termin");
|
||||
}
|
||||
|
||||
// ─── Invariante 2: kein Dispatch bei offenem Blocker / an Menschen ───
|
||||
// ─── Invariant 2: no dispatch with an open blocker / to humans ───
|
||||
|
||||
[Fact]
|
||||
public async Task Eine_blockierte_Aufgabe_wird_nicht_angestossen()
|
||||
@@ -115,7 +115,7 @@ public sealed class TaskScannerTests : IDisposable
|
||||
(await _repo.GetAsync("t-1", default))!.Status.ShouldBe(TaskItemStatus.Todo, "sie wartet unverändert");
|
||||
}
|
||||
|
||||
// ─── Invariante 3: doppelter Takt = ein Lauf ───
|
||||
// ─── Invariant 3: double tick = one run ───
|
||||
|
||||
[Fact]
|
||||
public async Task Zwei_gleichzeitige_Takte_stossen_eine_Aufgabe_nur_einmal_an()
|
||||
@@ -135,7 +135,7 @@ public sealed class TaskScannerTests : IDisposable
|
||||
}
|
||||
}
|
||||
|
||||
// ─── Wiederkehrende Tasks (ersetzt den Alt-Scheduler) ───
|
||||
// ─── Recurring tasks (replaces the legacy scheduler) ───
|
||||
|
||||
[Fact]
|
||||
public async Task Ein_wiederkehrender_Task_bleibt_nach_dem_Feuern_auf_todo()
|
||||
@@ -183,7 +183,7 @@ public sealed class TaskScannerTests : IDisposable
|
||||
dispatcher.Dispatched.ShouldBeEmpty();
|
||||
}
|
||||
|
||||
// ─── C1-Haken: Marktkalender ───
|
||||
// ─── C1 hook: market calendar ───
|
||||
|
||||
[Fact]
|
||||
public async Task Bei_geschlossenem_Markt_bleibt_ein_marktabhaengiger_Termin_liegen()
|
||||
@@ -198,7 +198,7 @@ public sealed class TaskScannerTests : IDisposable
|
||||
(await _repo.GetAsync("t-1", default))!.Status.ShouldBe(TaskItemStatus.Todo);
|
||||
}
|
||||
|
||||
// ─── Auto-Dispatch: Blocker fertig → Wartende frei ───
|
||||
// ─── Auto-dispatch: blocker done → waiting ones released ───
|
||||
|
||||
[Fact]
|
||||
public async Task Wird_der_letzte_Blocker_fertig_gibt_das_die_wartende_Aufgabe_frei()
|
||||
@@ -216,8 +216,8 @@ public sealed class TaskScannerTests : IDisposable
|
||||
[Fact]
|
||||
public async Task Solange_ein_Blocker_offen_ist_bleibt_die_wartende_Aufgabe_blockiert()
|
||||
{
|
||||
await SeedDue("t-b1"); // wird in diesem Takt fertig
|
||||
await SeedDue("t-b2", assignee: "@human"); // ein Mensch — bleibt offen
|
||||
await SeedDue("t-b1"); // finishes in this tick
|
||||
await SeedDue("t-b2", assignee: "@human"); // a human — stays open
|
||||
await SeedDue("t-wartend", status: TaskItemStatus.Blocked, blockedBy: ["t-b1", "t-b2"]);
|
||||
|
||||
await Scanner(new FakeDispatcher()).ScanOnceAsync(default);
|
||||
@@ -226,7 +226,7 @@ public sealed class TaskScannerTests : IDisposable
|
||||
TaskItemStatus.Blocked, "nicht alle Blocker sind erledigt");
|
||||
}
|
||||
|
||||
// ─── #643: Nicht gelaufene Aufgaben ───
|
||||
// ─── #643: tasks that did not run ───
|
||||
|
||||
[Fact]
|
||||
public async Task Eine_einmalige_Aufgabe_ohne_Budget_bleibt_faellig_statt_liegenzubleiben()
|
||||
@@ -260,7 +260,7 @@ public sealed class TaskScannerTests : IDisposable
|
||||
(await _repo.GetAsync("t-kaputt", default))!.LastOccurrence.ShouldNotBeNull("kein Retry-Sturm nach echtem Fehlschlag");
|
||||
}
|
||||
|
||||
// ─── Attrappen ───
|
||||
// ─── Fakes ───
|
||||
|
||||
private sealed class FakeDispatcher(bool succeed = true) : ITaskDispatcher
|
||||
{
|
||||
|
||||
Reference in New Issue
Block a user