一名开发者眼中的TiDB与MySQL选择
作者: angryart 原文来源:https://tidb.net/blog/60200e06
TiDB长期霸榜国产数据库第一名,社区活跃人气旺盛。作为TiDB其中的一个粉丝,我把近年的学习调研实践归纳如下,TiDB是一款通用性的数据解决方案,任何数据场景都可以使用它来解决问题,所以它与所有市场上所有的数据库产品 多多少少存在直接上的或者间接上的竞争关系。
那么市场竞争上谁是TiDB的第一梯队竞争对手,本人认为是MySQL是其中一个,当然也可以是Oracle、DB2等等,主要是MySQL在中国深入人心,工程师信手拿来就能使用。
TiDB与MySQL的对比
有些人直接称TiDB为大号的MySQL,其实不对,为了工程师像使用MySQL使用TiDB,TiDB在接口层下了大量的功夫,在语法、表名、引用甚至元数据方面尽量与MySQL贴合,但是每个语句背后执行的都是不同的数据流程和服务流向。
类型上比较,MySQL是纯粹单机式数据库,TiDB是分布式数据库,TiDB可以方便自由增加节点扩展存算能力,而MySQL增加节点增强性能,必须通过定向策略,例如中间件路由或者读写分离的方式,显得呆滞固化。
引擎上比较,MySQL有myisam、innodb、memory等引擎 ,也可以通过插件支持更多的引擎例如rocksdb,HandlerSocket等等,而TiDB虽然只有两个引擎,但是却能应对所有的应用场景。
架构上比较,MySQL是偏紧密耦合,分为三层分别是接口层、服务层、存储层,接口层负责请求处理、授权认证、安全,服务层负责查询解析、分析、优化、缓存、系统内置函数,存储层负责数据的 存储和处理,统一体现在一个服务进程上。TiDB则是松散耦合型,把数据库的关键组件抽象,根据本身分布式的特性,分别是计算层、存储层、协调层。
- TiDB计算层类似MySQL接口层,负责负责接收 SQL 请求,处理 SQL 相关的逻辑,并通过协调层找到存储计算所需存储层数据的地址,与 存储层交互获取数据,最终返回结果。
- TiDB存储层负责存储数据,数据的存储容量没有上限,存储层上同一份数据一般有3个副本,满足高并发需求。协调层会对存储层中的数据做出负载均衡的处理。
- TiDB协调层负责集群的管理模块,经常干的事情有3个,一个是集群的元信息,一个是对存储层的数据进行调度和负载均衡,一个分配全局唯一且递增的事务 ID。
数据处理技术上,MySQL是B+树的组织存储结构,B+树适合读多写少,如果写多了,写的影响动作主要是插入、删除,会导致全局的平衡树下面的页频繁分裂或者合并,直接影响性能,影响读放大。TiDB是LSM树的组织存储结构,擅长写多读少,如果读多了,在内存扫描不到数据,就会去硬盘里面去寻找无序的sst文件,所以数据越多越大就会读放大。
TiDB做了诸多优化,例如使用RocksDB作为背端存储,优化LSM机制等等,协同提高数据全链条的处理性能,而且是存算分离的组织完成这个性能的。
产品方向上比较,MySQL默认innodb,擅长OLTP的业务场景,同时MySQL可以插件组装各式引擎,换言之MySQL是一个通用型的数据库产品支持所有的业务场景。而TiDB默认悲观事务,同样是以OLTP为重,同样是一个通用型的数据库产品。但是两者是不一样的,由于MySQL是单机型的结构,如果它要扩展,只能通过数据库中间件路由划分,如果数据满了需要停机停服,重新进行数据的割分。
TiDB对业务无侵入性,扩展非常简单,发展至今安装与维护都非常成熟 ,通过Tiup就可以就可以对分布式集群进行组装维护的相关操作,并且支持在线升级,无缝迁移。
总结,TiDB与MySQL没有对比性, 他们不是同一类的数据产品,但是从数据库的特性和市场方向上出发 ,他们又有了对比的维度指标。事实上,TiDB努力向MySQL学习,甚至还聘请了innodb的内核开发工程师,努力调整TiDB的底盘,让TiDB从内向外都像MySQL。
同类竞争产品
TiDB是一款分布式数据库产品,以分布式为标识并能基于线下安装 ,国内同样竞比产品有OceanBase,国外同比有CockroachDB。TiDB的商业经营主要集中在云数据库上,所以PolarDB也是TiDB的竞争对手。那么TiDB与PolarDB、OceanBase、CockroachDB有什么不同?
从数据库处理的流程开始讲,从任务开始到任务结束。
- 用户发起请求, 数据库客户端发起请求到指定的数据库集群。
- 目标数据库响应 指定的数据库集群指定一个节点响应用户的请求。
- 两者建立会话, 数据库集群其中一个节点与客户端产生会话。
- 对象请求解析, 数据库将接收的请求进行 语法检查,对象解析、转换对应的关系代数结构、并进行计划任务优化。
- 调度并且执行, 寻找最合适的副本 ,根据优先级进行,是内存、缓存、数据快照、存储等等。
- 监测任务状态, 观测数据库的执行中状态。
- 返回数据结果, 数据库服务端返回结果给数据库客户端
最关键的是第2步、第4步、第5步。
第2步是 哪一个节点响应数据库客户的请求,分布式数据库有两种系统架构,一种是中心化架构【master\slave】,一种是去中心化架构。中心化架构的负色职责分清,负责干活、负责指挥、负责接待用户,而去中心货架构则是每个节点角色平等,对待客户的请求,其中的一个节点会瞬间切换成负责接待,剩余的节点根据情况转化执行。
TiDB在这里采用中心化的架构,节点角色之间的职责更加清晰,分工更加明确。
第4步和第5步是数据计算和数据存储的关键步骤,TiDB在这里做了深度的松散解耦,数据计算用TIDB,数据存储用TIKV,两者是真正意义上的存算分离,要增加存储容量,可以增加没有CPU的硬盘服务器,要增加计算能力,可以增加没有硬盘的服务器。关于分布式的功能和作用则集中在一个PD的模块上。
OB则是去中心架构,而且计算和存储高度耦合,所以OB又称为集中式的分布式架构,后面又称为单机式的分布式架构。
TiDB比起同类产品在架构上更加高度松散耦合,与云计算技术更加紧密协作,珠联壁合。
TiDB vs MySQL
如果TiDB要做大做强,必须要撼动广大码农的工作使用习惯,广大码民对MySQL的使用已经深入人心了,不管是TP应用,还是AP应用,先不管性能,首先用MySQL完成业务代码的开发,这意味着MySQL经常被当HTAP数据库来用。下面我用CH-benchmark 针对 TiDB6.0以及MySQL8.0来做一个测试。
TPC-CH 由未经修改的 TPC-C 模型和事务、以及 TPC-H 查询的改编版本构成,TPC-CH 保持所有 TPC-C 实体和关系完全不变,并集成了 TPC-H 模型中的 SUPPLIER、REGION 和 NATION 表。这些表在 TPC-H 查询中频繁使用,并允许以非侵入的方式集成到 TPC-C 模型中。SUPPLIER 包含固定数量(10,000条)的条目。因此,STOCK 中的一条记录可以通过 STOCK.S I ID × STOCK.S W ID mod 10, 000 = SUPPLIER.SU SUPPKEY 与其唯一的供应商(SUPPLIER 表中对应记录)关联起来。TPC-C 中的原始 CUSTOMER 表不包含引用自 NATION 表的外键。我们并没有改变原始模型,从而保持了与现有 TPC-C 的兼容性,所以外键是从字段 C STATE 的第一个字符开始计算的。TPC-C 规定第一个字符可以有62个不同的值(即大写字母、小写字母、数字),因此我们选择了62个国家来填充 NATION。根据 TPC-H 规范,主键 N NATIONKEY 是一个标识符。它的值被规定,从而使得与这些值相关联的 ASCII 值是一个字母或数字,即 N NATIONKEY ∈ [48, 57]∪[65, 90]∪[97. 122]。因此,不需要额外的计算来跳过 ASCII 码中数字、大写字母和小写字母之间的间隔。不支持从字符转换到 ASCII 码的数据库系统可能会偏离 TPC-H 模式,使用单个字符作为 NATION 的主键。REGION 包含国家的五个地区。新表之间的关系使用简单的外键字段来建模:NATION.N REGIONKEY 和 SUPPLIER.SU NATIONKEY。
在CH-Benchmark 中结合了 TPC-C 和 TPC-H 两种基准,它把原来 TPC-C 中的 9 个表和 TPC-H 中的 8 个表修改合并成了 12 个表,并将两者的伸缩模型也统一起来(Scaling TPC-H by the same factors of TPC-C)。
测试环境
硬件配置
操作系统 | CentOS Linux release 7.6.1810 |
---|---|
CPU | 8核 Intel(R) Xeon(R) |
内存 | 16 |
测试配置
软件版本 | IP | 作用 |
---|---|---|
MySQL8.0 | 192.168.1.X | MySQL单机 |
TiDB6.0 | 192.168.1.X | TiDB单机 |
CH-benchmark | 192.168.2.X | HTAP测试工具,生成数据 |
TiUP Bench | 192.168.2.X | HTAP测试工具,进行测试 |
生成数据
我这里是通过TiDB Bench对数据进行压测,但是数据却是通过CH-benchmark 去生成的。
安装CH-benchmark
https://github.com/DASLab-IDA/CH-benchmark -rwxr-xr-x. 1 root root 1007440 Mar 29 16:13 chBenchmark -rw-r--r--. 1 root root 12745 Mar 3 2022 chBenchmark.cpp -rw-r--r--. 1 root root 194096 Mar 29 16:13 chBenchmark.o -rw-r--r--. 1 root root 561 Mar 3 2022 LICENSE -rw-r--r--. 1 root root 1167 Mar 3 2022 Makefile -rw-r--r--. 1 root root 2650 Mar 3 2022 README.md drwxr-xr-x. 3 root root 4096 Mar 29 16:13 src [root@hdp1 CH-benchmark-main]# make 运行make之后会就对当天的文件进行编译,生成chBenchmark 执行命令 chBenchmark命令如下 Create initial database as CSV files: chBenchmark -csv -wh <WAREHOUSE_COUNT> -pa <INITIAL_DB_GEN_PATH> example: chBenchmark -csv -wh 50 -pa /path/to/any/directory 生成数据如下,生成一个warehouse的数据 chBenchmark -csv -wh 1 -pa /tmp/chBenchmark1
建表语句
CREATE TABLE `customer` ( `c_id` int NOT NULL, `c_d_id` int NOT NULL, `c_w_id` int NOT NULL, `c_first` varchar(16) DEFAULT NULL, `c_middle` char(2) DEFAULT NULL, `c_last` varchar(16) DEFAULT NULL, `c_street_1` varchar(20) DEFAULT NULL, `c_street_2` varchar(20) DEFAULT NULL, `c_city` varchar(20) DEFAULT NULL, `c_state` char(2) DEFAULT NULL, `c_zip` char(9) DEFAULT NULL, `c_phone` char(16) DEFAULT NULL, `c_since` datetime DEFAULT NULL, `c_credit` char(2) DEFAULT NULL, `c_credit_lim` decimal(12,2) DEFAULT NULL, `c_discount` decimal(4,4) DEFAULT NULL, `c_balance` decimal(12,2) DEFAULT NULL, `c_ytd_payment` decimal(12,2) DEFAULT NULL, `c_payment_cnt` int DEFAULT NULL, `c_delivery_cnt` int DEFAULT NULL, `c_data` varchar(500) DEFAULT NULL, PRIMARY KEY (`c_w_id`,`c_d_id`,`c_id`), KEY `idx_customer` (`c_w_id`,`c_d_id`,`c_last`,`c_first`) ); CREATE TABLE `district` ( `d_id` int NOT NULL, `d_w_id` int NOT NULL, `d_name` varchar(10) DEFAULT NULL, `d_street_1` varchar(20) DEFAULT NULL, `d_street_2` varchar(20) DEFAULT NULL, `d_city` varchar(20) DEFAULT NULL, `d_state` char(2) DEFAULT NULL, `d_zip` char(9) DEFAULT NULL, `d_tax` decimal(4,4) DEFAULT NULL, `d_ytd` decimal(12,2) DEFAULT NULL, `d_next_o_id` int DEFAULT NULL, PRIMARY KEY (`d_w_id`,`d_id`) ); CREATE TABLE `history` ( `h_c_id` int NOT NULL, `h_c_d_id` int NOT NULL, `h_c_w_id` int NOT NULL, `h_d_id` int NOT NULL, `h_w_id` int NOT NULL, `h_date` datetime DEFAULT NULL, `h_amount` decimal(6,2) DEFAULT NULL, `h_data` varchar(24) DEFAULT NULL, KEY `idx_h_w_id` (`h_w_id`), KEY `idx_h_c_w_id` (`h_c_w_id`) ); CREATE TABLE `item` ( `i_id` int NOT NULL, `i_im_id` int DEFAULT NULL, `i_name` varchar(24) DEFAULT NULL, `i_price` decimal(5,2) DEFAULT NULL, `i_data` varchar(50) DEFAULT NULL, PRIMARY KEY (`i_id`) ); CREATE TABLE `nation` ( `n_nationkey` tinyint NOT NULL, `n_name` char(25) NOT NULL, `n_regionkey` tinyint NOT NULL, `n_comment` char(152) NOT NULL, PRIMARY KEY (`n_nationkey`) ); CREATE TABLE `new_order` ( `no_o_id` int NOT NULL, `no_d_id` int NOT NULL, `no_w_id` int NOT NULL, PRIMARY KEY (`no_w_id`,`no_d_id`,`no_o_id`) ); CREATE TABLE `orderline` ( `ol_o_id` int NOT NULL, `ol_d_id` tinyint NOT NULL, `ol_w_id` int NOT NULL, `ol_number` tinyint NOT NULL, `ol_i_id` int DEFAULT NULL, `ol_supply_w_id` int DEFAULT NULL, `ol_delivery_d` date DEFAULT NULL, `ol_quantity` smallint DEFAULT NULL, `ol_amount` decimal(6,2) DEFAULT NULL, `ol_dist_info` char(24) DEFAULT NULL, PRIMARY KEY (`ol_w_id`,`ol_d_id`,`ol_o_id`,`ol_number`), KEY `fk_orderline_order` (`ol_w_id`,`ol_d_id`,`ol_o_id`), KEY `fk_orderline_stock` (`ol_supply_w_id`,`ol_i_id`) ); CREATE TABLE `orders` ( `o_id` int NOT NULL, `o_d_id` int NOT NULL, `o_w_id` int NOT NULL, `o_c_id` int DEFAULT NULL, `o_entry_d` datetime DEFAULT NULL, `o_carrier_id` int DEFAULT NULL, `o_ol_cnt` int DEFAULT NULL, `o_all_local` int DEFAULT NULL, PRIMARY KEY (`o_w_id`,`o_d_id`,`o_id`), KEY `idx_order` (`o_w_id`,`o_d_id`,`o_c_id`,`o_id`) ); CREATE TABLE `region` ( `r_regionkey` tinyint NOT NULL, `r_name` char(55) NOT NULL, `r_comment` char(152) NOT NULL, PRIMARY KEY (`r_regionkey`) ); CREATE TABLE `stock` ( `s_i_id` int NOT NULL, `s_w_id` int NOT NULL, `s_quantity` int DEFAULT NULL, `s_dist_01` char(24) DEFAULT NULL, `s_dist_02` char(24) DEFAULT NULL, `s_dist_03` char(24) DEFAULT NULL, `s_dist_04` char(24) DEFAULT NULL, `s_dist_05` char(24) DEFAULT NULL, `s_dist_06` char(24) DEFAULT NULL, `s_dist_07` char(24) DEFAULT NULL, `s_dist_08` char(24) DEFAULT NULL, `s_dist_09` char(24) DEFAULT NULL, `s_dist_10` char(24) DEFAULT NULL, `s_ytd` int DEFAULT NULL, `s_order_cnt` int DEFAULT NULL, `s_remote_cnt` int DEFAULT NULL, `s_data` varchar(50) DEFAULT NULL, PRIMARY KEY (`s_w_id`,`s_i_id`) ) ; CREATE TABLE `supplier` ( `s_suppkey` smallint NOT NULL, `s_name` char(25) NOT NULL, `s_address` char(40) NOT NULL, `s_nationkey` tinyint NOT NULL, `s_phone` char(15) NOT NULL, `s_acctbal` decimal(12,2) NOT NULL, `s_comment` char(101) NOT NULL, PRIMARY KEY (`s_suppkey`) ); CREATE TABLE `warehouse` ( `w_id` int NOT NULL, `w_name` varchar(10) DEFAULT NULL, `w_street_1` varchar(20) DEFAULT NULL, `w_street_2` varchar(20) DEFAULT NULL, `w_city` varchar(20) DEFAULT NULL, `w_state` char(2) DEFAULT NULL, `w_zip` char(9) DEFAULT NULL, `w_tax` decimal(4,4) DEFAULT NULL, `w_ytd` decimal(12,2) DEFAULT NULL, PRIMARY KEY (`w_id`) );
导入数据
导入数据前,注意要对tidb运行以下命令 ALTER DATABASE tpcch SET tiflash replica 1; mysql> SELECT * FROM information_schema.tiflash_replica WHERE TABLE_SCHEMA = 'tpcch'; +--------------+------------+----------+---------------+-----------------+-----------+----------+ | TABLE_SCHEMA | TABLE_NAME | TABLE_ID | REPLICA_COUNT | LOCATION_LABELS | AVAILABLE | PROGRESS | +--------------+------------+----------+---------------+-----------------+-----------+----------+ | tpcch | customer | 90 | 1 | | 0 | 0 | | tpcch | district | 93 | 1 | | 0 | 0 | | tpcch | history | 96 | 1 | | 0 | 0 | | tpcch | item | 99 | 1 | | 0 | 0 | | tpcch | nation | 102 | 1 | | 0 | 0 | | tpcch | new_order | 105 | 1 | | 0 | 0 | | tpcch | neworder | 108 | 1 | | 0 | 0 | | tpcch | order | 111 | 1 | | 0 | 0 | | tpcch | order_line | 113 | 1 | | 0 | 0 | | tpcch | orderline | 115 | 1 | | 0 | 0 | | tpcch | orders | 117 | 1 | | 0 | 0 | | tpcch | region | 119 | 1 | | 0 | 0 | | tpcch | stock | 121 | 1 | | 0 | 0 | | tpcch | warehouse | 125 | 1 | | 0 | 0 | | tpcch | supplier | 128 | 1 | | 0 | 0 | +--------------+------------+----------+---------------+-----------------+-----------+----------+ 15 rows in set (0.00 sec) LOAD DATA local INFILE '/tmp/chBenchmark1/CUSTOMER.tbl' INTO TABLE tpcch.customer FIELDS TERMINATED BY '|'; LOAD DATA local INFILE '/tmp/chBenchmark1/DISTRICT.tbl' INTO TABLE tpcch.district FIELDS TERMINATED BY '|'; LOAD DATA local INFILE '/tmp/chBenchmark1/HISTORY.tbl' INTO TABLE tpcch.history FIELDS TERMINATED BY '|'; LOAD DATA local INFILE '/tmp/chBenchmark1/ITEM.tbl' INTO TABLE tpcch.item FIELDS TERMINATED BY '|'; LOAD DATA local INFILE '/tmp/chBenchmark1/NATION.tbl' INTO TABLE tpcch.nation FIELDS TERMINATED BY '|'; LOAD DATA local INFILE '/tmp/chBenchmark1/NEWORDER.tbl' INTO TABLE tpcch.new_order FIELDS TERMINATED BY '|'; LOAD DATA local INFILE '/tmp/chBenchmark1/ORDER.tbl' INTO TABLE tpcch.orders FIELDS TERMINATED BY '|'; LOAD DATA local INFILE '/tmp/chBenchmark1/ORDERLINE.tbl' INTO TABLE tpcch.orderline FIELDS TERMINATED BY '|'; LOAD DATA local INFILE '/tmp/chBenchmark1/REGION.tbl' INTO TABLE tpcch.region FIELDS TERMINATED BY '|'; LOAD DATA local INFILE '/tmp/chBenchmark1/STOCK.tbl' INTO TABLE tpcch.stock FIELDS TERMINATED BY '|'; LOAD DATA local INFILE '/tmp/chBenchmark1/SUPPLIER.tbl' INTO TABLE tpcch.supplier FIELDS TERMINATED BY '|'; LOAD DATA local INFILE '/tmp/chBenchmark1/WAREHOUSE.tbl' INTO TABLE tpcch.warehouse FIELDS TERMINATED BY '|';
运行压测命令
192.168.2.x上面安装tiup bench
tiup install bench
持续对TIDB的数据库tpcch发起50个TP并发量,并进行一次AP的21个语句查询 tiup bench ch --host 192.168.1.x -Uhenley -pxxxxxx -P4000 --warehouses 1 run -D tpcch -T 50 -t 1 --time 1m 持续对mysql的数据库tpcch发起50个TP并发量,并进行一次AP的21个语句查询 tiup bench ch --host 192.168.1.x -Uhenley -pxxxxxx -P3306 --warehouses 1 run -D tpcch -T 50 -t 1 --time 1m
测试摘要
tiup bench ch --host 192.168.1.x -Uhenley -pxxxxxx -P3306 --warehouses 1 run -D tpcch -T 50 -t 1 --time 1m tpmC: 4168.9, tpmTotal: 9231.7, efficiency: 32417.2% [Summary] Q1 - Count: 1, Sum(ms): 67.7, Avg(ms): 67.7 [Summary] Q10 - Count: 1, Sum(ms): 30.6, Avg(ms): 30.6 [Summary] Q11 - Count: 1, Sum(ms): 558.8, Avg(ms): 558.6 [Summary] Q12 - Count: 1, Sum(ms): 19.8, Avg(ms): 19.8 [Summary] Q13 - Count: 1, Sum(ms): 163.9, Avg(ms): 163.9 [Summary] Q14 - Count: 1, Sum(ms): 14.5, Avg(ms): 14.5 [Summary] Q15_ERR - Count: 1, Sum(ms): 277.5, Avg(ms): 277.5 [Summary] Q2 - Count: 1, Sum(ms): 1360.0, Avg(ms): 1359.5 [Summary] Q3 - Count: 1, Sum(ms): 90.3, Avg(ms): 90.3 [Summary] Q4 - Count: 1, Sum(ms): 116.4, Avg(ms): 116.4 [Summary] Q5 - Count: 1, Sum(ms): 204.9, Avg(ms): 204.8 [Summary] Q6 - Count: 1, Sum(ms): 18.9, Avg(ms): 18.9 [Summary] Q7 - Count: 1, Sum(ms): 21.2, Avg(ms): 21.3 [Summary] Q8 - Count: 1, Sum(ms): 195.2, Avg(ms): 195.1 [Summary] Q9 - Count: 1, Sum(ms): 265.0, Avg(ms): 265.0 QphH: 62.5 tiup bench ch --host 192.168.2.xx -Uhenley -pP@xxx -P4000 --warehouses 1 run -D tpcch -T 50 -t 1 --time 1m tpmC: 1805.5, tpmTotal: 4092.0, efficiency: 14039.7% [Summary] Q1 - Count: 1, Sum(ms): 145.6, Avg(ms): 145.6 [Summary] Q10 - Count: 1, Sum(ms): 275.2, Avg(ms): 275.1 [Summary] Q11 - Count: 1, Sum(ms): 330.5, Avg(ms): 330.4 [Summary] Q12 - Count: 1, Sum(ms): 124.3, Avg(ms): 124.4 [Summary] Q13 - Count: 1, Sum(ms): 98.4, Avg(ms): 98.4 [Summary] Q14 - Count: 1, Sum(ms): 275.1, Avg(ms): 275.1 [Summary] Q15_ERR - Count: 1, Sum(ms): 1.1, Avg(ms): 1.1 [Summary] Q2 - Count: 1, Sum(ms): 469.7, Avg(ms): 469.6 [Summary] Q3 - Count: 1, Sum(ms): 283.8, Avg(ms): 283.8 [Summary] Q4 - Count: 1, Sum(ms): 481.1, Avg(ms): 481.2 [Summary] Q5 - Count: 1, Sum(ms): 256.7, Avg(ms): 256.7 [Summary] Q6 - Count: 1, Sum(ms): 98.1, Avg(ms): 98.1 [Summary] Q7 - Count: 1, Sum(ms): 192.4, Avg(ms): 192.3 [Summary] Q8 - Count: 1, Sum(ms): 143.1, Avg(ms): 143.1 [Summary] Q9 - Count: 1, Sum(ms): 667.7, Avg(ms): 667.7 QphH: 62.4
测试总结
保留对MySQL8.0和TiDB6.0的内部参数不变, 从load data数据插入、 tpmC性能、以及tpc-h的性能数据表面来看,MySQL8.0要比TiDB6.0要好,其实不然,TiDB还有很多调优的空间。前面说了,毕竟他们是两个不同的产品线,但是这里证明TiDB的友好性,它是十分兼容MySQL的,如果你从单机版TiDB开始,随着你的业务扩大,你可以自由轻易的扩展。
我对TiDB的展望
软件开发的角度,TiDB的解耦是完整的,如果TiDB的发展已经去到7.0。我对TiDB的未来展望是三路发展,TiDB模块源代码,可以做为分布式计算基础参考,派生更多的可能性,类似presto的路线延伸。TiKV模块源代码,可以作为分布式存储参考,以后的发展方向可能是文件数据存储。PD模块源代码的技术路径发展是轻量级的元数据存储的管理,三者兼进,帮助用户降低存储成本,提升计算弹性,通过分布式实现元数据最优存储,多姿多彩,发扬光大。

低调大师中文资讯倾力打造互联网数据资讯、行业资源、电子商务、移动互联网、网络营销平台。
持续更新报道IT业界、互联网、市场资讯、驱动更新,是最及时权威的产业资讯及硬件资讯报道平台。
转载内容版权归作者及来源网站所有,本站原创内容转载请注明来源。
- 上一篇
Uber实践:运维大型分布式系统的一些心得
本文是 Uber 的工程师 Gergely Orosz 的文章,原文地址在:https://blog.pragmaticengineer.com/operating-a-high-scale-distributed-system/ 在过去的几年里,我一直在构建和运营一个大型分布式系统:优步的支付系统。在此期间,我学到了很多关于分布式架构概念的知识,并亲眼目睹了高负载和高可用性系统运行的挑战(一个系统远远不是开发完了就完了,线上运行的挑战实际更大)。构建系统本身是一项有趣的工作。规划系统如何处理10x / 100x流量的增加,确保数据持久,面对硬件故障处理等等,这些都需要智慧。不管怎样,运维大型分布式系统对我来说是一次令人大开眼界的体验。 系统越大,墨菲的“什么可能出错,就会出错”的定律就越会体现。频繁部署、部署代码的开发人员数量很多,涉及多个数据中心、系统被大量全球用户使用,这种出错概率越大。在过去的几年里,我经历过各种各样的系统故障,其中很多让我感到惊讶。有些来自可预测的事情,比如硬件故障或一些看起来无害的Bug,还有数据中心线缆被挖断、同时发生多个级联故障。我经历了数十次业务停摆,...
- 下一篇
凹语言中文语法设计
设计理念 凹语言的中文语法(下面简称凹中文版)的设计理念是: 简洁:尽量减少冗余信息。例如:关键字尽量选择单字。 易读:代码读起来应当尽量贴近自然语言。关键语法信息应当足够醒目。 灵活:不必拘泥于英文编程语言的传统语法,可以尝试灵活的设计。 符号:作为中文编程语言,并不排除,而是妙用标点符号和拼音字母。 凹中文版的语法设计主要受到了文言编程语言的启发。 但与文言编程语言的主要区别,在于上述的第一条理念:简洁。 我认为文言文相对于白话文,最大的特色就是简洁。 而简洁的需求正是由于时代的背景所决定的:当时的书写工具和文字承载工具都非常昂贵,因此惜字如金并不只是比喻。 因此,为了尽量继承文言文的简洁精神,我在设计凹中语法时,与文言编程语言的风格有了很大的区别。 凹中文版的语法设计还参考了: 凹英文语法。凹语言的中文和英文语法是相互兼容的,每个语法结构都能找到对应。并且到现在为止,凹中的解析前端还是和凹语言英文语法强耦合的。 Go语言。凹语言初版的实现是用Go写的,且前端代码也是从Go语言的前端移植过来的,因此在设计与实现中会更倾向于贴近Go的风格。 Kotlin和D语言。凹语言的中文语法设计...
相关文章
文章评论
共有0条评论来说两句吧...
文章二维码
点击排行
推荐阅读
最新文章
- SpringBoot2编写第一个Controller,响应你的http请求并返回结果
- CentOS关闭SELinux安全模块
- CentOS7,CentOS8安装Elasticsearch6.8.6
- Jdk安装(Linux,MacOS,Windows),包含三大操作系统的最全安装
- Linux系统CentOS6、CentOS7手动修改IP地址
- Windows10,CentOS7,CentOS8安装MongoDB4.0.16
- CentOS8安装Docker,最新的服务器搭配容器使用
- Docker快速安装Oracle11G,搭建oracle11g学习环境
- SpringBoot2配置默认Tomcat设置,开启更多高级功能
- Springboot2将连接池hikari替换为druid,体验最强大的数据库连接池