Как реализовать персонализированный поток событий? - PullRequest
5 голосов
/ 06 декабря 2009

Я собираюсь поработать над вдохновляющим сайтом для неправительственной организации и собираюсь реализовать какой-то поток событий в стиле Facebook, с такими событиями, как «Майкл рекомендовал яблочный пирог », « Джон прокомментировал шоколадный торт »,« Карамельная помадка была опубликована 8 часов назад Алисой »и т. Д.

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

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

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

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

Ответы [ 5 ]

2 голосов
/ 06 декабря 2009

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

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

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

Я не использовал Gearman, но если это такая штука, которая позволяет вам загружать среду вашего приложения в фоновом режиме и получать события для обработки через очередь, то это, вероятно, хорошая идея.

Мое простое решение состояло в том, чтобы свернуть мои собственные, используя beanstalkd и мои собственные сценарии PHP.

1 голос
/ 07 декабря 2009

Вы смотрели на модуль Activity ? Вот выдержка из его страницы проекта:

... следит за тем, что люди делают на вашем сайте, и предоставляет мини-каналы этих действий в блоках, в специальной таблице и через RSS. Модуль является расширяемым, так что любой другой модуль может интегрироваться с ним. Создаваемые сообщения настраиваются через интерфейс администратора и являются контекстно-зависимыми.

Мне будет любопытно, что вы придумали, потому что нужно сделать что-то подобное в ближайшем будущем.

1 голос
/ 06 декабря 2009

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

1 голос
/ 06 декабря 2009

Это звучит как что-то, что может быть решено с надлежащим индексом. Я бы построил решение исходя из предположения, что база данных способна справиться с этим, но разместил службу перед базой данных и позволил всем клиентам пройти через это. Если дела начнутся слишком медленно, вы можете ввести различные типы кэширования в этом слое. Как и в случае большинства решений о производительности, попытка сделать это сразу, вероятно, не очень хорошая идея.

1 голос
/ 06 декабря 2009

Не знаю, как структурирована ваша БД (возможно, вы захотите рассказать нам больше), но что-то очевидное, например,

SELECT events.* FROM events, event_tags, user_tags
     WHERE event_tags.event_id = events.id 
         AND event_tags.tag_id = user_tags.tag_id
         AND  user_tags.user_id = <$user_id>

не кажется мне слишком тяжелым, если предположить, что у вас есть индексы повсюду

...