简体   繁体   English

自动包含实体框架属性

[英]Automatically include Entity Framework properties

the answer to my question might be trivial, but I can't figure out how to do it.我的问题的答案可能微不足道,但我不知道该怎么做。

Suppose, we have the following situation:假设,我们有以下情况:

A DB first EF-Entity with nested Properties:具有嵌套属性的数据库第一个 EF 实体:

public partial class Employee
{
     public int ID { get; set;}
     public virtual ICollection<EmployeeDepartmentHistory> EmployeeDepartmentHistory { get; set;}
     public virtual ICollection<JobCandidate> JobCandidate { get; set;}
}

A Domain Class Employee域类Employee

(related classes don't matter for this example) (相关类对于此示例无关紧要)

public class Employee
{
     public int ID { get; set;}
     public IEnumerable<Department> Departments { get; set;}
     public IEnumerable<JobCandidate> Candidates { get; set;}
}

A Service Class EmployeeService that applies business rules to the query将业务规则应用于查询的服务类EmployeeService

public class EmployeeService
    private RepoTestEntities1 _Database;

    public EmployeeService(RepoTestEntities1 database)
    {
        _Database = database;
    }

    public IQueryable<DomainModels.Employee> GetSalariedEmployeesByDepartmentName(string departmentName)
    {
        _Database.Configuration.LazyLoadingEnabled = false;
        return _Database.Employee
            .Include(e => e.EmployeeDepartmentHistory)
            .Include(e => e.JobCandidate)
            .Include(e => e.EmployeeDepartmentHistory.Select(his => his.Department))
            .AsNoTracking()
            .WhereDepartmentName(departmentName)
            .WhereSalariedFlag(true)
            .Select(e => CreateEmployee(e));
    }
    private DomainModels.Employee CreateEmployee(Employee e)
    {
        [...] (transform to domain)
    }

WhereDepartmentName and WhereSalariedFlag are implemented as extension methods to IQueryable<Employee> . WhereDepartmentNameWhereSalariedFlag被实现为IQueryable<Employee>扩展方法。

Now to the question现在的问题


Suppose I need further methods, that retrieve Employees from DbContext and I don't want to use Lazy loading.假设我需要进一步的方法,从 DbContext 检索员工,我不想使用延迟加载。

Repeatedly calling all those includes is redundant, error prone and tedious.重复调用所有这些包含是多余的、容易出错且乏味的。 Do you know an elegant way of always including the needed properties for all methods of the EmployeeService ?您知道一种始终包含EmployeeService所有方法所需属性的优雅方法吗?

Might a strategy pattern be a viable approach?策略模式可能是一种可行的方法吗?

If you REALLY need to Include all the navigation properties you can use this piece of code.如果您真的需要包含所有导航属性,您可以使用这段代码。
If you need to eagerly load also collections (not always a good idea) you can delete the continue statement in the code.如果您还需要急切地加载集合(并不总是一个好主意),您可以删除代码中的 continue 语句。
Context is your context ( this if you insert this code in your context)上下文是您的上下文( this如果插入你的背景下,这个代码)

    public IQueryable<T> IncludeAllNavigationProperties<T>(IQueryable<T> queryable)
    {
        if (queryable == null)
            throw new ArgumentNullException("queryable");

        ObjectContext objectContext = ((IObjectContextAdapter)Context).ObjectContext;
        var metadataWorkspace = ((EntityConnection)objectContext.Connection).GetMetadataWorkspace();

        EntitySetMapping[] entitySetMappingCollection = metadataWorkspace.GetItems<EntityContainerMapping>(DataSpace.CSSpace).Single().EntitySetMappings.ToArray();

        var entitySetMappings = entitySetMappingCollection.First(o => o.EntityTypeMappings.Select(e => e.EntityType.Name).Contains(typeof(T).Name));

        var entityTypeMapping = entitySetMappings.EntityTypeMappings[0];

        foreach (var navigationProperty in entityTypeMapping.EntityType.NavigationProperties)
        {
            PropertyInfo propertyInfo = typeof(T).GetProperty(navigationProperty.Name);
            if (propertyInfo == null)
                throw new InvalidOperationException("propertyInfo == null");
            if (typeof(System.Collections.IEnumerable).IsAssignableFrom(propertyInfo.PropertyType))
                continue;

            queryable = queryable.Include(navigationProperty.Name);
        }

        return queryable;
    }

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM