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:
Richard
2026-10-04 12:45:03 +02:00
co-authored by Claude Opus 5.5
parent da4ceac7d5
commit 837a634a22
311 changed files with 7238 additions and 7252 deletions
@@ -7,19 +7,19 @@ using Shouldly;
namespace ClawdDotNet.Core.Tests.Engine;
/// <summary>
/// Regressionstests für Bug B1: Die Compaction behält blind die letzten N Nachrichten.
/// Liegt diese Grenze mitten in einer Tool-Sequenz, entsteht eine tool-Antwort ohne
/// zugehörigen assistant-tool_call — die API lehnt das mit HTTP 400 ab.
/// Regression tests for bug B1: compaction blindly keeps the last N messages.
/// If this boundary lies in the middle of a tool sequence, a tool answer without
/// the corresponding assistant tool_call results — the API rejects that with HTTP 400.
/// </summary>
public sealed class ContextCompactorTests
{
private const string Model = "test/model";
/// <summary>Schwelle so gesetzt, dass Compaction sicher ausgelöst wird.</summary>
/// <summary>Threshold set so that compaction is surely triggered.</summary>
private static LoopGuardConfig AlwaysCompact => new()
{
MaxContextTokens = 1_000,
CompactionThreshold = 0.5 // Schwelle = 500 Tokens
CompactionThreshold = 0.5 // threshold = 500 tokens
};
private static LoopGuardConfig NeverCompact => new()
@@ -36,7 +36,7 @@ public sealed class ContextCompactorTests
}
// ═══════════════════════════════════════════════════════════
// C1/C2 — Die eigentliche Bug-Reproduktion
// C1/C2 — the actual bug reproduction
// ═══════════════════════════════════════════════════════════
[Theory]
@@ -50,14 +50,14 @@ public sealed class ContextCompactorTests
[InlineData(8)]
public async Task Compaction_erhaelt_gueltige_Sequenz_bei_beliebiger_Toolzyklus_Laenge(int toolCallsPerCycle)
{
// Je nach Anzahl der Tool-Calls fällt die "letzte 6 Nachrichten"-Grenze
// an eine andere Stelle im Zyklus. Mindestens eine Variante trifft mitten hinein.
// Depending on the number of tool calls the "last 6 messages" boundary falls
// at a different place in the cycle. At least one variant hits right in the middle.
var (compactor, _) = CreateCompactor();
var messages = Conversation.Start()
.Repeat(times: 4, toolCallsPerCycle: toolCallsPerCycle, resultLength: 200)
.Build();
ContextInvariants.AssertValid(messages); // Vorbedingung: Ausgangslage ist gültig
ContextInvariants.AssertValid(messages); // Precondition: the initial state is valid
await compactor.CompactIfNeededAsync(messages, AlwaysCompact, Model, default);
@@ -67,7 +67,7 @@ public sealed class ContextCompactorTests
[Fact]
public async Task Compaction_trennt_Toolantwort_nie_von_ihrem_Aufruf()
{
// Gezielt konstruiert: Der Tail von 6 Nachrichten beginnt genau bei einer tool-Antwort.
// Constructed on purpose: the tail of 6 messages begins exactly at a tool answer.
var (compactor, _) = CreateCompactor();
var messages = Conversation.Start()
.User("Erste Anfrage")
@@ -81,7 +81,7 @@ public sealed class ContextCompactorTests
ContextInvariants.AssertValid(messages);
// Keine verwaiste tool-Antwort
// No orphaned tool answer
for (var i = 0; i < messages.Count; i++)
{
if (messages[i].Role != "tool") continue;
@@ -126,7 +126,7 @@ public sealed class ContextCompactorTests
}
// ═══════════════════════════════════════════════════════════
// C5/C6 — Fehlerfälle der Zusammenfassung
// C5/C6 — failure cases of the summary
// ═══════════════════════════════════════════════════════════
[Fact]
@@ -158,7 +158,7 @@ public sealed class ContextCompactorTests
}
// ═══════════════════════════════════════════════════════════
// C7/C8 — Tool-Result-Pruning
// C7/C8 — tool result pruning
// ═══════════════════════════════════════════════════════════
[Fact]
@@ -192,7 +192,7 @@ public sealed class ContextCompactorTests
}
// ═══════════════════════════════════════════════════════════
// C9/C10 — Schätzung und Schwelle
// C9/C10 — estimate and threshold
// ═══════════════════════════════════════════════════════════
[Fact]
@@ -213,7 +213,7 @@ public sealed class ContextCompactorTests
[Fact]
public async Task Unterhalb_der_Schwelle_wird_kein_ApiCall_ausgeloest()
{
// Wichtig fürs Budget: Compaction darf nicht unnötig ein Modell anwerfen.
// Important for the budget: compaction must not fire up a model unnecessarily.
var (compactor, client) = CreateCompactor();
var messages = Conversation.Start().Repeat(2).Build();