4

我所定义的数据对象作为Id列:实体框架6创建即使其他主键被定义

public class SensorType : EntityData 
{ 
    //PKs 
    public string CompanyId { get; set; } 
    public string ServiceId { get; set; } 

    public string Type { get; set; } 
} 

并用于流利API做出CompanyId和SERVICEID复合键:

modelBuilder.Entity<SensorType>() 
      .HasKey(t => new { t.CompanyId, t.ServiceId }); 

//No autogeneration of PKs 
modelBuilder.Entity<SensorType>().Property(t => t.ServiceId) 
      .HasDatabaseGeneratedOption(System.ComponentModel.DataAnnotations.Schema.DatabaseGeneratedOption.None); 
modelBuilder.Entity<SensorType>().Property(t => t.CompanyId) 
      .HasDatabaseGeneratedOption(System.ComponentModel.DataAnnotations.Schema.DatabaseGeneratedOption.None); 

即使虽然已设置主键当我运行Add-Migration时,Entity Framework创建一个名为Id的列:

CreateTable(
      "dbo.SensorTypes", 
      c => new 
       { 
        CompanyId = c.String(nullable: false, maxLength: 128), 
        ServiceId = c.String(nullable: false, maxLength: 128), 
        Type = c.String(), 
        Id = c.String(
         annotations: new Dictionary<string, AnnotationValues> 
         { 
          { 
           "ServiceTableColumn", 
           new AnnotationValues(oldValue: null, newValue: "Id") 

        ... 
       }) 
      .PrimaryKey(t => new { t.CompanyId, t.ServiceId }) 
      .Index(t => t.CreatedAt, clustered: true); 

    } 

如何防止EF添加此列?

+1

是否故意尝试将两个字段的组合作为复合键使用?如果是这样,你有一个很好的理由吗? – Basic

+0

你不需要告诉实体框架关于DatabaseGeneratedOption。没有,只是设置与公司和服务表的关系 – Monah

+1

放置EntityData的代码,似乎实体数据包含Id,这就是使其成为主键的原因 – Monah

回答

2

我怀疑它做的事实上,你从EntityDataEntityData派生你的课程有一个名为Id的属性。我的猜测是EF令人困惑,因为有一个属性遵循关键命名约定(即Id)和明确定义的关键字。

我怀疑你必须告诉它明确忽略Id

MSDN: EntityData Class

UPDATE:

我假设你正在使用Azure的工作这一点。这SO question有一些额外的答案信息,可以帮助您找到最佳解决方案。

但是,我同意@Basic在他对你的问题的评论。由于他们介绍的复杂性(和其他问题),我通常回避与EF组合键。我怀疑您的CompanyIdServiceId字段上的唯一约束将实现您想要的内容,而不会将它们包含在SensorType的主键中。这也意味着您可以使用派生的Id属性作为主键,并避免整个问题。我不知道你的实施是否可行,但需要考虑。

+0

现在情况已经很清楚了,EntityData中的Id也生成为Id,他可以告诉流利的api忽略它,或者不让SensorType从EntityData继承。 – Monah

+0

忽略ID工作!但这是对Libskovs替代原则的违反。 是否有可能使用EF并让它在没有从EntityData继承的情况下生成一个控制器?它提供:CreatedAt,UpdatedAt等。当然还有Id。 –

+0

@Emil见此更新的一些想法。 –

-1

看到文档的文本:

实体框架依赖于具有它使用跟踪实体键值每个实体。代码首先依赖的约定之一是它是如何暗示哪些属性是每个代码第一类中的关键。该惯例是查找名为“Id”的属性或者将类名和“Id”组合在一起的属性,例如“BlogId”。该属性将映射到数据库中的主键列。

使用不同的密钥,您需要使用注释[关键],例如:

[Key] 
public int primaryKey { get; set; } 

Documentation Oficial

Tutorial Link