在尝试创建迁移时,您如何找到或知道 "non-owned" 实体类型在哪里?
How do you find or know where the "non-owned" entity type when trying to create a migration?
我有以下 类:
拥有 CreditCard 的 JobSeeker 具有 CreditCardType
public class JobSeeker : Entity
{
private readonly List<CreditCard> _creditCards;
public IEnumerable<CreditCard> CreditCards => _creditCards.AsReadOnly();
}
public class CreditCard : Entity
{
public CreditCardType CardType { get { return CreditCardType.From(_creditCardTypeID); } private set { } }
private readonly int _creditCardTypeID;}
public class CreditCardType : Enumeration
{
public static readonly CreditCardType Amex = new CreditCardType(1, nameof(Amex).ToLowerInvariant());
public static readonly CreditCardType Visa = new CreditCardType(2, nameof(Visa).ToLowerInvariant());
public static readonly CreditCardType MasterCard = new CreditCardType(3, nameof(MasterCard).ToLowerInvariant());
public static IEnumerable<CreditCardType> List() => new[] { Amex, Visa, MasterCard };}
我的 DBContext 配置是:
class JobSeekerEntityTypeConfiguration : IEntityTypeConfiguration<JobSeeker>
{
public void Configure(EntityTypeBuilder<JobSeeker> jsConfiguration)
{
if (jsConfiguration == null)
{
throw new ArgumentNullException(nameof(jsConfiguration));
}
// Build the model
jsConfiguration.OwnsOne(s => s.CompleteName);
jsConfiguration.OwnsOne(s => s.HomeAddress);
jsConfiguration.OwnsOne(s => s.BillingAddress);
jsConfiguration.OwnsOne(s => s.EmAddress);
jsConfiguration.OwnsOne(s => s.PersonalPhoneNumber);
jsConfiguration.OwnsMany(a => a.CreditCards);
//jsConfiguration.HasMany<CreditCard>().WithOne(JobSeeker).OnDelete(DeleteBehavior.Restrict);
jsConfiguration.Property<DateTime>("CreatedDate");
jsConfiguration.Property<DateTime>("UpdatedDate");
}
}
class CreditCardTypeEntityTypeConfiguration : IEntityTypeConfiguration<CreditCard>
{
public void Configure(EntityTypeBuilder<CreditCard> ccConfiguration)
{
if (ccConfiguration == null)
{
throw new ArgumentNullException(nameof(ccConfiguration));
}
// Build the model
ccConfiguration.HasOne(o => o.CardType).WithMany().HasForeignKey("_creditCardTypeID");
ccConfiguration.Property<DateTime>("CreatedDate");
ccConfiguration.Property<DateTime>("UpdatedDate");
}
}
class CreditCardEntityTypeConfiguration : IEntityTypeConfiguration<CreditCardType>
{
public void Configure(EntityTypeBuilder<CreditCardType> cctConfiguration)
{
if (cctConfiguration == null)
{
throw new ArgumentNullException(nameof(cctConfiguration));
}
// Build the model
cctConfiguration.ToTable("CreditCardTypes");
cctConfiguration.HasKey(o => o.Id);
cctConfiguration.Property(o => o.Id)
.HasDefaultValue(1)
.ValueGeneratedNever()
.IsRequired();
cctConfiguration.Property(o => o.Name)
.HasMaxLength(200)
.IsRequired();
cctConfiguration.HasData(
new { Id = 1, Name = "Amex" },
new { Id = 2, Name = "Visa" },
new { Id = 3, Name = "MasterCard" });
}
}
我的数据库上下文是:
public class JobSeekerContext : DbContext, IUnitOfWork
{
private static readonly Type[] EnumerationTypes = { typeof(CreditCardType) };
public const string DEFAULT_SCHEMA = "jobseeker";
private readonly ILoggerFactory MyConsoleLoggerFactory;
private readonly IMediator Mediator;
public DbSet<JobSeeker> JobSeekers { get; set; }
public DbSet<CreditCard> CreditCards { get; set; }
public DbSet<CreditCardType> CreditCardTypes { get; set; }
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
if (modelBuilder == null)
{
throw new ArgumentNullException(nameof(modelBuilder));
}
// Build the model
modelBuilder.ApplyConfiguration(new CreditCardTypeEntityTypeConfiguration());
modelBuilder.ApplyConfiguration(new CreditCardEntityTypeConfiguration());
modelBuilder.ApplyConfiguration(new JobSeekerEntityTypeConfiguration());
}
当我 运行 迁移时,出现以下错误:“类型 'CreditCard' 无法标记为拥有,因为已存在同名的非拥有实体类型。”
CreditCard 在哪里标记为非拥有?
Where is CreditCard
marked as non-owned?
在JobSeekerContext
这里
public DbSet<CreditCard> CreditCards { get; set; }
这里
modelBuilder.ApplyConfiguration(new CreditCardTypeEntityTypeConfiguration());
和整个(误导性命名)CreditCardTypeEntityTypeConfiguration
class 因为它是 IEntityTypeConfiguration<CreditCard>
.
Owned entity types 是通过 owner.
仅 配置、查询和更新的特殊实体
以下是当前 EF Core 文档的 By-design restrictions 部分的摘录:
- You cannot create a
DbSet<T>
for an owned type.
- You cannot call
Entity<T>()
with an owned type on ModelBuilder
.
请注意,应用 IEnityTypeConfiguration<T>
class 等同于在 ModelBuilder
上调用 Entity<T>()
。
所以你违反了上述两个限制。
你需要做的是
- 从上下文中删除
DbSet<CreditCard>
属性
- 删除
CreditCardTypeEntityTypeConfiguration
class和相应的ApplyConfiguration
调用
- 通过
OwnsMany
方法使用构建器 provided/returned 将 CreditCard
配置代码移动到所有者 JobSeeker
配置中。例如
jsConfiguration.OwnsMany(a => a.CreditCards, ccConfiguration =>
{
// Build the model
ccConfiguration.HasOne(o => o.CardType).WithMany().HasForeignKey("_creditCardTypeID");
ccConfiguration.Property<DateTime>("CreatedDate");
ccConfiguration.Property<DateTime>("UpdatedDate");
});
我有以下 类:
拥有 CreditCard 的 JobSeeker 具有 CreditCardType
public class JobSeeker : Entity { private readonly List<CreditCard> _creditCards; public IEnumerable<CreditCard> CreditCards => _creditCards.AsReadOnly(); } public class CreditCard : Entity { public CreditCardType CardType { get { return CreditCardType.From(_creditCardTypeID); } private set { } } private readonly int _creditCardTypeID;} public class CreditCardType : Enumeration { public static readonly CreditCardType Amex = new CreditCardType(1, nameof(Amex).ToLowerInvariant()); public static readonly CreditCardType Visa = new CreditCardType(2, nameof(Visa).ToLowerInvariant()); public static readonly CreditCardType MasterCard = new CreditCardType(3, nameof(MasterCard).ToLowerInvariant()); public static IEnumerable<CreditCardType> List() => new[] { Amex, Visa, MasterCard };}
我的 DBContext 配置是:
class JobSeekerEntityTypeConfiguration : IEntityTypeConfiguration<JobSeeker>
{
public void Configure(EntityTypeBuilder<JobSeeker> jsConfiguration)
{
if (jsConfiguration == null)
{
throw new ArgumentNullException(nameof(jsConfiguration));
}
// Build the model
jsConfiguration.OwnsOne(s => s.CompleteName);
jsConfiguration.OwnsOne(s => s.HomeAddress);
jsConfiguration.OwnsOne(s => s.BillingAddress);
jsConfiguration.OwnsOne(s => s.EmAddress);
jsConfiguration.OwnsOne(s => s.PersonalPhoneNumber);
jsConfiguration.OwnsMany(a => a.CreditCards);
//jsConfiguration.HasMany<CreditCard>().WithOne(JobSeeker).OnDelete(DeleteBehavior.Restrict);
jsConfiguration.Property<DateTime>("CreatedDate");
jsConfiguration.Property<DateTime>("UpdatedDate");
}
}
class CreditCardTypeEntityTypeConfiguration : IEntityTypeConfiguration<CreditCard>
{
public void Configure(EntityTypeBuilder<CreditCard> ccConfiguration)
{
if (ccConfiguration == null)
{
throw new ArgumentNullException(nameof(ccConfiguration));
}
// Build the model
ccConfiguration.HasOne(o => o.CardType).WithMany().HasForeignKey("_creditCardTypeID");
ccConfiguration.Property<DateTime>("CreatedDate");
ccConfiguration.Property<DateTime>("UpdatedDate");
}
}
class CreditCardEntityTypeConfiguration : IEntityTypeConfiguration<CreditCardType>
{
public void Configure(EntityTypeBuilder<CreditCardType> cctConfiguration)
{
if (cctConfiguration == null)
{
throw new ArgumentNullException(nameof(cctConfiguration));
}
// Build the model
cctConfiguration.ToTable("CreditCardTypes");
cctConfiguration.HasKey(o => o.Id);
cctConfiguration.Property(o => o.Id)
.HasDefaultValue(1)
.ValueGeneratedNever()
.IsRequired();
cctConfiguration.Property(o => o.Name)
.HasMaxLength(200)
.IsRequired();
cctConfiguration.HasData(
new { Id = 1, Name = "Amex" },
new { Id = 2, Name = "Visa" },
new { Id = 3, Name = "MasterCard" });
}
}
我的数据库上下文是:
public class JobSeekerContext : DbContext, IUnitOfWork
{
private static readonly Type[] EnumerationTypes = { typeof(CreditCardType) };
public const string DEFAULT_SCHEMA = "jobseeker";
private readonly ILoggerFactory MyConsoleLoggerFactory;
private readonly IMediator Mediator;
public DbSet<JobSeeker> JobSeekers { get; set; }
public DbSet<CreditCard> CreditCards { get; set; }
public DbSet<CreditCardType> CreditCardTypes { get; set; }
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
if (modelBuilder == null)
{
throw new ArgumentNullException(nameof(modelBuilder));
}
// Build the model
modelBuilder.ApplyConfiguration(new CreditCardTypeEntityTypeConfiguration());
modelBuilder.ApplyConfiguration(new CreditCardEntityTypeConfiguration());
modelBuilder.ApplyConfiguration(new JobSeekerEntityTypeConfiguration());
}
当我 运行 迁移时,出现以下错误:“类型 'CreditCard' 无法标记为拥有,因为已存在同名的非拥有实体类型。”
CreditCard 在哪里标记为非拥有?
Where is
CreditCard
marked as non-owned?
在JobSeekerContext
这里
public DbSet<CreditCard> CreditCards { get; set; }
这里
modelBuilder.ApplyConfiguration(new CreditCardTypeEntityTypeConfiguration());
和整个(误导性命名)CreditCardTypeEntityTypeConfiguration
class 因为它是 IEntityTypeConfiguration<CreditCard>
.
Owned entity types 是通过 owner.
仅 配置、查询和更新的特殊实体以下是当前 EF Core 文档的 By-design restrictions 部分的摘录:
- You cannot create a
DbSet<T>
for an owned type.- You cannot call
Entity<T>()
with an owned type onModelBuilder
.
请注意,应用 IEnityTypeConfiguration<T>
class 等同于在 ModelBuilder
上调用 Entity<T>()
。
所以你违反了上述两个限制。
你需要做的是
- 从上下文中删除
DbSet<CreditCard>
属性 - 删除
CreditCardTypeEntityTypeConfiguration
class和相应的ApplyConfiguration
调用 - 通过
OwnsMany
方法使用构建器 provided/returned 将CreditCard
配置代码移动到所有者JobSeeker
配置中。例如
jsConfiguration.OwnsMany(a => a.CreditCards, ccConfiguration =>
{
// Build the model
ccConfiguration.HasOne(o => o.CardType).WithMany().HasForeignKey("_creditCardTypeID");
ccConfiguration.Property<DateTime>("CreatedDate");
ccConfiguration.Property<DateTime>("UpdatedDate");
});