Skip to content

Commit f14546b

Browse files
committed
Use immutable DateTime
Ensure DateTime cannot be accidentally mutated when passed as an argument.
1 parent 483f4ee commit f14546b

File tree

13 files changed

+57
-63
lines changed

13 files changed

+57
-63
lines changed

src/controllers/Index.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -83,7 +83,7 @@ public function home(): void {
8383

8484
$lastUpdate = $this->itemsDao->lastUpdate();
8585
$result = [
86-
'lastUpdate' => $lastUpdate !== null ? $lastUpdate->format(\DateTime::ATOM) : null,
86+
'lastUpdate' => $lastUpdate !== null ? $lastUpdate->format(\DateTimeImmutable::ATOM) : null,
8787
'hasMore' => $items['hasMore'],
8888
'entries' => $items['entries'],
8989
'all' => $statsAll,

src/controllers/Items/Sync.php

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -49,26 +49,26 @@ public function sync(): void {
4949
$this->view->jsonError(['sync' => 'missing since argument']);
5050
}
5151

52-
$since = new \DateTime($params['since']);
53-
$since->setTimeZone(new \DateTimeZone(date_default_timezone_get()));
52+
$since = new \DateTimeImmutable($params['since']);
53+
$since = $since->setTimeZone(new \DateTimeZone(date_default_timezone_get()));
5454

5555
$lastUpdate = $this->itemsDao->lastUpdate();
5656

5757
$sync = [
58-
'lastUpdate' => $lastUpdate !== null ? $lastUpdate->format(\DateTime::ATOM) : null,
58+
'lastUpdate' => $lastUpdate !== null ? $lastUpdate->format(\DateTimeImmutable::ATOM) : null,
5959
];
6060

6161
if (array_key_exists('itemsSinceId', $params)) {
6262
$sinceId = (int) $params['itemsSinceId'];
6363
if ($sinceId >= 0) {
64-
$notBefore = isset($params['itemsNotBefore']) ? new \DateTime($params['itemsNotBefore']) : null;
64+
$notBefore = isset($params['itemsNotBefore']) ? new \DateTimeImmutable($params['itemsNotBefore']) : null;
6565
if ($sinceId === 0 || !$notBefore) {
6666
$sinceId = $this->itemsDao->lowestIdOfInterest() - 1;
6767
// only send 1 day worth of items
68-
$notBefore = new \DateTime();
69-
$notBefore->setTimeZone(new \DateTimeZone(date_default_timezone_get()));
70-
$notBefore->sub(new \DateInterval('P1D'));
71-
$notBefore->setTimeZone(new \DateTimeZone(date_default_timezone_get()));
68+
$notBefore = new \DateTimeImmutable();
69+
$notBefore = $notBefore->setTimeZone(new \DateTimeZone(date_default_timezone_get()));
70+
$notBefore = $notBefore->sub(new \DateInterval('P1D'));
71+
$notBefore = $notBefore->setTimeZone(new \DateTimeZone(date_default_timezone_get()));
7272
}
7373

7474
$itemsHowMany = $this->configuration->itemsPerpage;

src/controllers/Rss.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -96,7 +96,7 @@ public function rss(): void {
9696
}
9797

9898
if ($newestEntryDate === null) {
99-
$newestEntryDate = new \DateTime();
99+
$newestEntryDate = new \DateTimeImmutable();
100100
}
101101
$this->feedWriter->setDate($newestEntryDate);
102102

src/daos/ItemOptions.php

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@
44

55
namespace daos;
66

7-
use DateTime;
7+
use DateTimeImmutable;
88

99
/**
1010
* Object holding parameters for querying items.
@@ -24,13 +24,13 @@ final class ItemOptions {
2424
public ?int $pageSize = null;
2525

2626
/** @readonly */
27-
public ?DateTime $fromDatetime = null;
27+
public ?DateTimeImmutable $fromDatetime = null;
2828

2929
/** @readonly */
3030
public ?int $fromId = null;
3131

3232
/** @readonly */
33-
public ?DateTime $updatedSince = null;
33+
public ?DateTimeImmutable $updatedSince = null;
3434

3535
/** @readonly */
3636
public ?string $tag = null;
@@ -71,15 +71,15 @@ public static function fromUser(array $data): self {
7171
}
7272

7373
if (isset($data['fromDatetime']) && is_string($data['fromDatetime']) && strlen($data['fromDatetime']) > 0) {
74-
$options->fromDatetime = new \DateTime($data['fromDatetime']);
74+
$options->fromDatetime = new \DateTimeImmutable($data['fromDatetime']);
7575
}
7676

7777
if (isset($data['fromId']) && is_numeric($data['fromId'])) {
7878
$options->fromId = (int) $data['fromId'];
7979
}
8080

8181
if (isset($data['updatedsince']) && is_string($data['updatedsince']) && strlen($data['updatedsince']) > 0) {
82-
$options->updatedSince = new \DateTime($data['updatedsince']);
82+
$options->updatedSince = new \DateTimeImmutable($data['updatedsince']);
8383
}
8484

8585
if (isset($data['tag']) && is_string($data['tag']) && strlen($tag = trim($data['tag'])) > 0) {

src/daos/Items.php

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@
44

55
namespace daos;
66

7-
use DateTime;
7+
use DateTimeImmutable;
88
use DateTimeImmutable;
99
use helpers\Authentication;
1010

@@ -60,7 +60,7 @@ public function updateLastSeen(array $itemIds): void {
6060
$this->backend->updateLastSeen($itemIds);
6161
}
6262

63-
public function cleanup(?DateTime $minDate): void {
63+
public function cleanup(?DateTimeImmutable $minDate): void {
6464
$this->backend->cleanup($minDate);
6565
}
6666

@@ -69,7 +69,7 @@ public function cleanup(?DateTime $minDate): void {
6969
*
7070
* @param ItemOptions $options search, offset and filter params
7171
*
72-
* @return array<array{id: int, datetime: DateTime, title: string, content: string, unread: bool, starred: bool, source: int, thumbnail: string, icon: string, uid: string, link: string, updatetime: DateTime, author: string, sourcetitle: string, tags: string[]}> items as array
72+
* @return array<array{id: int, datetime: DateTimeImmutable, title: string, content: string, unread: bool, starred: bool, source: int, thumbnail: string, icon: string, uid: string, link: string, updatetime: DateTimeImmutable, author: string, sourcetitle: string, tags: string[]}> items as array
7373
*/
7474
public function get(ItemOptions $options): array {
7575
$items = $this->backend->get($options);
@@ -107,7 +107,7 @@ public function hasMore(): bool {
107107
return $this->backend->hasMore();
108108
}
109109

110-
public function sync(int $sinceId, DateTime $notBefore, DateTime $since, int $howMany): array {
110+
public function sync(int $sinceId, DateTimeImmutable $notBefore, DateTimeImmutable $since, int $howMany): array {
111111
return $this->backend->sync($sinceId, $notBefore, $since, $howMany);
112112
}
113113

@@ -147,7 +147,7 @@ public function lastUpdate(): ?DateTimeImmutable {
147147
return $this->backend->lastUpdate();
148148
}
149149

150-
public function statuses(DateTime $since): array {
150+
public function statuses(DateTimeImmutable $since): array {
151151
return $this->backend->statuses($since);
152152
}
153153

src/daos/ItemsInterface.php

Lines changed: 10 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@
44

55
namespace daos;
66

7-
use DateTime;
7+
use DateTimeImmutable;
88
use DateTimeImmutable;
99
use helpers\HtmlString;
1010

@@ -73,16 +73,16 @@ public function updateLastSeen(array $itemIds): void;
7373
/**
7474
* cleanup orphaned and old items
7575
*
76-
* @param ?DateTime $date date to delete all items older than this value
76+
* @param ?DateTimeImmutable $date date to delete all items older than this value
7777
*/
78-
public function cleanup(?DateTime $date): void;
78+
public function cleanup(?DateTimeImmutable $date): void;
7979

8080
/**
8181
* returns items
8282
*
8383
* @param ItemOptions $options search, offset and filter params
8484
*
85-
* @return array<array{id: int, datetime: DateTime, title: string, content: string, unread: bool, starred: bool, source: int, thumbnail: string, icon: string, uid: string, link: string, updatetime: DateTime, author: string, sourcetitle: string, tags: string[]}> items as array
85+
* @return array<array{id: int, datetime: DateTimeImmutable, title: string, content: string, unread: bool, starred: bool, source: int, thumbnail: string, icon: string, uid: string, link: string, updatetime: DateTimeImmutable, author: string, sourcetitle: string, tags: string[]}> items as array
8686
*/
8787
public function get(ItemOptions $options): array;
8888

@@ -96,12 +96,12 @@ public function hasMore(): bool;
9696
* Obtain new or changed items in the database for synchronization with clients.
9797
*
9898
* @param int $sinceId id of last seen item
99-
* @param DateTime $notBefore cut off time stamp
100-
* @param DateTime $since timestamp of last seen item
99+
* @param DateTimeImmutable $notBefore cut off time stamp
100+
* @param DateTimeImmutable $since timestamp of last seen item
101101
*
102-
* @return array<array{id: int, datetime: DateTime, title: string, content: string, unread: bool, starred: bool, source: int, thumbnail: string, icon: string, uid: string, link: string, updatetime: DateTime, author: string, sourcetitle: string, tags: string[]}> of items
102+
* @return array<array{id: int, datetime: DateTimeImmutable, title: string, content: string, unread: bool, starred: bool, source: int, thumbnail: string, icon: string, uid: string, link: string, updatetime: DateTimeImmutable, author: string, sourcetitle: string, tags: string[]}> of items
103103
*/
104-
public function sync(int $sinceId, DateTime $notBefore, DateTime $since, int $howMany): array;
104+
public function sync(int $sinceId, DateTimeImmutable $notBefore, DateTimeImmutable $since, int $howMany): array;
105105

106106
/**
107107
* Lowest id of interest
@@ -171,11 +171,11 @@ public function lastUpdate(): ?DateTimeImmutable;
171171
/**
172172
* returns the statuses of items last update
173173
*
174-
* @param DateTime $since minimal date of returned items
174+
* @param DateTimeImmutable $since minimal date of returned items
175175
*
176176
* @return array<array{id: int, unread: bool, starred: bool}> of unread, starred, etc. status of specified items
177177
*/
178-
public function statuses(DateTime $since): array;
178+
public function statuses(DateTimeImmutable $since): array;
179179

180180
/**
181181
* bulk update of item status

src/daos/StatementsInterface.php

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -93,11 +93,9 @@ public static function bool(bool $bool): string;
9393
* Convert a date into a representation suitable for comparison by
9494
* the database engine.
9595
*
96-
* @param \DateTime $date datetime
97-
*
9896
* @return string representation of datetime
9997
*/
100-
public static function datetime(\DateTime $date): string;
98+
public static function datetime(\DateTimeImmutable $date): string;
10199

102100
/**
103101
* Ensure row values have the appropriate PHP type. This assumes we are

src/daos/mysql/Items.php

Lines changed: 11 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@
66

77
use daos\DatabaseInterface;
88
use daos\ItemOptions;
9-
use DateTime;
9+
use DateTimeImmutable;
1010
use DateTimeImmutable;
1111
use helpers\Configuration;
1212
use helpers\HtmlString;
@@ -206,9 +206,9 @@ public function updateLastSeen(array $itemIds): void {
206206
/**
207207
* cleanup orphaned and old items
208208
*
209-
* @param ?DateTime $date date to delete all items older than this value
209+
* @param ?DateTimeImmutable $date date to delete all items older than this value
210210
*/
211-
public function cleanup(?DateTime $date): void {
211+
public function cleanup(?DateTimeImmutable $date): void {
212212
$this->database->exec('DELETE FROM ' . $this->configuration->dbPrefix . 'items
213213
WHERE source NOT IN (
214214
SELECT id FROM ' . $this->configuration->dbPrefix . 'sources)');
@@ -226,7 +226,7 @@ public function cleanup(?DateTime $date): void {
226226
*
227227
* @param ItemOptions $options search, offset and filter params
228228
*
229-
* @return array<array{id: int, datetime: DateTime, title: string, content: string, unread: bool, starred: bool, source: int, thumbnail: string, icon: string, uid: string, link: string, updatetime: DateTime, author: string, sourcetitle: string, tags: string[]}> items as array
229+
* @return array<array{id: int, datetime: DateTimeImmutable, title: string, content: string, unread: bool, starred: bool, source: int, thumbnail: string, icon: string, uid: string, link: string, updatetime: DateTimeImmutable, author: string, sourcetitle: string, tags: string[]}> items as array
230230
*/
231231
public function get(ItemOptions $options): array {
232232
$params = [];
@@ -375,12 +375,12 @@ public function hasMore(): bool {
375375
* Obtain new or changed items in the database for synchronization with clients.
376376
*
377377
* @param int $sinceId id of last seen item
378-
* @param DateTime $notBefore cut off time stamp
379-
* @param DateTime $since timestamp of last seen item
378+
* @param DateTimeImmutable $notBefore cut off time stamp
379+
* @param DateTimeImmutable $since timestamp of last seen item
380380
*
381-
* @return array<array{id: int, datetime: DateTime, title: string, content: string, unread: bool, starred: bool, source: int, thumbnail: string, icon: string, uid: string, link: string, updatetime: DateTime, author: string, sourcetitle: string, tags: string[]}> of items
381+
* @return array<array{id: int, datetime: DateTimeImmutable, title: string, content: string, unread: bool, starred: bool, source: int, thumbnail: string, icon: string, uid: string, link: string, updatetime: DateTimeImmutable, author: string, sourcetitle: string, tags: string[]}> of items
382382
*/
383-
public function sync(int $sinceId, DateTime $notBefore, DateTime $since, int $howMany): array {
383+
public function sync(int $sinceId, DateTimeImmutable $notBefore, DateTimeImmutable $since, int $howMany): array {
384384
$query = 'SELECT
385385
items.id, datetime, items.title AS title, content, unread, starred, source, thumbnail, icon, uid, link, updatetime, author, sources.title as sourcetitle, sources.tags as tags
386386
FROM ' . $this->configuration->dbPrefix . 'items AS items, ' . $this->configuration->dbPrefix . 'sources AS sources
@@ -575,11 +575,11 @@ public function lastUpdate(): ?DateTimeImmutable {
575575
/**
576576
* returns the statuses of items last update
577577
*
578-
* @param DateTime $since minimal date of returned items
578+
* @param DateTimeImmutable $since minimal date of returned items
579579
*
580580
* @return array<array{id: int, unread: bool, starred: bool}> of unread, starred, etc. status of specified items
581581
*/
582-
public function statuses(DateTime $since): array {
582+
public function statuses(DateTimeImmutable $since): array {
583583
$res = $this->database->exec(
584584
'SELECT id, unread, starred
585585
FROM ' . $this->configuration->dbPrefix . 'items
@@ -627,7 +627,7 @@ public function bulkStatusUpdate(array $statuses): void {
627627

628628
// sanitize update time
629629
if (array_key_exists('datetime', $status)) {
630-
$updateDate = new \DateTime($status['datetime']);
630+
$updateDate = new \DateTimeImmutable($status['datetime']);
631631
} else {
632632
$updateDate = null;
633633
}

src/daos/mysql/Statements.php

Lines changed: 3 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -128,13 +128,11 @@ public static function bool(bool $bool): string {
128128
* Convert a date into a representation suitable for comparison by
129129
* the database engine.
130130
*
131-
* @param \DateTime $date datetime
132-
*
133131
* @return string representation of datetime
134132
*/
135-
public static function datetime(\DateTime $date): string {
133+
public static function datetime(\DateTimeImmutable $date): string {
136134
// mysql supports ISO8601 datetime comparisons
137-
return $date->format(\DateTime::ATOM);
135+
return $date->format(\DateTimeImmutable::ATOM);
138136
}
139137

140138
/**
@@ -179,7 +177,7 @@ public static function ensureRowTypes(array $rows, array $expectedRowTypes): arr
179177
}
180178
break;
181179
case DatabaseInterface::PARAM_DATETIME:
182-
$value = new \DateTime($row[$columnIndex]);
180+
$value = new \DateTimeImmutable($row[$columnIndex]);
183181
break;
184182
default:
185183
$value = null;

src/daos/pgsql/Statements.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -104,7 +104,7 @@ public static function ensureRowTypes(array $rows, array $expectedRowTypes): arr
104104
}
105105
break;
106106
case DatabaseInterface::PARAM_DATETIME:
107-
$value = new \DateTime($row[$columnIndex]);
107+
$value = new \DateTimeImmutable($row[$columnIndex]);
108108
break;
109109
default:
110110
$value = null;

0 commit comments

Comments
 (0)