Sphinx Поиск нескольких таблиц и совокупных результатов с использованием PHP API

Я пытаюсь выполнить поиск нескольких таблиц MySQL с различными полями, используя Sphinx, и объединить все результаты в один набор, основанный на релевантности.

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

Когда я запрашиваю использование SEARCH через оболочку, я получаю всю информацию о результатах обратно, как ожидалось. Однако, когда я использую PHP API, результат возвращается только с идентификаторами строк и, следовательно, никак не может определить, из какой таблицы он пришел.

Есть ли способ заставить PHP API рассказать мне, какая таблица / индекс он пришел, чтобы я мог войти и запросить фактические данные?

Альтернатива, которую я рассматриваю, заключается в попытке обработать вывод из сценария оболочки, но это кажется беспорядочным.

Вот PHP: $ search = $ _GET ['query']; // Информация о соединении $ sphinxClient = new SphinxClient (); $ sphinxClient-> SetServer ('localhost', 9312); $ SphinxClient-> SetMaxQueryTime (5000);

 //Sphinx Result Configuration $sphinxClient->SetMatchMode(SPH_MATCH_ANY); $sphinxClient->SetRankingMode( SPH_RANK_PROXIMITY_BM25 ); $sphinxClient->SetLimits(0, 20); // Give me back the results as an array $sphinxClient->SetArrayResult(true); $searchResults = $sphinxClient->Query( $search, 'user model' ); 

Скрипт оболочки просто:

 ./search SEARCHTERM 

где SEARCHTERM – это поиск

который выводит что-то похожее:

Sphinx 2.0.3-release (r3043) Copyright (c) 2001-2011, Andrew Aksyonoff Авторское право (c) 2008-2011, Sphinx Technologies Inc (http://sphinxsearch.com)

используя файл конфигурации '/usr/local/sphinx/etc/sphinx.conf' … index 'user': query 'NEWTON': возвращено 10 совпадений из 10 всего за 0.000 секунд

отображение совпадений: 1. document = 1, weight = 2629, time = Thu Jan 1 00:33:32 1970 id = 1 first_name = Joe last_name = Shmo company = Acme

Выход API PHP в формате JSON: {"error": "", "warning": "", "status": "good", "fields": ["name", "code_name", "code", "description »,« рейтинг »,« углы »,« опубликованные »,« ключевые слова »,« referenced_num »,« одобренные »,« used_num »,« avg_runtime »,« примеры »,« editor »,« publish_time »],« attrs », : {"time": 2}, "matches": [{"id": 1, "weight": "1", "attrs": {"time": 2012}}], "total": "1" , "total_found": "1", "time": "0.000", "words": {"posuere": {"docs": "1", "hits": "2"}}}

Это нормально, что Sphinx возвращает идентификаторы объекта (строки). Проблема в вашей модели. Если вы не можете определить по id, какой именно объект, ваша модель неверна. Возможные варианты:

  • создать отдельный индекс sphinx для типа объекта (таблица или группа связанных таблиц)
  • улучшить нумерацию объектов, чтобы сделать возможной идентификацию объектов, например, некоторым префиксом.

Я абсолютно уверен, что при поиске по API вы не только получаете идентификаторы совпадающих документов, но и все другие значения int найденного документа.

Поэтому вы можете попробовать добавить в свой источник что-то вроде

 SELECT id, "1" as type FROM table1 sql_attr_uint = type 

и поле type теперь сообщает вам, в какой таблице находится идентификатор

Обратите внимание, однако, что есть несколько проблем с одновременным поиском нескольких индексов разных таблиц.

  1. Вам нужно убедиться, что идентификатор не отображается больше, чем один раз в вашем результирующем наборе (обычно предлагаемым решением было бы поместить идентификатор на 1000000 или каким-то другим способом, что лично я считаю ужасным)

  2. Результаты содержат только столбцы от первого найденного индекса. Вы должны убедиться, что все ваши источники возвращают одни и те же столбцы.

Лично каждый раз, когда я думал о поиске нескольких индексов сразу, я в конечном итоге искал каждый отдельно и представлял результаты как таковые.

Обновление: добавлен sql_attr_uint

если таблицы имеют одинаковую структуру, вы можете использовать объединение с вашими sql-запросами

 SELECT * FROM table1 WHERE id IN (ids,from,sphinx) UNION SELECT * FROM table2 WHERE id IN (ids,from,sphinx) ... UNION SELECT * FROM tableN WHERE id IN (ids,from,sphinx) 

будьте осторожны, что это интенсивный процессор