3

I have the following code, which prints out differences between two dates:

print_r((new DateTime('2018-01-01'))->diff(new DateTime('2018-11-01')));

print_r((new DateTime('2018-10-01'))->diff(new DateTime('2018-11-01')));

Output:

DateInterval Object
(
    [y] => 0
    [m] => 10
    [d] => 0
    [h] => 0
    [i] => 0
    [s] => 0
    [f] => 0
    [weekday] => 0
    [weekday_behavior] => 0
    [first_last_day_of] => 0
    [invert] => 0
    [days] => 304
    [special_type] => 0
    [special_amount] => 0
    [have_weekday_relative] => 0
    [have_special_relative] => 0
)
DateInterval Object
(
    [y] => 0
    [m] => 1
    [d] => 1
    [h] => 0
    [i] => 0
    [s] => 0
    [f] => 0
    [weekday] => 0
    [weekday_behavior] => 0
    [first_last_day_of] => 0
    [invert] => 0
    [days] => 31
    [special_type] => 0
    [special_amount] => 0
    [have_weekday_relative] => 0
    [have_special_relative] => 0
)

As you can see, the first date difference returns correctly 10 months and 0 days. The second one however, instead of returning 1 month a 0 days, returns incorrectly 1 month and 1 days.

What is causing this?

What baffles me, is that I tried to run this code on couple of PHP sandbox sites and I am getting inconsistent results:

My own server and https://wtools.io/php-sandbox returns the wrong amount of days for the second date. But for example http://sandbox.onlinephpfunctions.com/ returns correctly 0 days on the second date difference.

Askerman
  • 787
  • 1
  • 12
  • 31
  • Islam no, it doesn't work here https://3v4l.org/6v0XI but does here http://sandbox.onlinephpfunctions.com/code/8b8ae0255976604dccc20af7a531784ae8041334 – delboy1978uk Nov 07 '18 at 13:00
  • 1
    @delboy1978uk I'd removed my comment cuz I did notice the issue yes :) – Alexandre Elshobokshy Nov 07 '18 at 13:01
  • One thing that could be consistently different across servers is their time zone, which could affect functions such as `DateTime('now')`, which could affect total measurement. – DeDee Nov 07 '18 at 13:03

1 Answers1

5

This is because of server time zones. Just set everything as UTC and you should be alright.

print_r((new DateTime('2018-10-01', new DateTimeZone('UTC')))->diff(new DateTime('2018-11-01', new DateTimeZone('UTC'))));

https://3v4l.org/PWKiD

Without the timezone, it is indeed the unexpected value. https://3v4l.org/6v0XI

delboy1978uk
  • 12,118
  • 2
  • 21
  • 39
  • 2
    I *think* it's because of daylight savings... the clocks go back in October meaning that midnight on the 1st of October is an hour earlier than midnight on the first of November - and since the *time* wasn't specified in those `DateTime` objects... that's why the `UTC` fix works. Setting the time to midday (`2018-11-01 12:00:00`) also fixes the problem. – CD001 Nov 07 '18 at 13:11