-
Notifications
You must be signed in to change notification settings - Fork 3.4k
Description
When EF translates a lambda (e.g. Where(b => b.Name == foo), before actually translating the lambda body, we currently run "RemapLambdaBody"; this does a recursive search-and-replace pass, replacing instances of the ParameterExpression (b) with e.g. StructuralTypeShaperExpression. This way, when RelationalSqlTranslatingExpressionVisitor runs, it encounters the shaper rather than the ParameterExpression.
This extra path is bad for performance: the tree is almost always rewritten (it's not just a read-only pass), and multiple lambdas can be nested, leading to the same fragment being rewritten again and again (e.g. blogs.Where(b => b.Posts.Where(p => p.Comments.Where(c => ...)))).
In addition, this means that RelationalSqlTranslatingExpressionVisitor lacks context during visitation, and cannot know that it's visiting what used to be a lambda parameter. This is blocking work on #32980.
Note the similarity with #31309, which tracks removing another pre-visitation pass for handling owned navigations inside the lambda body.