![](/img/trans.png)
[英]C# -> Entity Framework 6.1.3 -> Composite nullable foreign key string
[英]How to use a composite primary key with Entity Framework from a foreign key in C#
我在現有數據庫和使用實體框架的主鍵/外鍵方面遇到了一個大問題。
它是一個現有的數據庫,不允許更改數據庫,至少不能更改現有的密鑰,因為它們已被其他程序使用。 為了解釋鍵的作用,我添加了一個局部圖。
parameterCode
和Type
是字符串索引鍵,因此它們與普通 ID 一樣
該數據庫由 4 個表組成:
范圍
這具有以下主鍵列(形成復合鍵):
參數類型
這具有以下主鍵:
參數文檔類型
主鍵:ParameterDocumentId
這具有以下外鍵
ParamaterCode
=> 連接到參數ParameterDocument
=> 這個工作正常,所以我把它放在外面我創建了配置和模型來連接所有表,但是連接到parameterType
的Parameter
表不接受配置。 當我將兩個鍵都聲明為主鍵時。
當連接也是主鍵一部分的parametertype
類型外鍵時,出現以下錯誤:
System.InvalidOperationException:“無法將屬性或導航‘ParameterType’添加到實體類型‘ParameterModel’,因為實體類型‘ParameterModel’上已存在同名的屬性或導航。”
我從所有其他值中剝離代碼以使其更小。
[![// configurations
public class ParameterConfiguration : IEntityTypeConfiguration<ParameterModel>
{
public void Configure(EntityTypeBuilder<ParameterModel> builder)
{
builder.ToTable("Parameter", table => table.ExcludeFromMigrations());
builder.HasKey(p => new { p.ParameterCode, p.ParameterType });
builder.Property(p => p.ParameterCode)
.HasColumnName("ParameterCode")
.HasColumnType("varchar(25)")
.IsRequired();
builder.Property(p => p.Description)
.HasColumnName("Description")
.HasColumnType("varchar(255)");
.IsRequired();
builder.HasOne(x => x.ParameterType) // error on creating this key
.WithMany(x => x.Parameters)
.HasForeignKey(x => x.Type)
.IsRequired();
}
}
// configurations ParameterTypeConfiguration
public class ParameterTypeConfiguration : IEntityTypeConfiguration<ParameterTypeModel>
{
public void Configure(EntityTypeBuilder<ParameterTypeModel> builder)
{
builder.ToTable("ParameterType", table => table.ExcludeFromMigrations());
builder.HasKey(p => p.ParameterTypeCode);
builder.Property(p => p.ParameterTypeCode)
.HasColumnName("ParameterTypeCode")
.HasColumnType("varchar(50)")
.IsRequired();
}
}
// configurations
public void Configure(EntityTypeBuilder<ParameterDocumentTypeModel> builder)
{
builder.ToTable("ParameterDocumentType", table => table.ExcludeFromMigrations());
builder.HasKey(p => p.ParameterDocumentTypeId);
builder.Property(p => p.ParameterDocumentTypeId)
.HasColumnName("ParameterDocumentTypeID")
.HasColumnType("bigint")
.UseIdentityColumn()
.ValueGeneratedOnAdd()
.IsRequired();
builder.Property(p => p.ParameterCode)
.HasColumnName("Parameter_Code")
.HasColumnType("varchar(50)")
.IsRequired();
builder.Property(p => p.Type)
.HasColumnName("Type")
.HasColumnType("varchar(25)")
.IsRequired();
builder.HasOne(p => p.Parameter)
.WithMany(p => p.ParameterDocumentTypes)
.HasForeignKey(p => p.ParameterCode)
.IsRequired(false);
}
}
// models
public class ParameterDocumentTypeModel
{
public long ParameterDocumentTypeId { get; set; }
public long? DocumentTypeId { get; set; }
// used for the connection with parameter
public virtual ParameterModel Parameter { get; set; }
public string ParameterTypeCode
{
get => Parameter?.Type;
}
}
public class ParameterModel
{
public string ParameterCode { get; set; }
public string Type { get; set; }
public virtual ParameterTypeModel ParameterType { get; set; }
// used to connect to parameterType
public virtual ICollection<ParameterDocumentTypeModel> ParameterDocumentTypes { get; set; }
}
public class ParameterTypeModel
{
public string ParameterTypeCode { get; set; }
public string Description { get; set; }
// used to connect to parameter
public ICollection<ParameterModel> Parameters { get; set; }
}
實體類型“ParameterModel”上已存在同名屬性或導航
因為您試圖將 ParameterType 配置為關鍵屬性,無論如何稍后都會失敗,因為只有標量可以是關鍵屬性。
這個
builder.HasKey(p => new { p.ParameterCode, p.ParameterType });
應該
builder.HasKey(p => new { p.ParameterCode, p.Type });
更正后:builder.HasKey(p => new { p.ParameterCode, p.ParameterType });
非常感謝大衛·布朗
我還需要為外鍵做同樣的事情。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.