diff --git a/src/TypeConverter/TimestampTypeConverter.php b/src/TypeConverter/TimestampTypeConverter.php index 8e547b3..260406c 100644 --- a/src/TypeConverter/TimestampTypeConverter.php +++ b/src/TypeConverter/TimestampTypeConverter.php @@ -21,6 +21,7 @@ use Sunrise\Hydrator\AnnotationReaderAwareInterface; use Sunrise\Hydrator\AnnotationReaderInterface; use Sunrise\Hydrator\Dictionary\ContextKey; +use Sunrise\Hydrator\Exception\InvalidObjectException; use Sunrise\Hydrator\Exception\InvalidValueException; use Sunrise\Hydrator\Type; use Sunrise\Hydrator\TypeConverterInterface; @@ -34,6 +35,7 @@ use const FILTER_NULL_ON_FAILURE; use const FILTER_VALIDATE_INT; +use const PHP_MAJOR_VERSION; /** * @since 3.1.0 @@ -76,6 +78,11 @@ public function castValue($value, Type $type, array $path, array $context): Gene return; } + // The DateTimeImmutable::createFromFormat method returns self instead of static... + if (PHP_MAJOR_VERSION === 7 && $className !== DateTimeImmutable::class) { + throw InvalidObjectException::unsupportedType($type); + } + // phpcs:ignore Generic.Files.LineLength $format = $this->annotationReader->getAnnotations(Format::class, $type->getHolder())->current()->value ?? $context[ContextKey::TIMESTAMP_FORMAT] ?? self::DEFAULT_FORMAT; @@ -110,14 +117,14 @@ public function castValue($value, Type $type, array $path, array $context): Gene throw InvalidValueException::mustBeString($path); } - /** @var int|string $value */ + $value = (string) $value; $timezone = null; if (isset($context[ContextKey::TIMEZONE])) { $timezone = new DateTimeZone($context[ContextKey::TIMEZONE]); } - $timestamp = $className::createFromFormat($format, (string) $value, $timezone); + $timestamp = $className::createFromFormat($format, $value, $timezone); if ($timestamp === false) { throw InvalidValueException::invalidTimestamp($path, $format); } diff --git a/tests/HydratorTest.php b/tests/HydratorTest.php index 49f24fe..dbf4e5b 100644 --- a/tests/HydratorTest.php +++ b/tests/HydratorTest.php @@ -1864,6 +1864,8 @@ public function testHydrateTimestampPropertyWithoutValue(): void // phpcs:ignore Generic.Files.LineLength public function testHydrateOverriddenDateTimeImmutable(array $data, string $expected, ?string $format = null, ?string $timezone = null): void { + $this->phpRequired('8.0'); + $object = new class { public Fixture\OverriddenDateTimeImmutable $value; };