我有一个表(“ ProductParameter”)将两个表(“ Product”和“ Parameter”)链接在一起,它具有字段Id,ProductId,ParameterId,Value,每个ParameterId都有一组[Value]我需要过滤
一一过滤一个ParameterId(其中pp.ParameterId = 4)后,首先由两个ParameterId(其中pp.ParameterId = 4或pp1.ParameterId = 2和pp1.Value ='Standard')收集。示例:
+---------+-------------+------------+---------+
| ID | ProductId |ParameterId | Value |
+---------+-------------+------------+---------+
| 25 | 14 | 2 | Standard|
| 26 | 14 | 3 | CK45 |
| 27 | 14 | 4 | 63 |
| 28 | 15 | 2 | XXX |
| 29 | 15 | 3 | CK45 |
| 30 | 15 | 4 | 70 |
| 34 | 17 | 2 | Standard|
| 35 | 17 | 3 | CK45 |
| 36 | 17 | 4 | 40 |
| 37 | 25 | 2 | Standard|
| 38 | 25 | 3 | CK45 |
| 39 | 25 | 4 | 20 |
+---------+-------------+------------+---------+-
应返回:
+-------+
| Value |
+-------+
| 63 |
| 40 |
| 20 |
+-------+
查询的逻辑如下:
select distinct pp.Value from ProductParameters pp
join ProductParameters pp1 on pp1.ProductId = pp.ProductId and
pp1.ParameterId = 2 and pp1.Value = 'Standard'
where pp.ParameterId = 4
这是我在EF核心中的查询:
public async Task<IEnumerable<ProductParameter>> GetProductDiameters(long id, string param = "Standard")
{
var value = await _context.ProductParameters
.Include(p => p.Product)
.ThenInclude(p => p.ProductParameters.Where(i => i.Value == param))
.Where(p => p.ParameterId == id)
.Distinct()
.ToListAsync();
return value;
}
引发异常:
ArgumentException:ThenInclude属性lambda表达式'p => {来自p.ProductParameters中的ProductParameter i,其中[[i] .Value == __param_0)选择[i]}'无效。该表达式应表示属性访问:“ t => t.MyProperty”。要定位在派生类型上声明的导航,请指定目标类型的显式键入的lambda参数,例如'(派生d)=> d.MyProperty'。
哪里出了错?
答案 0 :(得分:0)
EF抱怨是因为您试图在。ThenInclude(..)
语句中进行过滤。
var value = await _context.ProductParameters
.Include(p => p.Product)
.ThenInclude(p => p.ProductParameters.Where(i => i.Value == param)) //<-- here
.Where(p => p.ParameterId == id)
.Distinct()
.ToListAsync();
这是个问题,因为EF会使用EF内部的函数来确定应该紧急加载的表。 Include(..)
和ThenInclude(..)
中的这些函数应该始终指向相关的表,并且没有其他:)
正确的查询方式如下:
var value = await _context.ProductParameters
.Include(p => p.Product)
.ThenInclude(p => p.ProductParameters) // <- removed the Where clause from here
.Where(p => p.ParameterId == id)
.Where(p => p.ProductParameters.Value == param)) //<- and added it here
.Distinct()
.ToListAsync();