Skip to content

Commit ed2abda

Browse files
committed
Deprecate passing timezone information to methods where it is ignored
1 parent b30518d commit ed2abda

File tree

2 files changed

+91
-4
lines changed

2 files changed

+91
-4
lines changed

src/Types/DateImmutableType.php

Lines changed: 37 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,22 @@ public function convertToDatabaseValue($value, AbstractPlatform $platform)
3535
}
3636

3737
if ($value instanceof DateTimeImmutable) {
38+
$offset = $value->format('O');
39+
$defaultOffset = (new DateTimeImmutable())->format('O');
40+
41+
if ($offset !== $defaultOffset) {
42+
Deprecation::triggerIfCalledFromOutside(
43+
'doctrine/dbal',
44+
'https://github.com/doctrine/dbal/pull/6020',
45+
'Passing a timezone offset (%s) different than the default one (%s) is deprecated'
46+
. ' as it will be lost, use %s::%s() instead.',
47+
$offset,
48+
$defaultOffset,
49+
DateTimeTzImmutableType::class,
50+
__FUNCTION__,
51+
);
52+
}
53+
3854
return $value->format($platform->getDateFormatString());
3955
}
4056

@@ -56,7 +72,27 @@ public function convertToDatabaseValue($value, AbstractPlatform $platform)
5672
*/
5773
public function convertToPHPValue($value, AbstractPlatform $platform)
5874
{
59-
if ($value === null || $value instanceof DateTimeImmutable) {
75+
if ($value === null) {
76+
return null;
77+
}
78+
79+
if ($value instanceof DateTimeImmutable) {
80+
$offset = $value->format('O');
81+
$defaultOffset = (new DateTimeImmutable())->format('O');
82+
83+
if ($offset !== $defaultOffset) {
84+
Deprecation::triggerIfCalledFromOutside(
85+
'doctrine/dbal',
86+
'https://github.com/doctrine/dbal/pull/6020',
87+
'Passing a timezone offset (%s) different than the default one (%s) is deprecated'
88+
. ' as it may be lost, use %s::%s() instead.',
89+
$offset,
90+
$defaultOffset,
91+
DateTimeTzImmutableType::class,
92+
__FUNCTION__,
93+
);
94+
}
95+
6096
return $value;
6197
}
6298

tests/Types/DateImmutableTypeTest.php

Lines changed: 54 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -4,17 +4,22 @@
44

55
use DateTime;
66
use DateTimeImmutable;
7+
use DateTimeZone;
78
use Doctrine\DBAL\ParameterType;
89
use Doctrine\DBAL\Platforms\AbstractPlatform;
910
use Doctrine\DBAL\Types\ConversionException;
1011
use Doctrine\DBAL\Types\DateImmutableType;
12+
use Doctrine\Deprecations\PHPUnit\VerifyDeprecations;
13+
use InvalidArgumentException;
1114
use PHPUnit\Framework\MockObject\MockObject;
1215
use PHPUnit\Framework\TestCase;
1316

1417
use function get_class;
1518

1619
class DateImmutableTypeTest extends TestCase
1720
{
21+
use VerifyDeprecations;
22+
1823
/** @var AbstractPlatform&MockObject */
1924
private AbstractPlatform $platform;
2025

@@ -48,10 +53,18 @@ public function testConvertsDateTimeImmutableInstanceToDatabaseValue(): void
4853
$this->platform->expects(self::once())
4954
->method('getDateFormatString')
5055
->willReturn('Y-m-d');
51-
$date->expects(self::once())
56+
$date->expects(self::exactly(2))
5257
->method('format')
53-
->with('Y-m-d')
54-
->willReturn('2016-01-01');
58+
->willReturnCallback(static function (string $format): string {
59+
switch ($format) {
60+
case 'O':
61+
return 'UTC';
62+
case 'Y-m-d':
63+
return '2016-01-01';
64+
default:
65+
throw new InvalidArgumentException();
66+
}
67+
});
5568

5669
self::assertSame(
5770
'2016-01-01',
@@ -117,4 +130,42 @@ public function testRequiresSQLCommentHint(): void
117130
{
118131
self::assertTrue($this->type->requiresSQLCommentHint($this->platform));
119132
}
133+
134+
/** @dataProvider provideDateTimeInstancesWithTimezone */
135+
public function testTimezoneDeprecationFromConvertsToDatabaseValue(DateTimeImmutable $date): void
136+
{
137+
$defaultOffset = (new DateTimeImmutable())->format('O');
138+
139+
self::assertFalse($defaultOffset === $date->format('O'));
140+
141+
$this->platform->expects(self::once())
142+
->method('getDateFormatString')
143+
->willReturn('Y-m-d');
144+
145+
$this->expectDeprecationWithIdentifier('https://github.com/doctrine/dbal/pull/6020');
146+
147+
$this->type->convertToDatabaseValue($date, $this->platform);
148+
}
149+
150+
/** @psalm-return iterable<string, array<0: DateTimeImmutable>> */
151+
public function provideDateTimeInstancesWithTimezone(): iterable
152+
{
153+
yield 'timezone' => [
154+
(new DateTimeImmutable())->setTimezone(new DateTimeZone('America/Argentina/Buenos_Aires')),
155+
];
156+
yield 'offset' => [
157+
(new DateTimeImmutable())->setTimezone(new DateTimeZone('-0300')),
158+
];
159+
}
160+
161+
public function testNoTimezoneFromConvertsToDatabaseValue(): void
162+
{
163+
$this->platform->expects(self::once())
164+
->method('getDateFormatString')
165+
->willReturn('Y-m-d');
166+
167+
$this->expectNoDeprecationWithIdentifier('https://github.com/doctrine/dbal/pull/6020');
168+
169+
$this->type->convertToDatabaseValue(new DateTimeImmutable(), $this->platform);
170+
}
120171
}

0 commit comments

Comments
 (0)