我将DataObject定义为:

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);

即使已设置主键,当我运行添加迁移时, 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添加此列?

最佳答案

我怀疑这与您从EntityData派生您的类并且EntityData具有一个名为Id的属性有关。我的猜测是EF变得困惑,因为有一个属性遵循其键命名约定(即Id)和一个显式定义的键。

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

MSDN: EntityData Class

更新:

我假设您正在为此使用Azure。答案中的此SO question具有一些其他信息,可以帮助您找到最佳解决方案。

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

10-05 22:51
查看更多