php.net |  support |  documentation |  report a bug |  advanced search |  search howto |  statistics |  random bug |  login
Bug #71913 extra hour in DateTime modify (Daylight Saving Time problem)
Submitted: 2016-03-29 09:07 UTC Modified: 2016-03-29 09:33 UTC
Votes:1
Avg. Score:5.0 ± 0.0
Reproduced:1 of 1 (100.0%)
Same Version:1 (100.0%)
Same OS:1 (100.0%)
From: public at RTLer dot com Assigned:
Status: Not a bug Package: Date/time related
PHP Version: 7.0.4 OS: Ubuntu 14.04.4 LTS (GNU/Linux 3.
Private report: No CVE-ID: None
Welcome back! If you're the original bug submitter, here's where you can edit the bug or add additional notes.
If you forgot your password, you can retrieve your password here.
Password:
Status:
Package:
Bug Type:
Summary:
From: public at RTLer dot com
New email:
PHP Version: OS:

 

 [2016-03-29 09:07 UTC] public at RTLer dot com
Description:
------------
i use php library "Carbon/Carbon" witch use DateTime directly 
and when i add one day to this exact day "2016-03-20" with timezone of "Asia/Tehran" it give one extra hour
but when i add two day it works just fine.

Test script:
---------------
$timezone = new DateTimeZone('Asia/Tehran');
$dayStart = new DateTime('2016-03-20 00:00:00.000000', $timezone);

$dayOne = (new DateTime('2016-03-20 00:00:00.000000', $timezone))->modify('1 day');
$dayTwo = (new DateTime('2016-03-20 00:00:00.000000', $timezone))->modify('2 day');


echo json_encode([
    '$dayStart' => $dayStart,
    '$dayOne' => $dayOne,
    'diff of $dayOne' => $dayStart->diff($dayOne,true),
    '$dayTwo' => $dayTwo,
    'diff of $dayTwo' => $dayStart->diff($dayTwo,true),
]);
die;

Expected result:
----------------
{
    "$dayStart": {
        "date": "2016-03-20 00:00:00.000000",
        "timezone_type": 3,
        "timezone": "Asia\/Tehran"
    },
    "$dayOne": {
        "date": "2016-03-21 00:00:00.000000",
        "timezone_type": 3,
        "timezone": "Asia\/Tehran"
    },
    "diff of $dayOne": {
        "y": 0,
        "m": 0,
        "d": 1,
        "h": 0,
        "i": 0,
        "s": 0,
        "weekday": 0,
        "weekday_behavior": 0,
        "first_last_day_of": 0,
        "invert": 0,
        "days": 1,
        "special_type": 0,
        "special_amount": 0,
        "have_weekday_relative": 0,
        "have_special_relative": 0
    },
    "$dayTwo": {
        "date": "2016-03-22 00:00:00.000000",
        "timezone_type": 3,
        "timezone": "Asia\/Tehran"
    },
    "diff of $dayTwo": {
        "y": 0,
        "m": 0,
        "d": 2,
        "h": 0,
        "i": 0,
        "s": 0,
        "weekday": 0,
        "weekday_behavior": 0,
        "first_last_day_of": 0,
        "invert": 0,
        "days": 2,
        "special_type": 0,
        "special_amount": 0,
        "have_weekday_relative": 0,
        "have_special_relative": 0
    }
}

Actual result:
--------------
{
    "$dayStart": {
        "date": "2016-03-20 00:00:00.000000",
        "timezone_type": 3,
        "timezone": "Asia\/Tehran"
    },
    "$dayOne": {
        "date": "2016-03-21 01:00:00.000000",
        "timezone_type": 3,
        "timezone": "Asia\/Tehran"
    },
    "diff of $dayOne": {
        "y": 0,
        "m": 0,
        "d": 1,
        "h": 1,
        "i": 0,
        "s": 0,
        "weekday": 0,
        "weekday_behavior": 0,
        "first_last_day_of": 0,
        "invert": 0,
        "days": 1,
        "special_type": 0,
        "special_amount": 0,
        "have_weekday_relative": 0,
        "have_special_relative": 0
    },
    "$dayTwo": {
        "date": "2016-03-22 00:00:00.000000",
        "timezone_type": 3,
        "timezone": "Asia\/Tehran"
    },
    "diff of $dayTwo": {
        "y": 0,
        "m": 0,
        "d": 2,
        "h": 0,
        "i": 0,
        "s": 0,
        "weekday": 0,
        "weekday_behavior": 0,
        "first_last_day_of": 0,
        "invert": 0,
        "days": 2,
        "special_type": 0,
        "special_amount": 0,
        "have_weekday_relative": 0,
        "have_special_relative": 0
    }
}

Patches

Pull Requests

History

AllCommentsChangesGit/SVN commitsRelated reports
 [2016-03-29 09:12 UTC] requinix@php.net
-Status: Open +Status: Not a bug
 [2016-03-29 09:12 UTC] requinix@php.net
Asia/Tehran did not have a 2016-03-21 00:00:00 because of the start of daylight savings. 01:00:00 is the most logical result.
It did have a 2016-03-22 00:00:00 so that is as expected.
 [2016-03-29 09:33 UTC] derick@php.net
This is because "March 21st, 00:00" does not exist, but "March 22nd, 00:00" does exist. Because "March 21st, 00:00" to "00:59" do not exist, the library skips to "01:00" - this is on purpose.

However, you can argue that the *diff* between $dayStart and $dayOne should be "1 day" too. The RFC in https://wiki.php.net/rfc/datetime_and_daylight_saving_time describes what should happen in that case.
 
PHP Copyright © 2001-2026 The PHP Group
All rights reserved.
Last updated: Tue Oct 06 12:00:01 2026 UTC