前言

继上次参与了matrixone社区的活动之后,我进入了matrixone社区的用户群。群里经常有最新的科技资讯和技术讨论,我受益匪浅。某天,突然留意到matrixone社区有发起了一项新的活动matrixKV初体验。正好最近在写mit6.824的 lab,对于分布式和数据库本身也是很感兴趣,于是我参加了这次活动,希望能了解一下MatrixOne社区是怎样设计和实现的。

经历

这次主要是跟着活动介绍来一步一步体验的,MatrixCube揭秘102——300行实现的完整分布式存储系统MatrixKV

MatrixKV是一个简单的分布式强一致KV存储系统,采用Pebble作为底层的存储引擎,MatrixCube作为分布式组件,以及自定义了最简单的读写请求接口。用户可以非常简单的在任意一个节点发起读写数据的请求,也可以从任意一个节点读到需要的数据。

本次实验以Docker模拟一个小型MatrixKV集群的形式,来进一步说明MatrixCube的功能与运作机制。

  1. 我们先安装docker和docker-compose,克隆仓库代码git clone https://github.com/matrixorigin/matrixkv
  2. 对于不同的节点而言,有不同的身份。 我们这次实验准备的这个小型集群有四个节点,其中三个为Prophet节点, 一个为数据节点。我们以docker进行容器包装的形式来在单机上进行模拟。
  3. /cfg文件夹中有node0-node3的配置文件,其中Node0-Node2均为Prophet节点,Node3为数据节点。image-20220714205556179
  4. 各配置文件的配置项的作用原文已经很详细描述了,在此要说明的是新建一个数据目录data/matrixkv,更改toml文件指向相对路径。然后更改docker-compose.ymlvolumes使 ./data/matrixkv/node0:/data/matrixkv将当前目录下的./data/matrixkv/node0挂载到docker镜像中的/data/matrixkv中,这样可以在当前目录下观察到docker节点的实时数据文件,便于分析观察。如果不修改则需要在用户根目录下创建/data/matrixkv,十分混乱。具体修改内容可以参考我的提交change config.
  5. 直接make docker即可构建镜像。需要注意的是一些人需要先执行go mod vendor,我的arch会遇到这个问题。

image-20220714210719859

  1. 构建后docker-comose up启动集群。观察到‘Listening and serving HTTP on node0:8080’ 输出表示集群启动完成。

image-20220714211002678

  1. 根据提示进行put,get,delete,其中对于8080–>node08081–>node1,8082–>node2,8083–>node3的操作映射。(截图显示我们对于node0的put k1->v1 ,在node3上也可以读取到正确的值,这表示数据确实通过一致性协议去保证了强一致性)。

image-20220714211334313

  1. 查看此时节点的shard情况。node0->null, node1=node2=node3 !=null
  2. image-20220714211631791
  3. 构建一个超级大的kv,使得MatrixCube会在写入的数据量达到一定级别的时候产生Shard分裂。(比如set item0 kkkkkkkkkkkkkk…….
  4. 再次观察shard情况。此时集群中shade变多。
  5. 手动停止node3,然后取数据。image-20220714212105318 这时get node3失败,但是get node2/1/0 都能正确返回。
  6. 再次查看节点shard情况,此时为了维护三副本,原先node0的空shard已经有了值。image-20220714212307378
  7. 观察源码。

    > 通过整个实验我们已经完整体验了在MatrixCube帮助下将一个单机的KV存储引擎Pebble变成了一个分布式的KV存储。而其中需要MatrixKV本身实现的代码是非常简单的。总的来说就只有4个go文件,不到300行代码就可以完成MatrixKV的全部搭建。
    >
    > 1. /cmd/matrixkv.go: 整体程序启动的入口,进行最基本的初始化并启动服务。
    >
    > 2. /pkg/config/config.go: 定义了一个MatrixKV整体配置的数据结构。
    >
    > 3. /pkg/metadata/metadata.go:定义了用户与MatrixKV读写交互请求的数据结构。
    >
    > 4. /pkg/server/server.go:这是MatrixKV的最主体功能,其中主要做了三件事:
    >
    > - 定义MatrixKV server的数据结构。
    > - 定义Set/Get/Delete等相关请求的Executor具体实现。
    > - 调用Pebble库作为单机存储引擎,实现MatrixCube指定的DataStorage接口,将MatrixCube的Config项设置到相应方法上。
    

其中最关键的是/pkg/server/server.go下的内容,实现了我们使用的所有命令和handShards来保证数据多副本的一致性。短短几百行,却实现了一个可靠的分布式kv系统,这让我对分布式有了新的认识。也让我对分布式有了更多的理解。