我想为我的门票生成一个唯一的门票 ID。但如何让doctrine生成唯一的id呢?
/**
* @ORM\Column(name="id", type="integer")
* @ORM\Id()
* @ORM\GeneratedValue(strategy="AUTO")
*/
protected $id;
再解释一下:
从版本 2.3 开始,您只需将以下注释添加到您的属性中:
/**
* @ORM\Column(type="guid")
* @ORM\Id
* @ORM\GeneratedValue(strategy="UUID")
*/
protected $id;
使用自定义的GenerateValue策略:
1. 在您的实体类中:
/**
* @ORM\Id
* @ORM\Column(type="integer")
* @ORM\GeneratedValue(strategy="CUSTOM")
* @ORM\CustomIdGenerator(class="AppBundle\Doctrine\RandomIdGenerator")
*/
protected $id;
2.然后创建包含内容的文件
AppBundle/Doctrine/RandomIdGenerator.php
namespace AppBundle\Doctrine;
use Doctrine\ORM\Id\AbstractIdGenerator;
class RandomIdGenerator extends AbstractIdGenerator
{
public function generate(\Doctrine\ORM\EntityManager $em, $entity)
{
$entity_name = $em->getClassMetadata(get_class($entity))->getName();
// Id must be 6 digits length, so range is 100000 - 999999
$min_value = 100000;
$max_value = 999999;
$max_attempts = $min_value - $max_value;
$attempt = 0;
while (true) {
$id = mt_rand($min_value, $max_value);
$item = $em->find($entity_name, $id);
// Look in scheduled entity insertions (persisted queue list), too
if (!$item) {
$persisted = $em->getUnitOfWork()->getScheduledEntityInsertions();
$ids = array_map(function ($o) { return $o->getId(); }, $persisted);
$item = array_search($id, $ids);
}
if (!$item) {
return $id;
}
// Should we stop?
$attempt++;
if ($attempt > $max_attempts) {
throw new \Exception('RandomIdGenerator worked hardly, but failed to generate unique ID :(');
}
}
}
}
您可以使用 PrePersist 注释,如下所示:
/**
* @ORM\PrePersist()
*/
public function preSave() {
$this->id = uniqid();
}
顾名思义,它将在对象持久化到数据库之前运行。
对于唯一 id,我只需使用本机 php uniqid() 函数 http://php.net/manual/en/function.uniqid.php 它将返回 13 个字符。要仅获取 6 个字符,请参阅此 PHP Ticket ID Generation
在 $id 属性中,我认为您还需要删除此行以防止自动生成它的值:
@ORM\GeneratedValue(strategy="AUTO")
Doctrine 会将此字段视为您的主键(因为
@Id
注释),因此该字段已经是唯一的。如果您在 @GeneratedValue
策略上有 AUTO
注释,Doctrine 将确定在数据库平台上使用哪种策略。在 MySql 上它将默认为 IDENTITY
,然后该字段将是 auto_increment
。
可以如下编写不带括号的id注释。
虽然我支持 Jonhathan 建议的 UUID 方法,但您可能更喜欢更短、更易读的标识符。在这种情况下,您可以使用 ShortId Doctrine 包。