首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >如何在实体框架核心2.0中使用模型本身的OnModelCreating?

如何在实体框架核心2.0中使用模型本身的OnModelCreating?
EN

Stack Overflow用户
提问于 2018-01-19 17:14:02
回答 1查看 1.5K关注 0票数 2

我对实体框架()非常陌生,所以请轻松一点,但我想让我的模型的fluent API更接近使用,并将它放在模型对象本身中。我在文档中找不到任何东西,也无法通过谷歌搜索一个内置的方法来实现这一点,所以我想,如果从DbContext.OnModelCreating()方法中存在静态方法,也许我可以在模型上调用一个静态方法。这是我想出的,但在我运行Add-MigrationScript-Migration时,它似乎不起作用,即使我首先删除了所有迁移。知道我在这件事上哪里出错了吗?或者是更好的方法?

Trademark.cs (模型)

代码语言:javascript
复制
public class Trademark
{
    public string Name { get; set; }
    // ... 
    protected static void OnModelCreating( ModelBuilder modelBuilder )
    {
        modelBuilder.Entity<Trademark>().HasIndex(x=>x.Name).IsUnique();
    }
}

PartDbContext.cs (DbContext)

代码语言:javascript
复制
public class PartDbContext: DbContext
{
    // ...
    public DbSet<Trademark> Trademarks { get; set; }
    public PartDbContext( DbContextOptions options ): base(options)
    {
    }
    protected override void OnModelCreating( ModelBuilder modelBuilder )
    {
        dynamic m = modelBuilder.Model.GetType().GetMethod("OnModelCreating",System.Reflection.BindingFlags.Static);
        if( m != null )
            m.OnModelCreating(modelBuilder);
    }
}

我认为问题是modelBuilder.Model.GetType()返回的是typeof(IMutableModel),而不是typeof(Trademark)。所以,也许我只需要知道如何从modelBuilder获得模型的类型。

注意:如果我将modelBuilder.Entity<Trademark>().HasIndex(x => x.Name).IsUnique();放在PartDbContext.OnModelCreating()中,就会添加唯一的约束。所以,我知道我至少有一点正确。

更新

对于其他有兴趣这样做的人,我决定将使用范围缩小一点,只传递EntityTypeBuilder而不是整个ModelBuilder

PartDbContext.cs

代码语言:javascript
复制
protected override void OnModelCreating( ModelBuilder modelBuilder )
{
    foreach( var entityType in modelBuilder.Model.GetEntityTypes() )
    {
        var method = entityType.ClrType.GetMethod("OnEntityCreating",BindingFlags.Static|BindingFlags.NonPublic);
        if( method != null )
        {
            var entityBuilder = new object[] {
                typeof(ModelBuilder)
                .GetMethod("Entity",new Type[]{})
                .MakeGenericMethod(entityType.ClrType)
                .Invoke(modelBuilder,null)
            };
            method.Invoke(null,entityBuilder);
        }
    }
}

Trademark.cs

代码语言:javascript
复制
public class Trademark
{
    public string Name { get; set; }
    protected static void OnEntityCreating( EntityTypeBuilder<Trademark> entityBuilder )
    {
        entityBuilder.HasIndex(x=>x.Name).IsUnique();
    }

}
EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2018-01-19 17:58:21

您可以迭代所有发现的实体类型并通过反射调用自定义方法(如果定义的话):

代码语言:javascript
复制
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
    var parameters = new object[] { modelBuilder };
    foreach (var entityType in modelBuilder.Model.GetEntityTypes())
    {
        var method = entityType.ClrType.GetMethod("OnModelCreating", BindingFlags.Static | BindingFlags.NonPublic);
        if (method != null)
            method.Invoke(null, parameters);
    }
}
票数 5
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/48346253

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档