Я не знаю, какой способ хранить временную метку в базе данных. Я хочу сохранить всю дату часами и секундами, но она хранит только дату (например, 2012-07-14), и я хочу хранить 2012-07-14 HH: MM: SS. Я использую объект dateTime. Вот код:
В контроллере:
$user->setCreated(new \DateTime());
В объекте:
/** * @var date $created * * @ORM\Column(name="created", type="date") */ private $created;
Лучше ли хранить дату и время отдельно в базе данных? или лучше хранить все вместе, как ГГГГ-ММ-ДД ЧЧ: ММ: СС? Затем я буду сравнивать даты и рассчитать оставшиеся времена, так что это важно для упрощения операций позже. Так что ты думаешь ? может кто-нибудь мне помочь?
Лучший способ сохранить временную метку в базе данных, очевидно, использовать столбец timestamp, если ваша база данных поддерживает этот тип. И так как вы можете установить этот столбец для autoupdate при создании, вам даже не нужно предоставлять ему сеттер.
Существует временное расширение поведения для Doctrine 2, которое делает именно это с пользовательской стороны:
Временное поведение автоматизирует обновление полей даты в ваших сущностях или документах. Он работает через аннотации и может обновлять поля при создании, обновлении или даже при изменении значения определенного свойства.
Особенности:
- Автоматическое предварительное обновление поля даты при создании, обновлении и даже при изменении свойств записи
- Поддержка ORM и ODM с использованием того же прослушивателя
- Конкретные аннотации для свойств и отсутствие интерфейса
- Может реагировать на конкретные свойства или изменения отношения к определенному значению
- Может быть вложен в другое поведение
- Аннотация, поддержка отображения Ямл и Xml для расширений
При таком поведении все, что вам нужно сделать, это изменить аннотацию на
/** * @var datetime $created * * @Gedmo\Timestampable(on="create") * @ORM\Column(type="datetime") */ private $created;
Тогда вам не нужно вызывать setCreated
в вашем коде. Поле будет установлено автоматически, когда Entity будет создан в первый раз.
Чтобы сохранить дату создания без использования временного поведения доктрины, вы также можете использовать @ORM\HasLifecycleCallbacks
LifeCycle , добавив аннотацию @ORM\HasLifecycleCallbacks
при объявлении класса. Вот что будет работать в вашем случае для хранения ГГГГ-ММ-ДД ЧЧ: ММ: СС в базе данных.
/** * @ORM\Entity * @ORM\HasLifecycleCallbacks * @ORM\Table(name="yourTable") */ class Nasy { /** * @ORM\Column(name="created", type="string", length=255) */ private $created; /** * @ORM\PrePersist */ public function doStuffOnPrePersist() { $this->created = date('Ymd H:i:s'); }
Наконец, если у вас есть проблема с часовым поясом, вы можете установить часовой пояс в сеансе, используя прослушиватель событий при входе в систему. Мэтт Дролетт сделал замечательную работу в своем блоге. Вероятно, вы всегда будете хранить время в часовом поясе, на котором находится ваш сервер. Затем вы используете часовой пояс, установленный в сеансе, чтобы отобразить нужное время для пользователя. Удачи.
Основываясь на ответе @ Пратта, я сделал это. У меня есть 2 поля в моих сущностях, один для созданных и один для модифицированных.
/** * @ORM\Column(type="datetime") */ protected $created_at; /** * @ORM\Column(type="datetime") */ protected $modified_at;
И затем, используя аннотацию, я вызываю это на prePersist и preUpdate
/** * @ORM\PrePersist * @ORM\PreUpdate */ public function updatedTimestamps() { $this->setModifiedAt(new \DateTime(date('Ymd H:i:s'))); if($this->getCreatedAt() == null) { $this->setCreatedAt(new \DateTime(date('Ymd H:i:s'))); } }
Функция может быть разбита на 2 функции, которые создаются для обновления, но это работает, поэтому я не вижу причин для дополнительного кода, когда он работает правильно.
Вы можете использовать @Version следующим образом:
/** * @var date $created * * @ORM\Column(name="created", type="datetime") * @ORM\Version */ private $created;
Это будет работать только с типом datetime.