Извлечение затронутой таблицы при полнотекстовом поиске

#php #full-text-search #union

#php #полнотекстовый поиск #объединение

Вопрос:

Я просматриваю 3 разные таблицы с помощью полнотекстового поиска, и мне нужно определить, из какой таблицы получен результат. Это то, что у меня есть сейчас:

 SELECT id, title AS page_title, MATCH(title) AGAINST(:search_term IN BOOLEAN MODE) AS score FROM pages WHERE MATCH(title) AGAINST(:search_term IN BOOLEAN MODE) UNION
SELECT id, title AS agenda_title, MATCH(title) AGAINST(:search_term IN BOOLEAN MODE) AS score FROM agenda WHERE MATCH(title) AGAINST(:search_term IN BOOLEAN MODE) UNION
SELECT id, title AS news_title, MATCH(title) AGAINST(:search_term IN BOOLEAN MODE) AS score FROM news WHERE MATCH(title) AGAINST(:search_term IN BOOLEAN MODE) ORDER BY score ASC
  

Я определяю, был ли установлен page_title, а если нет, был ли установлен заголовок повестки дня и т.д.
Но результат всегда из первого запроса (страницы). Таким образом, если посетитель выполнит поиск и найдет новость, в этом случае она будет отображаться как страница.

Итак, мой вопрос в том, что я делаю не так? И это лучший способ сделать это?

Заранее спасибо!

Ответ №1:

Когда вы используете UNIONs подобным образом, добавьте столбец-определитель, просто константу, к каждой таблице, чтобы вы знали, из какой таблицы взята каждая запись.

 SELECT source, id, title, score
    FROM
    (SELECT 'pages' AS source, id, title, MATCH(title) AGAINST(:search_term IN BOOLEAN MODE) AS score
        FROM pages WHERE MATCH(title) AGAINST(:search_term IN BOOLEAN MODE)
    UNION
    SELECT 'agenda' AS source, id, title, MATCH(title) AGAINST(:search_term IN BOOLEAN MODE) AS score 
        FROM agenda WHERE MATCH(title) AGAINST(:search_term IN BOOLEAN MODE) UNION
    SELECT 'news' AS source, id, title, MATCH(title) AGAINST(:search_term IN BOOLEAN MODE) AS score 
        FROM news WHERE MATCH(title) AGAINST(:search_term IN BOOLEAN MODE)
) ORDER BY score ASC
  

Вам также нужно будет обернуть ее в SELECT to ORDER BY по всему объединенному набору, я думаю, что порядок, который у вас был, будет только в последней таблице. Изменение title атрибута также не является хорошей идеей, поскольку имена столбцов должны быть одинаковыми для UNION , иначе они будут объединены с первым встречающимся заголовком или просто очистят имя столбца.

Ответ №2:

Попробуйте запрос типа:

 SELECT 'pages' AS used_table,id, title, MATCH(title) AGAINST(:search_term IN BOOLEAN MODE) AS score FROM pages WHERE MATCH(title) AGAINST(:search_term IN BOOLEAN MODE) UNION
SELECT 'agenda' AS used_table,id, title , MATCH(title) AGAINST(:search_term IN BOOLEAN MODE) AS score FROM agenda WHERE MATCH(title) AGAINST(:search_term IN BOOLEAN MODE) UNION
SELECT 'news' AS used_table,id, title , MATCH(title) AGAINST(:search_term IN BOOLEAN MODE) AS score FROM news WHERE MATCH(title) AGAINST(:search_term IN BOOLEAN MODE) ORDER BY score ASC
  

и проверьте поле used_table, чтобы проверить, использовалась ли таблица witch.