Skip to content

Commit

Permalink
Accept strings or util.TimeZone instances
Browse files Browse the repository at this point in the history
  • Loading branch information
thekid committed Dec 30, 2024
1 parent dead44e commit e0f4713
Show file tree
Hide file tree
Showing 2 changed files with 42 additions and 20 deletions.
41 changes: 26 additions & 15 deletions src/main/php/util/Date.class.php
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
<?php namespace util;

use DateTime;
use DateTime, DateTimeZone;
use lang\{IllegalArgumentException, IllegalStateException, Value};

/**
Expand Down Expand Up @@ -38,28 +38,36 @@ static function __static() {
* timezone is used.
*
* @param ?int|float|string|DateTime $in
* @param ?util.TimeZone $timezone default NULL string of timezone
* @param ?string|util.TimeZone $timezone
* @throws lang.IllegalArgumentException in case the date is unparseable
*/
public function __construct($in= null, ?TimeZone $timezone= null) {
public function __construct($in= null, $timezone= null) {
if (null === $timezone) {
$tz= null;
} else if ($timezone instanceof TimeZone) {
$tz= $timezone->getHandle();
} else {
$tz= new DateTimeZone($timezone);
}

if (null === $in) {
$this->handle= date_create('now', $timezone ? $timezone->getHandle() : null);
$this->handle= date_create('now', $tz);
} else if ($in instanceof DateTime) {
$this->handle= $in;
} else if (is_int($in) || (string)(int)$in === $in) {

// Specially mark timestamps for parsing (we assume here that strings
// containing only digits are timestamps)
$this->handle= date_create('@'.$in);
$timezone && date_timezone_set($this->handle, $timezone->getHandle());
$tz && date_timezone_set($this->handle, $tz);
} else if (is_float($in)) {

// Timestamps with microseconds are defined as `"@" "-"? [0-9]+ "." [0-9]{0,6}`,
// see https://www.php.net/manual/en/datetime.formats.php#datetime.formats.relative
$this->handle= date_create('@'.sprintf('%.6f', $in));
$timezone && date_timezone_set($this->handle, $timezone->getHandle());
$tz && date_timezone_set($this->handle, $tz);
} else {
if (false === ($this->handle= date_create($in ?? 'now', $timezone ? $timezone->getHandle() : null))) {
if (false === ($this->handle= date_create($in ?? 'now', $tz))) {
throw new IllegalArgumentException('Given argument is neither a timestamp nor a well-formed timestring: '.Objects::stringOf($in));
}
}
Expand Down Expand Up @@ -96,13 +104,16 @@ public function __unserialize($data) {
* @param int $hour
* @param int $minute
* @param int $second
* @param ?util.TimeZone $tz default NULL
* @param ?string|util.TimeZone $timezone
* @return self
*/
public static function create($year, $month, $day, $hour, $minute, $second, ?TimeZone $tz= null): self {
$date= date_create();
if ($tz) {
date_timezone_set($date, $tz->getHandle());
public static function create($year, $month, $day, $hour, $minute, $second, $timezone= null): self {
if (null === $timezone) {
$date= date_create();
} else if ($timezone instanceof TimeZone) {
$date= date_create('now', $timezone->getHandle());
} else {
$date= date_create('now', new DateTimeZone($timezone));
}

try {
Expand Down Expand Up @@ -133,9 +144,9 @@ public function equals($cmp): bool {
return $cmp instanceof self && $this->getTime() === $cmp->getTime();
}

/** Static method to get current date/time */
public static function now(?TimeZone $tz= null): self {
return new self(null, $tz);
/** @param ?string|util.TimeZone $timezone */
public static function now($timezone= null): self {
return new self(null, $timezone);
}

/** Compare this date to another date */
Expand Down
21 changes: 16 additions & 5 deletions src/test/php/util/unittest/DateTest.class.php
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,12 @@
class DateTest {
private $nowTime, $nowDate, $refDate, $tz;

/** @return iterable */
private function timezones() {
yield 'Europe/Berlin';
yield new TimeZone('Europe/Berlin');
}

#[Before]
public function setUp() {

Expand Down Expand Up @@ -51,11 +57,11 @@ public function constructorUnixtimestampWithoutTz() {
$this->assertDateEquals('2007-08-23T12:35:47+00:00', new Date(1187872547));
}

#[Test]
public function constructorUnixtimestampWithTz() {
$this->assertDateEquals('2007-08-23T14:35:47+02:00', new Date(1187872547, new TimeZone('Europe/Berlin')));
#[Test, Values(from: 'timezones')]
public function constructorUnixtimestampWithTz($tz) {
$this->assertDateEquals('2007-08-23T14:35:47+02:00', new Date(1187872547, $tz));
}

#[Test]
public function constructorParseTz() {
$date= new Date('2007-01-01 01:00:00 Europe/Berlin');
Expand Down Expand Up @@ -157,7 +163,12 @@ public function dateCreate() {
// Test with a date before 1971
Assert::equals(-44668800, Date::create(1968, 8, 2, 0, 0, 0)->getTime());
}


#[Test, Values(from: 'timezones')]
public function create_date_with_timezone($tz) {
Assert::equals(-44672400, Date::create(1968, 8, 2, 0, 0, 0, $tz)->getTime());
}

#[Test]
public function pre1970() {
$this->assertDateEquals('1969-02-01T00:00:00+00:00', new Date('01.02.1969'));
Expand Down

0 comments on commit e0f4713

Please sign in to comment.