Skip to content

.Any() on collection navigations after projection can cause client-side evaluation #12728

@csboling

Description

@csboling

In some cases using Where clauses of the form .Where(x => x.Collection.Any(...)) or
.Where(x => x.Collection.Where(...).Any()) can cause client-side evaluation when the Where clause follows .Select. It seems that presence or absence of .ToList() inside .Select(...) makes a difference here when projecting to a DTO with an IEnumerable collection property.

Steps to reproduce

Here is a project which configures client-side evaluation as an exception, causing some Xunit test cases to fail.

A query like

dbContext.Set<Library>()
    .Where(l => l.Books.Any(b => b.Title == "The Cat in the Hat"))
    .Select(l => new LibraryDto { . . . })

is translated to SQL as expected (WHERE EXISTS . . .). However, when the projection comes first,

dbContext.Set<Library>()
    .Select(l => new LibraryDto { . . . })
    .Where(l => l.Books.Any(b => b.Title == "The Cat in the Hat"))    

cannot be translated. When .ToList() is not present in the .Select(...), a query like

dbContext.Set<Library>()
    .Select(l => new LibraryDto { . . . })
    .Where(l => l.Books.Any())

can be translated, but this is evaluated client-side when .Any() contains a comparison on the collection items or when ToList() is used for the collection navigation property.

Not sure if this is a duplicate issue or a limitation of projection when dealing with correlated subqueries.

Further technical details

EF Core version: 2.1.1
Database Provider: Sqlite in the test project, but affects other providers as well.
Operating system: Windows 10
IDE: Visual Studio 2017 15.7.5, .NET Core SDK 2.1.302.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type
    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions