C# 基类中的索引数据批注异常
我从C# 基类中的索引数据批注异常,c#,asp.net-core-2.1,entity-framework-core-2.1,C#,Asp.net Core 2.1,Entity Framework Core 2.1,我从ASP.net Core开始创建我的模型。 我刚刚创建了两个:一个名为dto,它将是我所有数据库模型的基础,如下所示: public abstract class Dto { [DatabaseGenerated(DatabaseGeneratedOption.Identity)] public Guid Id { get; set; } [Clustered] public DateTime CreatedAt { get; set; } = DateTim
ASP.net Core
开始创建我的模型。我刚刚创建了两个:一个名为
dto
,它将是我所有数据库模型的基础,如下所示:public abstract class Dto
{
[DatabaseGenerated(DatabaseGeneratedOption.Identity)]
public Guid Id { get; set; }
[Clustered]
public DateTime CreatedAt { get; set; } = DateTime.UtcNow;
public DateTime LastUpdate { set; get; }
}
public class Subscription:Dto
{
public string Name { get; set; }
public decimal Price { set; get; }
public string MeliApiKey { get; set; }
public int MaxQueries { get; set; }
public int UsedQueries { get; set; }
}
另一个被称为subscription
,它看起来是这样的:public abstract class Dto
{
[DatabaseGenerated(DatabaseGeneratedOption.Identity)]
public Guid Id { get; set; }
[Clustered]
public DateTime CreatedAt { get; set; } = DateTime.UtcNow;
public DateTime LastUpdate { set; get; }
}
public class Subscription:Dto
{
public string Name { get; set; }
public decimal Price { set; get; }
public string MeliApiKey { get; set; }
public int MaxQueries { get; set; }
public int UsedQueries { get; set; }
}
我在Fluent API上有以下配置:
modelBuilder.Entity<Dto.Dto>().Property(x => x.CreatedAt).HasDefaultValueSql("SYSUTCDATETIME()");
modelBuilder.Entity<Dto.Dto>().Property(x => x.LastUpdate).HasComputedColumnSql("SYSUTCDATETIME()");
foreach (var entity in modelBuilder.Model.GetEntityTypes())
{
foreach (var prop in entity.GetProperties())
{
var attr = prop.PropertyInfo?.GetCustomAttribute<ClusteredAttribute>(true);
if (attr != null)
{
var index = entity.AddIndex(prop);
index.IsUnique = true;
index.SqlServer().IsClustered = true;
}
}
}
modelBuilder.Entity();
modelBuilder.Entity().Property(x=>x.LastUpdate).HasComputedColumnSql(“SYSUTCDATETIME()”);
foreach(modelBuilder.Model.GetEntityTypes()中的var实体)
{
foreach(entity.GetProperties()中的var prop)
{
var attr=prop.PropertyInfo?.GetCustomAttribute(true);
如果(attr!=null)
{
var指数=实体加总指数(prop);
index.IsUnique=true;
index.SqlServer().IsClustered=true;
}
}
}
我只添加了subscription
作为dbset
,因为我不想使用dto
继承每个层次表
运行添加迁移时,出现以下错误:
“无法将索引{'CreatedAt'}添加到实体类型
“订阅”,因为相同属性上的索引已存在
关于实体类型“Dto”
现在我已经在谷歌上搜索了错误,但我看不到任何地方如何解决这个问题。
我是否应该删除dto
类,并向表示我的模型的每个对象添加相同的属性?作为错误状态,并且已经在基类的属性上定义了索引。检查属性是否在当前正在处理的同一类型的实体中声明,如下所示:
var propertiesToProcess = entity.GetProperties()
.Where( p => entity.ClrType == p.PropertyInfo.DeclaringType );
我最终删除了这些行:
modelBuilder.Entity<Dto.Dto>().Property(x => x.CreatedAt).HasDefaultValueSql("SYSUTCDATETIME()");
modelBuilder.Entity<Dto.Dto>().Property(x => x.LastUpdate).HasComputedColumnSql("SYSUTCDATETIME()");
告诉实体框架使用当前UTC时间创建列CreateAt具有默认值,并使用for循环中实际实体的当前UTC时间更新LastUpdate列
最后,这段代码得到了错误,因为Dto类被包含在数据库实体中,所以它为它创建了索引,并且因为在数据库实体中包含该类会在下一个实体尝试创建索引时触发TPH,所以会弹出错误(我们试图在同一个表中创建相同的索引,因为TPH只有一个表)
foreach(entity.GetProperties()中的var prop)
{
var attr=prop.PropertyInfo?.GetCustomAttribute(true);
如果(attr!=null)
{
var指数=实体加总指数(prop);
index.IsUnique=true;
index.SqlServer().IsClustered=true;
}
}
但是现在我们已经为每个实体分离了表,它就可以工作了
这本书帮了大忙
以下是帮助我实现这一目标的其他答案:
我会尝试一下,让你知道它现在起作用了,我会发布我所做的作为答案,你的答案帮助很大,但我最终做的不同,因为entity.ClrType==p.PropertyInfo.DeclaringType
只有当当前实体是数据时,这个比较才是正确的,如果你有一个不是从D派生的实体TO
但是使用了Clustered
属性?很好的问题,刚才去掉了if语句,但是我的所有实体都派生自Dto
,因为我为将保存到数据库的所有对象显式创建了父类,Clustered
属性也是我创建的自定义类我不会在OnModelCreating()
中逐个实体手动更改索引,只需检查属性以设置该属性,这意味着我控制之外的任何其他实体都不会将该属性用于非DTO
继承的对象
foreach (var prop in entity.GetProperties())
{
var attr = prop.PropertyInfo?.GetCustomAttribute<ClusteredAttribute>(true);
if (attr != null)
{
var index = entity.AddIndex(prop);
index.IsUnique = true;
index.SqlServer().IsClustered = true;
}
}