c# - .NET Core/EF Core 2.0 升级后急切加载 "No coercion operator is defined between types"

标签 c# linq .net-core entity-framework-core eager-loading

在 .NET Core 1.x 中,我们有一个如下所示的方法:

public async Task<(PaperRecord Component, PaperPointerRecord Pointer)> GetOneAsync(DbSet<PaperPointerRecord> paperPointerRecords,
                                                                                   int? paperId = null,
                                                                                   long? externalPaperId = null,
                                                                                   Expression<Func<PaperPointerRecord, bool>> filter = null)
{
    var query = filter is null ? paperPointerRecords.AsQueryable() : paperPointerRecords.Where(filter);

    if (paperId.HasValue)
        query = query.Where(_ => _.PaperPointerId == paperId);

    if (externalPaperId.HasValue)
        query = query.Where(_ => _.ExternalId == externalPaperId);

    var record = await query.Include(_ => _.Paper)
                            .ThenInclude(_ => _.PaperColors)
                            .Select(_ => new
                                         {
                                             PaperRecord = _.Paper,
                                             PaperPointerRecord = _
                                         })
                            .SingleOrDefaultAsync();

    return !(record is null) ? (record.PaperRecord, record.PaperPointerRecord) : throw NewPaperRecordNotFoundException(paperId, externalPaperId);
}

这对我们非常有用。将整个项目升级到所有 .NET Core 2.0 和 EF Core 2.0 后,该方法抛出此异常:

System.InvalidOperationException occurred: No coercion operator is defined between types 'PaperPointerRecord' and 'PaperRecord'.

这个异常发生在这个 block 中:

var record = await query.Include(_ => _.Paper)
                        .ThenInclude(_ => _.PaperColors)
                        .Select(_ => new
                                     {
                                         PaperRecord = _.Paper,
                                         PaperPointerRecord = _
                                     })
                        .SingleOrDefaultAsync();

如果我删除预先加载并像这样设置它,那么错误就会消失,但我也没有得到预期的结果:

var record = await query.Select(_ => new
                                     {
                                         PaperRecord = _.Paper,
                                         PaperPointerRecord = _
                                     })
                        .SingleOrDefaultAsync();

我检查了 Microsoft Documentation为此,我没有看到那里显示任何表明我们在预加载方面做错了什么。

最佳答案

Include 在这种情况下没有用,因为您正在返回一个投影并且 Include 被忽略(阅读关于忽略的包含 here )。

如果“预期结果”是指您希望 record.PaperRecord.Paper 具有一个值,只需将其包含在您的投影中即可; EF 将建立关系。

new
{
    PaperRecord = _.Paper,
    PaperPointerRecord = _,
    PaperColor = _.Paper.PaperColor,
}

关于c# - .NET Core/EF Core 2.0 升级后急切加载 "No coercion operator is defined between types",我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/46323562/

相关文章:

c# - 无需互操作即可获取 PDF 中的所有单词及其位置

c# - 在 C# 中重新设置基于 1 的数组

c# - 从列表中删除相似的矩形

c# - 如何使用 Linq 和 C# 3.5 从 ComboBox 中的 SelectedItem 获取值

c# - 为什么在 .net core 3.1 中找不到 Web Api 授权服务?

c# - 为什么我无法反序列化 KnownType 的 anyType?

c# - 在组合框中设置默认项

c# - 在 x.Kind = "value"时选择 Top(x)

heroku - AddStackExchangeRedisCache和heroku Redis连接字符串

c# - PostAsync() 方法在点网核心窗口服务中不起作用