内存悲观锁

背景

在 v6.0.0 版本,针对悲观事务引入了内存悲观锁的优化(in-memory lock),从压测数据来看,带来的性能提升非常明显。

TiDB 事务模型从最初的乐观事务到悲观事务;在悲观事务上,又针对悲观锁进行的 ”pipelined 写入“ 和 ”in-memory lock“ 优化,从功能特性上可以看出演进过程。

乐观事务

乐观事务在提交时,可能因为并发写造成写写冲突,不同设置会出现以下两种不同的现象:

  • 关闭乐观事务重试,事务提交失败:也就是执行 DML 成功(不会被阻塞),但是在执行 commit 时候失败,表现出与 MySQL 等数据库不一致的行为。

  • 开启乐观事务重试,自动重试后返回成功,但是因为重试 DML 使用的 start_ts 是重新获取的,不是事务开始的 start_ts,也就是说实际执行结果相当于同一个事务中读和写是使用不同的 start_ts,执行结果可能跟预期不一致。

悲观事务

针对乐观事务存在的问题,悲观事务通过在执行 DML 过程中加悲观锁,来达到与传统数据库的行为:

  • 并发执行 DML,对同一行数据进行更改,先执行者会加悲观锁,后执行者被锁阻塞

  • 悲观锁避免了写冲突的问题,使得 commit 顺利完成

悲观事务写入悲观锁,相对乐观事务带来以下开销:

  • 悲观锁写入 TiKV,增加了 RPC 调用流程并同步等待悲观锁写入成功,导致 DML 时延增加

  • 悲观锁信息会通过 raft 写入多个副本,给 TiKV raftstore、磁盘等带来处理压力

pipelined

针对悲观锁带来的时延增加问题,在 TiKV 层增加了 pipelined 加锁流程优化,优化前后逻辑对比:

  • 优化前:满足加锁条件,等待 lock 信息通过 raft 写入多副本成功,通知 TiDB 加锁成功

  • pipelined :满足加锁条件,通知 TiDB 加锁成功、异步 lock 信息 raft 写入多副本(两者并发执行)

异步 lock 信息 raft 写入流程后,从用户角度看,悲观锁流程的时延降低了。

in-memory

pipelined 优化只是减少了 DML 时延,lock 信息跟优化前一样需要经过 raft 写入多个 region 副本,这个过程会给 raftstore、磁盘带来负载压力。

内存悲观锁针对 lock 信息 raft 写入多副本,做了更进一步优化,总结如下:

  • lock 信息只保存在内存中,不用写入磁盘

  • lock 信息不用通过 raft 写入多个副本,只要存在于 region leader

  • lock 信息写内存,延迟相对于通过 raft 写多副本,延迟极小

从优化逻辑上看,带来的

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值