Skip to content

WHERE ... IN ... for .Contains(.Convert()) expressions issue #8207

Closed as duplicate
@Remleo

Description

@Remleo

Code to reproduce:

// Models
public class ProductCard
{
        public virtual int Id { get; set; }
        //...
        public virtual int? GroupId { get; set; }
        public virtual ProductGroup Group { get; set; }
        //...
}

public class ProductGroup
{
        public virtual int Id { get; set; }
        //...
}
// Code 1
var someIds = new [] {1, 2, 3}; // Have some Ids from method's parameter for example
dbContext.ProductCards.Where(
                    card => someIds.Contains((int)card.GroupId)).Load();

// Code 2
dbContext.ProductCards.Where(
                    card => dbContext.ProductGroups.Select(group => group.Id).Where(...)
                                        .Contains( (int)card.GroupId) 
).Load();

The Code 1 throws warning:
Microsoft.EntityFrameworkCore.Query.Internal.SqlServerQueryCompilationContextFactory:Warning: The LINQ expression 'Contains(Convert([card].GroupId))' could not be translated and will be evaluated locally.

But the Code 2 generates correct SQL (ignores .Convert()):

SELECT [card].[Id], ...
FROM [ProductCard] AS [card]
WHERE [card].[GroupId] IN (
    SELECT [group].[Id]
    FROM [ProductGroup] AS [group]
)

The problem is in convertation from int? to int. The PK is int, but the FK is int?.

I can use .Cast<int?> via extra local var, but it's an extra work for CPU and memory. LINQ to SQL compiler can simply ignore .Convert().

In the EF Core 1.1.0-preview1-final works fine! This problem appeared in version 1.1.1.

Metadata

Metadata

Assignees

Labels

No labels
No labels

Type

No type

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions