- Veröffentlicht am
- • How2-Tipps
PHP-Zeit & Zeitzone korrekt einstellen – inkl. Troubleshooting (Apache/Nginx, PHP-FPM, Frameworks & DB)
- Autor
-
-
- Benutzer
- tmueller
- Beiträge dieses Autors
- Beiträge dieses Autors
-
Die richtige Zeitzone ist für Logs, Cronjobs, Termine und Reports essenziell. In PHP gibt es mehrere Ebenen, die die Zeit beeinflussen: php.ini, PHP-FPM/Apache/Nginx, Projekt-Code/Framework, Datenbank und sogar Frontend-JavaScript. Dieser Leitfaden zeigt die saubere Grundkonfiguration – und wie du typische „Warum steht da immer noch UTC?“-Fallen findest und behebst.
1) Zielbild verstehen
- Systemzeit:
timedatectl(Linux) – wirkt auf Dienste wie Webserver, DB, Cron. - PHP-Laufzeit:
date.timezone(php.ini) + ggf.date_default_timezone_set()im Code. - Webserverbindung: Richtiger FPM-Socket/Handler (z. B.
php8.4-fpm.sock). - Framework/Code: Laravel/Symfony/WordPress/TYPO3-Einstellungen.
- Datenbank: MySQL/MariaDB/PostgreSQL Session-/Server-TZ.
- Frontend: JS-Formatter können UTC erzwingen.
2) Standardlösung: Zeitzone in der php.ini
Dauerhaft pro SAPI (FPM, Apache, CLI):
date.timezone = Europe/Berlin
Typische Debian/Ubuntu-Pfade:
/etc/php/8.4/fpm/php.ini # für PHP-FPM (Web)
/etc/php/8.4/apache2/php.ini # für mod_php (falls genutzt)
/etc/php/8.4/cli/php.ini # für CLI/Cron
Danach Dienst neu starten:
sudo systemctl restart php8.4-fpm
sudo systemctl reload apache2 # bzw. sudo systemctl reload nginx
3) Projektbezogen (wenn keine php.ini-Zugriffe möglich)
Apache (.htaccess / vHost)
php_value date.timezone "Europe/Berlin"
Im PHP-Code (Entry-Point, z. B. public/index.php, wp-config.php)
date_default_timezone_set('Europe/Berlin');
Das im Code ist ein schneller, robuster Workaround – sollte aber nicht den Server-Fix dauerhaft ersetzen.
4) Verifizieren: Läuft die Einstellung wirklich im Web?
Lege eine Testseite an:
<?php
echo 'ini: '.ini_get('date.timezone')."<br>";
echo 'php: '.date_default_timezone_get()."<br>";
echo 'now: '.date('Y-m-d H:i:s')."<br>";
phpinfo(); // optional
Erwartung:
ini: Europe/Berlin
php: Europe/Berlin
now: 2025-10-23 17:xx:xx (Sommerzeit = UTC+2, Winterzeit = UTC+1)
In phpinfo() müssen Loaded Configuration File und Additional .ini files parsed zur richtigen 8.4-FPM-Instanz passen.
5) Häufigste Ursache: falscher FPM-Socket/vHost-Handler
Nach PHP-Upgrades zeigen vHosts gern noch auf alte Sockets.
Apache + FPM (vHost)
SetHandler "proxy:unix:/run/php/php8.4-fpm.sock|fcgi://localhost/"
Nginx (server/location)
fastcgi_pass unix:/run/php/php8.4-fpm.sock;
Danach:
sudo systemctl restart php8.4-fpm
sudo systemctl reload apache2 # bzw. nginx
6) Overrides finden (die dich zurück auf UTC ziehen)
Spätere ini-Dateien oder Pool-Configs gewinnen.
Suche nach allen TZ-Treffern:
grep -Rni "date.timezone" /etc/php/8.4
Typische Stellen:
/etc/php/8.4/fpm/conf.d/*.ini/etc/php/8.4/fpm/pool.d/*.conf(z. B.php_admin_value[date.timezone] = Europe/Berlin)- Apache vHost /
.htaccess .user.iniim Webverzeichnis
Wenn irgendwo UTC auftaucht → anpassen oder auskommentieren.
7) Framework-/CMS-Einstellungen (erzwingen oft eine TZ)
Laravel (config/app.php)
'timezone' => 'Europe/Berlin',
Caches leeren:
php artisan config:clear
Symfony (config/packages/framework.yaml)
framework:
default_timezone: 'Europe/Berlin'
WordPress Einstellungen → Allgemein → Zeitzone „Europa/Berlin“ wählen (nicht UTC+X).
TYPO3 (config/system/settings.php oder LocalConfiguration.php)
$GLOBALS['TYPO3_CONF_VARS']['SYS']['phpTimeZone'] = 'Europe/Berlin';
8) Code-Fallen: gmdate() & harte UTC
Suche nach harten UTC-Setzungen:
grep -RniE "gmdate\(|DateTimeZone\('UTC'\)|date_default_timezone_set\('UTC'|Carbon::now\('UTC'|->setTimezone\('UTC'" /var/www
gmdate()liefert immer UTC → durchdate()ersetzen, wenn lokale Zeit gewünscht.- Harte
DateTimeZone('UTC')entfernen/ersetzen.
9) Datenbank-Zeitzone
MySQL/MariaDB
SELECT @@global.time_zone, @@session.time_zone;
-- Sicher (ohne TZ-Tabelle):
SET time_zone = '+02:00'; -- Sommer
-- Besser (mit TZ-Daten):
SET time_zone = 'Europe/Berlin';
Dauerhaft: im App-DB-Connector nach Login setzen oder Server konfigurieren.
PostgreSQL
SHOW TIMEZONE;
SET TIME ZONE 'Europe/Berlin';
-- dauerhaft z.B.:
ALTER DATABASE deine_db SET TIMEZONE TO 'Europe/Berlin';
10) CLI & Cronjobs nicht vergessen
Für Cron zählt die CLI-SAPI:
/etc/php/8.4/cli/php.ini
Prüfen:
php -i | grep -E "Loaded Configuration|date.timezone"
Zusätzlich Systemzeit checken:
timedatectl
# → Time zone: Europe/Berlin
11) Frontend-Zeitformatierung
Bibliotheken wie moment/dayjs/Intl.DateTimeFormat können auf UTC eingestellt sein.
Beispiel lokal formatiert (ohne UTC-Zwang):
new Date().toLocaleString('de-DE', { timeZone: 'Europe/Berlin' });
Falls du bewusst UTC speichern willst, lokal nur für Anzeige umrechnen.
12) Checkliste „UTC spukt noch herum?“
phpinfo()zeigtEurope/Berlin(Local & Master)? ✅- vHost zeigt auf php8.4-fpm.sock? ✅
- Keine
UTC-Overrides inconf.d,pool.d,.htaccess,.user.ini? ✅ - Framework-TZ gesetzt & Cache geleert? ✅
- Kein
gmdate()/harte UTC im Code? ✅ - DB-Session/Server-TZ passend? ✅
- CLI/cron ebenfalls
Europe/Berlin? ✅ - Frontend formatiert lokal? ✅
13) Best Practice: Robustheitsschicht im Entry-Point
Selbst mit sauberer Server-Konfiguration ist es sinnvoll, im Entry-Point der App abzusichern:
date_default_timezone_set('Europe/Berlin');
So verhinderst du, dass spätere Deploys/Module die Zeitzone heimlich ändern.
Wenn php.ini richtig gesetzt ist, aber weiterhin UTC irgendwo auftaucht, liegt es fast immer außerhalb von PHPs Grundkonfiguration: falscher FPM-Socket, späte Overrides, Framework-Settings, DB-Zeitzone, Cron/CLI oder Frontend-Formatierung. Mit der obigen Checkliste bekommst du das in wenigen Minuten sauber und konsistent – von Server bis UI.