【问题标题】:How to resolve error with enitiy freamwork include如何解决实体框架的错误包括
【发布时间】:2020-12-02 11:09:37
【问题描述】:

我使用 .Net 5 和 Entity Freamwork Core 编写应用程序。 我有正在寻找一些数据的方法。 它看起来像这样:

        public async Task<Result<List<Company>>> Search(string keyword, DateTime From, DateTime To, JobTitle jobTitle)
        {
            return Result.Ok(await _dataContext.Companies
                .Include(x => x.Employes
                    .WhereIf(From != default && To != default,
                        x => x.DateOfBirth >= From && x.DateOfBirth <= To && x.JobTitle == jobTitle))
                .WhereIf(!string.IsNullOrEmpty(keyword), 
                    x => x.Name.Contains(keyword))
                .ToListAsync());
        }

WhereIf 看起来像这样:

    public static class LinqExtension
    {
        public static IQueryable<TSource> WhereIf<TSource>(this IQueryable<TSource> source, bool condition, Expression<Func<TSource, bool>> predicate)
        {
            if (condition)
                return source.Where(predicate);

            return source;
        }

        public static IEnumerable<TSource> WhereIf<TSource>(this IEnumerable<TSource> source, bool condition, Func<TSource, bool> predicate)
        {
            if (condition)
                return source.Where(predicate);

            return source;
        }
    }

当我使用这种方法时,我得到了这个错误:

System.InvalidOperationException: The expression 'x.Employes.WhereIf(__p_0, x => (((x.DateOfBirth >= __From_1) AndAlso (x.DateOfBirth <= __To_2)) AndAlso (Convert(x.JobTitle, Int32) == Convert(__jobTitle_3, Int32))))' is invalid inside an 'Include' operation, since it does not represent a property access: 't => t.MyProperty'. To target navigations declared on derived types, use casting ('t => ((Derived)t).MyProperty') or the 'as' operator ('t => (t as Derived).MyProperty'). Collection navigation access can be filtered by composing Where, OrderBy(Descending), ThenBy(Descending), Skip or Take operations. For more information on including related data

如何解决这个错误?

【问题讨论】:

    标签: .net entity-framework asp.net-core entity-framework-core


    【解决方案1】:

    答案很简单。 EF Core 不会在 Include 定义中调用自定义方法。没关系,因为这个方法不是 IQueryable 方法。

    所以只需重写你的代码:

    public async Task<Result<List<Company>>> Search(string keyword, DateTime From, DateTime To, JobTitle jobTitle)
    {
       IQueryable<Company> query = _dataContext.Companies;
       if (From != default && To != default)
          query = query.Include(x => x.Employes
                     .Where(x => x.DateOfBirth >= From && x.DateOfBirth <= To && x.JobTitle == jobTitle));
       else
          query = query.Include(x => x.Employes);
    
       query = query.WhereIf(!string.IsNullOrEmpty(keyword), x => x.Name.Contains(keyword));
    
       return Result.Ok(await query.ToListAsync());
    }
    

    或者您可以使用附加扩展来包含:

    public static class LinqExtension
    {
        public static IIncludableQueryable<TEntity, IEnumerable<TProp>> IncludeFiltered<TEntity, TProp>(
            this IQueryable<TEntity> source, bool condition, 
            Expression<Func<TEntity, IEnumerable<TProp>>> selector, 
            Expression<Func<TProp, bool>> predicate) 
            where TEntity : class
        {
            if (condition)
            {
                var newBody = Expression.Call(typeof(Enumerable), "Where", new[] {typeof(TProp)}, 
                    selector.Body,
                    predicate);
    
                selector = Expression.Lambda<Func<TEntity, IEnumerable<TProp>>>(newBody, selector.Parameters);
            }
    
            return source.Include(selector);
        }
    }
    
    public async Task<Result<List<Company>>> Search(string keyword, DateTime From, DateTime To, JobTitle jobTitle)
    {
       return Result.Ok(await _dataContext.Companies
          .IncludeFiltered(From != default && To != default, 
             x => x.Employes, x => x.DateOfBirth >= From && x.DateOfBirth <= To && x.JobTitle == jobTitle)
          .WhereIf(!string.IsNullOrEmpty(keyword), 
             x => x.Name.Contains(keyword))
          .ToListAsync());
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-06-21
      • 1970-01-01
      • 1970-01-01
      • 2017-03-02
      • 1970-01-01
      相关资源
      最近更新 更多