简体   繁体   English

EF Core 在插入时发送 PK 值

[英]EF Core sending PK value on Insert

I'm getting an error:我收到一个错误:

Cannot insert explicit value for identity column in table 'ScheduleTransactionLink' when IDENTITY_INSERT is set to OFF当 IDENTITY_INSERT 设置为 OFF 时,无法在表“ScheduleTransactionLink”中插入标识列的显式值

The SQL generated is:生成的 SQL 为:

INSERT INTO [ScheduleTransactionLink] ([Id], [CreatedByUserId], [CreatedDate], [Deleted], [LastUpdateDate], [LastUpdatedByUserId], [PaymentNumber], [ScheduleId])
VALUES (@p0, @p1, @p2, @p3, @p4, @p5, @p6, @p7);`

So obviously the issue is something related to passing in an Id value, and I have IDENTITY INSERT to on.所以很明显,这个问题与传递一个Id值有关,我有IDENTITY INSERT But I'm not sending an Id.但我没有发送身份证。

My table is defined as:我的表定义为:

internal class ScheduleTransactionLink : EntityAudit
{
    [Required, Key]
    public int Id { get; set; }

    [Required]
    public Schedule Schedule { get; set; }

    [Required]
    public Transaction Transaction { get; set; }

    [Required]
    public int PaymentNumber { get; set; }
}

Same as all my other tables.和我所有的其他桌子一样。 But only this bit of code is failing.但只有这段代码失败了。 As I can see, the generated SQL is sending 'Id'.如我所见,生成的 SQL 正在发送“Id”。

This only started happening after I added a navigational property to this table for a very complete query elsewhere.这只是在我向该表添加导航属性以在其他地方进行非常完整的查询后才开始发生的。

  modelBuilder.Entity<Transaction>()
      .HasOne(x => x.ScheduleTransactionLink)
      .WithOne(t => t.Transaction)
      .HasForeignKey<ScheduleTransactionLink>();

An example of how I save my entity is here:我如何保存我的实体的示例如下:

ScheduleTransactionLink link = new ScheduleTransactionLink
{
    CreatedByUserId = _jwt.UserId,
    CreatedDate = DateTime.UtcNow,
    PaymentNumber = paymentNumber,
    Schedule = schedule,
    Transaction = transaction
};

_context.ScheduleTransactionLink.Add(link);

var result = await _context.SaveChangesAsync();

It's on the SaveChangesAsync where it errors out.它位于出错的SaveChangesAsync上。

I have also added this code to OnModelCreating :我还将此代码添加到OnModelCreating

modelBuilder.Entity<ScheduleTransactionLink>(entity =>
{
    entity.Property(e => e.Id).UseIdentityColumn();
});

Looking at the database, the table is created correctly:查看数据库,表创建正确:

CREATE TABLE [dbo].[ScheduleTransactionLink]
(
    [Id] [int] IDENTITY(1,1) NOT NULL,
    ....

How do I stop EF from sending the PK value?如何阻止 EF 发送 PK 值?

You need to tell EF Core when it's a generated value - see the official MS docs on that topic.您需要在生成值时告诉 EF Core - 请参阅有关该主题的官方 MS 文档

To handle an IDENTITY column, use this annotation:要处理IDENTITY列,请使用以下注释:

internal class ScheduleTransactionLink : EntityAudit
{
    [Required, Key]
    [DatabaseGenerated(DatabaseGeneratedOption.Identity)]
    public int Id { get; set; }

    [Required]
    public Schedule Schedule { get; set; }

    [Required]
    public Transaction Transaction { get; set; }

    [Required]
    public int PaymentNumber { get; set; }
}

I suspect that EF isn't able to fully work out how your 1:1 entities relate.我怀疑 EF 无法完全确定您的 1:1 实体之间的关系。 It looks like it's grasped that Transaction is the principal but i suspect it's trying to forge a relationship by putting the transaction ID into the ScheduleTransaction.Id - that's an independent PK in its own right, not an FK of transaction ID.. You might have to help it out some by doing:看起来它已经掌握了 Transaction 是主体,但我怀疑它试图通过将事务 ID 放入 ScheduleTransaction.Id 来建立关系 - 这本身就是一个独立的 PK,而不是事务 ID 的 FK。你可能有通过这样做来帮助它:

internal class ScheduleTransactionLink : EntityAudit
{
    [ Key]
    public int Id { get; set; }

    [Required]
    public Schedule Schedule { get; set; }

    public int TransactionId { get; set; }
    [Required]
    public Transaction Transaction { get; set; }

    [Required]
    public int PaymentNumber { get; set; }
}
modelBuilder.Entity<Transaction>()
  .HasOne(x => x.ScheduleTransactionLink)
  .WithOne(t => t.Transaction)
  .HasForeignKey<ScheduleTransactionLink>(stl => stl.TransactionId);

It might work to not add a TransactionId and just:不添加 TransactionId 可能会起作用,而只是:

modelBuilder.Entity<Transaction>()
  .HasOne(x => x.ScheduleTransactionLink)
  .WithOne(t => t.Transaction)
  .HasForeignKey<ScheduleTransactionLink>(stl => stl.Transaction); 

..but it's not something I've come across/can test atm and the docs for configuring 1:1s do specifically have the "int Id property and nominate it in the fluent" approach. ..但这不是我遇到/可以测试atm的东西,配置1:1的文档确实特别具有“int Id属性并以流利的方式提名它”。 Give it a test, and if it works/doesn't let me know and I'll amend the answer给它一个测试,如果它有效/不让我知道,我会修改答案

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM