簡體   English   中英

EF6-使用可為空的屬性(外鍵,TPH)時,SQL查詢無效

[英]EF6 - invalid SQL query when using nullable property (foreign key, TPH)

實體框架為以下LINQ查詢生成無效的SQL查詢:

Car[] results = this.DbContext.Cars
    .Where(x => !x.ParentId.HasValue) // also for x.ParentId == null
    .ToArray();

我的ParentId屬性是可以為null的int,指向同一表的外鍵(Id屬性)。 我的結果是一個空數組,但不應該。 我使用其他表使用類似的查詢(檢查可空屬性是否沒有值),並且工作正常。 在這種情況下,區別在於ParentId是外鍵,數據庫表使用TPH。 這是一個錯誤還是我犯了一些錯誤? 為什么EF完全忽略可為空的屬性? 我的配置和通過EF生成的SQL(命名僅作為示例,例如“ Car”):

上下文配置:

// TPH (Table per Hierarchy)
modelBuilder.Entity<Car>()
    .Map<CarA>(x => x.Requires("type").HasValue(1))
    .Map<CarB>(x => x.Requires("type").HasValue(2))
    .Map<CarC>(x => x.Requires("type").HasValue(3))
    .Map<CarD>(x => x.Requires("type").HasValue(4));

// parent child relationship
modelBuilder.Entity<Car>()
    .HasMany(x => x.Children)
    .WithRequired()
    .HasForeignKey(child => child.ParentId);

我的課程屬性:

[Column("parent_id")]
public int? ParentId { get; set; }

public virtual List<Car> Children { get; set; }

對於:

Car[] results = this.DbContext.Cars
    .Where(x => !x.ParentId.HasValue)
    .ToArray();

我生成的SQL空結果:

SELECT 
    CAST(NULL AS int) AS [C1], 
    CAST(NULL AS int) AS [C2], 
    ...
    ...
    ...
    CAST(NULL AS decimal(18,2)) AS [C20], 
    CAST(NULL AS datetime2) AS [C21]
    FROM  ( SELECT 1 AS X ) AS [SingleRowTable1]
    WHERE 1 = 0

但是應該是:

...
...
WHERE [Extent1].[car] IS NULL

對於:

var results = this.DbContext.Cars
    .Where(x => x.ParentId.HasValue)
    .ToArray();

我得到所有具有生成的SQL的實體(ParentId被忽略):

SELECT 
    [Extent1].[type] AS [type], 
    [Extent1].[id] AS [id], 
    [Extent1].[parent_id] AS [parent_id], 
    [Extent1].[name] AS [name], 
    ...
    ...
    ...
    FROM [dbo].[car] AS [Extent1]
    WHERE [Extent1].[type] IN (1,2,3,4)

在EF6 6.0.2 / 6.1.1和MS SQL Server上進行了測試。

哇……這是一個有趣的行為,但是解決方案非常簡單。 您具有可為空的外鍵屬性,但已根據需要定義了關系。 只是改變

modelBuilder.Entity<Car>()
    .HasMany(x => x.Children)
    .WithRequired()
    .HasForeignKey(child => child.ParentId);

modelBuilder.Entity<Car>()
    .HasMany(x => x.Children)
    .WithOptional()
    .HasForeignKey(child => child.ParentId);

而且它將起作用。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM