Automatic values for updated_at, created_at in Doctrine

前端 未结 5 1317
感动是毒
感动是毒 2021-01-31 07:42

I want to make fields updated_at and created_at in my Doctrine entities to update automatically.

In Ruby on Rails models there

相关标签:
5条回答
  • 2021-01-31 08:02

    The most convinient solution for me is Timestampable feature of StofDoctrineExtensionsBundle.

    Simple configuration and later you are able to make fields createdAt and updatedAt of Entity filled out automatically by adding two simple annotations like:

    @Gedmo\Mapping\Annotation\Timestampable(on="create")

    and/or

    @Gedmo\Mapping\Annotation\Timestampable(on="update")

    e.g.

    /**
     * @var \DateTime
     * @Gedmo\Mapping\Annotation\Timestampable(on="create")
     * @Doctrine\ORM\Mapping\Column(type="datetime")
     */
    protected $createdAt;
    
    /**
     * @var \DateTime
     * @Gedmo\Mapping\Annotation\Timestampable(on="update")
     * @Doctrine\ORM\Mapping\Column(type="datetime")
     */
    protected $updatedAt;
    

    Without any redundant code in pure PHP.

    0 讨论(0)
  • 2021-01-31 08:03

    I would suggest using timestampable trait

    https://symfonycasts.com/screencast/symfony4-doctrine/timestampable

    use Gedmo\Timestampable\Traits\TimestampableEntity;
    
    class Article
    {
        use TimestampableEntity;
    }
    

    will add all appropriate functionality automatically

    0 讨论(0)
  • 2021-01-31 08:08
    1. You can call $this->setCreatedAt(new \DateTime()) in __construct method.
    2. You can use Life Cycle Callbacks
    /**
     * @ORM\PrePersist
     * @ORM\PreUpdate
    */
    public function updatedTimestamps(): void
    {
        $this->setUpdatedAt(new \DateTime('now'));    
        if ($this->getCreatedAt() === null) {
            $this->setCreatedAt(new \DateTime('now'));
        }
    }
    

    And don't forget to add into entity class notation: @ORM\HasLifecycleCallbacks

    0 讨论(0)
  • 2021-01-31 08:09

    You can implement it as a trait as well - like this:

    <?php
    
    namespace App\Entity\Traits;
    
    use DateTime;
    use DateTimeInterface;
    use Exception;
    
    /**
     * Trait TimeStampableTrait
     * @package App\Entity\Trait
     */
    trait TimeStampableTrait
    {
        /**
         * @ORM\Column(type="datetime")
         */
        private $createdAt;
    
        /**
         * @ORM\Column(type="datetime")
         */
        private $updatedAt;
    
        /**
         * @return DateTimeInterface|null
         * @throws Exception
         */
        public function getCreatedAt(): ?DateTimeInterface
        {
            return $this->createdAt ?? new DateTime();
        }
    
        /**
         * @param DateTimeInterface $createdAt
         * @return $this
         */
        public function setCreatedAt(DateTimeInterface $createdAt): self
        {
            $this->createdAt = $createdAt;
    
            return $this;
        }
    
        /**
         * @return DateTimeInterface|null
         */
        public function getUpdatedAt(): ?DateTimeInterface
        {
            return $this->updatedAt ?? new DateTime();
        }
    
        /**
         * @param DateTimeInterface $updatedAt
         * @return $this
         */
        public function setUpdatedAt(DateTimeInterface $updatedAt): self
        {
            $this->updatedAt = $updatedAt;
    
            return $this;
        }
    
        /**
         * @ORM\PrePersist()
         * @ORM\PreUpdate()
         */
        public function updateTimestamps(): void
        {
            $now = new DateTime();
            $this->setUpdatedAt($now);
            if ($this->getId() === null) {
                $this->setCreatedAt($now);
            }
        }
    }
    

    Add this trait to your entity (and don't forget @ORM\HasLifecycleCallbacks() notation):

    <?php
    
    namespace App\Entity;
    
    use App\Entity\Traits\TimeStampableTrait;
    use Doctrine\ORM\Mapping as ORM;
    
    /**
     * @ORM\Entity(repositoryClass="App\Repository\MyEntityRepository")
     * @ORM\HasLifecycleCallbacks()
     */
    class MyEntity
    {
        use TimeStampableTrait;
    }
    
    0 讨论(0)
  • 2021-01-31 08:25

    This is another option if you would ever want to handle them separately.

    use Doctrine\ORM\Mapping as ORM;
    
    /**
     * @ORM\Entity
     * @ORM\Table(name="person")
     * @ORM\HasLifecycleCallbacks
     */
    class Person
    {
        ..........
    
        /**
         * @var datetime $created
         *
         * @ORM\Column(type="datetime")
         */
        protected $created;
    
        /**
         * @var datetime $updated
         * 
         * @ORM\Column(type="datetime", nullable = true)
         */
        protected $updated;
    
    
        /**
         * Gets triggered only on insert
    
         * @ORM\PrePersist
         */
        public function onPrePersist()
        {
            $this->created = new \DateTime("now");
        }
    
        /**
         * Gets triggered every time on update
    
         * @ORM\PreUpdate
         */
        public function onPreUpdate()
        {
            $this->updated = new \DateTime("now");
        }
    
        ..........
    }
    
    0 讨论(0)
提交回复
热议问题