1.Redis 缓存结构
1.每个用户一个 “发送” 动态流集合。用于存放自己发布的动态列表。(redis 的有序集合 SortedSets 解决)
-
redis结构如:key:user_feedlist_by_用户唯一标识 | member:动态id | Score:发布动态的时间(时间戳格式)
(保留自己发送集合,可以只看到自己发布的内容)
2.每个用户一个” 收取 “动态流集合。用于存放好友的动态列表。(redis 的有序集合 SortedSets 解决)
-
redis结构如:key:user_friend_feedlist_by_用户唯一标识 | menber:动态id+好友的用户id | Score:发布动态的时间(时间戳格式)
(
系统只需要根据自身用户的【” 收取 “动态流集合】加载出动态内容,对内容进行筛选和过滤即可)
3.一个用户发送动态待处理消息队列(redis 的 List 解决)
用户发布新动态时,进入该队列。
当后端消费者队列发现待处理消息队列出现新消息时,取出首消息里面的数据。
根据动态发布者的 uid,加载其关注者列表(粉丝)。循环对其每个粉丝的【” 收取 “动态流集合】进行插入动态。(如遇粉丝数量庞大的时候,需要进行条件分批插入。例如:可根据活跃时间、互动程度、注册时间、账号资料完善度等进行有限推送,根据自身系统的需求灵活扩展)
4.一个用户关系变更待处理消息队列(redis 的 List 解决)
用户关系变更待处理消息队列,用户进行关注,取关,拉黑等操作时触发进入该队列。
后端消费者进程根据【动作标识】 关注 / 取关 / 拉黑等操作对目标用户的【” 收取 “动态流集合】进行增减
如果是关注,将被关注者的最近几条动态插入到自己的【” 收取 “动态流集合】
如果是取关,将自己的【” 收取 “动态流集合】剔除对方的动态
如果是拉黑 [解除双方任何关系], 将自己的【” 收取 “动态流集合】以及对方的【” 收取 “动态流集合】剔除掉双方的动态
5.一个或多个负责维护用户的收 / 发动态流集合的定时进程。避免数据过多,到 300-500 条后清理之前不必要的动态集合。(swoole 多进程 + 定时器解决)
维护用户的收 / 发动态流集合进程
当用户好友过多以后,用户的【” 收取 “动态流集合】内容就会过多,成千上万条。但实际上用户并不会真正浏览成千上万条动态。一般在浏览几百条动态后就会使用户感觉到疲劳,后面的数据根本用不上!所以才有前文提到的【维护用户的收 / 发动态流集合的定时进程】,对用户的【收 / 发动态流集合】数量维持在 300-500 左右即可,再多就是浪费内存
所以我们需要有一个或多个进程去遍历用户的【” 收取 “动态流集合】,对集合进行删减,剔除掉过早的动态数据。只保留最近几百条的动态数据。
参考
https://www.utf8.hk/archives/php_redis_weibo_feed.html