Thanks to visit codestin.com
Credit goes to github.com

Skip to content

[Serializer] Add DateTimeNormalizer::CAST_KEY context option #53056

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions src/Symfony/Component/Serializer/CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,6 +1,11 @@
CHANGELOG
=========

7.1
---

* Add `DateTimeNormalizer::CAST_KEY` context option

7.0
---

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -61,4 +61,12 @@ public function withTimezone(\DateTimeZone|string|null $timezone): static

return $this->with(DateTimeNormalizer::TIMEZONE_KEY, $timezone);
}

/**
* @param 'int'|'float'|null $cast
*/
public function withCast(?string $cast): static
{
return $this->with(DateTimeNormalizer::CAST_KEY, $cast);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -25,10 +25,12 @@ final class DateTimeNormalizer implements NormalizerInterface, DenormalizerInter
{
public const FORMAT_KEY = 'datetime_format';
public const TIMEZONE_KEY = 'datetime_timezone';
public const CAST_KEY = 'datetime_cast';

private array $defaultContext = [
self::FORMAT_KEY => \DateTimeInterface::RFC3339,
self::TIMEZONE_KEY => null,
self::CAST_KEY => null,
];

private const SUPPORTED_TYPES = [
Expand Down Expand Up @@ -59,7 +61,7 @@ public function getSupportedTypes(?string $format): array
/**
* @throws InvalidArgumentException
*/
public function normalize(mixed $object, ?string $format = null, array $context = []): string
public function normalize(mixed $object, ?string $format = null, array $context = []): int|float|string
{
if (!$object instanceof \DateTimeInterface) {
throw new InvalidArgumentException('The object must implement the "\DateTimeInterface".');
Expand All @@ -73,7 +75,11 @@ public function normalize(mixed $object, ?string $format = null, array $context
$object = $object->setTimezone($timezone);
}

return $object->format($dateTimeFormat);
return match ($context[self::CAST_KEY] ?? $this->defaultContext[self::CAST_KEY] ?? false) {
'int' => (int) $object->format($dateTimeFormat),
'float' => (float) $object->format($dateTimeFormat),
default => $object->format($dateTimeFormat),
};
}

public function supportsNormalization(mixed $data, ?string $format = null, array $context = []): bool
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,7 @@ public function testWithers(array $values)
$context = $this->contextBuilder
->withFormat($values[DateTimeNormalizer::FORMAT_KEY])
->withTimezone($values[DateTimeNormalizer::TIMEZONE_KEY])
->withCast($values[DateTimeNormalizer::CAST_KEY])
->toArray();

$this->assertEquals($values, $context);
Expand All @@ -51,11 +52,13 @@ public static function withersDataProvider(): iterable
yield 'With values' => [[
DateTimeNormalizer::FORMAT_KEY => 'format',
DateTimeNormalizer::TIMEZONE_KEY => new \DateTimeZone('GMT'),
DateTimeNormalizer::CAST_KEY => 'int',
]];

yield 'With null values' => [[
DateTimeNormalizer::FORMAT_KEY => null,
DateTimeNormalizer::TIMEZONE_KEY => null,
DateTimeNormalizer::CAST_KEY => null,
]];
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -154,6 +154,72 @@ public static function normalizeUsingTimeZonePassedInContextAndExpectedFormatWit
];
}

/**
* @dataProvider provideNormalizeUsingCastCases
*/
public function testNormalizeUsingCastPassedInConstructor(\DateTimeInterface $value, string $format, ?string $cast, string|int|float $expectedResult)
{
$normalizer = new DateTimeNormalizer([DateTimeNormalizer::CAST_KEY => $cast]);

$this->assertSame($normalizer->normalize($value, null, [DateTimeNormalizer::FORMAT_KEY => $format]), $expectedResult);
}

/**
* @dataProvider provideNormalizeUsingCastCases
*/
public function testNormalizeUsingCastPassedInContext(\DateTimeInterface $value, string $format, ?string $cast, string|int|float $expectedResult)
{
$this->assertSame($this->normalizer->normalize($value, null, [DateTimeNormalizer::FORMAT_KEY => $format, DateTimeNormalizer::CAST_KEY => $cast]), $expectedResult);
}

/**
* @return iterable<array{0: \DateTimeImmutable, 1: non-empty-string, 2: 'int'|'float'|null, 3: 'int'|'float'|'string'}>
*/
public static function provideNormalizeUsingCastCases(): iterable
{
yield [
\DateTimeImmutable::createFromFormat('U', '1703071202'),
'Y',
null,
'2023',
];

yield [
\DateTimeImmutable::createFromFormat('U', '1703071202'),
'Y',
'int',
2023,
];

yield [
\DateTimeImmutable::createFromFormat('U', '1703071202'),
'Ymd',
'int',
20231220,
];

yield [
\DateTimeImmutable::createFromFormat('U', '1703071202'),
'Y',
'int',
2023,
];

yield [
\DateTimeImmutable::createFromFormat('U.v', '1703071202.388'),
'U.v',
'float',
1703071202.388,
];

yield [
\DateTimeImmutable::createFromFormat('U.u', '1703071202.388811'),
'U.u',
'float',
1703071202.388811,
];
}

public function testNormalizeInvalidObjectThrowsException()
{
$this->expectException(InvalidArgumentException::class);
Expand Down