实体框架:对数据库提交的更改,但更新对象上下文时发生错误

时间:2015-09-28 20:55:52

标签: entity-framework-6

我有一个带有属性Id(类型为int)的抽象基础对象。我有" DatabaseGeneratedOption.Identity"选项。 (这可以在下面看到)。

有两个派生实体,节点和标签。它们都没有Id属性,因为它们被假定从基类继承它。 (也见下面的代码)。

当使用相同的DbContext实例时,我可以添加任意数量的节点,然后保存更改。但是,只要我添加一个Tag(并且只在我添加了节点之后),就抛出异常。当我做相反的事情时也是如此。我可以添加任意数量的标签,然后保存更改,但只要我添加一些节点并尝试保存更改,就会抛出异常。

例外:

  

System.InvalidOperationException:对数据库的更改是   已成功提交,但更新时发生错误   对象上下文。 ObjectContext可能处于不一致状态。   内部异常消息:保存或接受更改失败,因为   不止一个实体类型' Entities.Node'拥有相同的主键   值。确保显式设置的主键值是唯一的。   确保正确配置数据库生成的主键   在数据库和实体框架模型中。使用实体   Database First / Model First配置的Designer。使用   ' HasDatabaseGeneratedOption"流利的API或   ' DatabaseGeneratedAttribute'用于Code First配置。 --->   System.InvalidOperationException:保存或接受更改失败   因为不止一个实体类型为'Entities.Node'有同样的   主键值。确保显式设置主键值   独特。确保已配置数据库生成的主键   正确地在数据库和实体框架模型中。使用   数据库优先/模型优先配置的实体设计器。使用   ' HasDatabaseGeneratedOption"流利的API或   ' DatabaseGeneratedAttribute'用于Code First配置。

DbContext定义:

// Node Entity
modelBuilder.Entity<Node>().HasRequired(t => t.NodeTypeEntity).
    WithMany(t => t.Nodes).HasForeignKey(t => t.NodeTypeId);
modelBuilder.Entity<Node>().HasOptional(t => t.Parent).
    WithMany(t => t.Children).HasForeignKey(t => t.ParentId);
modelBuilder.Entity<Node>().HasMany(t => t.Children).
    WithOptional(t => t.Parent);
modelBuilder.Entity<Node>().HasMany(t => t.Tags).WithMany(t => t.Nodes);
modelBuilder.Entity<Node>().Property(t => t.Location).IsOptional().HasMaxLength(100);
modelBuilder.Entity<Node>().Ignore(t => t.SourceDefinitions);
modelBuilder.Entity<Node>().Ignore(t => t.NodeType);



// Tags Entity

modelBuilder.Entity<NWatchTag>().Property(t => t.TagDesc).
                IsOptional().HasMaxLength(500);
            modelBuilder.Entity<NWatchTag>().Property(t => t.IsSystem).IsOptional();
            modelBuilder.Entity<NWatchTag>().HasMany(t => t.Nodes).WithMany(t => t.Tags); 


// Base Entity
modelBuilder.Entity<BaseEntityObject>().HasKey(t => t.Id);
modelBuilder.Entity<BaseEntityObject>().Property(t => t.Id).
    HasDatabaseGeneratedOption(DatabaseGeneratedOption.Identity);
modelBuilder.Entity<BaseEntityObject>().Property(t => t.NativeId).IsRequired();
modelBuilder.Entity<BaseEntityObject>().Property(t => t.Name).
    IsRequired().HasMaxLength(100);
modelBuilder.Entity<BaseEntityObject>().Property(t => t.DisplayName).
    IsOptional().HasMaxLength(100);
modelBuilder.Entity<BaseEntityObject>().Property(t => t.Alias).
    IsOptional().HasMaxLength(100);
modelBuilder.Entity<BaseEntityObject>().Property(t => t.SourceId).IsRequired();
modelBuilder.Entity<BaseEntityObject>().Property(t => t.AccessLevel).IsRequired();
modelBuilder.Entity<BaseEntityObject>().Property(t => t.CreatedOn).IsRequired();
modelBuilder.Entity<BaseEntityObject>().Property(t => t.CreatedBy).
    IsRequired().HasMaxLength(50);
modelBuilder.Entity<BaseEntityObject>().Property(t => t.ModifiedOn).IsOptional();
modelBuilder.Entity<BaseEntityObject>().Property(t => t.ModifiedBy).
    IsOptional().HasMaxLength(50);


public override int SaveChanges()
{
    var changeSet = ChangeTracker.Entries<BaseEntityObject>();

    foreach (var entity in changeSet)
    {
        switch (entity.State)
        {
            case EntityState.Added:
                entity.Entity.CreatedOn = DateTime.UtcNow;
                if (String.IsNullOrEmpty(entity.Entity.CreatedBy))
                {
                    entity.Entity.CreatedBy = "System";
                }
                break;
            case EntityState.Modified:
                entity.Entity.ModifiedOn = DateTime.UtcNow;
                if (String.IsNullOrEmpty(entity.Entity.ModifiedBy))
                {
                    entity.Entity.ModifiedBy = "System";
                }
                break;
        }
    }

    return base.SaveChanges();
}

使用DbContext进行编程:

var testTag = new Tag("TestTag");
dbContext.Tags.Add(testTag);
dbContext.SaveChanges();


dbContext.Nodes.Add(new Node(1, "node1", testType, Source.CasApi));
dbContext.SaveChanges();   <=== EXCEPTION THROWN HERE

0 个答案:

没有答案