Tedis:基于 TiKV 构建的 NoSQL 数据库

Easter79
• 阅读 716

作者介绍: 陈东明,饿了么北京技术中心架构组负责人,负责饿了么的产品线架构设计以及饿了么基础架构研发工作。曾任百度架构师,负责百度即时通讯产品的架构设计。具有丰富的大规模系统构 建和基础架构的研发经验,善于复杂业务需求下的大并发、分布式系统设计和持续优化。个人微信公众号 dongming_cdm。

Tedishttps://github.com/eleme/tedis)是基于开源 TiKV 的兼容 Redis 协议的强一致性的 NoSQL 数据库开源项目。 本文介绍一下 Tedis 开源项目的架构设计和特性,以及架构背后的一些思考(包括为何选择 TiKV 和 Redis 协议)。

先来讨论为什么基于 TiKV 构建我们自己的 NoSQL 数据库。

首先简述一下 TiKV[1],TiKV 是 TiDB 的一个子项目,TiDB 是一个分布式的关系型数据库 [2],TiKV 是 TiDB 的存储层。TiKV 本身是可独立于 TiDB 的单独项目。它是一个强一致、可水平扩展的、高可用的分布式 Key-Value 存储系统。

选择 TiKV 的第一个原因是 TiKV 是一个强一致的系统。 在我的另外一篇文章中(发表在 InfoQ, 参看 https://www.infoq.cn/article/rhzs0KI2G*Y2r9PMdeNv ),我阐述了一个观点:NoSQL 数据库应该具有一致性,并且通过多副本技术达到实际的高可用,也就是说 NoSQL 数据库应该是一个“实际上的 CA” (effectively CA)系统。但是在这篇文章中我并没有明确说明 NoSQL 该具有的一致性是哪种一致性。实际上,我所说的一致性其实就是一种强一致性 [3],或者更准确的说是线性一致性 [4]。TiKV 正是具有这种线性一致性。TiKV 中的每个数据都会保存 3 个副本,在只有一个副本的节点宕机或者出现网络分区的情况下,另外 2 个副本仍然能够对外提供服务。理论上来讲,同时出现 2 个以上副本同时坏掉的可能性很小,也就是理论上可以达到非常高的可用性。通过 TiKV 滚动升级等运维辅助,如果在实际的生产中,有良好的运维,可以达到实际上非常高的可用性。也就是称为一个“实际上的 CA”(effectively CA)系统。

TiKV 通过 Raft [5] 协议实现了线性一致性和高可用 2 个特性。Raft 是一种分布式共识协议,通过 Raft 协议,数据可以被认为是原子的写入到 3 个副本上。共识协议的一个特点就是要写入大多数,才会认为写入成功,3 个副本的大多数就是 2 个,也就是在只有一个副本宕机或者网络分区的情况下,仍然可以成功写入,并且提供读服务。

选择 TiKV 的第二个原因是 TiKV 的架构可扩展和生态。 在 TiDB 中 TiKV 是独立的一层,形成了一个很好的可扩展架构,实际上可以在 TiKV 上扩展出很多不同的数据库出来。TiDB 层本身就是这种架构上的一个扩展。这种架构类似于 Google 公司的第一代的 Spanner 系统 [6],Spanner 系统本身也是一个强一致性的、高可用的分布式 Key-Value 系统。在 Spanner 的基础之上,Google 构建了 F1 系统 [7],实现了 SQL 协议。2017 年,Google 升级了 Spanner 到第二代 [8],让 Spanner 本身就具有了 SQL 能力。虽然一代 Spanner+F1 是这样的架构,但它仍然是一种非常优秀的架构。我们的 Tedis 项目,也是构建在这一可扩展架构上的一个项目,依托于 TiKV 提供的底层能力,向上构建了不同于 SQL 协议的 Redis 协议。我相信 TiKV 的这种可扩展架构,未来可以成为一种生态,还可以在上面“⻓出”其他的类型的数据库,比如说 Mango 协议、图协议。这些数据库都具有与底层 TiKV 相同的线性一致性和高可用性,区别只在于对外的接口协议不同。 目前这种生态已初⻅端倪,Titan(https://github.com/distributedio/titan) 这个开源项目,与我们的 Tedis 项目非常类似,他们的开源步伐先于我们,目前做的也非常不错。我相信,我们肯定不是这个生态中的最后一个。

Tedis:基于 TiKV 构建的 NoSQL 数据库

总之基于 TiKV,Tedis 实现了以下的技术特性:

1. 大数据量,可以存储至少数十 TB 级别的数据。

2. 高性能,在满足高 QPS 的同时,保证比较低的延时。

3. 高可靠,数据被可靠的持久化存储,少量机器的损坏不会导致数据的丢失。

4. 高可用,作为在线服务的底层依赖存储,要有非常完善的高可用性能力,外卖服务不同于电子商务,对实时性要求非常高,对系统的可用性的要求则是更高的。

5. 易运维,可以在不停服的基础上进行数据迁移和集群扩容。

接下来,我们讨论第二个问题,为什么选择 Redis 协议。

SQL 语言与其背后的关系模型,从 1970s 发明以来,一直在应用开发领域占据这统治地位,虽然在 CAP 定理的推动下 [4],在 NoSQL 运动中,出现很多 NoSQL 系统,就如我前面阐述的一样,一致性不应该是 NoSQL 出现的理由,去 SQL 和关系模型才是 NoSQL 出现的动力。但我并不认为 NoSQL 会代替 SQL。虽然 NoSQL 出现的时候,原本表达的意思是 “NO SQL(没有 SQL),但是我觉得另外一种对 NoSQL 的解释更合适,也就是“Not Only SQL不仅仅有 SQL)”。NoSQL 不是 SQL 的替代品,应该是 SQL 的有力补充。在 NoSQL 运动中,涌现出来的非常优秀的 NoSQL 系统大多都有自己的独有的接口协议,比如 Redis、MongoDB、Cassandra、图数据库等等。他们都有各自非常适用的使用场景,比如 MongoDB 贴近面向对象,图数据库适合节点的图关系运算。而 Redis 贴近开发者数据结构思维,相信每个开发者都是从数组、hash 表、队列这样的数据结构中成⻓起来的。

另外,Redis 本身是一个非常优秀的产品,它的普及程度非常高,特别是在互联网行业。在每个互联网公司,Redis 都已经成为工程师开发工具箱中,必备的工具之一。Redis 已经是开发者除 SQL 之外,第二熟悉的产品了。

但是,选择 Redis 协议,也给我带来一些实际的困扰,我们有些使用者最初接触 Tedis 时,总是拿我们和 Redis 相比。但是,虽然我们采用的是 Redis 接口,但是 Tedis 本身并不对标 Redis 这个产品。Redis 是非常优秀的缓存。虽然 Redis 也可以开启持久化功能,由于 Redis 本身架构设计,开启持久化的 Redis 仍然不能达到“实际上的 CA”(effectively CA),和 100% 的持久性(durability)。这是 Redis 和 Tedis 的一个很大的区别,Tedis 是一个数据库,不是一个缓存。

讨论完上面的 2 个架构思考,我们来看一下 Tedis 的架构设计。

Tedis:基于 TiKV 构建的 NoSQL 数据库

在 Tedis 中,我们封装了一个 TiKV 的 SDK,对 Redis 的协议进行了解析,并且将 Redis 协议转成对 TiKV 的调用。

目前 Tedis 仍然有很多要完善的地方,但是我们会尽快完善如下的事项,在我们的开源日程表中:

1. Redis 命令的补全

2. 压缩和限流等一些扩展功能

3. Cassandra 协议的支持

写在最后

作为存储系统,不应该让使用者在一致性、可用性这些技术特性上做过多的选择,使用者应该更多的考虑哪种接口更适合自己的应用场景,自己更熟练使用哪种接口,能用哪种接口更快的进行功能开发。

由于篇幅所限,本文中关于强一致性、线性一致性、Redis、Raft、Spanner 的很多技术细节的阐述未能详尽,拟另行成文讨论。

参考资料:

  1. https://github.com/pingcap/tikv

  2. https://github.com/pingcap/TiDB

  3. Eventually Consistent - Revisited,Werner Vogels, 2008, http://www.allthingsdistributed.com/2008/12/event ually_consistent .html

  4. Linearizability: A Correctness Condition for Concurrent Objects,Maurice P. Herlihy and Jeannette M. Wing,1990

  5. In Search of an Understandable Consensus Algorithm, Diego Ongaro and John Ousterhout, 2014

  6. Spanner: Google’s Globally-Distributed Database, James C. Corbett, Jeffrey Dean et al., 2012

  7. F1: A Distributed SQL Database That Scales, Jeff Shute et al., 2013 8.Spanner: Becoming a SQL System, David F. Bacon et al., 2017

Tedis:基于 TiKV 构建的 NoSQL 数据库

点赞
收藏
评论区
推荐文章
blmius blmius
3年前
MySQL:[Err] 1292 - Incorrect datetime value: ‘0000-00-00 00:00:00‘ for column ‘CREATE_TIME‘ at row 1
文章目录问题用navicat导入数据时,报错:原因这是因为当前的MySQL不支持datetime为0的情况。解决修改sql\mode:sql\mode:SQLMode定义了MySQL应支持的SQL语法、数据校验等,这样可以更容易地在不同的环境中使用MySQL。全局s
皕杰报表之UUID
​在我们用皕杰报表工具设计填报报表时,如何在新增行里自动增加id呢?能新增整数排序id吗?目前可以在新增行里自动增加id,但只能用uuid函数增加UUID编码,不能新增整数排序id。uuid函数说明:获取一个UUID,可以在填报表中用来创建数据ID语法:uuid()或uuid(sep)参数说明:sep布尔值,生成的uuid中是否包含分隔符'',缺省为
Jacquelyn38 Jacquelyn38
3年前
2020年前端实用代码段,为你的工作保驾护航
有空的时候,自己总结了几个代码段,在开发中也经常使用,谢谢。1、使用解构获取json数据let jsonData  id: 1,status: "OK",data: 'a', 'b';let  id, status, data: number   jsonData;console.log(id, status, number )
Stella981 Stella981
3年前
KVM调整cpu和内存
一.修改kvm虚拟机的配置1、virsheditcentos7找到“memory”和“vcpu”标签,将<namecentos7</name<uuid2220a6d1a36a4fbb8523e078b3dfe795</uuid
Easter79 Easter79
3年前
Twitter的分布式自增ID算法snowflake (Java版)
概述分布式系统中,有一些需要使用全局唯一ID的场景,这种时候为了防止ID冲突可以使用36位的UUID,但是UUID有一些缺点,首先他相对比较长,另外UUID一般是无序的。有些时候我们希望能使用一种简单一些的ID,并且希望ID能够按照时间有序生成。而twitter的snowflake解决了这种需求,最初Twitter把存储系统从MySQL迁移
Wesley13 Wesley13
3年前
00:Java简单了解
浅谈Java之概述Java是SUN(StanfordUniversityNetwork),斯坦福大学网络公司)1995年推出的一门高级编程语言。Java是一种面向Internet的编程语言。随着Java技术在web方面的不断成熟,已经成为Web应用程序的首选开发语言。Java是简单易学,完全面向对象,安全可靠,与平台无关的编程语言。
Stella981 Stella981
3年前
Django中Admin中的一些参数配置
设置在列表中显示的字段,id为django模型默认的主键list_display('id','name','sex','profession','email','qq','phone','status','create_time')设置在列表可编辑字段list_editable
Stella981 Stella981
3年前
Docker 部署SpringBoot项目不香吗?
  公众号改版后文章乱序推荐,希望你可以点击上方“Java进阶架构师”,点击右上角,将我们设为★“星标”!这样才不会错过每日进阶架构文章呀。  !(http://dingyue.ws.126.net/2020/0920/b00fbfc7j00qgy5xy002kd200qo00hsg00it00cj.jpg)  2
Wesley13 Wesley13
3年前
MySQL部分从库上面因为大量的临时表tmp_table造成慢查询
背景描述Time:20190124T00:08:14.70572408:00User@Host:@Id:Schema:sentrymetaLast_errno:0Killed:0Query_time:0.315758Lock_
Python进阶者 Python进阶者
10个月前
Excel中这日期老是出来00:00:00,怎么用Pandas把这个去除
大家好,我是皮皮。一、前言前几天在Python白银交流群【上海新年人】问了一个Pandas数据筛选的问题。问题如下:这日期老是出来00:00:00,怎么把这个去除。二、实现过程后来【论草莓如何成为冻干莓】给了一个思路和代码如下:pd.toexcel之前把这
Easter79
Easter79
Lv1
今生可爱与温柔,每一样都不能少。
文章
2.8k
粉丝
5
获赞
1.2k