Change wfTimestamp() to an array() and add a bunch of timestamp tests hard for 32...
authorPlatonides <platonides@users.mediawiki.org>
Sun, 31 Oct 2010 23:30:41 +0000 (23:30 +0000)
committerPlatonides <platonides@users.mediawiki.org>
Sun, 31 Oct 2010 23:30:41 +0000 (23:30 +0000)
Intended to ease transition to DateTime. See r74778 and Bug 25451

includes/GlobalFunctions.php
maintenance/tests/phpunit/includes/GlobalTest.php

index c082acc..7b23e3d 100644 (file)
@@ -2017,32 +2017,33 @@ function wfTimestamp( $outputtype = TS_UNIX, $ts = 0 ) {
                        (int)$da[2], (int)$da[3], (int)$da[1] );
        }
 
-       switch( $outputtype ) {
-               case TS_UNIX:
+       static $formats = array (
+               TS_UNIX => 'U',
+               TS_MW => 'YmdHis',
+               TS_DB => 'Y-m-d H:i:s',
+               TS_ISO_8601 => 'Y-m-d\TH:i:s\Z',
+               TS_ISO_8601_BASIC => 'Ymd\THis\Z',
+               TS_EXIF => 'Y:m:d H:i:s', // This shouldn't ever be used, but is included for completeness
+               TS_RFC2822 => 'D, d M Y H:i:s',
+               TS_ORACLE => 'd-m-Y H:i:s.000000', //Was 'd-M-y h.i.s A' . ' +00:00' before r51500
+               TS_POSTGRES => 'Y-m-d H:i:s',
+               TS_DB2 => 'Y-m-d H:i:s',
+       );
+       
+       if ( !isset( $formats[$outputtype] ) ) {
+               throw new MWException( 'wfTimestamp() called with illegal output type.' );
+       }
+               
+       if ( TS_UNIX == $outputtype )
                        return $uts;
-               case TS_MW:
-                       return gmdate( 'YmdHis', $uts );
-               case TS_DB:
-                       return gmdate( 'Y-m-d H:i:s', $uts );
-               case TS_ISO_8601:
-                       return gmdate( 'Y-m-d\TH:i:s\Z', $uts );
-               case TS_ISO_8601_BASIC:
-                       return gmdate( 'Ymd\THis\Z', $uts );
-               // This shouldn't ever be used, but is included for completeness
-               case TS_EXIF:
-                       return gmdate( 'Y:m:d H:i:s', $uts );
-               case TS_RFC2822:
-                       return gmdate( 'D, d M Y H:i:s', $uts ) . ' GMT';
-               case TS_ORACLE:
-                       return gmdate( 'd-m-Y H:i:s.000000', $uts );
-                       //return gmdate( 'd-M-y h.i.s A', $uts ) . ' +00:00';
-               case TS_POSTGRES:
-                       return gmdate( 'Y-m-d H:i:s', $uts ) . ' GMT';
-               case TS_DB2:
-                       return gmdate( 'Y-m-d H:i:s', $uts );
-               default:
-                       throw new MWException( 'wfTimestamp() called with illegal output type.' );
+       
+       $output = gmdate( $formats[$outputtype], $uts );
+       
+       if ( ( $outputtype == TS_RFC2822 ) || ( $outputtype == TS_POSTGRES ) ) {
+               $output .= ' GMT';
        }
+       
+       return $output;
 }
 
 /**
index e41fbf1..a4aa2e3 100644 (file)
@@ -145,6 +145,10 @@ class GlobalTest extends PHPUnit_Framework_TestCase {
                        '20010115123456',
                        wfTimestamp( TS_MW, $t ),
                        'TS_UNIX to TS_MW' );
+               $this->assertEquals(
+                       '19690115123456',
+                       wfTimestamp( TS_MW, -30281104 ),
+                       'Negative TS_UNIX to TS_MW' );
                $this->assertEquals(
                        979562096,
                        wfTimestamp( TS_UNIX, $t ),
@@ -193,6 +197,83 @@ class GlobalTest extends PHPUnit_Framework_TestCase {
                        'TS_DB to TS_ISO_8601_BASIC' );
        }
        
+       /**
+        * This test checks wfTimestamp() with values outside.
+        * It needs PHP 64 bits or PHP > 5.1.
+        * See r74778 and bug 25451
+        */
+       function testOldTimestamps() {
+               $this->assertEquals( 'Fri, 13 Dec 1901 20:45:54 GMT',
+                       wfTimestamp( TS_RFC2822, '19011213204554' ),
+                       'Earliest time according to php documentation' );
+
+               $this->assertEquals( 'Tue, 19 Jan 2038 03:14:07 GMT',
+                       wfTimestamp( TS_RFC2822, '20380119031407' ),
+                       'Latest 32 bit time' );
+
+               $this->assertEquals( '-2147483648',
+                       wfTimestamp( TS_UNIX, '19011213204552' ),
+                       'Earliest 32 bit unix time' );
+
+               $this->assertEquals( '2147483647',
+                       wfTimestamp( TS_UNIX, '20380119031407' ),
+                       'Latest 32 bit unix time' );
+
+               $this->assertEquals( 'Fri, 13 Dec 1901 20:45:52 GMT',
+                       wfTimestamp( TS_RFC2822, '19011213204552' ),
+                       'Earliest 32 bit time' );
+
+               $this->assertEquals( 'Fri, 13 Dec 1901 20:45:51 GMT',
+                       wfTimestamp( TS_RFC2822, '19011213204551' ),
+                       'Earliest 32 bit time - 1' );
+
+               $this->assertEquals( 'Tue, 19 Jan 2038 03:14:08 GMT',
+                       wfTimestamp( TS_RFC2822, '20380119031408' ),
+                       'Latest 32 bit time + 1' );
+
+               $this->assertEquals( '19011212000000',
+                       wfTimestamp(TS_MW, '19011212000000'),
+                       'Convert to itself r74778#c10645' );
+
+               $this->assertEquals( '-2147483649',
+                       wfTimestamp( TS_UNIX, '19011213204551' ),
+                       'Earliest 32 bit unix time - 1' );
+
+               $this->assertEquals( '2147483648',
+                       wfTimestamp( TS_UNIX, '20380119031408' ),
+                       'Latest 32 bit unix time + 1' );
+
+               $this->assertEquals( '19011213204551',
+                       wfTimestamp( TS_MW, '-2147483649' ),
+                       '1901 negative unix time to MediaWiki' );
+
+               $this->assertEquals( '18010115123456',
+                       wfTimestamp( TS_MW, '-5331871504' ),
+                       '1801 negative unix time to MediaWiki' );
+
+               $this->assertEquals( 'Tue, 09 Aug 0117 12:34:56 GMT',
+                       wfTimestamp( TS_RFC2822, '0117-08-09 12:34:56'),
+                       'Death of Roman Emperor [[Trajan]]');
+
+               /* FIXME: 00 to 101 years are taken as being in [1970-2069] */
+
+               $this->assertEquals( 'Sun, 01 Jan 0101 00:00:00 GMT',
+                       wfTimestamp( TS_RFC2822, '-58979923200'),
+                       '1/1/101');
+
+               $this->assertEquals( 'Mon, 01 Jan 0001 00:00:00 GMT',
+                       wfTimestamp( TS_RFC2822, '-62135596800'),
+                       'Year 1');
+
+               /* It is not clear if we should generate a year 0 or not 
+                * We are completely off RFC2822 requirement of year being 
+                * 1900 or later.
+                */
+               $this->assertEquals( 'Wed, 18 Oct 0000 00:00:00 GMT',
+                       wfTimestamp( TS_RFC2822, '-62142076800'),
+                       'ISO 8601:2004 [[year 0]], also called [[1 BC]]');
+       }
+
        function testBasename() {
                $sets = array(
                        '' => '',