Befunde aus dem Testbetrieb auf der Linux-VM behoben (#572)

- #578: Abgebrochene Laeufe (Schrittgrenze, Zeitueberschreitung, Abbruch,
  Ausnahme) tragen ihre bezahlten Token - vorher 0 in RunUsage, fuer das
  Budget unsichtbar.
- #580: WebFetch prueft die aufgeloeste Zieladresse beim Verbinden; ein
  erlaubter Name, der auf 127.0.0.1 aufloest, wird gesperrt.
- #575: Dateien entstehen unter Unix mit 0600 (AtomicFile, Protokolle,
  FileRW-Anhaengen, state.db), Protokollverzeichnisse mit 0700.
- #576: SIGTERM/SIGINT beenden auch mit Fenster geordnet.
- #593: OpenRouter-Statusdienst wird gestartet.
- #589: Auftragsnachricht nennt aktuelle Zeit, Zeitzone und Termin.
- #581: Unvollstaendiges Argument-JSON erreicht das Werkzeug nicht mehr;
  das Modell bekommt eine verstaendliche Rueckmeldung statt Parsertext.
- #591: Weboberflaeche liest die Felder, die API und Ereignisstrom liefern
  (Freigaben, Protokoll, Taskboard mit Termin, Werkzeug-Einstellungen,
  Tokennutzung); Ereignisstrom in camelCase.
- #592: Chat zeigt Nachrichten nicht mehr doppelt.
- #536 (teilweise): A2A-Antworten tragen Absender und Empfaenger, Parser
  wirft nicht mehr; Datums- und Volltextfilter in Agenten-Chats.
- deploy/publish.py: Packager-Pfad net10.0, Schalter --agent-file.
- Version 0.1.4.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
This commit is contained in:
Richard
2026-09-14 15:40:56 +02:00
co-authored by Claude Opus 5
parent e2567a466f
commit 6581fd0187
29 changed files with 1128 additions and 190 deletions
+52
View File
@@ -46,6 +46,56 @@ public partial class App : Application
/// </summary>
private bool _managed;
// #576: Muessen leben, solange die Anwendung laeuft - eine eingesammelte
// Registrierung meldet sich ab.
private System.Runtime.InteropServices.PosixSignalRegistration? _sigterm;
private System.Runtime.InteropServices.PosixSignalRegistration? _sigint;
/// <summary>
/// SIGTERM und SIGINT beenden auch mit Fenster geordnet (#576).
///
/// <para>Kopflos war das seit HeadlessRun verdrahtet, mit Fenster nicht: Unter Linux
/// reagierte die Instanz auf SIGTERM gar nicht und wurde nach Ablauf jeder Frist hart
/// abgeschossen - beim Abmelden, bei systemctl stop, beim Herunterfahren. Derselbe Weg
/// wie die Bitte des Instanzmanagers: das Fenster ohne Rueckfrage schliessen, das
/// geordnete Ende laeuft von dort.</para>
/// </summary>
private void RegisterSignals(IClassicDesktopStyleApplicationLifetime desktop)
{
void Beenden(System.Runtime.InteropServices.PosixSignalContext context)
{
// Abfangen, nicht durchlassen: Sonst raeumte die Laufzeit den Prozess ab,
// waehrend das geordnete Ende noch laeuft.
context.Cancel = true;
var signal = context.Signal.ToString();
Dispatcher.UIThread.Post(() =>
{
_host?.LoggerFactory.CreateLogger("ClawdDotNet.Shutdown")
.LogInformation("Signal {Signal} empfangen - die Instanz endet geordnet.", signal);
if (_host is null)
desktop.Shutdown();
else if (desktop.MainWindow is MainWindow fenster)
fenster.BeendenOhneRueckfrage();
else
_ = BeendeGeordnetAsync(desktop, signal);
});
}
try
{
_sigterm = System.Runtime.InteropServices.PosixSignalRegistration.Create(
System.Runtime.InteropServices.PosixSignal.SIGTERM, Beenden);
_sigint = System.Runtime.InteropServices.PosixSignalRegistration.Create(
System.Runtime.InteropServices.PosixSignal.SIGINT, Beenden);
}
catch (PlatformNotSupportedException)
{
// Ohne Signale bleibt es beim Schliessen ueber Fenster und Manager.
}
}
public override void Initialize() => AvaloniaXamlLoader.Load(this);
public override void OnFrameworkInitializationCompleted()
@@ -71,6 +121,8 @@ public partial class App : Application
if (_host is not null) await _host.DisposeAsync();
};
RegisterSignals(desktop);
// Nicht abwarten: OnFrameworkInitializationCompleted muss zurückkehren,
// damit die Nachrichtenschleife anläuft — sonst gäbe es keinen Faden, auf
// dem die Fenster des Startvorgangs überhaupt erscheinen könnten.