【转】Redis学习---阿里云Redis多线程性能增强版详解
【原文】https://www.toutiao.com/i6594620107123589635/
摘要
Redis做为高性能的K-V数据库,由于其高性能,丰富的数据结构支持,易用等特性,而得到广泛的应用。但是由于redis单进程单线程的模型限制,单Redis Server QPS最高只能达到10万级别。本文试图通过对Redis做多线程的优化,来达到增强性能的目的。
二、背景
众所周知redis是单进程单线程模型(不完全是单进程单线程,还有若干后端线程主要做刷脏数据,关闭文件描述符等后台清理工作)。redis中负责主要工作的是主线程,主线程的工作包括但不限:接收客户端连接,处理连接读写事件,解析请求,处理命令,处理定时器事件,数据同步等相关工作。单进程单线程只能跑满一个CPU核,在小包场景下,单个redis server的QPS在8~10万级别。如果QPS超过这个级别,单个redis server就无法满足需求。而常用的解决办法就是数据分片,采用多server的分布式架构予以解决。然而数据分片,多redis server方式也存在若干问题:redis server过多,难以管理;分片之后一些在单redis server上使用的命令无法支持;分片无法解决热点读写问题;分片后数据倾斜,数据重分布,数据扩缩容等也比较复杂。由于单进程单线程的局限,我们期望通过多线程的改造以期充分利用SMP多核架构的优势,从而达到提高单redis server吞吐的目的。对redis做多线程化,最容易想到的方案是每个线程既做IO又做命令处理等工作,但由于redis处理的数据结构相对比较复杂,多线程需要锁来保证线程安全性,而锁粒度处理不好性能反而可能会出现下降。
我们的思路是通过增加IO线程,将连接中数据的读写,命令的解析和数据包的回复放到单独的IO线程来处理,而对命令的处理,定时器事件的执行等仍让单一的线程来处理,以此达到提高单redis server吞吐的目的。
三、单进程单线程的优点和不足
1、优点
因为单进程单线程模型的限制,redis在实现上将耗时的操作分解成多步,多次来执行(例如dict rehash, 过期key删除等操作),尽量避免长时间执行一个操作,从而避免长时间阻塞在一个操作上。单进程单线程代码编写简单,可以减少多进程多线程导致的上下文切换和锁的争抢。
2、不足
- 只能使用一个CPU核,无法发挥多核优势。
- 对于重IO应用来说,大量的cpu耗费在网络IO操作上。对于将redis做为缓存的应用,往往都是重IO的应用。这类应用基本上都是QPS很高,使用的命令相对比较简单(多为get,set,incr等操作),但是对RT响应很敏感。这类应用通常带宽占用很高,甚至会跑到百兆级别。当前由于万兆,25G网卡的普及,网络往往已不再是瓶颈,而如何发挥多核优势,充分发挥网卡性能成为需要考虑的事情。
四、实现
1、线程划分
- 主线程(MAIN THREAD)
- IO线程(IO THREAD)
- WORKER线程(WORKER THREAD)
2、线程模型
- 主线程:接受连接,创建client,将连接转发给IO线程。
- IO线程:处理连接的读写事件,解析命令,将解析的完整命令转发给WORKER线程处理,发送response包,负责删除连接等。
- WORKER线程:负责命令的处理,生成客户端回包,定时器事件的执行等。
- 主线程,IO线程,WORKER线程都有单独的事件驱动。
- 线程之间通过无锁队列交换数据,通过管道进行消息通知。
五、收益
1、 压测结果
- 从压测结果来看,小包场景下,读写性能差不多有三倍左右的性能提升。
2、主从同步速度提升
3、主从同步优化
Master向Slave发送同步数据时,数据在IO线程中发送,Slave从主读取数据时,全量数据在WORKER线程中读取,增量数据在IO线程中读取,因此可以相对比较有效的增加同步的速度。
4、后续工作
- 现在所做的第一部分工作是增加IO线程,优化IO读写能力。进一步的优化可以考虑对WORKER线程进行拆分:每个线程既负责IO读取,也负责WORKER工作处理。
5、IO线程数设置
- 从测试结果来看,IO线程数最大不要超过6个。超过之后对简单操作来说,WORKER线程往往已经成为瓶颈。
- 进程在启动时需要设置IO线程的个数,在进程运行期间IO线程个数无法修改,按当前的连接分配策略,修改IO线程的个数涉及到连接的重新分配,处理相对比较复杂。
六、展望
- 随着万兆网卡,25G网卡的普及,如何充分利用硬件的性能需要充分的考虑。多网络IO线程,By pass内核的用户态协议栈等都是可利用的技术。
- 通过IO线程实现数据的迁移,可以无阻塞,IO线程对数据进程Encode,或者命令转发,目标节点实现数据Decode,或者命令执行。
【转】Redis学习---阿里云Redis多线程性能增强版详解的更多相关文章
- 阿里云部署 Flask + WSGI + Nginx 转载详解
我采用的部署方案是: Web 服务器采用 uwsgi host Flask 用 Supervisor 引用 uwsgi 作常规启动服务 基于 Nginx 作反向代理 首先, 阿里云服务器可以通过 SS ...
- 使用阿里云主机离线部署CDH步骤详解
一.Linux文件系统准备 1. 拍摄快照 登录阿里云控制台,拍摄快照,注意有几个关键点尽量拍摄快照,系统初始状态.CM环境准备完成.CM安装完成.CDH安装完成. 2. 挂载设备 三个主机都执行. ...
- 阿里云轻量应用服务器 配置mysql详解(转载)
1.服务器规格 1.地域选择 考虑个人地址因素因此选择了华南. 2.选择应用镜像/系统镜像 这个应该看个人需求,因为我只是想用来放数据库的,所以就随便选了个WordPress. 选好之后购买就完事了, ...
- ServiceStack.Redis连接阿里云redis服务时使用连接池出现的问题
创建连接池 private static PooledRedisClientManager prcm = CreateManager(new string[] { "password@ip: ...
- 一份完整的阿里云 Redis 开发规范,值得收藏!
来源:yq.aliyun.com/articles/531067 作者:付磊-起扬 本文主要介绍在使用阿里云Redis的开发规范,从下面几个方面进行说明. 键值设计 命令使用 客户端使用 相关工具 通 ...
- 阿里云Redis开发规范
转自: https://yq.aliyun.com/articles/531067 摘要: 本文介绍了在使用阿里云Redis的开发规范,从键值设计.命令使用.客户端使用.相关工具等方面进行说明,通过本 ...
- 阿里云Redis开发规范[转]
一.键值设计 1. key名设计 (1)[建议]: 可读性和可管理性 以业务名(或数据库名)为前缀(防止key冲突),用冒号分隔,比如业务名:表名:id ugc:video:1 (2)[建议]:简洁性 ...
- 阿里云Redis开发规范(转)
一.键值设计 1. key名设计 (1)[建议]: 可读性和可管理性 以业务名(或数据库名)为前缀(防止key冲突),用冒号分隔,比如业务名:表名:id ugc:video: (2)[建议]:简洁性 ...
- 解密阿里云Redis助力双十一背后的技术
摘要: Redis是一个使用范围很广的NOSQL数据库,阿里云Redis同时在公有云和阿里集团内部进行服务,本文介绍了阿里云Redis双11的一些业务场景:微淘社区之亿级关系链存储.天猫直播之评论商品 ...
随机推荐
- T-SQL触发器,限制一次只能删除一条数据
/****** Object: Trigger [dbo].[trg_del] Script Date: 01/01/2016 12:58:28 ******/ SET ANSI_NULLS ON G ...
- MySQL 5.7 新备份工具mysqlpump 使用说明 - 运维小结
之前详细介绍了Mysqldump备份工具使用,下面说下MySQL5.7之后新添加的备份工具mysqlpump.mysqlpump是mysqldump的一个衍生,mysqldump备份功能这里就不多说了 ...
- BeanDefinition到Bean
转自:http://songzi0206.iteye.com/blog/1430239 当 BeanDefinition 注册完毕以后, Spring Bean 工厂就可以随时根据需要进行实例化了.对 ...
- 第一次项目上Linux服务器(三:安装Tomcat及相关命令)
一.下载Tomcat 去官网:http://tomcat.apache.org/ 找到要下载的Tomcat 本人下载的是apache-tomcat-8.5.29.tar.gz,百度云资源链接:链接:h ...
- 安装win8/win10提示无法在驱动器0分区上安装windows解决方法
在通过U盘或光盘安装win8/win8.1/win10系统时,不少用户遇到无法安装的问题,提示“无法在驱动器0的分区1上安装windows”,格式化分区1也不能解决,进而提示Windows无法安装到这 ...
- 使用clamav模块对数据流进行病毒检测
准备工作:linux下安装clamav成功,启动clamav并打开本地socket监听"/tmp/clamav.socket" clamav开源工程目录:/usr/local/ 修 ...
- 【SpringBoot系列1】SpringBoot整合MyBatis
前言: 一直看网上说SpringBoot是解锁你的配置烦恼,一种超级快速开发的框架.一直挺想学的,正好最近也有时间,就学了下 这个是SpringBoot整合MyBatis的一个教程,用了阿里的drui ...
- GCD之同步异步
博客地址:http://blog.csdn.net/chaoyuan899/article/details/12554603
- 并发编程——ConcurrentHashMap#transfer() 扩容逐行分析
前言 ConcurrentHashMap 是并发中的重中之重,也是最常用的数据结果,之前的文章中,我们介绍了 putVal 方法.并发编程之 ConcurrentHashMap(JDK 1.8) pu ...
- c#关于路径的总结(转)
来源:http://www.cnblogs.com/yugongmengjiutian/articles/5521165.html 前一段时间写代码时经常遇到获取路径问题,总是感觉有点乱,于是就总结了 ...