虚拟属性不会在实体框架 6 中延迟加载(有警告)

本文关键字:延迟加载 警告 框架 属性 实体 虚拟 | 更新日期: 2023-09-27 18:35:11

我被困住了...

这是我的模型:

public class Payment 
{
    [ForeignKey("RecipientId")]
    public virtual Account Recipient { get; set; }
    public string RecipientId { get; set; } 
    [Key, Column(TypeName = "char"), MaxLength(36)]
    public string PaymentId { get; set; }
}

此模型通过流畅的 API 表示如下:

modelBuilder.Entity<Payment>()
    .HasRequired(t => t.Recipient)
    .WithMany()
    .HasForeignKey(t => t.RecipientId)
    .WillCascadeOnDelete(false);

这已经工作了近 3 年。我们从来没有遇到过这种映射的问题。

最近,我们决定将" MaxLength "属性更改为您在上面看到的内容。它从"8"变成了"36"。

我们以前的ID开始发生冲突,因此是时候改变了。

更改代码中的所有内容都很好。我们的单元测试都通过了。当我们在本地运行项目时,我们会看到正确的结果。

推动生产也是相当名义上的。我们更改了表格并重新调整了索引以反映新的列类型长度(从 MaxLength(8)MaxLength(36))。

再。。。这与我们在当地执行的程序相同。

问题来了:

使用新的、更长的"PaymentId"创建和保存的实体(付款)不会出错。添加关系似乎也正常工作,没有错误。

当我们在实体框架(Find,ToList,SingleOrDefault等)中执行任何一个查询API时,就会出现错误。

我们的延迟加载不起作用。收件人为空!但是,在跟踪查询时,我们注意到SQL实际上正在返回数据。出于某种原因,实体框架不会创建代理,并且对 Payment.Receiver 的任何引用都是空的。

此外,当我们对现有 ID 执行请求时(在长度更改之前),我们得到的结果没有问题。

所以问题:

  1. 为什么在本地工作(两个 ID 长度)而不是远程工作(在生产环境中)?

    • 它们可能是什么类型的数据库设置会干扰此更改。
  2. 原始 SQL 执行在生产中有效,但在创建 poxy EF 时不起作用,为什么?

任何帮助都会很棒!

--

添加原始 SQL --

错误请求

=========================================================
ID: 'bf08bdf4-a9d5-42e0-9236-a65faa4cc6ea                  '
=========================================================
SELECT 
    [Extent1].[TransactionId] AS [TransactionId],
    [Extent1].[RecipientId] AS [RecipientId],
    [Extent2].[AccountId] AS [AccountId], 
    [Extent2].[Name] AS [Name],
    FROM   [dbo].[Payment] AS [Extent1]
    INNER JOIN [dbo].[Account] AS [Extent2] ON [Extent1].[RecipientId] = [Extent2].[AccountId]
=========================================================
Recipient is null...

好要求

=========================================================
ID: 'f0e9beef                               ' 
=========================================================
SELECT 
    [Extent1].[TransactionId] AS [TransactionId],
    [Extent1].[RecipientId] AS [RecipientId],
    [Extent2].[AccountId] AS [AccountId], 
    [Extent2].[Name] AS [Name],
    FROM   [dbo].[Payment] AS [Extent1]
    INNER JOIN [dbo].[Account] AS [Extent2] ON [Extent1].[RecipientId] = [Extent2].[AccountId]
=========================================================
Recipient is not null!
RecipientId: '835cbb56                          '    
Name: John Doe

!!更新 !!

我正在调查 RAW sql 的结果,发现新更改的属性上保存了额外的空间......

我偶然发现了Ro Miller的这篇文章:

http://romiller.com/2014/10/20/ef6-1workaround-trailing-blanks-issue-in-string-joins/

传达字符串截断可能是一个问题......让我们来了解一下...

虚拟属性不会在实体框架 6 中延迟加载(有警告)

是的,

更改 ID 字段的长度后,我在返回 LINQ 到实体查询时收到不需要的"空格"。

通过遵循 Ro Miller 的拦截器指南,我能够保证在进入数据库的过程中修剪所有字符串字段。

http://romiller.com/2014/10/20/ef6-1workaround-trailing-blanks-issue-in-string-joins/

请务必注意,感受器功能最近才在 EF6.1 中提供。

希望对某人有所帮助...我今天花了11个小时。