-
Notifications
You must be signed in to change notification settings - Fork 3.2k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
[Query] Implement Reference Include #15789
Conversation
src/EFCore/Query/NavigationExpansion/Visitors/NavigationExpansionReducingVisitor.cs
Outdated
Show resolved
Hide resolved
src/EFCore/Query/NavigationExpansion/Visitors/NavigationExpansionReducingVisitor.cs
Outdated
Show resolved
Hide resolved
src/EFCore.Relational/Query/Pipeline/RelationalProjectionBindingExpressionVisitor.cs
Show resolved
Hide resolved
_includeReferenceMethodInfo.MakeGenericMethod(entityClrType, relatedEntityClrType), | ||
QueryCompilationContext2.QueryContextParameter, | ||
RelationalProjectionBindingRemovingExpressionVisitor.DataReaderParameter, | ||
// We don't need to visit entityExpression since it is supposed to be a parameterExpression only |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
entity expression can be another include for cases where we chain include on the same entity, e.g.
customers.Include("A").Include("B");
we would generate the following:
customers.Select(c => IncludeExpression(IncludeExpression(c, "A"), "B")
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
ShapedQueryExpression:
QueryExpression:
Projection Mapping:
SELECT o.OrderID, o.ProductID, o.Discount, o.Quantity, o.UnitPrice, o0.OrderID, o0.CustomerID, o0.EmployeeID, o0.OrderDate, p.ProductID, p.Discontinued, p.ProductName, p.SupplierID, p.UnitPrice, p.UnitsInStock
FROM Order Details AS o
INNER JOIN Orders AS o0 ON o.OrderID == o0.OrderID
INNER JOIN Products AS p ON o.ProductID == p.ProductID
ShaperExpression:
{
namelessParameter{0} = EntityShaperExpression:
EntityType: OrderDetail
ValueBufferExpression:
ProjectionBindingExpression: /0
Include(
namelessParameter{0},
{
namelessParameter{1} = EntityShaperExpression:
EntityType: Order
ValueBufferExpression:
ProjectionBindingExpression: /5
return namelessParameter{1}
}, Order)
Include(
namelessParameter{0},
{
namelessParameter{2} = EntityShaperExpression:
EntityType: Product
ValueBufferExpression:
ProjectionBindingExpression: /9
return namelessParameter{2}
}, Product)
return namelessParameter{0}
}
This is how it works ;)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
cc: @roji
This is how we process the materializer and convert nested include to flat structure.
Works for Sync/Async both with multi level support Resolves #15064 Changes: - Flow IncludeExpression in tree rather than method call. This will get converted to client method during compilation - Introduce Client method to perform include in relational layer (which also calls appropriate functions and does tracking) - Pull out components into variables in shaper recursively - Dedupe client projections in SelectExpression
8caaa28
to
b601867
Compare
Works for Sync/Async both with multi level support
Resolves #15064
Changes: