feat(shared) : add Timestampable + Blamable Shared pattern (Trait + Interfaces + Subscriber + test)
This commit is contained in:
@@ -0,0 +1,65 @@
|
||||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
namespace App\Shared\Infrastructure\Doctrine;
|
||||
|
||||
use App\Shared\Domain\Contract\BlamableInterface;
|
||||
use App\Shared\Domain\Contract\TimestampableInterface;
|
||||
use DateTimeImmutable;
|
||||
use Doctrine\Bundle\DoctrineBundle\Attribute\AsDoctrineListener;
|
||||
use Doctrine\ORM\Event\PrePersistEventArgs;
|
||||
use Doctrine\ORM\Event\PreUpdateEventArgs;
|
||||
use Doctrine\ORM\Events;
|
||||
use Symfony\Bundle\SecurityBundle\Security;
|
||||
use Symfony\Component\Security\Core\User\UserInterface;
|
||||
|
||||
/**
|
||||
* Listener Doctrine global qui remplit automatiquement les colonnes
|
||||
* Timestampable + Blamable.
|
||||
*
|
||||
* Pattern aligne sur AuditListener (cf.
|
||||
* src/Module/Core/Infrastructure/Doctrine/AuditListener.php) : declare via
|
||||
* #[AsDoctrineListener], auto-wire par le DoctrineBundle.
|
||||
*
|
||||
* Regle Blamable : si aucun utilisateur n'est authentifie (CLI, cron,
|
||||
* migration), les FK `created_by` / `updated_by` restent a null. L'affichage
|
||||
* front gere le libelle « Systeme » pour null.
|
||||
*/
|
||||
#[AsDoctrineListener(event: Events::prePersist)]
|
||||
#[AsDoctrineListener(event: Events::preUpdate)]
|
||||
final class TimestampableBlamableSubscriber
|
||||
{
|
||||
public function __construct(private readonly Security $security) {}
|
||||
|
||||
public function prePersist(PrePersistEventArgs $args): void
|
||||
{
|
||||
$entity = $args->getObject();
|
||||
$now = new DateTimeImmutable();
|
||||
$user = $this->security->getUser();
|
||||
|
||||
if ($entity instanceof TimestampableInterface) {
|
||||
$entity->setCreatedAt($now);
|
||||
$entity->setUpdatedAt($now);
|
||||
}
|
||||
|
||||
if ($entity instanceof BlamableInterface && $user instanceof UserInterface) {
|
||||
$entity->setCreatedBy($user);
|
||||
$entity->setUpdatedBy($user);
|
||||
}
|
||||
}
|
||||
|
||||
public function preUpdate(PreUpdateEventArgs $args): void
|
||||
{
|
||||
$entity = $args->getObject();
|
||||
$user = $this->security->getUser();
|
||||
|
||||
if ($entity instanceof TimestampableInterface) {
|
||||
$entity->setUpdatedAt(new DateTimeImmutable());
|
||||
}
|
||||
|
||||
if ($entity instanceof BlamableInterface && $user instanceof UserInterface) {
|
||||
$entity->setUpdatedBy($user);
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user