如何从EF EntitySet获取对象的类型

时间:2016-04-01 13:39:40

标签: c# entity-framework entity-framework-6

我创建了一个EF约定,它根据它直接或间接实现的接口为类设置模式名称。

public class TableNameConvention<T> : IStoreModelConvention<EntitySet>
{
    private readonly string SchemaName;

    public TableNameConvention(string schemaName)
    {
        this.SchemaName = schemaName;
    }

    public virtual void Apply(EntitySet entitySet, DbModel model)
    {
        // Get the name of the Entity
        string name = entitySet.Name;

        // Check TEntityType Assembly for entitySet type
        Type type = typeof(T).Assembly.GetTypes().Where(x => x.Name == name).SingleOrDefault();

        // Check if type was found
        if (type != null)
        {
            // Check if type implements Type Parameter and if so, set schema
            if (typeof(T).IsAssignableFrom(type)) entitySet.Schema = SchemaName;
        }

        entitySet.Table = FormatName(name);
    }

95%的情况下都能正常工作。但是,如果在程序集中的任何位置有另一个具有相同名称的类,它将返回默认值。我可以将其更改为FirstOrDefault,但仍然无法保证第一个是我正在寻找的那个。

我知道没有完全合格的名字,它永远不会是100%,但有没有人有任何建议来帮助提高获得正确类型的机会?

更新

我更改了以下内容:

Type type = AppDomain.CurrentDomain.GetAssemblies()
                       .SelectMany(t => t.GetTypes())
                       .Where(t => t.IsClass && t.Namespace == typeof(T).Namespace)
                       .FirstOrDefault(t => t.Name.Equals(name));

但是,只有派生类与基类位于同一名称空间中才会起作用。所以,如果有人有任何其他建议,请帮忙!

2 个答案:

答案 0 :(得分:0)

这会有用吗?

        // Check TEntityType Assembly for entitySet type
        Type type = typeof(T).Assembly.GetTypes().Where(x => x == entitySet.GetType()).SingleOrDefault();

答案 1 :(得分:0)

简短的回答是,无法直接从EF Type获取实体的实际EntitySet,至少不在存储模型中。

为了使上面的代码工作,我更新了类,如下所示:

private readonly string SchemaName;
private readonly string Namespace;

public TableNameConvention(string schemaName, string @namespace)
{
    this.SchemaName = schemaName;
    this.Namespace = @namespace;
}

然后更新Linq查询的where方法以从AppDomain获取类型

Type type = AppDomain.CurrentDomain.GetAssemblies()
                   .SelectMany(t => t.GetTypes())
                   .Where(t => t.IsClass && t.Namespace == this.Namespace)
                   .FirstOrDefault(t => t.Name.Equals(name));