Postgresql:'uuid'的自动生成不适用于Entity Framework

时间:2014-05-19 15:22:41

标签: sql entity-framework postgresql identity sql-insert

我使用' PostgreSql'在.NET中使用实体框架(POCO方法)。

我的目标是在数据库端创建Id(uuid)的数据库中创建一条新记录,并将生成的Id检索到服务器(这种情况与SQL Server完美配合)。

我的模型看起来像:

public class MyClass
{
   [Key]
   [DatabaseGenerated(DatabaseGeneratedOption.Identity)]
   public Guid Id { get; set; }

   public string Name { get; set; }
}

在PostgreSql专栏中' Id'有默认值' uuid_generate_v4()'

当我尝试使用EF向数据库添加新对象时,出现以下错误:

A null store-generated value was returned for a non-nullable member 'Id' of type...

我检查EF发送给PostgreSQL的SQL查询:

INSERT INTO "public"."MyClass"("Name") VALUES ("Test");
SELECT currval(pg_get_serial_sequence('"public"."MyClass"', 'Id')) AS "Id"

第一个看起来不错。如果我执行它,则在DB中创建新行(使用新生成的id) 第二个返回NULL,列的名称是' Id bigint'。 看来,此功能仅适用于数字ID。

是否可以使其适用于自动生成的“uuid”列?类型?

3 个答案:

答案 0 :(得分:1)

您没有写下您使用的EF提供商。我认为它是npgsql。

根据最新消息来源,它应该返回Sql Erwin Brandstetter发布:

INSERT INTO public."MyClass"("Name") VALUES ("Test") RETURNING "Id";

以下是sql生成器的相关部分: SqlInsertGenerator classAppendReturning method

我会尝试最新版本的npgsql(甚至可以自己从源代码构建它)。

答案 1 :(得分:0)

使用RETURNING子句简化:

INSERT INTO public."MyClass"("Name") VALUES ("Test") RETURNING "Id";

没有单独的SELECT,因此不会混淆与SELECT中的函数匹配的列的默认值。更简单,更快速,更清洁。

更多细节:
PostgreSQL next value of the sequences?

答案 2 :(得分:0)

我假设你正在使用https://github.com/npgsql/Npgsql

我想知道您使用的是什么版本,因为您可能正在使用源代码构建自己的dll,因为https://github.com/npgsql/Npgsql/pull/91还不是任何版本的一部分......如果您选择了PR91,那么您可能应该这样做樱花挑选这个PR160 https://github.com/npgsql/Npgsql/pull/160可以解决你的问题。