PHP: Wie ermittelt man Datum und Uhrzeit?

Das aktuelle Datum auszugeben ist eine Zeile Code. Sobald du damit aber rechnest oder es in einer anderen Zeitzone anzeigst, kommen ein paar Dinge dazu die man kennen sollte.

Der schnelle Weg

<?php
  echo date('Y-m-d H:i:s');   // 2026-08-28 22:08:12
  echo date('d.m.Y');         // 28.08.2026
  echo date('Y');             // 2026
?>

date() formatiert die aktuelle Zeit nach einem Muster. Brauchst du nur das Jahr oder nur den Tag, bist du hier fertig.

Zuerst die Zeitzone

Das ist der häufigste Grund dafür, dass “die Uhrzeit nicht stimmt”. PHP verwendet die in der php.ini eingestellte Zeitzone, und die ist oft UTC. Derselbe Zeitpunkt sieht dann so aus:

12:00 in UTC        : 2026-08-28 12:00:00 UTC
derselbe Zeitpunkt  : 2026-08-28 14:00:00 CEST

Der Unix-Timestamp ist in beiden Fällen identisch, nur die Anzeige unterscheidet sich. Setzen kannst du die Zeitzone entweder global in der php.ini:

date.timezone = Europe/Vienna

oder zur Laufzeit:

<?php
  date_default_timezone_set('Europe/Vienna');
?>

Speicherst du Zeitpunkte in einer Datenbank, speichere sie in UTC und rechne erst bei der Anzeige um. Dann hast du keine Probleme mit der Sommerzeit und keine mit Benutzern in anderen Zeitzonen.

Der bessere Weg: DateTimeImmutable

Sobald du mehr machst als anzeigen, nimm ein Objekt:

<?php
  $jetzt = new DateTimeImmutable('now', new DateTimeZone('Europe/Vienna'));

  echo $jetzt->format('d.m.Y');      // 28.08.2026
  echo $jetzt->format(DATE_ATOM);    // 2026-08-28T22:08:12+02:00
  echo $jetzt->getTimestamp();       // 1787947692
?>

DATE_ATOM ist dabei praktisch, wenn der Wert eine Schnittstelle verlässt — das Format ist eindeutig und enthält die Zeitzone.

Warum Immutable?

Es gibt zwei Klassen: DateTime und DateTimeImmutable. Der Unterschied ist größer als der Name vermuten lässt:

<?php
  $a = new DateTimeImmutable('2026-08-28 10:00:00');
  $b = $a->modify('+1 day');

  $c = new DateTime('2026-08-28 10:00:00');
  $d = $c->modify('+1 day');
?>
DateTimeImmutable  $a : 2026-08-28    (unverändert)
                   $b : 2026-08-29

DateTime           $c : 2026-08-29    <- verändert!
                   $d : 2026-08-29

Bei DateTime verändert modify() das Objekt selbst und gibt es zusätzlich zurück. $c und $d sind danach zwei Namen für dasselbe Objekt. Übergibst du so ein Objekt an eine Funktion, die daran rechnet, hast du anschließend ein anderes Datum als vorher — ohne dass es an der Aufrufstelle sichtbar wäre.

Nimm im Zweifel immer DateTimeImmutable.

Mit Zeit rechnen

<?php
  $start = new DateTimeImmutable('2026-08-28 23:30:00');

  $ende = $start->add(new DateInterval('PT2H'));   // +2 Stunden
  echo $ende->format('Y-m-d H:i');                 // 2026-08-29 01:30

  echo $start->modify('+1 month')->format('Y-m-d'); // 2026-09-28
?>

DateInterval nimmt eine Angabe im ISO-8601-Format: P leitet die Periode ein, T trennt den Zeitanteil ab. PT2H sind also zwei Stunden, P1D ein Tag, P1M ein Monat.

Die Monatsfalle

Und damit zu der Stelle, an der sich viele wundern:

31.01. + 1 Monat   =>   2026-03-03

Nicht der 28. Februar, sondern der 3. März. Der Grund ist die Rechenweise: PHP erhöht zuerst die Monatszahl und normalisiert danach. Aus dem “31. Februar” wird also der 3. März, weil der Februar 2026 nur 28 Tage hat.

Das ist dokumentiertes Verhalten und kein Fehler, überrascht aber zuverlässig. Willst du das, was man meistens meint, dann sag es ausdrücklich:

<?php
  echo $jan31->modify('last day of next month')->format('Y-m-d');  // 2026-02-28
?>

strtotime versteht auch Text

Für schnelle Fälle ist strtotime() sehr praktisch:

'now'                    => 2026-08-28
'tomorrow'               => 2026-08-29
'next monday'            => 2026-08-31
'+2 weeks'               => 2026-09-11
'last day of this month' => 2026-08-31

Dieselben Ausdrücke kannst du auch an DateTimeImmutable und modify() übergeben.

Ungültige Eingaben

Hier verhalten sich die beiden Wege unterschiedlich:

new DateTimeImmutable('kein datum') : DateMalformedStringException
strtotime('kein datum')             : false

Seit PHP 8.3 gibt es dafür die eigene Ausnahme DateMalformedStringException. strtotime() liefert dagegen nur false — und weil false beim Rechnen als 0 durchgeht, landest du damit im Zweifel beim 1. Januar 1970. Prüfe den Rückgabewert also mit ===.

Zusammenfassung

  • Zeitzone setzen, sonst rechnest du in UTC ohne es zu merken.
  • date() zum Anzeigen, DateTimeImmutable zum Rechnen.
  • DateTime verändert sich beim modify() selbst, DateTimeImmutable nicht.
  • 31.01. + 1 Monat ist der 3. März, nicht der 28. Februar.
  • In der Datenbank UTC speichern und erst bei der Anzeige umrechnen.

Hinweis zu Netcup (Werbung)

Der deutsche Hoster Netcup bietet unter anderem günstige und zugleich leistungsstarke Webhosting Pakete, KVM-basierte Root Server und dezidierte Server an. Mit unseren Gutscheincodes kannst du noch mehr Geld sparen (6€ bei deiner ersten Bestellung, 30% Rabatt auf alle KVM-basierten Root Server, ...).