Doctrine2没有将序列设置为id列的默认值(postgres)

时间:2011-05-20 18:30:21

标签: php postgresql sequence doctrine-orm

只是一个简单的例子:如果我想在postgres中创建一个带有自动填充id的表,我运行这个sql:

CREATE SEQUENCE person_id_seq  START 1;

CREATE TABLE person (
    id         integer PRIMARY KEY DEFAULT nextval('person_id_seq'),
    name       varchar(100) NOT NULL
);

在学说中我设置了所有属性

class Person {

/**
 * @Id
 * @Column(type="integer", nullable=false)
 * @GeneratedValue(strategy="SEQUENCE")
 * @SequenceGenerator(sequenceName="person_id_seq", initialValue=1, allocationSize=100)
 */
private $id;

但是当我生成sql(php doctrine orm:schema-tool:create --dump-sql)时,我明白了:

CREATE TABLE person (
    id INT NOT NULL,
    name VARCHAR(100) NOT NULL
);
CREATE SEQUENCE person_id_seq INCREMENT BY 100 MINVALUE 1 START 1

但不要将其设为默认

\ d person

      Column       |              Type              | Modifiers
-------------------+--------------------------------+-----------
 id                | integer                        | not null
...
..
.

4 个答案:

答案 0 :(得分:24)

来自fine manual

  

<强> 4.8.1。标识符生成策略
  ...
  AUTO(默认值):告诉Doctrine选择所使用的数据库平台首选的策略。首选策略是MySQL,SQLite和MsSQL的IDENTITY以及Oracle和PostgreSQL的SEQUENCE。该策略提供了完全的可移植性   ...
  IDENTITY:告诉Doctrine在数据库中使用特殊标识列,这些列在插入行时生成值。此策略目前不提供完全可移植性,并受以下平台支持:MySQL / SQLite(AUTO_INCREMENT),MSSQL(IDENTITY)和PostgreSQL(SERIAL)。

他们建议AUTO以获得最大的可移植性:

/**
 * @Id
 * @Column(type="integer", nullable=false)
 * @GeneratedValue
 */

那应该为你创建和连接一个序列。另一种方法是使用serial策略要求IDENTITY列:

/**
 * @Id
 * @Column(type="integer", nullable=false)
 * @GeneratedValue(strategy="IDENTITY")
 */

这个应该创建id列作为serial类型,PostgreSQL将创建序列并为您设置默认值。

文档表明您正在做的事情应该有效,但文档通常只提供现实的简化版本。

尝试使用strategy="AUTO"。如果这不起作用,请尝试strategy="IDENTITY"

答案 1 :(得分:4)

我今天遇到了这个问题,我发现:

  • IDENTITY工作正常,因为它为PostgreSQL使用SERIAL类型,它自动创建相关序列并将默认值设置为nextval(序列)

  • AUTO创建表格然后创建相关序列,但不设置id列的默认值。 可以通过添加以下代码来设置:

    /**
     * Webpage's ID
     *
     * @ORM\Id
     * @ORM\Column(type="integer", options={"default"="nextval('webpages_id_seq'::regclass)"})
     * @ORM\GeneratedValue(strategy="IDENTITY")
     */
    protected $id;
    

    但不幸的是Doctrine首先创建表,所以我们需要交换SQL代码创建表和序列,以便首先创建序列

  • SEQUENCE与AUTO

  • 的作用相同

答案 2 :(得分:0)

我也遇到,序列已生成,但未分配。

所以,这是bin/console doctrine:schema:create --dump-sql

的输出
CREATE TABLE data_sample (id INT NOT NULL, hashvalue VARCHAR(64) DEFAULT NULL, date TIMESTAMP(0) WITHOUT TIME ZONE NOT NULL, refdate TIMESTAMP(0) WITHOUT TIME ZONE NOT NULL, value NUMERIC(20, 2) NOT NULL, PRIMARY KEY(id));

CREATE SEQUENCE data_sample_id_seq INCREMENT BY 1 MINVALUE 1 START 1;

答案 3 :(得分:0)

XML PostgreSQL Serial 类型示例

<id name="addressId" type="integer" column="address_id">
  <generator strategy="IDENTITY"/>
  <options>
    <option name="default">nextval('decide_config.address_address_id_seq'::regclass)</option>
  </options>
</id>