Doctrine ORM увеличивает AUTO_INCREMENT при ошибке MySQL #1062
Создаю сущность в доктрине орм, конфигурация ID такая
#[ORM\Id]
#[ORM\Column(type: Types::INTEGER)]
#[ORM\GeneratedValue]
private int $id;
, у сущности есть уникальные ключи
#[ORM\Column(type: Types::STRING, unique: true)]
private string $username;
#[ORM\Column(type: Types::STRING, unique: true)]
private string $email;
Проблема в том, что если попытаться в транзакции добавить вторую запись с одним и тем же email или username, несмотря на то, что INSERT не выполнится и будет отловлено исключение
"An exception occurred while executing a query: Duplicate entry 'username' for key 'users.username'" и сделано $conn->rollBack()
, AUTO_INCREMENT возрастет. И при следующем добавлении (если до этого удачный INSERT вернул ID = 1) он (ID) будет не 2, а 3.
Как правильно реализовать правильное увеличение и/ или формирование AI?
UPD: + добавил prePersist
public function checkExistingRecords(array $fields, LifecycleEventArgs $args) {
$obj = $args->getObject();
$repository = $args->getObjectManager()->getRepository($obj::class)->findOneBy($fields);
if($repository instanceof $obj) {
throw new EntityAlreadyExistsException($obj::class);
}
}
Ответы (1 шт):
Автор решения: Михаил Сазанов
→ Ссылка
Собственно кому надо, вот ответ (решение)
#[ORM\Id]
#[ORM\Column(type: Types::INTEGER)]
#[ORM\GeneratedValue(strategy: 'CUSTOM')]
#[ORM\CustomIdGenerator(class: IdGenerator::class)]
private int|null $id = null;
<?php
namespace CLB\Database;
use Doctrine\ORM\EntityManager;
use Doctrine\ORM\Id\AbstractIdGenerator;
class IdGenerator extends AbstractIdGenerator
{
public function generate(EntityManager $em, $entity)
{
$table = $em->getClassMetadata($entity::class)->getTableName();
$maxId = $em->getConnection()->createQueryBuilder()
->select('MAX(id)')
->from($table)
->executeQuery()
->fetchOne();
return is_null($maxId) ? 1 : $maxId + 1;
}
}