Alle vier Core-Fenster sind damit portiert. TERMINAL: - Live-Ausgabe als virtualisiertes ItemsControl ueber eine begrenzte Zeilenliste statt RichTextBox. Damit entfaellt das Auto-Clear der WinForms-Fassung, das bei Erreichen der Zeichengrenze den GESAMTEN Verlauf verwarf - jetzt werden nur die aeltesten Zeilen verdraengt (Ringpuffer, 5000 Zeilen), der juengste Verlauf bleibt immer sichtbar. Die Zeilenzahl steht in der Statuszeile. - Log-Viewer unveraendert im Funktionsumfang: JSONL-Tagesdateien, Filter nach Datum, Level, CID und Volltext, Doppelklick uebernimmt die CID (Signal-Kette verfolgen). ZEITZONE (Befund aus der Linux-Analyse, hier faellig geworden): Die Terminal-Ansicht rechnete hart gegen die WINDOWS-ID 'W. Europe Standard Time'. Auf Linux traegt die nur ueber die ICU-Zuordnung und faellt ganz aus, wenn ICU fehlt oder InvariantGlobalization gesetzt ist - das Fenster haette beim Oeffnen geworfen. Neu: PolyTraderSharp.Services.AppTimeZone + ServerSettings.ApplicationTimeZoneId (Default 'Europe/Berlin', IANA-Schreibweise). Aufloesung versucht die ID direkt, dann die jeweils andere Schreibweise (IANA<->Windows), zuletzt die Systemzeitzone - ein unbekannter Wert ist damit nie fatal, sondern erzeugt nur eine Warnung. Beide Programm-Einstiege setzen sie einmalig beim Start; laut Vorgabe wird sie bei der Installation festgelegt und nicht im laufenden Betrieb gewechselt (Aenderung verschiebt Logdatei-Tagesgrenzen). 8 neue Tests (AppTimeZoneTests) halten fest: IANA- UND Windows-ID liefern denselben UTC-Versatz (Winter +1, Sommer +2), unbekannte IDs fallen mit Warnung auf die Systemzeitzone zurueck, leere Angabe = Systemzeitzone, UTC wird korrekt umgerechnet. Verifiziert: Solution baut, 450 Tests gruen, --smoke-ui gruen (6 Fenster + Editor-Pruefung, Zeitzone loest als Europe/Berlin auf), App laeuft real, Linux-Publish laeuft. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
71 lines
2.6 KiB
C#
71 lines
2.6 KiB
C#
using System;
|
||
using PolyTraderSharp.Services;
|
||
using Xunit;
|
||
|
||
namespace PolyTrader.Tests
|
||
{
|
||
/// <summary>
|
||
/// Sicherheitsnetz für die Anzeige-Zeitzone. Die frühere Fassung rechnete hart gegen die
|
||
/// WINDOWS-ID "W. Europe Standard Time" – auf Linux ohne vollständiges ICU wirft das.
|
||
/// Diese Tests halten fest, dass beide Schreibweisen tragen und ein unbekannter Wert
|
||
/// niemals fatal ist, sondern auf die Systemzeitzone zurückfällt.
|
||
/// </summary>
|
||
public class AppTimeZoneTests
|
||
{
|
||
[Theory]
|
||
[InlineData("Europe/Berlin")] // IANA – Empfehlung, funktioniert auf beiden Plattformen
|
||
[InlineData("W. Europe Standard Time")] // Windows – Altbestand muss weiter tragen
|
||
public void Known_ids_resolve_to_the_same_zone(string id)
|
||
{
|
||
AppTimeZone.Configure(id);
|
||
|
||
// Der Bezeichner unterscheidet sich je Plattform; entscheidend ist der Versatz.
|
||
var berlinWinter = new DateTime(2026, 1, 15, 12, 0, 0, DateTimeKind.Utc);
|
||
Assert.Equal(TimeSpan.FromHours(1), AppTimeZone.Current.GetUtcOffset(berlinWinter));
|
||
|
||
var berlinSommer = new DateTime(2026, 7, 15, 12, 0, 0, DateTimeKind.Utc);
|
||
Assert.Equal(TimeSpan.FromHours(2), AppTimeZone.Current.GetUtcOffset(berlinSommer));
|
||
}
|
||
|
||
[Fact]
|
||
public void Unknown_id_falls_back_to_system_zone_and_warns()
|
||
{
|
||
string? warning = null;
|
||
AppTimeZone.Configure("Gibt/EsNicht", w => warning = w);
|
||
|
||
Assert.Equal(TimeZoneInfo.Local.Id, AppTimeZone.Current.Id);
|
||
Assert.NotNull(warning);
|
||
Assert.Contains("Gibt/EsNicht", warning);
|
||
}
|
||
|
||
[Theory]
|
||
[InlineData(null)]
|
||
[InlineData("")]
|
||
[InlineData(" ")]
|
||
public void Empty_id_means_system_zone(string? id)
|
||
{
|
||
AppTimeZone.Configure(id);
|
||
Assert.Equal(TimeZoneInfo.Local.Id, AppTimeZone.Current.Id);
|
||
}
|
||
|
||
[Fact]
|
||
public void ToDisplay_converts_utc_into_the_configured_zone()
|
||
{
|
||
AppTimeZone.Configure("Europe/Berlin");
|
||
|
||
// 12:00 UTC im Januar = 13:00 Berliner Zeit (MEZ).
|
||
var utc = new DateTime(2026, 1, 15, 12, 0, 0, DateTimeKind.Utc);
|
||
Assert.Equal(13, AppTimeZone.ToDisplay(utc).Hour);
|
||
}
|
||
|
||
[Fact]
|
||
public void ToDisplay_leaves_already_local_timestamps_alone()
|
||
{
|
||
AppTimeZone.Configure(null); // Systemzeitzone
|
||
|
||
var local = new DateTime(2026, 1, 15, 12, 0, 0, DateTimeKind.Local);
|
||
Assert.Equal(12, AppTimeZone.ToDisplay(local).Hour);
|
||
}
|
||
}
|
||
}
|