Allow standalone set operations (and ValuesExpression) without a wrapping SelectExpression
- Dominant language
- C#
- Stars
- 14.8k
- Forks
- 3.4k
- PR merge metrics
- PR metrics pending
Description
Our SQL query tree architecture currently represents each set operation as wrapped by a SelectExpression; in SQL generation, if the SelectExpression is detected to be a simple wrapper with no other clauses ([code](https://github.com/dotnet/efcore/blob/main/src/EFCore.Relational/Query/QuerySqlGenerator.cs#L288)), the SelectExpression isn't outputted.
We should change our SQL tree to exactly match the SQL it will output, allowing bare set operations/ValuesExpressions to appear directly as a table in a select expression (and even as the top-level node in the tree).
Having the SelectExpression wrapper in the tree causes some complications, such as having to manage aliases for SelectExpressions that will never actually appear in the output, etc.
Note that to do this, we'll likely need to empty SelectExpression entirely out of private state (otherwise e.g. UnionExpression will also need to have `_projectionMapping`, identifiers etc.). This also depends on switching to immutability during translation (at least for this), since applying a set operation would no longer mutate a select (pushing itself down), but rather return a new set operation expression wrapping that select.
Contributor guide
Assessment
This issue has not been assessed yet.