《亿级流量系统架构设计与实战》第十一章 Timeline Feed服务
Timeline Feed服务
- 一、概述
- 1、分类
- 2、功能
- 二、设计原理
- 1、拉模式与用户发件箱
- 2、推模式与用户收件箱
- 3、推拉模式结合
- 三、关键技术
- 1、内容与用户收件箱的交互(推模式)
- 2、推送拆分子任务
- 3、收件箱模型设计
内容总结自《亿级流量系统架构设计与实战》
一、概述
1、分类
Feed 流的功能在当今的互联网应用和网络社交平台中非常重要,它是一种以时间线为基础的信息流展示形式,把用户感兴趣的内容呈现在用户的Feed页面上。如果你使用过一些互联网应用就会发现,很多互联网应用的主页都是Feed页面,它们把Feed流当作自己的“门面”。Feed 流在内容聚合维度上包括但不限于如下几种形式。
- 推荐 Feed 流:按照你的浏览兴趣菜合内容,你可能不认识 Feed 流内容的发布者,但是他发布的内容你可能很感兴趣。
- 关注 Feed 流:你关注的用户发布的内容被聚合为 Feed 流,并且按照内容的发布时间从近到远展示你所关注的那些人最近发布的内容。按照内容的发布时间排序,也就是遊循时间线,所以这种 Feed 流是一种 Timeline Feed 流。徽信朋友閣和微博首页都是典型的对关注 Feed 流的应用。
- 附近 Feed 流:顾名思义,就是你附近的用户最近发布的内容,这对于社交类应用来说较为常见。推荐 Feed 流的重点是推荐算法,附近 Feed 流的重点是地理位置判断,其相关技术差异巨大,不具备通用性
2、功能
Timeline Feed 流提供的数据应该是我们所关注的人在指定的时问段内发布的内容列表,并且内容按照时间由近及远排序。
用户在客户端浏览Timeline Feed页面时一般有如下两种操作方式。
- 下拉操作:刷新Feed流,拉取当前时间最新的 N条 Feed 流。
- 上滑操作:拉取更早时间的 N条Feed 流。
总之,Timeline Feed 服务主要负资两种读取数据的方式:下拉与上滑。
其中,下拉负责拉取用户从未看过的最新内容列表,上滑负资拉取更早的内容列表,并限制所能拉取到内容最大数量。无论是何种读取方式,内容列表均找照内容的发布时间从近到远排序。
二、设计原理
1、拉模式与用户发件箱
较为符合我们直觉的实现Timeline Feed服务的方式是拉模式。每个内容发布者都有自己的“发件箱”,每当用户发布一个内容时,就把内容存放到发件箱中,由其他用户来拉取内容

在拉模式下,用户每刷新一次Feed流,系统就需要读取N个用户的发件箱(这里的N指用户关注的人数),这意味着一次用户请求会放大产生N倍的读请求,故而这种模式也被称为“读扩散”。如果用户量级较大,那么获取Feed流会是一个高并发场景,而且用户关注的人数也会较多。所以这种扩散读会增加用户请求延迟,并可能击垮存储用户内容列表的服务器
2、推模式与用户收件箱
与拉模式相反,在推模式下,每个用户都有一个“收件箱”,当某个用户成功发布了内容时,系统会将该内容推送到其每个粉丝用户的收件箱中。粉丝用户在获取Feed流时,直接从收件箱中读取内容即可。在推模式下,用户获取Feed流的性能比在拉模式下好。

缺点:
- 存储压力大:每个用户都有收件箱,势必增加收件箱存储开销,用户越多,收收件箱占用的存储资源也越多
- 写扩散:某用户存在100w粉丝,当发布完内容后,需要推送到100w粉丝的收件箱,即会产生100w个写请求。巨量写请求,会击垮收件箱所依赖的数据库
3、推拉模式结合
推模式和拉模式优缺点互补,可以相互结合。大V的内容就拉模式(推模式要推的人太多),普通内容推模式(拉模式牵涉的人数太多)

用户-区分活跃用户
大V在发布内容后,我们依然可以采用推模式,但是现在仅将内容推送给粉丝列表中的部分活跃用户,因为这些用户使用 Timeline Feed 流功能的频常相对较高,所以将内容主动推送到他们的收件箱中更有可能提高获取Timeline Feed流的性能。至于那些很长时间都没有打开应用的用户,则完全没有必要把内容存储到他们的收件箱中。如果有一天这些用户登录应用并使用Timeline Feed流功能,那么保持采用推拉结合模式结合来获取数据就好。
综上所述,对推拉模式的结合方式总结如下:
- 如果内容的发布者是普通用户,则完全可以采用推模式,把内容推送到全部粉丝的收件箱中
- 如果内容的发布者是大V,则进一步区分活跃用户和非活跃用户。对于活跃用户,采用推模式;对于非活跃用户,则采用拉模式
三、关键技术
1、内容与用户收件箱的交互(推模式)
内容发布服务需要与Timeline Feed服务解耦,而且要尽可能提高推送的可用性,最好的办法就是在这两个服务之间建立消息队列通道。我们可以创建一个消费者服务负责接收内容发布服务的内容变更事件,如果发现有新内容发布,则执行遍历推送操作

2、推送拆分子任务
Timeline消费者遍历推送毕竟是串行操作,如果需要将一条内容推送给更多的粉丝,那么遍历推送可能会消耗更长的时间,进而造成内容发布服务与Timeline消费者之间的消息队列中的消息积压,导致内容到用户收件箱的投递延迟。我们可以将对大量粉丝的遍历推送拆分为多个并行执行的子任务,每个子任务负责对一批粉丝的推送。
比如需要将内容A推送给3000个粉丝,且粉丝的用户ID是1~3000,那么可以将这个任务拆分为3个子任务
- 子任务1:负责将内容发送给粉丝1~1000
- 子任务2:负责将内容发送给粉丝1001~2000
- 子任务3:负责将内容发送给粉丝2001~3000

3、收件箱模型设计
用户查询时的业务动作含义是:以某个时间点为基准,向前或者向后获取当前用户关联的内容id
1)使用数据库
新增表:inbox
字段名 | 类型 | 含义 |
---|---|---|
id | bigint | 主键 |
user_id | bigint | 用户id |
content_id | bigint | 内容id |
publish_time | datetime | 内容发布时间 |
idx_feed(user_id,publish_time,content_id)
每个用户的收件箱内容都会按照publish_time从小到大排列,当publish_time相同时,再进一步按照content_id从小到大排列,所以从后向前扫描索引正好与Timeline Feed流内容的排序规则相吻合
2)使用ZSET
- key为inbox_{用户ID},表示一个ZSET对象是哪个用户的收件箱
- Member为内容id
- Score为内容发布时间。ZSET可以按照内容发布时间从小到大排列内容ID
不断获取内容ID的方案:
- 根据last_content_id 直接定位下一条内容,但这种方案不适合推拉结合模式;
- 先获取发布时间小于或等于ts的全部内容,再过滤筛选;
- 对第二种方案的优化,把内容ID格式化为 20 位长度的字符串用作Member 字段,保证在ZSET中发布时间相同的内容按照内容ID的数值从小到大排列,这样一来,在ZSET中从后向前扫描就与Timeline Feed流内容的排序规则相吻合了。
相关文章:

《亿级流量系统架构设计与实战》第十一章 Timeline Feed服务
Timeline Feed服务 一、概述1、分类2、功能 二、设计原理1、拉模式与用户发件箱2、推模式与用户收件箱3、推拉模式结合 三、关键技术1、内容与用户收件箱的交互(推模式)2、推送拆分子任务3、收件箱模型设计 内容总结自《亿级流量系统架构设计与实战》 一…...

氙灯老化试验箱试验机
氙灯老化试验箱,采用6.5KW大功率的精密水冷式氙灯,曝晒面积达到了6500cm2 功能强大,测试结果可靠 ◆ 满足国内外所有氙灯测试标准要求。 ◆ 采用氙灯灯管及滤光器组件,保证试验数据的可比性和重现性。 ◆ 自动旋转式三层鼓型样板架…...

【Qt】常用控件QRadioButton
常用控件QRadioButton QRadioButton是单选按钮,可以在多个选项中选择一个。 作为QAbstractButton和QWidget的子类,其属性和用法,对于QRadioButton同样适用。 属性说明 checkable 是否能选中 checked 是否已经被选中. checkable 是 checked…...

Mysql 离线版下载安装-(详细版)
Mysql 离线版下载安装-(详细版) 文章目录 Mysql 离线版下载安装-(详细版)1.0 下载地址2.0 解压到本地2.0.1 配置环境变量2.0.2 新建mysql配置文件ini2.0.3使用管理员启动 cmd 3.0 初始化密码忘记了4.0 修改初始化密码5.0 使用可视化工具登录Mysql 1.0 下载地址 地址࿱…...

Spring Boot和OCR构建车牌识别系统
博客主页: 南来_北往 系列专栏:Spring Boot实战 OCR介绍 OCR(Optical Character Recognition)是光学字符识别技术的缩写,它能够将图像中的文本转换为机器可读和编辑的数字文本格式。这种技术广泛应用于数据输入、文档管理…...

Java-自定义注解中成员变量是Class<?>
在Java中,自定义注解可以包含各种类型的成员变量,包括 Class<?> 类型。这种类型的成员变量 通常用于表示某个类的类型信息。下面我将详细介绍如何定义一个包含 Class<?> 类型成员变量的 自定义注解,并给出一些示例代码。 1. 定义自定义注解 定义一个自定义…...

SX_UNIX套接字通信_15
UNIX套接字通信的优势: UNIX套接字通信常用于一个项目中的进程之间通信,UNIX提供了与网络套接字相似的特性,但是避免了网络延迟,提高了性能,但是它只能在同一台机器上使用,无法跨越网络的进程间通信 实例&…...

JS模块化总结 | CommonJS、ES6
BV13W42197jR 个人笔记 目录 JS模块化基础知识1. 概述1.1 什么是模块化1.2 为什么需要模块化? 2 模块化规范3 导入&导出4 CommonJS规范4.1 初步体验4.2 导出数据4.3 导入数据4.4 扩展理解4.5 浏览器端运行 5 ES6模块化规范5.1 初步体验5.2 Node中运行ES65.3 导出数据①分别…...

25考研计算机组成原理复习·3.5高速缓冲存储器
高速缓冲存储器Cache 工作原理:将某些主存块复制到Cache中,缓和CPU与主存之间的速度矛盾局部性原理 时间局部性:现在访问的地址,不久之后也很可能被再次访问空间局部性:现在访问的地址,其附近的地址也很可…...

餐厅管理系统
目录 一、 系统简介 1.1需求分析 1.2 编程环境与工具 二、 系统总体设计 2.1 系统的功能模块图。 2.2 各功能模块简介。 三、 主要业务流程 (1)用户及管理员登录流程图 (2)信息添加流程 (3…...

杭州百腾教育科技 TiDB 6.5 to 7.5 升级记录
作者: reAsOn2010 原文来源: https://tidb.net/blog/612103f3 背景 使用 TiDB 作为我们的全量数据库已经有六七年了,当时还是 2.0 版本。早期TiDB的迭代和新特性的发布对于实际使用的影响还是很大的,所以从那个时候开始就有每…...

Redis的缓存穿透、击穿、雪崩
目录 缓存穿透 定义: 解决方法: 缓存击穿 定义: 解决方案: 缓存雪崩 定义: 解决方案: 缓存穿透、缓存击穿和缓存雪崩的区别 缓存穿透 定义: 查询一个不存在的数据,数据库未…...

【Django开发】前后端分离django美多商城项目第1篇:欢迎来到美多 项目主要页面介绍【附代码文档】
本教程的知识点为: 项目准备 项目准备 配置 1. 修改settings/dev.py 文件中的路径信息 2. INSTALLED_APPS 3. 数据库 用户部分 图片 1. 后端接口设计: 视图原型 2. 具体视图实现 用户部分 使用Celery完成发送 判断帐号是否存在 1. 判断用户名是否存在 后…...

【软件造价咨询】信息化项目预算评审看什么?
在信息化项目预算评审中,各方往往只重视预算金额部分,而忽视了项目建设的全局性和整体性把关,导致信息系统的重复建设、分散建设、业务和系统两张皮、重功能轻数据、重投资轻方案等问题频出,从而大幅降低财政投资效益。 例如&…...

第37讲:Cephfs文件系统的正确使用姿势
文章目录 1.Cephfs文件系统简介2.Cephfs文件系统细节介绍2.1.Cephfs文件系统多客户端隔离挂载2.2.Ceph集群中多个Cephfs如何单独使用 3.挂载多个Cephfs文件系统4.Cephfs文件系统多客户端隔离挂载实战4.1.创建一个Cephfs文件系统4.2.将Cephfs文件系统挂载到本地路径4.3.在Cephfs…...

单片机烧录
在设计芯片的时候,关于烧录的环节是一个不得不考虑的问题。 我们首先排除掉,由外部直接硬件操控FLASH 的方案,这个方案有很多缺点。 1、每个IC使用的FLASH型号是各不相同的,每种型号的FLASH的烧录命令和流程都有差别,这…...

mysql实现分布式锁
利用数据库的悲观锁实现分布式锁,实际应用中要考虑mysql的高可用。 DistributedLock.h #ifndef DistributedLock_H_ #define DistributedLock_H_// // DistributedLock.h: // #include "base/MySQLDriver.h" class CDistributedLock { public://// Construction/D…...

MySQL快速使用
关系型数据库(RDBMS):建立在关系模型基础上,由多张相互连接的二维表组成的数据库 特点:使用表存储数据,格式统一方便维护;使用SQL语言操作,标准统一使用方便 通用语法: …...

LeetCode41.缺失的第一个正数
1. 题目大意 给你一个未排序的整数数组 nums ,请你找出其中没有出现的最小的正整数。 请你实现时间复杂度为 O(n) 并且只使用常数级别额外空间的解决方案。 2. 思路分析 示例 1: 输入:nums [3,4,-1,1] 输出:2 解释࿱…...

ee trade:黄金投资与股票投资的区别
黄金和股票, 是金融市场中两种常见的投资工具, 它们拥有截然不同的特点和风险, 了解它们的差异, 可以帮助投资者制定更合理的投资策略。 一、 投资性质: 避险与成长, 两种投资方向 黄金: 被视…...

AI视频创作原理
重磅推荐专栏: 《大模型AIGC》 《课程大纲》 《知识星球》 本专栏致力于探索和讨论当今最前沿的技术趋势和应用领域,包括但不限于ChatGPT和Stable Diffusion等。我们将深入研究大型模型的开发和应用,以及与之相关的人工智能生成内容(AIGC)技术。通过深入的技术解析和实践经…...

idea vue项目删除node_modules时报文件损坏且无法读取,导致删除失败
解决办法,查看node_modules所在盘,右击点击属性-工具,点击检查驱动,查完后修复即可, 就能够成功删除损坏的文件了...

Linux下编译安装-单机模式
1.1 Linux下编译安装-单机模式 1.1.1 安装 (1).把安装包放在Linux文件系统下 (2).解压缩 tar -zxf redis-4.0.2.tar.gz (3).切换到解压后的目录 cd redis-4.0.2(4).编译 make(5).进入到src目录 cd src(6).执行安装 make install(7) .返回上级目录 cd .. (8) .修改配置&…...

RSSI定位算法
文章目录 一、定位算法简介1.1. 定位技术原理1.2. 定位算法二、RSSI测距原理2.1. 建模与测量终端到基站的距离三、定位3.1. 三边定位算法3.2. 加权三边定位算法3.3. 加权三角形质心定位算法3.4. 程序定位算法的执行流程一、定位算法简介 1.1. 定位技术原理 定位终端接收到iBe…...

布局管理(Layouts)-Qt-思维导图-学习笔记
布局管理(Layouts) Qt 提供了非常丰富的布局类,主要包括以下基本布局管理类 QBoxLayout 提供了水平和垂直的布局管理,可以将子部件按行或列排列。根据排列方向的不同,QBoxLayout 分为 QHBoxLayout(水平布局)和 QVBox…...

《区块链赋能游戏业:破解虚拟资产交易与确权难题》
在当今数字化的时代,游戏行业正以前所未有的速度发展,虚拟资产在游戏中的重要性日益凸显。然而,虚拟资产的交易和确权问题一直困扰着游戏开发者和玩家。随着区块链技术的引入,为解决这些问题带来了新的曙光。 首先,我…...
机器学习第十一章-特征选择与稀疏学习
11.1子集收集与评价 属性称为"特征" ,对当前学习任务有用的属性称为"相关特征" 、没什么用的属性称为"无关特 征" . 从给定的特征集合中选择出相关特征于集的过程,称为"特征选择"。 特征选择是一个重要的"…...

C#中客户端直接引用服务端Proto文件
gRPC 客户端是从 .proto 文件生成的具体客户端类型。 具体 gRPC 客户端具有转换为 .proto 文件中 gRPC 服务的方法。 下一步打开【服务引用】 控制面板 选择grpc选项,然后继续 到此配置完成,然后就和服务共用一份protocol文件...

SiLM5932SHO系列SiLM5932SHOCG-DG 12A/12A强劲驱动电流能力 支持主动短路保护功能(ASC)单通道隔离门极驱动器
SiLM5932SHO系列是一款单通道隔离驱动器,提供12A源电流和12A灌电流。主动保护功能包括退饱和过流检测、UVLO、隔离故障报警和 4A 米勒钳位。输入侧电源的工作电压为3V至5.5V,输出侧电源的工作电压范围为13V至30V。所有电源电压引脚都有欠压锁定 (UVLO) 保…...

本地项目上传github
一、先在github(GitHub: Let’s build from here GitHub)上创建仓库 1,登录github后,点击右上角头像,点击 Your repositories 2,点击new 3,填写仓库名,假设命名 testhub࿰…...