Ti-KV

news/2024/11/18 13:25:44/

目录

TiKV 持久化

TiKV架构及作用 

RocksDB 

RocksDB:查询

RocksDB:列簇

TiKV 分布式事务

TiKV Raft

Propose

Append

Replicate

Committed

Apply 

Raft Leader选举

TiKV读写与Coprocessor

ReadIndex Read

Lease Read

Follower Read 

Coprocessor 

例题


TiKV 持久化

TiKV架构及作用 

rocksdb:负责数据的落地,即持久化

rocksdb实例包括:

rocksdb raft:负责raft log日志的存取

rocksdb kv:负责键值对和图数据的存取

对与数据的分布式储存,有两种方式HashRange

Hash:按照 Key做Hash,根据Hash值选择对应的存储节点

Range:按照Key分Range,某一段连续的 Key 都保存在一个存储节点上

raft group:raft gruop包括每个region和它的副本

TiKV的读写

rocksdb的读写:针对单个TiKV node的读写,是纵向的

raft共识算法的读写:针对多个TiKV node中的的region副本,是横向的

Raft协议通过Raft共识算法保证数据的分布式储存和数据的一致性,同时仅可能,将数据均衡的分布在集群的所有节点中

Coprocessor协调处理器

提供算子下推能力,使TiKV具有一部分过滤,聚合等SQL计算的能力,且是并行的

RocksDB 

使用RSM Tree存储Key-Value的数据结构 

与MySQL的B+ Tree相比,写入效率更,但查询效率较

RocksDB:写入

写友好型,具有顺序性,且比B+ Tree效率高

 插入,删除先储存在内存,合并后写入磁盘

WAL 预写日志:保证写入的原子性和持久性,即使系统宕机也能进行故障恢复

参数symc_log=true:使写入信息直接写入磁盘WAL文件中,不经过内存

参数write_buffer_size:用于设置MemTable的大小;若超过设置的大小,数据则被转存至immutable,并开辟一个新的Memtable

immutable

设置immutab的目的在于进行磁盘IO时,作为SST文件的中间状态,不阻塞客户端写入;但只要有存在immutable,就开始向磁盘写入当写入操作过多,使immutable达到5个时,则触发rocksdb流控机制(write stall),即限制写入速度

ps:immutable不支持继续写入 

磁盘内部运作机制

Level 0中的内容与immutable的内容相同,是immutable的转存,即immutable的副本

进升Level的条件

当到达4个(默认情况下)SST文件,就进行数据压缩(compaction),将4个SST文件合并为一个,并移至下一个Level(移至下一个Level数据量*10);在压缩过程中,会对Key进行重新排序

ps:写入需要一次内存IO,一次磁盘IO

RocksDB:查询

比B+ Tree慢

Block Cache

存储最近最长读取的数据

查询机制

只读最新,如果在更前Level中查到所需的Key,则不必向下一个Level查找

 若key值为SST文件的Min和Max之间,使用二分法进行查找(若就是Min或Max直接返回)

若不在,则查找下一个SST文件

bloom Filter

用于判断元素是否在集合内

机制:

过滤器判断不在,一定不在
过滤器判断在,不一定在(有误判率)

RocksDB:列簇

列簇用于数据分片

使一个rocksdb有多个内存区域和多套SST文件,但WAL文件是所有列簇是共享

写入时可以指定列簇,不指定则默认在default列簇

TiKV 分布式事务

begin:通过PD获取事务开始时间,即start_ts

提交的两阶段:

prewrite:将内存中的数据和将锁信息写入TiKV node中

commit:通过PD获取事务结束时间(或称提交时间),即commit_ts

               向Write列簇写入提交信息

               向Lock列簇写入解锁信息

其中:

 当一个事务有多行时,只给事务的第一行添加主锁,其他行依附于该锁,即锁的指向

 TiKV Node使用3个列簇存储有关事务的执行信息:

Default列簇:存储修改数据(大于255字节),且只存修改值(方便查询);Key=事务id+事务开始的时间戳

Lock列簇:存储锁信息,且只给事务的第一行添加主锁(即pk),其他行依附于该锁(锁的指向)

Write列簇:存储提交信息和一些小事务(小于255字节);Key=事务id+事务结束的时间戳,Value=事务的开始时间戳

简而言之,短数据存在Write列簇,长数据存在Default列簇

得出结论

prewrite阶段使用Default列簇(修改信息)和Lock列簇(锁信息)

commit阶段使用Lock列簇(解锁信息)和Write列簇(事务提交信息)

ps:解锁不是直接删除Lock列簇中的信息,而是添加一条解锁信息 

根据锁的存在能否被其他会话感知,分为:

乐观事务:在提交时将锁信息写入TiKV node,使其他会话无法感知锁的存在

悲观事务:在提交前将锁信息写入TiKV node,使其他会话可以感知锁的存在

 如上图所示,分布式事务在不同TiKV node中

 @1,锁的指向,即表示该锁执行事务id=1的事务,即主锁的位置

若发生如下情况,事务的某一行在向Write列簇写入提交信息时宕机,也未添加解锁信息(如下图),TiDB如何恢复事务的执行

通过Lock列簇的写锁信息中锁的指向,找到指向的主锁,查找事务信息,继续未执行的步骤

以上图为例,通过查询事务id=1的执行,发现事务已完成,故接下来向Write列簇中添加事务提交信息并向Lock列簇中添加解锁信息、

MVCC 多版本并发控制

MVCC的运作原理:

修改时,生成所修改的region副本(同时向PD获取时间戳)并在其该副本中修改数据;在未提交修改时,则读取的数据来自未修改的版本即原本,使写不阻塞读

这些修改产生的副本,又叫快照(snapshot),即为GC垃圾清理的目标

补充:MVCC只在read commited和repeatable read两个隔离级别下工作,与隔离级别snapshot isolation无关

以上图为例,事务1完成了整个过程,而事务2未完成commit阶段

若此时,对事务2进行读取,结果为<1,Jack><2,Candy><4,Tony>

若此时,对事务2进行修改,则因锁而被阻塞

故在执行分布式事务的整个阶段,只阻塞写,不阻塞读

事务的读取

首先查询Write列簇,是否存在相应事务的提交信息

若查找到相应事务的提交信息(即以被持久化),则在相应的列簇(Default列簇)查询相应的事务信息(通过相应的Key=事务id+事务开始数据)
若Write列簇无相应事务的提交信息,且Lock列簇中存在锁信息,则无法修改该事务

对于MVCC是如何阻塞其他会话写入的的,需要三个指针(三个列簇分布一个)

如图(此时TSO=120),有会话写入事务id=1,在Write列簇中查找到事务id=1的提交信息(TSO=110),当在TSO=115时又添加了一把写锁(W)且为主锁(pk),没有解锁信息,写被阻塞

 当有会话写入事务id=2(此时TSO=120),在Write列簇中查找到事务id=2的提交信息(TSO=110),且Lock列簇中没有关于事务id=2的锁,故写入未被阻塞

当有会话写入事务id=4(此时TSO=120),在Write列簇中查找到事务id=2的提交信息(TSO=110),当在TSO=115时又添加了一把写锁(W)且指向事务id=1的主锁,没有解锁信息,写被阻塞

TiKV Raft

raft group:region及其副本(上图以3副本为例)

Multi raft:由多个raft goup组成

raft log利用region ID+日志的顺序ID来作为唯一标识 

所有客户端的读写流量都通过leader 

Propose

操作被leader收到,leader准备同步并将写入请求转化为raft log的形式(Key=region id+log id) 

Append

Append操作将raft log存入rocksdb实例中(rocksdb raft),进行(在leader中的)持久化

Replicate

leader将raft log复制给follower并在(follower中的)rocksdb中进行持久化(横向复制)

Committed

当大多数(超过一半,但不是所有的)follower将raft log持久化成功(返回append完成)

ps:但此时写入的数据未持久化(未在rocksdb kv中),只有当Apply操作后才写入rocksdb

整个阶段一共有两个Committed;一个是事务的提交,另一个是raft log的横向复制的完成

Apply 

leader将raft log(rocksdb raft中)的操作apply至rocksdb kv中的数据,写入完成

ps:若大多数(超过一半的)follower没有持久化成功(Replicate),则日志不会被Apply

Raft Leader选举

leader周期性向follower发出含有统治信息的心跳(参数heartbeat time interval);若follower长时间收不到统治信息(参数election timeout),某个region将会转换为candidate(候选者),并发起投票重新选取leader

election timeout:控制收不到统治信息时,发起选举的阈值;一般用于初始化时进行选举(集群刚被创建))

heartbeat time interval:控制发出心跳的周期,当收不到心跳的时间且超过election timeout的阈值,发起选举;一般用于集群运行中

 如图,当leader宕机,TiKV node 3长时间收不到心跳并率先达到阈值,自身转化为candidate,进入下一个term并发起选举
向其他region发起请求,进行投票;其他follower接收请求并同意比自己term大的请求(term=2<term=3)

 如图,若碰巧所有Tikv node都转为candidate企图发起选取,election timeout参数将会初始为随机值,减小每个TiKV node达到阈值的记录;若还是有多个candidate重复该过程,整个过程发起了多次选取

election timeout

        raft-election-timeout-ticks:设置 election timeout有多少个相对时间单位(ticks,默认1s)

        raft-base-tick-interval:设置每个相对时间单位(ticks)有多长时间

heartbeat time interval

        raft-heartbeat-ticks:设置 heartbeat time interval有多少个相对时间单位(ticks,默认1s)

        raft-base-tick-interval:设置每个相对时间单位(ticks)有多长时间

假设raft-election-timeout-ticks=5,raft-base-tick-interval=1s,则election timeout=5*1=5s

ps:election timeout ticks不能小于heartbeat ticks

TiKV读写与Coprocessor

首先向PD获取所region的位置(哪一个leader,在哪一个TiKV上)

线程池:

raftstore pool:将数据被转化为raft log并持久化至rocksdb raft;向其他副本横向复制(propose,append,replicate,committed)

apply pool:将raft log应用于rocksdb kv(apply)

ReadIndex Read

本质上属于一种判断操作是否apply至rocksdb的机制,如下图

当某一会话提交操作(TSO=10:00),但其操作未apply至rocksdb;此时ReadIndex=1-95,ApplyIndex=1-92,rocksdb中的数据为1-92

当另一会话企图读取被修改的数据(TSO=10:05),此时raftstore pool将日志commit至1-97,但applypool将操作应用至1-93(该案例假设没有MVCC机制,若有则读取的是之前的数据即1-93);即将ReadIndex=1-97并阻塞commit,使其等待apply操作至1-97

当apply至1-95时,事务的commit完成

当apply至1-97时,即ApplyIndex等于ReadIndex,此时根据raft log的顺序性,事务1-95肯定已被持久化至rocksdb

总结:利用日志的顺序性,通过判断后面的日志是否已apply推断出要读取的日志是否apply

ReadIndex一定大于要读的raft log,当ApplyIndex等于ReadIndex时判断

Lease Read

若某个TiKV发出心跳,则该TiKV在发出心跳的heart time interval内均为leader,但heart time interval之后未发出心跳,此时不会立马发起选举,而要直到election timeout

例如leader发送心跳的周期为10ms,则在心跳发送后10ms内,则该TiKV node在这个时间段内一定为leader

Follower Read 

在数据的读取中,leader及follower都会使用Reader Index机制绑定操作是否已应用于rocksdb;但是follower的往往会比leader更先得出结果(follower的apply速度比leader的快)

当收到读取请求时,follower向leader获取CommitIndex,当follower中的ApplyIndex大于向leader获取的CommitIndex,则说明修改以应用并读取数据

本质上是ReadIndex的变体,ReadIndex读取方式都在leader中执行,而Follower Read中CommitIndex在leader,但ApplyIndex在follower

Leader中:

 Follower中:

Coprocessor 

若不使用Coprocessor ,则数据将汇总在TiDB对网络带宽和CPU负载都有极高要求

 而使用Coprocesser,TiDB的计算将下推至TiKV

当TiDB收到SQL语句,得出物理执行计划,推出可以由TiKV Coprocessor计算的部分

Coprocessor包括三大计算:

  • 执行物理算子
  • 分析数据
  • 提交信息

下推的算子包括:索引扫,表扫,过滤等

例题

1.下列属于TiKV相关功能的是?(选4项)

A.系统参数和元数据信息的持久化 

B.产生TSO

C.分布式事务实现

D.MVCC

E.生成物理执行计划

F.表统计信息的持久化

答案:A,C,D,F

解析:B:TSO由PD产生;E:由TiDB Server生成物理执行计划

注:元数据信息如用户名,密码,表名等

2关于TiKV数据持久化,下列说法不正确的是?

A.RocksDB有2个实例,分别用来持久化raft log和key value数据

B. RocksDB中WAL用来保证写不丢失

C.对于删除操作,只需要在原key value数据上标记已删除即可

D.RocksDB中,除了Level 0层的数据,其他Level都是单一排序持久化的

答案:C

解析:A:rocksdb包括两个实例,持久化raft log的rocksdb raft和持久化key value的rocksdb kv;B:WAL预习日志,直接将写入持久化至磁盘,即使系统宕机也能故障恢复;C:TiDB使用LSM Tree进行操作,LSM Tree是以插入为基础,如更新操作,也是在原有的那一行直接插入数据;D:Level 0的内容等于immutable的内容,而immutable有多个分批写入磁盘,没有进行排序,而其他Level均是有更低的Level压缩合并后按Key值排序而来


http://www.ppmy.cn/news/372528.html

相关文章

vtk能干什么(适用范围)

参考博客&#xff1a;VTK能做什么_51CTO博客_vtk是什么 1、求一点与一条线之间的距离 2、两点之间的距离 3、生成均匀分布的随机数 4、生成高斯分布的随机数 5、确定点是否在面上 6、读取xgml文件 7、读取一个简单的点文件 8、读取XYZ A格式的点文件 9、读取一个文本文…

VTK渲染引擎

本文翻译自VTK user guide. VTK渲染引擎由VTK中的类组成&#xff0c;这些类负责获取可视化管道的结果并将其显示到窗口中。这涉及以下组件。注意&#xff0c;这并不是一个完备的列表&#xff0c;而是渲染引擎中最常用对象的含义。这里使用的副标题是VTK中表示这种类型对象的最高…

VTK简介

VTK(Visualization ToolKit) 是一个开放源码、自由获取的软件系统&#xff0c;全世界的数以千计的研究人员和开发人员用它来进行3D 计算机图形&#xff0c;图像处理&#xff0c;可视化。VTK 包含一个c 类库&#xff0c;众多的翻译接口层&#xff0c;包括Tcl/Tk &#xff0c;Jav…

VTRK+PICO

碰撞检测 1、通过刚体组件&#xff08;Rigidbody&#xff09;和碰撞器组件&#xff08;Collider&#xff09;来进行检测 选择一个物体添加刚性物体 2、触发检测条件&#xff1a;至少有一方是刚性物体&#xff0c;双方都有mesh collider ​ 碰撞检测条件&#xff1a;主动方是…

VTK- vtkStripper

前言&#xff1a;本博文主要研究接口vtkStripper的实现原理及主要的应用场景&#xff0c;希望对各位小伙伴有所帮助。 描述&#xff1a;vtkStripper是一个过滤器&#xff0c;用于从输入多边形、三角形带和线中生成三角形带和/或折线。输入多边形仅当它们是三角形时才被组装成三…

git 提交到远程仓库 报错 error: failed to push some refs to ‘https://xxxxxx.git‘

git 学习地址 参考链接 报错如下 error: failed to push some refs to https://github.com/GDDXZ/RobotDenso.git hint: Updates were rejected because the remote contains work that you do hint: not have locally. This is usually caused by another repository pushi…

2014世界10大DRAM公司

DRAM(Dynamic Random Access Memory)&#xff0c;即动态随机存取存储器&#xff0c;是一种 最常见的半导体存储器&#xff0c;主要的作用原理是利用电容内存储电荷的多寡来代表一个二进制比特(bit)是1还是0。据IHS调查显示&#xff0c;2013年世界DRAM的销售值比上年窜升了32.5%…

linux新机怎么下载软件,新机安装linux日记

新主机: CPU: AMD 闪龙2800 主板:昂达N61V (芯片组nVIDIA MPC61) 安装fc5 插入第一张光盘,在:kernel_thread_helper0x4/0xb 就在这里就停住不动了.诸处寻因不得果. 开始以为主板不支持linux,后得知只要芯片组支持就可以了,而且这个芯片组是支持了,因为据说安装uBUNTU没问题. 后…