【问题标题】:'Cannot insert the value NULL into column 'UserId', table 'UserDB.dbo.Users'; column does not allow nulls. INSERT fails [closed]'无法将值 NULL 插入到列 'UserId'、表 'UserDB.dbo.Users' 中;列不允许空值。插入失败[关闭]
【发布时间】:2018-10-05 14:12:22
【问题描述】:

使用 ASP.NET MVC 和实体框架在 SQL Server 中保存数据时出现错误。该错误表示它无法插入具有空主键的数据。我已经将IsIdentity 设置为自动递增 1。

这是代码:

public ActionResult Index(User user)
{
    if (ModelState.IsValid) 
    {
        if (user.UserId != 0) 
            db.Entry(user).State = EntityState.Modified;
        else
            user.IsActive = true;

        db.Users.Add(user);
        db.SaveChanges();
    }

    return View(user);
}

【问题讨论】:

  • 请分享您尝试执行的表创建语句和插入语句。
  • 违反主键约束“PK_Users”。无法在对象“dbo.Users”中插入重复键。重复键值为 (0)。
  • 很难帮你解决这个问题。你声称一件事,你的错误声称另一件事。显然,例外是告诉你真相。
  • 请包括表定义,create table ... 语句。另外,请分享确切的错误。

标签: asp.net sql-server asp.net-mvc entity-framework


【解决方案1】:

这是一个 SQL 的东西。如果您有一个包含IDName 列的表,其中ID 是主键,伴随着标识设置和NOT NULLUNIQUE 约束,插入语句必须看起来像这样:

INSERT INTO [table] (name) values ('Vivek')

这将自动处理 ID 列。但是,这将失败:

INSERT INTO [table] (ID, name) values (NULL, 'Vivek')

它试图告诉数据库您希望ID 列的值为NULL。当然这会失败,因为 NOT NULL 约束。它不同于第一个选项,其中允许数据库使用标识来设置ID 列的值。

现在开始(大概)C# 代码。这里有一个User 对象,它还没有ID 值,因为您只是在创建它。可能这个User类型(不是共享的,所以我只能猜测)对于ID有一个简单的int值,而这个int还没有被初始化(意思是值是default(int),也就是@987654339 @)。现在你去插入记录。 Linq 会生成类似这样的 SQL 语句:

INSERT INTO [table] (ID, name) values (0, 'Vivek')

但是在过去的某个地方,您运行过相同的代码,ID 具有相同的0 值,因此表中已经存在具有该 ID 值的另一条记录。这使 UNIQUE 约束失败,并且 SQL Server(正确地)拒绝 SQL 语句。

要解决此问题,我们将开始将此模型上的 ID 值更改为使用 int? 类型。我知道你可能不希望到处都这样,所以如果它对你有帮助,你实际上可以在这里使用不同的类 (NewUser)。这将允许生成的 SQL 中的 ID 列具有真正的空 (NULL) 值。

但是现在我们遇到了一个新问题:我们最终得到了一个插入,就像我的第二个示例一样。我们看到这还不够;我们需要告诉 linq 在生成的 SQL 中根本不要使用该列。您可以通过从特殊的 NewUser 类中完全删除 ID 属性来做到这一点。

但我们还可以做得更好。 Linq 允许我们使用名为 attributes 的东西来装饰属性,其中包含影响生成的 SQL 的信息。你可以在这里告诉它如何处理 ID 列:

[Column(DbType="INT NOT NULL IDENTITY", IsPrimaryKey=true, IsDbGenerated=true)]
public int ID {get; set;}

this 可以与现有的 User 类一起使用,而无需创建全新的类型。

【讨论】:

  • DbType,IsPrimaryKey,IsDbGenerated 命名空间无法添加到类中
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2023-03-23
  • 1970-01-01
  • 2017-10-31
  • 1970-01-01
相关资源
最近更新 更多