使用LINQ查询EF关联数据时出现Include路径表达式指向导航属性错误如何解决
错误产生原因
Include是Entity Framework体系中用于指定预加载导航属性的专用方法,传入的表达式必须直接指向实体类上定义的导航属性,不能在表达式内对导航属性执行过滤、投影、ToList()等额外操作。你当前的写法在Include内嵌套了Where查询和ToList()调用,不符合Include的语法要求,因此触发参数异常。
修复方案
方案1:EF Core 5.0+ 版本直接使用过滤Include(最简方案)
EF Core 5.0开始原生支持在Include中对集合导航属性添加过滤条件,只需要去掉Include内的ToList()调用即可:
var Owner = db.Owners .Where(m => m.ID == id) .Include(m => m.Products.Where(item1 => products.Any(item2 => item2.ProductID == item1.ProductID))) .FirstOrDefault();
注意:过滤Include仅支持Where、OrderBy、Take、Skip这类集合操作,不能嵌套ToList、Select等会改变导航属性类型的操作
方案2:低版本EF/EF6 兼容写法
如果使用的是低于5.0的EF Core版本,或者是.NET Framework下的EF6,可通过拆分查询或者投影实现需求:
方式A:先查主实体,再显式加载过滤后的关联数据
// 先查询主实体 var Owner = db.Owners.FirstOrDefault(m => m.ID == id); if(Owner != null) { // 显式加载过滤后的Products导航属性 db.Entry(Owner) .Collection(m => m.Products) .Query() .Where(item1 => products.Any(item2 => item2.ProductID == item1.ProductID)) .Load(); }
方式B:用匿名类型投影后再映射
var Owner = db.Owners .Where(m => m.ID == id) .Select(m => new { Owner = m, FilteredProducts = m.Products.Where(item1 => products.Any(item2 => item2.ProductID == item1.ProductID)) }) .FirstOrDefault() ?.Owner;
内容的提问来源于stack exchange,提问作者user15750282
相关产品推荐
相关产品推荐

