Skip to content
Advertisement

Weird behavior PHP DateTime and DateTimeZone

PHP DateTime and DateTimeZone works incorrectly for me around DST change dates.

I wrote a simple function to convert local time to UTC and I called it with the midnight time from the 24th of Oct to the 2nd of Nov with the timezones Europe/Paris and CET:

<?php
function timeToUTC($time, $timeZone, $format='Y-m-d H:i:sP')
{
    $dt = new DateTime($time, new DateTimeZone($timeZone));
    $dt->setTimeZone(new DateTimeZone('UTC'));
    return $dt->format($format);
}

$localTimes = [
    '2020-10-24 00:00:00',
    '2020-10-25 00:00:00',
    '2020-10-26 00:00:00',
    '2020-10-27 00:00:00',
    '2020-10-28 00:00:00',
    '2020-10-29 00:00:00',
    '2020-10-30 00:00:00',
    '2020-10-31 00:00:00',
    '2020-11-01 00:00:00',
    '2020-11-02 00:00:00',
];

foreach (['Europe/Paris', 'CET'] as $timeZone) {
    echo "******** $timeZone ********" . PHP_EOL;
    foreach ($localTimes as $localTime) {
        $utcTime = timeToUTC($localTime, $timeZone);
        echo "$localTime $utcTime" . PHP_EOL;
    }
}

The output:

******** Europe/Paris ********
2020-10-24 00:00:00 2020-10-23 22:00:00+00:00
2020-10-25 00:00:00 2020-10-24 22:00:00+00:00
2020-10-26 00:00:00 2020-10-25 23:00:00+00:00
2020-10-27 00:00:00 2020-10-26 23:00:00+00:00
2020-10-28 00:00:00 2020-10-27 23:00:00+00:00
2020-10-29 00:00:00 2020-10-28 23:00:00+00:00
2020-10-30 00:00:00 2020-10-29 23:00:00+00:00
2020-10-31 00:00:00 2020-10-30 23:00:00+00:00
2020-11-01 00:00:00 2020-10-31 23:00:00+00:00
2020-11-02 00:00:00 2020-11-01 23:00:00+00:00
******** CET ********
2020-10-24 00:00:00 2020-10-23 23:00:00+00:00
2020-10-25 00:00:00 2020-10-24 23:00:00+00:00
2020-10-26 00:00:00 2020-10-25 23:00:00+00:00
2020-10-27 00:00:00 2020-10-26 23:00:00+00:00
2020-10-28 00:00:00 2020-10-27 23:00:00+00:00
2020-10-29 00:00:00 2020-10-28 23:00:00+00:00
2020-10-30 00:00:00 2020-10-29 23:00:00+00:00
2020-10-31 00:00:00 2020-10-30 23:00:00+00:00
2020-11-01 00:00:00 2020-10-31 23:00:00+00:00
2020-11-02 00:00:00 2020-11-01 23:00:00+00:00

For Europe/Paris I got the changed DST instead of the 31st of October at the 26th. And even worth that there is no change at all for the timezone CET.

What do I wrong? Is it about a PHP bug?

It’s about PHP on Ubuntu. I tried Ubuntu 16.04 with PHP 7.2.34-8 and Ubuntu 18.04 with 7.2.24-0.

Advertisement

Answer

The output is correct.

France switched to winter time October 25th, and most abbreviation timezones like CET don’t have DST rules.

Countries like France are in CET 6 months out of the year, and CEST the other 6. The abbreviated timezones are confusing, so generally I just recommend people to not use them.

echo (new DateTime('2020-10-01', new DateTimeZone('Europe/Paris')))->format('T'), "n";
echo (new DateTime('2020-11-01', new DateTimeZone('Europe/Paris')))->format('T'), "n";

Output:

CEST
CET
User contributions licensed under: CC BY-SA
2 People found this is helpful
Advertisement