Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why does EF generate this sql when querying reference property

When using the AdventureWorks database and issuing this query:

   AdventureWorksEntities entities = new AdventureWorksEntities();
   entities.Contacts.Where(x => x.FirstName == "A" 
                               || x.FirstName == "B" 
                               || x.FirstName == "C")
                     .ToList();

Will be translated to this sql, which is the best it can:

//ommited for brevity
FROM [Person].[Contact] AS [Extent1]
WHERE [Extent1].[FirstName] IN (N'A',N'B',N'C')

However when I issue this query:

entities.Employee.Where(x => x.Contact.FirstName == "A" 
                             || x.Contact.FirstName == "B" 
                             || x.Contact.FirstName == "C")
                .ToList();

I get this SQL:

//ommited for brevity
FROM   [HumanResources].[Employee] AS [Extent1]
INNER JOIN [Person].[Contact] AS [Extent2] ON [Extent1].[ContactID] = [Extent2].[ContactID]
LEFT OUTER JOIN [Person].[Contact] AS [Extent3] ON [Extent1].[ContactID] = [Extent3].[ContactID]
WHERE [Extent2].[FirstName] = N'A' OR [Extent3].[FirstName] IN (N'B',N'C')

Why am I getting an inner and outer join and is EF splitting the where across both of them?

Of Note using contains creates the same SQL:

var names = new List<string>{"A", "B", "C"};
entities.Employee.Where(x => names.Contains(x.Contact.FirstName)).ToList();

EDIT: So it appears to be a EF bug, I've accepted the answer which provided a work around

EDIT: Opened connect issue, it's located here

like image 981
BennyM Avatar asked Jan 28 '11 14:01

BennyM


People also ask

How does SQL determine EF generated?

For use this, you're going to want to set a breakpoint below your EF Core query. Breakpoint hit after the query. Once the breakpoint is hit hover over query to expand then click on > Debug View > The dropdown beside the magnifying glass> Text Visualizer. There you have it, the SQL that will be sent to the database.

How do I turn off Entity Framework tracking?

In Entity Framework, change tracking is enabled by default. You can also disable change tracking by setting the AutoDetectChangesEnabled property of DbContext to false. If this property is set to true then the Entity Framework maintains the state of entities.

How do I see SQL query generated by Entity Framework Core?

Visual Studio Output The latest versions of . NET Core make it pretty easy to output the SQL when debugging. You can set the logging level for Microsoft to “Information”. Then you can view the SQL in the output log when running in debug mode from Visual Studio.


1 Answers

Write a Stored Procedure which accepts a TVP as input parameter and let EF materialize the results from the SP :)

like image 127
Tim Mahy Avatar answered Oct 01 '22 19:10

Tim Mahy