10

here are some debug expressions i put into eclipse, if you don't believe me:

"strtotime("2110-07-16 10:07:47")" = (boolean) false    
"strtotime("2110-07-16")" = (boolean) false 

i'm using it in my function which returns a random date between the start and end dates:

public static function randomDate($start_date, $end_date, $format = DateTimeHelper::DATE_FORMAT_SQL_DATE)
    {
        if($start_date instanceof DateTime)     $start_date = $start_date->format(DateTimeHelper::DATE_FORMAT_YMDHMS);
        if($end_date instanceof DateTime)       $end_date   = $end_date->format(DateTimeHelper::DATE_FORMAT_YMDHMS);

        // Convert timetamps to millis
        $min = strtotime($start_date);
        $max = strtotime($end_date);

        // Generate random number using above bounds
        $val = rand($min, $max);

        // Convert back to desired date format
        return date($format, $val);
    }

any idea how to get it to return the right unix time for a future date?

thanks!

Garrett
  • 11,451
  • 19
  • 85
  • 126
  • 3
    We believe you, except it's expected behaviour for the date values you're passing that fall outside of the 32-bit PHP date range – Mark Baker Jul 16 '10 at 14:52
  • 3
    From PHP documentation: The valid range of a timestamp is typically from Fri, 13 Dec 1901 20:45:54 UTC to Tue, 19 Jan 2038 03:14:07 UTC. (These are the dates that correspond to the minimum and maximum values for a 32-bit signed integer.) Additionally, not all platforms support negative timestamps, therefore your date range may be limited to no earlier than the Unix epoch. This means that e.g. dates prior to Jan 1, 1970 will not work on Windows, some Linux distributions, and a few other operating systems. PHP 5.1.0 and newer versions overcome this limitation though. – Ivar Bonsaksen Jul 16 '10 at 14:53
  • i'm using php 5.3 =S 5.2 on my live server. shouldnt it work, then? – Garrett Jul 16 '10 at 15:19
  • No, PHP 5.1.0+ fixes the "additionally, not all platforms support negative timestamps" bit, not the "to Tue, 19 Jan 2038" bit. – Lightness Races in Orbit Mar 16 '11 at 11:26

5 Answers5

12

Try to keep it before Tue, 19 Jan 2038 03:14:07 UTC, when the unix timestamp epoch for 32 bit systems rolls over!

It's even described in the manual at http://php.net/strtotime

edit: Just tested: It's fixed by installing a 64 bit OS and appropriate 64 bit version of php. I guess we have time enough to fix a reincarnated millenium bug:

$one = strtotime("9999-12-31 23:59:59");  
$two = strtotime("10000-01-01 00:00:00");
var_dump($one);
var_dump($two);

int(253402297199)
bool(false)
mvds
  • 45,755
  • 8
  • 102
  • 111
  • 1
    Re: Edit - Note that 64-bit PHP (VC9 Thread safe) on Vista 64-bit still uses 32-bit signed integer timestamp range for date values – Mark Baker Jul 16 '10 at 15:45
  • I presume that this is because `strtotime()` is not a php function, but just a piece of piping to connect to (g)libc (at least in unix land) – mvds Jul 16 '10 at 15:54
  • Possibly, I was rather irked when I discovered it while doing some date testing on various platforms recently. It's also interesting to note that the date string formats passed to the dateTime constructor accept a number of formats that strtotime will reject; but I've not looked at the internals to see what the two are using – Mark Baker Jul 16 '10 at 16:47
12

If you want to work with dates that fall outside the 32-bit integer date range, then use PHP's dateTime objects

try {
    $date = new DateTime('2110-07-16 10:07:47');
} catch (Exception $e) {
    echo $e->getMessage();
    exit(1);
}

echo $date->format('Y-m-d');
Mark Baker
  • 209,507
  • 32
  • 346
  • 385
  • actually, that seems like it is going to kill my randomDate function. how can i make a random date with a DateTime? – Garrett Jul 16 '10 at 15:23
  • 2
    how is this answer accepted when the question was how to get a unix timestamp? – mvds Jul 16 '10 at 15:25
  • 5
    dateTime objects http://uk2.php.net/manual/en/book.datetime.php have been available since PHP v5.2.0 and use a 64-bit integer internally, giving a date range from about from about 292 billion years ago to about 292 billion years in the future. This should be adequate for most applications, unless you're a paleobiologist. – Mark Baker Jul 16 '10 at 15:27
  • 2
    @mvds because you can call format() with U to get a Unixtime back. See http://php.net/manual/en/datetime.format.php and http://www.php.net/manual/en/function.date.php. – floriank Jun 03 '13 at 12:50
3

From the PHP manual:

The valid range of a timestamp is typically from Fri, 13 Dec 1901 20:45:54 GMT to Tue, 19 Jan 2038 03:14:07 GMT. (These are the dates that correspond to the minimum and maximum values for a 32-bit signed integer). However, before PHP 5.1.0 this range was limited from 01-01-1970 to 19-01-2038 on some systems (e.g. Windows).

See also: Year 2038 problem - Wikipedia

igorw
  • 27,759
  • 5
  • 78
  • 90
2

You cant convert dates that occur after the unix time rollover (2038)

pauljwilliams
  • 19,079
  • 3
  • 51
  • 79
1

Simple replacement of strtotime

$date = '2199-12-31T08:00:00.000-06:00';

echo date('Y-m-d', strtotime($date)); // fails with 1970 result

echo date_format(  date_create($date) , 'Y-m-d'); // works perfect with 5.2+

Actual post here.

Azghanvi
  • 934
  • 10
  • 22