Das Planen von Ereignissen in verschiedenen Zeitzonen ist mit dem alten Date-Objekt bekanntermaßen schwierig, insbesondere bei der Umstellung auf die Sommerzeit, wenn Stunden übersprungen oder wiederholt werden können.
Die Temporal API bietet Temporal.ZonedDateTime, um ein Datum und eine Uhrzeit in einer bestimmten Zeitzone darzustellen, wobei die Umstellung auf Sommerzeit automatisch und vorhersehbar erfolgt.
Implementierung
So koordinieren Sie globale Ereignisse und gehen mit potenziellen Konflikten bei der Sommerzeit um:
- OBLIGATORISCH: ZonedDateTime erstellen: Verwenden Sie
Temporal.ZonedDateTime.from(), um ein zeitzonenabhängiges Datum-Uhrzeit-Objekt zu erstellen. - OBLIGATORISCH: Mehrdeutigkeit behandeln: Verwenden Sie die Option
disambiguation, um das Verhalten zu steuern, wenn eine Zeit mehrdeutig ist oder nicht existiert (z.B. bei Zeitumstellungen). - OBLIGATORISCH: Zeitzonen umrechnen: Verwende
.withTimeZone(), um die entsprechende Zeit an einem anderen Ort zu sehen.
Beispiel: Planung und Konflikterkennung
// 1. Define the event time and target time zone
const date = "2025-03-09";
const time = "02:30"; // This time is skipped in New York during Spring Forward
const timeZone = "America/New_York";
const inputStr = `${date}T${time}[${timeZone}]`;
// 2. Detect conflicts using 'reject'
let hasConflict = false;
try {
// 'reject' throws RangeError if the time is ambiguous or does not exist
Temporal.ZonedDateTime.from(inputStr, { disambiguation: 'reject' });
} catch (e) {
if (e instanceof RangeError) {
hasConflict = true;
console.log("This time falls in a DST transition gap or overlap.");
}
}
// 3. Resolve the time safely using 'compatible' (default)
// 'compatible' will resolve to a valid time even if skipped or repeated
const hostTime = Temporal.ZonedDateTime.from(inputStr, { disambiguation: 'compatible' });
console.log(`Resolved time: ${hostTime.toString()}`);
// 4. Convert to another time zone (e.g., Tokyo)
const tokyoTime = hostTime.withTimeZone("Asia/Tokyo");
// Use toLocaleString() for user-facing display instead of manual hour/minute padding
console.log(`Tokyo time: ${tokyoTime.toLocaleString('en-US', { hour: 'numeric', minute: '2-digit' })}`);
Strategische Implementierung und Best Practices
- Verwenden Sie
Temporal.ZonedDateTimefür Ereignisse, die an einen bestimmten geografischen Standort gebunden sind (z. B. eine Besprechung in einer bestimmten Stadt). - DO use
disambiguation: 'reject'if you need to detect and warn users about scheduling conflicts during DST transitions. - VERWENDEN Sie
disambiguation: 'compatible'(Standard), wenn das System bei Konflikten automatisch einen sinnvollen Zeitpunkt auswählen soll. - Verwenden Sie
Temporal.PlainDateTimeNICHT für globale Ereignisse, da es keine Zeitzoneninformationen enthält und keine Änderungen der Sommerzeit berücksichtigt. - VERWENDEN Sie
.withTimeZone(), um die entsprechende Zeit an anderen Orten zu berechnen, ohne das ursprüngliche Objekt zu verändern (Temporal-Objekte sind unveränderlich). - DO: Verwenden Sie für die für Nutzer sichtbare Zeitanzeige die native
.toLocaleString()-Formatierung (z. B.{ hour: 'numeric', minute: '2-digit' }) anstelle von manuellen Zeitberechnungen und Padding.
Fallback-Strategie
Fallbacks und Browserunterstützung für Temporal
Für Browser, die die native Temporal API noch nicht unterstützen, können Sie die Funktionserkennung verwenden und temporal-polyfill dynamisch laden (~15 KB min+gz).
Beachten Sie, dass das Importieren von temporal-polyfill das Temporal-Objekt nicht automatisch dem globalen Bereich zuweist. Weisen Sie ihn explizit zu, wenn Ihr Code auf globalThis.Temporal basiert.
// Check if Temporal is supported natively
(async () => {
if (typeof Temporal === 'undefined') {
// Load the polyfill conditionally
const module = await import('https://esm.sh/temporal-polyfill');
globalThis.Temporal = module.Temporal;
// Extend Date.prototype if needed
Date.prototype.toTemporalInstant = module.toTemporalInstant;
}
initializeApp();
})();