entity-framework-core - 在 Entity Framework Core 中查询必须包含一组值的记录
问题描述
我正在尝试在站点中创建一个过滤系统,该系统可以用多个标签标记的一组记录。最终我希望过滤器支持 OR、AND 和 NOT,但现在我只是想让 AND 工作。
以下是具有相关属性的实体,它们只是在 EF Core 中建模的多对多关系。
public class Record
{
public int Id { get; set; }
public ICollection<RecordTag> RecordTags { get; set; }
}
public class RecordTag
{
public int RecordId { get; set; }
public Song Record { get; set; }
public int TagId { get; set; }
public Tag Tag { get; set; }
}
public class Tag
{
public int Id { get; set; }
public string Name { get; set; }
public ICollection<RecordTag> RecordTags { get; set; }
}
我尝试编写一个 EF Core 查询,如下所示:
var tagList = tags.Split(',');
// tagList now contains the strings of tags the user has filtered on
Records = recordRepository.Query() // simply returns IQueryable<Records>
.Where(r=> tagList.All( // For each record, iterate through all tags selected by the user
t => r.RecordTags.Select(rt => rt.Tag.Name).Contains(t))) // For each user selected tag, get all the tags on the record and ensure it contains the tag we're iterating over
.Include(r => r.RecordTags).ThenInclude(rt => rt.Tag).ToList(); // Include the tag data back with the parent entity.
但是,这会引发错误
[查询] 无法翻译。以可翻译的形式重写查询,或通过插入对 AsEnumerable()、AsAsyncEnumerable()、ToList() 或 ToListAsync() 的调用显式切换到客户端评估
我宁愿不必带回更大的集合并在应用程序服务器上对其进行过滤,而是直接针对数据库正确构建查询。
为什么这个查询无效?还有另一种写法吗?
解决方案
您可以在 foreach 循环中添加 where 条件。
var recordRepositoryQuery = recordRepository.Query();
foreach(var tag in taglist)
{
recordRepositoryQuery = recordRepositoryQuery.Where(r => r.RecordTags.Select(rt => rt.Tag.Name).Contains(tag))
}
推荐阅读
- python - 如何将文本文件转换为一个列表
- python - 如何为微调器选择 kivy 旧值
- c# - 如何将泛型接口作为方法参数传递?
- javascript - 我们如何提高使用递归组件呈现深度嵌套树数据的反应应用程序的性能
- python - PHPExcel:加载大文件时遇到问题
- c++ - ifstream 文件不会在 C++ 中打开
- vue.js - Vuetify 在滚动时淡入淡出
- nginx - Nginx 重定向到 Phoenix 丢失授权标头
- javascript - jquery我怎样才能让一键做不止一件事,比如有没有中断功能或什么?
- ios - SwiftUI - 将 ListStyle 包装在一个枚举中并将其转换回 ListStyle