Позвольте мне сразу начать, сказав, что я знаю, что это не лучшее решение.Я знаю, что это глупо и чертовски многозначительно. Но вот почему я здесь!
Этот вопрос / работа строится на некотором обсуждении Quora с Эндрю Босвортом , создателем новостной ленты Facebook.
Я создаю ленту новостей сортов.Он построен исключительно в PHP
и MySQL
.
MySQL
Реляционная модель для канала состоит из двух таблиц.Одна таблица функционирует как журнал активности;на самом деле он называется activity_log
.Другая таблица - newsfeed
. Эти таблицы почти идентичны.
Схема для журнала - activity_log(uid INT(11), activity ENUM, activity_id INT(11), title TEXT, date TIMESTAMP)
... и схема дляфид - это newsfeed(uid INT(11), poster_uid INT(11), activity ENUM, activity_id INT(11), title TEXT, date TIMESTAMP)
.
Каждый раз, когда пользователь делает что-то соответствующее ленте новостей, например, задает вопрос, он регистрируется в журнале активности немедленно.
Генерация новостных лент
Затем каждые X минут (в данный момент 5 минут изменится на 15-30 минут спустя), Я запускаю задание cron , которое выполняет приведенный ниже скрипт.Этот сценарий проходит по всем пользователям в базе данных, находит все действия для всех друзей этого пользователя, а затем записывает эти действия в ленту новостей.
В данный момент SQL
, который отбрасываетактивность (называемая ActivityLog::getUsersActivity()
) имеет LIMIT 100
, наложенную по соображениям производительности *.* Не то, чтобы я знал, о чем говорю.
<?php
$user = new User();
$activityLog = new ActivityLog();
$friend = new Friend();
$newsFeed = new NewsFeed();
// Get all the users
$usersArray = $user->getAllUsers();
foreach($usersArray as $userArray) {
$uid = $userArray['uid'];
// Get the user's friends
$friendsJSON = $friend->getFriends($uid);
$friendsArray = json_decode($friendsJSON, true);
// Get the activity of each friend
foreach($friendsArray as $friendArray) {
$array = $activityLog->getUsersActivity($friendArray['fid2']);
// Only write if the user has activity
if(!empty($array)) {
// Add each piece of activity to the news feed
foreach($array as $news) {
$newsFeed->addNews($uid, $friendArray['fid2'], $news['activity'], $news['activity_id'], $news['title'], $news['time']);
}
}
}
}
Отображение новостных лент
В коде клиента при получении новостной ленты пользователя я делаю что-то вроде:
$feedArray = $newsFeed->getUsersFeedWithLimitAndOffset($uid, 25, 0);
foreach($feedArray as $feedItem) {
// Use a switch to determine the activity type here, and display based on type
// e.g. User Name asked A Question
// where "A Question" == $feedItem['title'];
}
Улучшение новостной ленты
Теперь простите мое ограниченное понимание лучших практик по разработке новостной ленты, но я понимаю подход, который я использую, чтобы бытьограниченная версия так называемого разветвления при записи , ограниченная в том смысле, что я выполняю задание cron в качестве промежуточного этапа вместо прямой записи в новостные ленты пользователей.Но это очень отличается от модели извлечения, в том смысле, что новостная лента пользователя не компилируется при загрузке, а скорее на регулярной основе.
Это большой вопрос, который, вероятно, заслуживает большого количества обратнойи далее, но я думаю, что это может послужить пробным камнем для многих важных разговоров, которые нужны новым разработчикам, таким как я.Я просто пытаюсь выяснить, что я делаю не так, как я могу улучшить, или как я, возможно, даже должен начать с нуля и попробовать другой подход.
Еще одна вещь, которая меня беспокоит в этой моделиявляется то, что он работает на основе актуальности, а не актуальности.Если кто-нибудь может подсказать, как это можно улучшить, чтобы работать в релевантности, я был бы всем заинтересован.Я использую API Directed Edge для генерации рекомендаций, но кажется, что для чего-то вроде новостной ленты рекомендатели не будут работать (так как ранее ничего не было одобрено!).