所以,我的问题可能比标题所暗示的要复杂一些 - 我不确定如何用简洁的标题来描述它。
假设我有两个实体,它们之间具有多对多关系:问题
和类别
。在数据库中,关系在连接表中定义。 问题
是此关系中的“拥有方” - 就像本例中的那样:https://typeorm.io/#/many-to-many-relations/what-are-many-to-many-relations
现在是我遇到困难的部分:我总是想返回问题的类别关系,以防有任何关系。如果我通过存储库执行此操作,我可以很容易地使用如下所示的方法来执行此操作:
let question = questionRepository.find(id, {relation: ['categories']};
它将返回问题及其所有类别。
当我想使用 QueryBuilder 来完成此操作时,这会变得更加困难。原因是,我试图根据一系列类别列出所有类别的问题。想象一下以下数据:
问题:
- 问题A
- 问题B
- 问题C
类别:
- 类别1
- 类别2
关系:
- 问题 A - 类别 1
- 问题 A - 类别 2
- 问题 B - 类别 1
同样,我想获取所有类别的问题。我尝试通过在 where 子句中使用 CategoryID 数组来使用 QueryBuilder 来完成此操作。这是我当前的查询构建器:
let count = categoryIds.length;
let queryBuilder = questionRepository.createQueryBuilder('q')
.leftJoin('q.categories', category)
.where('category.id IN (:categoryIds), {categoryIds})
.groupBy('q.id)
.having(COUNT(DISTINCT category.id) = :count, {count})
.getMany();
就检索包含所提供类别的所有问题而言,这效果很好。这里的问题是我想返回它找到的问题的所有类别。
想象一下,如果 categoryIds
仅包含 Category1
,它将同时返回 QuestionA
和 QuestionB
。但是,它不会返回其所有类别。
即使我将.leftJoin('q.categories',category)
更改为.leftJoinAndSelect('q.categories',category)
,它也只会在两个问题的 categories
数组中返回 Category1
。
我一直无法弄清楚这个问题,所以任何帮助将不胜感激!谢谢。
最佳答案
这完全取决于您想要实现的目标。 TypeORM 给你很多选择。有时在实体的定义中使用装饰器就足够了。
let results = questionRepository.createQueryBuilder('q')
.leftJoin('q.categories', 'cat', 'cat.id IN(:...categoryIds)', {categoryIds})
.getMany();
在其他情况下,您必须手动构造 ON
子句。
let results = questionRepository.createQueryBuilder('q')
.innerJoin('relations', 'r', 'q.id = r.queryId')
.innerJoinAndMapMany('q.categories', 'categories', 'c',
'c.id = r.categoryId AND c.id IN(:...categoryIds)', {categoryIds})
.getMany();
关于many-to-many - TypeORM多对多检索所有关系,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/62478859/