dotnet / dotnet/efcore

Consider removing subquery pushdown in preprocessing (SubqueryMemberPushdownExpressionVisitor)

Open
#36,335 0 comments 0 reactions 0 assignees View on GitHub
area-query
Dominant language
C#
Stars
14.8k
Forks
3.4k
PR merge metrics
PR metrics pending

Description

For this test:

```c#
public virtual Task Index_constant(bool async)
=> AssertQuery(
async,
ss => ss.Set().Where(e => e.RelatedCollection[0].Int == 21),
ss => ss.Set().Where(e => e.RelatedCollection.Count > 0 && e.RelatedCollection[0].Int == 21));
```

In preprocessing, before SubqueryMemberPushdownExpressionVisitor we have the following tree:

```
DbSet()
.Where(e => e.RelatedCollection
.AsQueryable()
.ElementAt(0).Int == 21)
```

Afterwards we have:

```
DbSet()
.Where(e => e.RelatedCollection
.AsQueryable()
.Select(s => s.Int)
.ElementAt(0) == 21)
```

In other words, the member access for `Int` gets "pushed down" to before the `ElementAt()` call, and transformed to a Select(). For some context, see https://github.com/dotnet/efcore/issues/30386#issuecomment-1452643142.

Trouble is, this makes the tree complicated to process for e.g. simple complex translation: the original tree corresponds very well to simple JSON drilling into the document, where as the transformed one does not, and requires later hackery in the query pipeilne.

See also #30386, where this caused issues in EFCore.PG.

Contributor guide

Open the contributing guide

Assessment

This issue has not been assessed yet.

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.