Skip to content

Commit

Permalink
Merge pull request #205 from joshbmarshall/master
Browse files Browse the repository at this point in the history
Fix relative and fixed time parsing with timezones
  • Loading branch information
markstory authored Jun 17, 2019
2 parents c981a91 + 9505b7c commit 0292f06
Show file tree
Hide file tree
Showing 4 changed files with 60 additions and 7 deletions.
3 changes: 2 additions & 1 deletion src/Chronos.php
Original file line number Diff line number Diff line change
Expand Up @@ -110,7 +110,8 @@ public function __construct($time = 'now', $tz = null)
$testNow = $testNow->modify($time);
}

if ($tz !== $testNow->getTimezone()) {
$relativetime = static::isTimeExpression($time);
if (!$relativetime && $tz !== $testNow->getTimezone()) {
$testNow = $testNow->setTimezone($tz === null ? date_default_timezone_get() : $tz);
}

Expand Down
4 changes: 2 additions & 2 deletions src/MutableDateTime.php
Original file line number Diff line number Diff line change
Expand Up @@ -101,10 +101,10 @@ public function __construct($time = 'now', $tz = null)
$testNow = $testNow->modify($time);
}

if ($tz !== $testNow->getTimezone()) {
$relativetime = static::isTimeExpression($time);
if (!$relativetime && $tz !== $testNow->getTimezone()) {
$testNow = $testNow->setTimezone($tz === null ? date_default_timezone_get() : $tz);
}

$time = $testNow->format('Y-m-d H:i:s.u');
parent::__construct($time, $tz);
}
Expand Down
20 changes: 17 additions & 3 deletions src/Traits/RelativeKeywordTrait.php
Original file line number Diff line number Diff line change
Expand Up @@ -21,19 +21,33 @@ trait RelativeKeywordTrait
protected static $relativePattern = '/this|next|last|tomorrow|yesterday|midnight|today|[+-]|first|last|ago/i';

/**
* Determine if there is a relative keyword in the time string, this is to
* create dates relative to now for test instances. e.g.: next tuesday
* Determine if there is just a time in the time string
*
* @param string $time The time string to check.
* @return bool true if there is a keyword, otherwise false
*/
public static function hasRelativeKeywords($time)
private static function isTimeExpression($time)
{
// Just a time
if (preg_match('/^[0-2]?[0-9]:[0-5][0-9](?::[0-5][0-9])?$/', $time)) {
return true;
}

return false;
}

/**
* Determine if there is a relative keyword in the time string, this is to
* create dates relative to now for test instances. e.g.: next tuesday
*
* @param string $time The time string to check.
* @return bool true if there is a keyword, otherwise false
*/
public static function hasRelativeKeywords($time)
{
if (self::isTimeExpression($time)) {
return true;
}
// skip common format with a '-' in it
if (preg_match('/[0-9]{4}-[0-9]{1,2}-[0-9]{1,2}/', $time) !== 1) {
return preg_match(static::$relativePattern, $time) > 0;
Expand Down
40 changes: 39 additions & 1 deletion tests/DateTime/TestingAidsTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -227,7 +227,7 @@ public function testParseRelativeWithMinusSignsInDate($class)
* @dataProvider classNameProvider
* @return void
*/
public function testTimeZoneWithTestValueSet($class)
public function testParseWithTimeZone($class)
{
$notNow = $class::parse('2013-07-01 12:00:00', 'America/New_York');
$class::setTestNow($notNow);
Expand All @@ -237,6 +237,44 @@ public function testTimeZoneWithTestValueSet($class)
$this->assertSame('2013-07-01T09:00:00-07:00', $class::parse('now', 'America/Vancouver')->toIso8601String());
}

/**
* @dataProvider classNameProvider
* @return void
*/
public function testParseRelativeWithTimeZone($class)
{
$notNow = $class::parse('2013-07-01 12:00:00', 'America/New_York');
$class::setTestNow($notNow);

$this->assertSame('2013-07-01T10:55:00-05:00', $class::parse('5 minutes ago', 'America/Mexico_City')->toIso8601String());
$this->assertSame('2013-07-01 10:55:00', $class::parse('5 minutes ago', 'America/Mexico_City')->toDateTimeString());
}

/**
* Test parse() with relative values and timezones
*
* @dataProvider classNameProvider
* @return void
*/
public function testParseRelativeWithTimezoneAndTestValueSet($class)
{
$notNow = $class::parse('2013-07-01 12:00:00', 'America/New_York');
$class::setTestNow($notNow);

$this->assertSame('06:30:00', $class::parse('2013-07-01 06:30:00', 'America/Mexico_City')->toTimeString());
$this->assertSame('06:30:00', $class::parse('6:30', 'America/Mexico_City')->toTimeString());

$this->assertSame('2013-07-01T06:30:00-04:00', $class::parse('2013-07-01 06:30:00')->toIso8601String());
$this->assertSame('2013-07-01T06:30:00-05:00', $class::parse('2013-07-01 06:30:00', 'America/Mexico_City')->toIso8601String());

$this->assertSame('2013-07-01T06:30:00-04:00', $class::parse('06:30')->toIso8601String());
$this->assertSame('2013-07-01T06:30:00-04:00', $class::parse('6:30')->toIso8601String());
$this->assertSame('2013-07-01T06:30:00-05:00', $class::parse('6:30', 'America/Mexico_City')->toIso8601String());

$this->assertSame('2013-07-01T06:30:00-05:00', $class::parse('6:30:00', 'America/Mexico_City')->toIso8601String());
$this->assertSame('2013-07-01T06:30:00-05:00', $class::parse('06:30:00', 'America/Mexico_City')->toIso8601String());
}

/**
* @dataProvider classNameProvider
* @return void
Expand Down

0 comments on commit 0292f06

Please sign in to comment.