MySQL Search Query - Поиск по тегам тоже :( - PullRequest
0 голосов
/ 21 июня 2010

Итак, у меня есть веб-приложение, которое позволяет пользователям отправлять код.Представления хранятся в таблице code, и пара столбцов с полнотекстовым индексированием.Вот как я выполнял поиск до сих пор.

Но пользователи могут отправлять свои заявки с таким количеством тегов, как им нравится - и я бы хотел, чтобы они также были включены в поиск (но всев одном запросе ...).Теги хранятся в таблице tags, и есть таблица пересечений под названием code_tags, в которой хранятся code_id и tag_id.Стандартный материал.

Мой «старый» поисковый запрос был таким:

SELECT *
  FROM code
 WHERE MATCH (title, summary, code) AGAINST ('$searchterm')

$searchterm был получен через PHP $ _POST.

Поэтому я попытался написать немногобольше «продвинутого» запроса:

SELECT code.*, 
       code_tags.*, 
       tags.*, 
       tags.tag
  FROM code, code_tags, tags
 WHERE code_tags.code_id = code.id
   AND tags.id = code_tags.tag_id
   AND MATCH (title, summary, code) AGAINST ('$searchterm') 

Но все, что он сделал, это вернул ... Ничего .Даже когда был введен совершенно правильный поисковый термин.

Поэтому я закомментировал последнюю строку:

SELECT code.*, code_tags.*, tags.*, tags.tag
  FROM code, code_tags, tags
 WHERE code_tags.code_id = code.id
   AND tags.id = code_tags.tag_id
-- AND MATCH (title, summary, code) AGAINST ('php') 

. Это возвращает каждую отправку в базу данных.Но одна и та же строка повторяется столько раз, сколько для нее есть тегов (единственное отличие - тег в каждой возвращаемой строке).

EG:

Ошибка запроса http://i48.tinypic.com/2m5z80m.png

Итак, наконец , я подумал, что буду умным и GROUP_CONCAT теги:

SELECT code.*, code_tags.*, tags.*, GROUP_CONCAT(tags.tag SEPARATOR ' ') AS taggroup
  FROM code, code_tags, tags
 WHERE code_tags.code_id = code.id
   AND tags.id = code_tags.tag_id
-- AND MATCH (title, summary, code, taggroup) AGAINST ('php')`

С этим связаны две довольно большие проблемы.

  1. С закомментированной последней строкой AND MATCH возвращается только одна строка (со всеми деталями первой записи вcode таблица - и группа тегов перечисляет каждый тег для каждой отправки!
  2. С учетом последней строки AND MATCH я получаю следующую ошибку: Unknown column 'taggroup' in 'where clause' - черт!

Итак, что я должен делать?: S

Ответы [ 2 ]

0 голосов
/ 21 июня 2010

Причина следующая:

SELECT code.*, code_tags.*, tags.*, tags.tag
  FROM code, code_tags, tags
 WHERE code_tags.code_id = code.id
   AND tags.id = code_tags.tag_id
   AND MATCH (title, summary, code) AGAINST ('php') 

... не возвращает никаких результатов из-за того, что у вас нет записей таблицы code, заголовок / сводка / код которых совпадают с "php" И имеют отношение к таблицам CODE_TAGS или TAGS. Переключаясь на синтаксис ANSI-92 JOIN, попробуйте:

SELECT c.*, ct.*
  FROM CODE c
  JOIN CODE_TAGS ct ON ct.code_id = c.id
 WHERE MATCH (title, summary, code) AGAINST ('php')

Если ничего не возвращается, то проблема в том, что ни одна из записей, удовлетворяющих полнотекстовому поиску, не связана с чем-либо в таблице CODE_TAGS - вам нужно добавить ассоциации, прежде чем она заработает. Это должно пролить свет на то, если добавление JOIN в таблицу TAGS повлияет на что-либо:

SELECT c.*, ct.*
  FROM CODE c
  JOIN CODE_TAGS ct ON ct.code_id = c.id
  JOIN TAGS t ON t.id = ct.tag_id
 WHERE MATCH (title, summary, code) AGAINST ('php')
0 голосов
/ 21 июня 2010

Не знаю, как вы можете выбрать tags.* и GROUP_CONCAT одновременно, но некоторое время назад, так как я работал с MySQL, в любом случае объедините ваши данные и сгруппируйте их по столбцам, которые, как вы хотите, должны работать. Пример ниже.

SELECT code.id, code.title, GROUP_CONCAT(tags.tag SEPARATOR ' ')
  FROM code
 INNER JOIN code_tags ON code.id = code_tags.code_id
 INNER JOIN tags ON code_tags.tag_id = tags.id
 WHERE MATCH (code.title, code.summary, code.code) AGAINST ('php')
 GROUP BY code.id, code.title
...