最近在項(xiàng)目中,我們使用doctrine orm管理數(shù)據(jù)庫,其中涉及大量的日期時(shí)間字段。由于datetime對(duì)象的特性,在某些情況下,我們無意中修改了日期時(shí)間值,導(dǎo)致數(shù)據(jù)不一致,甚至程序崩潰。這種問題難以調(diào)試,嚴(yán)重影響了開發(fā)效率。
例如,在獲取實(shí)體的創(chuàng)建時(shí)間后,如果不小心修改了這個(gè)DateTime對(duì)象,數(shù)據(jù)庫中的數(shù)據(jù)也會(huì)被修改,而我們并沒有通過Doctrine的持久化機(jī)制進(jìn)行更新,這就會(huì)導(dǎo)致數(shù)據(jù)與數(shù)據(jù)庫不同步。 更糟糕的是,這種錯(cuò)誤可能在代碼運(yùn)行一段時(shí)間后才暴露出來,排查起來非常困難。
為了解決這個(gè)問題,我們決定使用不可變的DateTimeImmutable對(duì)象替代DateTime對(duì)象。 幸運(yùn)的是,我們找到了vasek-purchart/doctrine-date-time-immutable-types這個(gè)優(yōu)秀的composer庫。 這個(gè)庫為Doctrine提供了DateTimeImmutable、DateImmutable、TimeImmutable和DateTimeTzImmutable等類型,完美解決了我們的問題。
安裝這個(gè)庫非常簡(jiǎn)單,只需要使用Composer:
composer require vasek-purchart/doctrine-date-time-immutable-types
接下來,我們需要注冊(cè)這些新的類型:
use DoctrineDBALTypesType;use VasekPurchartDoctrineTypeDateTimeImmutableDateImmutableType;use VasekPurchartDoctrineTypeDateTimeImmutableDateTimeImmutableType;use VasekPurchartDoctrineTypeDateTimeImmutableDateTimeTzImmutableType;use VasekPurchartDoctrineTypeDateTimeImmutableTimeImmutableType;Type::addType(DateImmutableType::NAME, DateImmutableType::class);Type::addType(DateTimeImmutableType::NAME, DateTimeImmutableType::class);Type::addType(DateTimeTzImmutableType::NAME, DateTimeTzImmutableType::class);Type::addType(TimeImmutableType::NAME, TimeImmutableType::class);
你也可以選擇覆蓋Doctrine默認(rèn)的日期時(shí)間類型:
Type::overrideType(Type::DATETIMETZ, DateTimeTzImmutableType::class);
最后,在實(shí)體映射中,將字段類型改為datetime_immutable (或者date_immutable, time_immutable, datetimetz_immutable):
<?phpuse DoctrineORMMapping as ORM;/<strong> <em> @ORMEntity() </em>/class LogRow{ /</strong> <em> @ORMColumn(type="datetime_immutable") </em> @var DateTimeImmutable */ private $createdDate; public function getCreatedDate(): DateTimeImmutable { return $this->createdDate; }}
現(xiàn)在,即使你嘗試修改getCreatedDate()返回的DateTimeImmutable對(duì)象,也不會(huì)影響到數(shù)據(jù)庫中的數(shù)據(jù),因?yàn)镈ateTimeImmutable對(duì)象是不可變的。 這極大地提升了代碼的健壯性,避免了因意外修改日期時(shí)間字段而導(dǎo)致的bug。
通過使用vasek-purchart/doctrine-date-time-immutable-types,我們成功地解決了DateTime對(duì)象的可變性問題,顯著提高了代碼的可維護(hù)性和可靠性。 在處理日期時(shí)間相關(guān)的業(yè)務(wù)邏輯時(shí),強(qiáng)烈推薦使用這個(gè)庫,以避免潛在的錯(cuò)誤和提高開發(fā)效率。 此外,如果你正在使用symfony框架,還可以考慮使用vasek-purchart/doctrine-date-time-immutable-types-bundle,它可以更方便地集成這個(gè)庫。 記住,選擇合適的工具,可以讓你事半功倍!