分布式场景
2024-03-26 17:22:47 2 举报
AI智能生成
分布式事务 分布式缓存等
作者其他创作
大纲/内容
分布式事务
什么是事务?
事务是恢复和并发控制的基本单位,事务有四个特性(ACID),原子性(Atomicity),一
致性(Consistency),隔离性(Isolation),持久性(Durability)。
致性(Consistency),隔离性(Isolation),持久性(Durability)。
由一组跨家族的操作构成的可靠、独立的工作单元
分布式事务解决方案1
XA
组成部分
全局事务
• 由全局事务管理器全局管理
• 由全局事务管理器全局管理
事务管理器
• 管理全局事务状态与参与的资源,协 同资源的一致提交/回滚
• 管理全局事务状态与参与的资源,协 同资源的一致提交/回滚
TX协议
• 应用与应用服务器与事务管理器的接口
• 应用与应用服务器与事务管理器的接口
XA协议
• 全局事务管理器与资源管理器的接口
• 全局事务管理器与资源管理器的接口
XA是由X/Open组织提出的分布式事务的规范。
XA规范主要定义了(全局)事务管理器(TM) 和(局部)资源管理器(RM)之间的接口。
主流的关系型数据库产品都是实现了XA接口的
XA规范主要定义了(全局)事务管理器(TM) 和(局部)资源管理器(RM)之间的接口。
主流的关系型数据库产品都是实现了XA接口的
XA接口是双向的系统接口,在事务管理器(TM)以及一个或多个资源管理器(RM)之间形成通信桥梁。
XA之所以需要引入事务管理器是因为,在分布式系统中,从理论上讲两台机器理论上无法达成一致的状态,需要引入一个单点进行协调
由全局事务管理器管理和协调的事务,可以跨越多个资源(如数据库或JMS队列)和进程。
全局事务管理器一般使用XA二阶段提交协议与数据库进行交互。
全局事务管理器一般使用XA二阶段提交协议与数据库进行交互。
XA是刚性事务,效率较低
分布式事务解决方案2
3pc
阶段1:CanCommit
1、协调者向参与者发出CanCommit请求,询问是否可以提交事务,并等待所有参与者答复。
2、参与者收到CanCommit请求后,如果认为可以执行事务操作,则反馈YES,否则反馈NO
1、协调者向参与者发出CanCommit请求,询问是否可以提交事务,并等待所有参与者答复。
2、参与者收到CanCommit请求后,如果认为可以执行事务操作,则反馈YES,否则反馈NO
阶段2:PreCommit
1、所有参与者均反馈YES,即执行事务预提交。
2、任何一个参与者反馈NO,或者等待超时后协调者尚无法收到所有参与者的反馈,即中断事务。
1、所有参与者均反馈YES,即执行事务预提交。
2、任何一个参与者反馈NO,或者等待超时后协调者尚无法收到所有参与者的反馈,即中断事务。
阶段3:do Commit
1、所有参与者均反馈Ack响应,即执行真正的事务提交。
2、任何一个参与者反馈NO,或者等待超时后协调者尚无法收到所有参与者的反馈,即中断事务。
1、所有参与者均反馈Ack响应,即执行真正的事务提交。
2、任何一个参与者反馈NO,或者等待超时后协调者尚无法收到所有参与者的反馈,即中断事务。
分布式事务解决方案3
TCC事务、补偿型
Try-Confirm-Cancel
分布式事务解决方案4
异步确保型
分布式事务解决方案5
最大努力通知型
微信支付
常用的分布式框架
TX-LCN框架
定义
锁定事务单元(lock)
确认事务模块状态(confirm)
通知事务(notify)
确认事务模块状态(confirm)
通知事务(notify)
框架定位
LCN 并不生产事务,LCN 只是本地事务的协调工
TX-LCN 定位于一款事务协调性框架,框架其本身并不操作事务,而是基于对事务的协调从而达到事务一致性的效果
TX-LCN 定位于一款事务协调性框架,框架其本身并不操作事务,而是基于对事务的协调从而达到事务一致性的效果
Seata框架
分布式缓存
1.什么情况下使用缓存
1.访问频率高
2.更改频率低
3.一致性要求不高
2.重要指标
缓存命中率
Miss率 = 没有从缓存中读取的次数 / (总读取次数[从缓存中读取次数 + 从慢速设备上读取的次数])
命中率 = 从缓存中读取次数 / (总读取次数[从缓存中读取次数 + 从慢速设备上读取的次数])
移除策略
FIFO(First In First Out) :先进先出算法,即先放入缓存的先被移除
LRU(LeastRecentlyUsed) :最久未使用算法,使用时间距离现在最久的那个被移除
LFU(Least Frequently Used) :最近最少使用算法,一定时间段内使用次数(频率)
最少的那个被移除
最少的那个被移除
TTL(Time To Live )
存活期,即从缓存中创建时间点开始直到它到期的一个时间段(不管在这个时间段内有
没有访问都将过期
存活期,即从缓存中创建时间点开始直到它到期的一个时间段(不管在这个时间段内有
没有访问都将过期
TTI(Time To Idle)
空闲期,即一个数据多久没被访问将从缓存中移除的时间。
空闲期,即一个数据多久没被访问将从缓存中移除的时间。
3.缓存过期和一致性
1.数据允许短期时间不一致(采用过期时间策略)
弱一致性,基于缓存本身的失效机制
优点:实现简单,无须引入额外逻辑
缺点:有一定延迟,存在缓存击穿/雪崩问题
2.定时任务跑数据
最终一致性,采用任务调度框架,按照一定频率更新
优点:不影响正常业务
缺点:不保证一致性,依赖定时任务
3.实时更新(同步调用redis操作方法)
更新数据库同时更新缓存,使用缓存工具类和或编码实现
优点:数据实时同步更新,保持强一致性
缺点:代码耦合,对业务代码有侵入性
4.准实时更新(mq)
准一致性,更新数据库后,异步更新缓存,使用观察者模式/发布订阅/MQ实现;
优点:数据同步有较短延迟 ,与业务解耦
缺点:实现复杂,架构较重
5.缓存数据更新策略
双删(先删除缓存,再更新数据库,再删缓存(双删,第二次删可异步延时)
4.缓存击穿,缓存穿透,缓存雪崩
缓存击穿
缓存击穿是指缓存中没有但数据库中有的数据(一般是缓存时间到期) ,这时由于
并发用户特别多,同时读缓存没读到数据,又同时去数据库去取数据,引起数据库压力
瞬间增大,造成过大压力
并发用户特别多,同时读缓存没读到数据,又同时去数据库去取数据,引起数据库压力
瞬间增大,造成过大压力
缓存雪崩
缓存雪崩是指缓存中数据大批量到过期时间,而查询数据量巨大,引起数据库压
力过大甚至down机。和缓存击穿不同的是,缓存击穿指并发查同一条数据,缓存雪崩
是不同数据都过期了,很多数据都查不到从而查数据库
力过大甚至down机。和缓存击穿不同的是,缓存击穿指并发查同一条数据,缓存雪崩
是不同数据都过期了,很多数据都查不到从而查数据库
缓存穿透
缓存穿透是指缓存和数据库中都没有的数据,而用户不断发起请求,如发起为id
为“-1”的数据或id为特别大不存在的数据。这时的用户很可能是攻击者,攻击会导
致数据库压力过大
为“-1”的数据或id为特别大不存在的数据。这时的用户很可能是攻击者,攻击会导
致数据库压力过大
解决方案
1.过期时间设置为随机数,防止在某个时间段集中过期造成缓存雪崩
2.加锁限流(对某个key只是让一个线程进行加锁和写缓存)
3.布隆过滤器防止缓存穿透
4.假key也设置进去到redis
5.缓存数据被动失效改为主动失效
6.缓存预热,提前将数据存取到redis
分布式锁
实现方案
1.mysql
利用数据库锁机制,行级锁,创建主键
优点:简单可靠
缺点:性能差,无法适应高并发场景;
容易出现死锁的情况;
无法优雅的实现阻塞式锁;
容易出现死锁的情况;
无法优雅的实现阻塞式锁;
2.redis
使用Setnx和lua脚本机制实现,保证对缓存操作序列的原子性
性能好
实现相对较复杂
有出现死锁的可能性;
无法优雅的实现阻塞式锁
有出现死锁的可能性;
无法优雅的实现阻塞式锁
3.zookeeper
基于zk的节点特性以及watch机制实现;
性能好,稳定可靠性高,能较好的实现阻塞式锁;
实现相对复杂
实现细节:
getLock
获取锁的时候,tryLock判断是否可以拿到锁,如果拿不到锁的话就调用waitLock,然后在getLock递归
tryLock的时候,首先创建有序临时节点,判断是否是第一个节点,是的说明他拿到锁了,不是第一个节点的话,那么就拿到这个节点的子节点集合,然后获取到它的上一个节点,返回false。
tryLock返回false的话,调用waitLock,这个时候将上一个节点注册watch 的删除事件,判断上个节点是否存在,存在的话countLatch阻塞这个线程,如果上个节点unlock 删除节点话,触发这个watch事件,这时候这个线程释放,开始取消这个监听,继续尝试获取锁
unlock
删除节点,这个zkclient关闭
使用zk的临时有序节点可以防止出现羊群效应,如果并发集中到一个临时无序节点上,会出现服务器压力过大,这里使用临时有序节点的话,可以使得每一个线程都拿到一个有序id,序号小的优先获取锁,做相应的操作,序号大的按照zk节点的顺序获取锁
0 条评论
下一页