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
@@ -2,21 +2,21 @@ using System.Text.Json;
namespace ClawdDotNet.Core.Deploymentcenter;
/// <summary>Ein für diese Instanz ausgestelltes Sub-Token.</summary>
/// <param name="Token">Der Klartext — wird nur einmal ausgeliefert.</param>
/// <param name="TokenId">Kennung zum Widerrufen in der Verwaltung.</param>
/// <param name="Scopes">Welche Rechte tatsächlich durchgereicht wurden.</param>
/// <summary>A sub-token issued for this instance.</summary>
/// <param name="Token">The plain text — delivered only once.</param>
/// <param name="TokenId">ID for revoking it in the administration.</param>
/// <param name="Scopes">Which rights were actually passed through.</param>
public sealed record ProvisionedToken(string Token, string TokenId, IReadOnlyList<string> Scopes);
/// <summary>
/// Was ein Token über sich selbst sagt (<c>GET /api/tokens/v1/whoami</c>, seit SDK 2.7.1).
/// What a token says about itself (<c>GET /api/tokens/v1/whoami</c>, since SDK 2.7.1).
///
/// <para><see cref="ProjectSlug"/> ist das Feld, auf das es ankommt. Seit SDK 2.8.1 erbt
/// ein Watchdog-Monitor das Projekt seines Ping-Tokens — ist dort nichts eingetragen,
/// landen die Befunde im Scheinprojekt „default", und eine Abfrage nach dem eigenen
/// Projekt liefert für eine laufende, meldende Instanz <b>null Befunde</b>. Die Aufsicht
/// sähe dann aus wie „nichts auffällig", und das ist der schlechteste aller
/// Irrtümer.</para>
/// <para><see cref="ProjectSlug"/> is the field that matters. Since SDK 2.8.1
/// a watchdog monitor inherits the project of its ping token — if nothing is entered there,
/// the findings land in the phantom project "default", and a query for the own
/// project returns <b>zero findings</b> for a running, reporting instance. Supervision
/// would then look like "nothing unusual", and that is the worst of all
/// mistakes.</para>
/// </summary>
public sealed record TokenIdentity(
string TokenId,
@@ -26,26 +26,26 @@ public sealed record TokenIdentity(
string Environment,
IReadOnlyList<string> Scopes)
{
/// <summary>Ob dieses Token an ein Projekt gebunden ist — siehe Klassenkommentar.</summary>
/// <summary>Whether this token is bound to a project — see the class comment.</summary>
public bool IsProjectBound => !string.IsNullOrWhiteSpace(ProjectSlug);
}
/// <summary>
/// Der Zugang zu <c>/api/tokens/v1/…</c>: ein Sub-Token je Instanz ausstellen
/// (<c>provision</c>) und ein Token nach sich selbst fragen (<c>whoami</c>).
/// Access to <c>/api/tokens/v1/…</c>: issue a sub-token per instance
/// (<c>provision</c>) and ask a token about itself (<c>whoami</c>).
///
/// <para>Das ersetzt die frühere Selbstregistrierung über <c>POST /api/register</c> —
/// diesen Endpunkt gibt es im Deploymentcenter nicht (und im alten WatchDog-Server war
/// er der einzige Weg, überhaupt an einen Token zu kommen). Der Zweck bleibt derselbe
/// und ist es wert, erhalten zu bleiben: Auf den Instanzen liegt danach nicht das
/// Master-Token, sondern ein eingeschränktes, einzeln widerrufbares.</para>
/// <para>This replaces the former self-registration via <c>POST /api/register</c> —
/// that endpoint does not exist in the Deploymentcenter (and in the old WatchDog server it
/// was the only way to get a token at all). The purpose stays the same
/// and is worth keeping: afterwards the instances do not hold the
/// master token, but a restricted one that can be revoked individually.</para>
///
/// <para>Rechte lassen sich dabei nur einschränken, nie erweitern — was das
/// Master-Token nicht hat, bekommt auch das Sub-Token nicht.</para>
/// <para>Rights can only be restricted in the process, never extended — what the
/// master token does not have, the sub-token does not get either.</para>
/// </summary>
public sealed class TokenProvisioner(DeploymentcenterApi api)
{
/// <summary>Was eine Instanz braucht: Heartbeats senden und Fehler melden.</summary>
/// <summary>What an instance needs: send heartbeats and report errors.</summary>
public static readonly string[] InstanceScopes = ["watchdog:ping", "bugtracker:report"];
public async Task<ProvisionedToken> ProvisionAsync(
@@ -94,12 +94,12 @@ public sealed class TokenProvisioner(DeploymentcenterApi api)
}
/// <summary>
/// Fragt das Token, mit dem diese Verbindung arbeitet, nach sich selbst.
/// Asks the token this connection works with about itself.
///
/// <para>Nicht Neugier, sondern die einzige Möglichkeit, die Projektbindung zu
/// erfahren: Sie steht nicht im Token und ergibt sich nicht aus dem, was beim
/// Ausstellen mitgeschickt wurde — sie ist eine Eigenschaft, die der Server führt.
/// Siehe <see cref="TokenIdentity"/>, warum das nicht gleichgültig ist.</para>
/// <para>Not curiosity, but the only way to learn the project binding:
/// it is not in the token and does not follow from what was sent along when
/// issuing it — it is a property the server keeps.
/// See <see cref="TokenIdentity"/> for why that is not unimportant.</para>
/// </summary>
public async Task<TokenIdentity> WhoAmIAsync(CancellationToken ct = default)
{
@@ -122,7 +122,7 @@ public sealed class TokenProvisioner(DeploymentcenterApi api)
scopes);
}
/// <summary>Eine Zeichenkette aus der Antwort; <c>null</c> auch bei JSON-<c>null</c>.</summary>
/// <summary>A string from the response; <c>null</c> also for JSON <c>null</c>.</summary>
private static string? Text(JsonElement root, string name)
=> root.TryGetProperty(name, out var v) && v.ValueKind == JsonValueKind.String
? v.GetString()