@lolrofl01

Как составить такой запрос с поиском по тегам?

Добрый день.
Пишу фильтр постов, и столкнулся с большой проблемой. Фильтровать посты можно по юзеру, дате, статусу, тегам. С последним и возникла проблема. У меня есть промежуточная таблица postTags. У нее следующие колонки:
id
post_id
tag_id

Фильтрую пока вот так:
SELECT p.*, u.name FROM posts p
LEFT JOIN users u ON u.id = p.user_id
LEFT JOIN postTags pt ON pt.post_id = p.id
WHERE p.user_id = 4
AND pt.tag_id IN (3,5,7)


Разумеется, мне показываются посты, которые присутствуют хотя бы в одном из тегов с айди 3, 5, 7.
Но необходимо чтобы пост ОБЯЗАТЕЛЬНО был с тегами, у которых айди 3, 5, 7. Если хотя бы одного из этих тегов нет - значит пост не подходит под условия.

Перекопал документацию, но что-то никаких аналогов IN я не нашел...видел какой-то пример с having count, но что-то совсем его не понял...
  • Вопрос задан
  • 111 просмотров
Решения вопроса 1
@alexalexes
Решение 1 - с модификацией запроса под определенный набор параметров.
Сколько одновременных тегов должно присутствовать на входе, столько и будет join-ов таблицы тегов.
SELECT p.*, u.name FROM posts p
JOIN users u ON u.id = p.user_id
JOIN postTags pt1 ON pt1.post_id = p.id and pt1.tag_id = 3
JOIN postTags pt2 ON pt2.post_id = p.id and pt2.tag_id = 5
JOIN postTags pt3 ON pt3.post_id = p.id and pt3.tag_id = 7
WHERE p.user_id = 4

PS: Если в where указали конкретного пользователя, то users мы присоединяем полностью (без left), так будет работать быстрее.
Решение 2 - контролируем число уникальных тегов на выходе.
Select a.*
from
(
SELECT p.*, u.name, count (distinct  pt1.tag_id) over (partition by p.id) unik_tag_count
 FROM posts p
JOIN users u ON u.id = p.user_id
JOIN postTags pt1 ON pt1.post_id = p.id
WHERE p.user_id = 4
and pt1.tag_id in (3, 5, 7)
) a
where  a.unik_tag_count = 3 -- уникальное кол-во тегов на один пост
Ответ написан
Пригласить эксперта
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Войти через центр авторизации
Похожие вопросы