【发布时间】:2019-08-11 21:15:52
【问题描述】:
我有一个包含 4 个表的简单博客数据库结构:
每个表中的一些示例数据如下所示:
博客表:
帖子表:
标签表:
PostTags 表:
我有这个 SQL 脚本。
SELECT b.Id,
b.Title,
p.Id,
p.Title,
p.PostContent,
t.Name
FROM dbo.Blogs b
JOIN Posts p ON p.BlogId = b.Id
LEFT JOIN PostTags pt ON pt.PostId = p.Id
LEFT JOIN Tags t ON t.Id = pt.TagId
WHERE b.Id = 1
AND p.IsDeleted = 0;
有几种方法可以使用 EF Core 执行此脚本。一种是直接从代码中调用这个 SQL 脚本。另一种创建存储过程或视图并从代码中调用它的方法。
假设我有以下类来映射 EF Core 执行的 SQL 脚本的结果。
public partial class Blog
{
public int Id { get; set; }
public string Title { get; set; }
public string Slogan { get; set; }
public virtual ICollection<Post> Posts { get; set; }
}
public partial class Post
{
public int Id { get; set; }
public int BlogId { get; set; }
public string Title { get; set; }
public string PostContent { get; set; }
public virtual ICollection<PostTag> PostTags { get; set; }
}
public partial class Tag
{
public int Id { get; set; }
public string Name { get; set; }
public virtual ICollection<PostTag> PostTags { get; set; }
}
public partial class PostTag
{
public int Id { get; set; }
public int PostId { get; set; }
public int TagId { get; set; }
public virtual Post Post { get; set; }
public virtual Tag Tag { get; set; }
}
这是控制器中的一个方法:
[Route("posts/{blogId}")]
[HttpGet]
public async Task<IActionResult> GetBlogPosts(int blogId)
{
string sql = @"
SELECT b.Id,
b.Title,
p.Id,
p.Title,
p.PostContent,
t.Id,
t.Name
FROM dbo.Blogs b
JOIN Posts p ON p.BlogId = b.Id
LEFT JOIN PostTags pt ON pt.PostId = p.Id
LEFT JOIN Tags t ON t.Id = pt.TagId
WHERE b.Id = 1
AND p.IsDeleted = 0;
";
// this is not working
var result = db.Blogs.FromSql(sql).ToList().FirstOrDefault();
return Ok(result);
}
如何将 SQL 脚本的结果映射到 Blog 对象,以便获得以下结果?
{
"Blog": [
{
"Id": 1,
"Title": "Another .NET Core Guy",
"Posts": [
{
"Id": 1,
"Title": "Post 1",
"PostContent": "Content 1 is about EF Core and Razor page",
"Tags": [
{
"Id": 1,
"Name": "Razor Page"
},
{
"Id": 2,
"Name": "EF Core"
}
]
},
{
"Id": 2,
"Title": "Post 2",
"PostContent": "Content 2 is about Dapper",
"Tags": [
{
"Id": 3,
"Name": "Dapper"
}
]
},
{
"Id": 4,
"Title": "Post 4",
"PostContent": "Content 4",
"Tags": [
{
"Id": 5,
"Name": "SqlKata"
}
]
}
]
}
]
}
更新 2019 年 8 月 13 日:
EF Core 尚不支持此类功能,因为它已在 EF Core Github 页面 https://github.com/aspnet/EntityFrameworkCore/issues/14525 上声明了这里
【问题讨论】:
-
您必须使用原始 SQL 查询而不是 linq-to-entity 的任何特殊原因?
-
@Lowkey,没有特别的原因。这是因为“Inlucde”或“ThenInclude”中没有选项有过滤器。见这里github.com/aspnet/EntityFrameworkCore/issues/1833
标签: c# entity-framework-core asp.net-core-2.0