У меня есть сайт социальной сети, построенный на основе Elgg (php + mysql). Моя цель - найти всех друзей данного пользователя, а также дружеские отношения между этими друзьями.
Вся необходимая информация находится в двух таблицах:
- таблица «users», в которой пользователи идентифицируются по уникальному идентификатору guid
- и таблица «отношений», где отношения друзей представлены триплетами (guid_one, friend, guid_two)
Дружеские отношения в Elgg могут быть как односторонними, так и двунаправленными, это больше похоже на отношения Twitter «следуй». Уникальность отношений триплетов гарантирована.
Краткий пример:
Учитывая (1, «Джо»), (2, «Джек») (3, «Джим») пользователей и следующие отношения (1, «друг», 2), (2, «друг», 1), (1 , "друг", 3), (2, "друг", 3), это можно интерпретировать как
- Джо и Джек - общие друзья (следуют друг за другом)
- За Джимом следуют Джо и Джек
Я бы хотел получить
- список всех отношений между друзьями для любого данного пользователя
- в порядке убывания количества отношений (т.е. сначала перечислите отношения для тех друзей, которые следуют за большинством моих друзей)
- желательно в одном запросе
Какой самый эффективный способ сделать это?
РЕДАКТИРОВАТЬ Пока у меня есть это:
SELECT
u1.guid, u1.name, u2.guid, u2.name
FROM
users u1
INNER JOIN relationships r1 ON
(u1.guid = r1.guid_one AND r1.relationship = "friend")
INNER JOIN users u2 ON (r1.guid_two = u2.guid)
INNER JOIN relationships r2 ON
((r2.guid_one = xxx AND r2.guid_two = u1.guid)
OR (r2.guid_two = xxx AND r2.guid_one = u1.guid))
INNER JOIN relationships r3 ON
((r3.guid_one = xxx AND r3.guid_two = u2.guid)
OR (r3.guid_two = xxx AND r3.guid_one = u2.guid))
Где ххх обозначает руководство пользователя, которое меня интересует. С этим связаны две основные проблемы: он не упорядочен по количеству связей и мучительно медленен из-за большого количества соединений. Также он получает только односторонние отношения (кто за кем следует среди моих друзей) - как бы это ни было решено профсоюзом, я думаю.
Есть идеи, как улучшить это?