-
-
Notifications
You must be signed in to change notification settings - Fork 20
昆仑分布式数据库集群应用入门
编译和安装
首先如果使用昆仑分布式数据库社区版本,那么需要从源码构建(build),参考这个文档。
如果下载社区版或者企业版的二进制程序或者docker镜像,则不需要从源码构建而是可以直接开始下面的步骤 ---集群安装。
昆仑分布式数据库集群安装的方法见这两篇文档:一键安装和手动安装。
昆仑分布式数据库集群部署规范和建议
在实际部署一个昆仑数据库集群时,每台计算机服务器上可以部署任意数量的计算、存储节点,并且同一台服务器上的所有的计算节点可以共用同一套程序目录,同一台服务器上的所有存储节点和元数据节点也可以共有同一套程序目录。不过,在这样做会导致未来程序升级不方便。推荐的做法是每一个计算节点、存储节点和元数据节点实例有一套专属的程序目录,即使这些节点部署在同一台服务器硬件上也是如此。集群的节点部署可以非常灵活,与服务器硬件没有绑定关系,比如可以把集群的多个计算节点、存储节点和服务器节点部署在同一台计算机服务器上面。在实际生产系统部署中,通常建议集群的每一个计算节点和存储节点和元数据节点都部署在一台独立的服务器硬件中,这样可以达到最高的性能和可用性。 集群当前所有的计算节点、存储节点和元数据集群的IP地址、端口号、用户名和密码等连接信息可以从创建集群时使用的配置文件中得到,也可以从元数据集群中查询到。不过集群每个计算、存储、元数据集群实例在服务器的放置路径,在元数据集群中并没有存储,只在配置文件中保持,所以建议DBA妥善保管安装集群使用的配置文件。DBA会经常需要用到这些信息来管理每一个集群。而应用软件只需要知道计算节点的连接信息即可,应用系统不需要直接连接存储集群或者元数据集群。 元数据集群和cluster_mgr模块完全可以由多个昆仑数据库集群共用,系统设计时我们做了这样的共用设计,因为这些组件的实际负载很低,不需要为每个昆仑数据库集群部署一套。
昆仑分布式数据库集群安装好后,就可以正式使用了,详见下文。
启动集群
首先需要启动所有的计算节点,存储节点(不需要特定顺序,可以任意先后顺序启动)。如果多集群共用的cluster_mgr和元数据集群没有启动,那么在所有节点都启动后最后启动cluster_mgr。
计算节点
进入计算节点程序根目录CNROOT下的scripts目录,然后用以下命令依次启动集群的每一个计算节点:。 python start_pg.py port=4003 注意这里的4003 确实列在了 CNROOT/etc/instance_list.txt 里面才可以。
应用系统无论使用什么语言开发而成,都可以连接集群的任何一个计算节点或者使用LVS等机制自动连接某一个计算节点。 昆仑数据库计算节点完全使用PostgreSQL的客户端协议,因此目前昆仑数据库支持所有主流编程语言的客户端连接库,包括 Java,Scala(JDBC),Python,PHP, Perl, C/C++, Rust, Go, C#,Lua等等。 无论使用什么语言的客户端库连接PostgreSQL或者昆仑数据库的计算节点,都需要指定一个已经存在的database,这个连接中只可以访问这个database中的数据库对象(schema、表、索引、存储过程等)
也可以用psql连接计算节点:
./psql -hlocalhost -p4003 -Udzw postgres
未来昆仑数据库的计算节点也会支持MySQL客户端协议以及MySQL私有的DML语法,这样任何使用MySQL客户端协议的应用代码不需要任何代码修改和重新编译构建(build)就直接可以连接到昆仑数据库集群来读写数据。
存储节点和元数据节点
用以下命令分别启动每一个元数据节点和存储节点。这里的4002端口的实例使用的是~/mysql_installs/percona-8.0.18-bin-dbg/ 这个程序目录,即它的配置存在于~/mysql_installs/percona-8.0.18-bin-dbg/instance_list.txt 文件中,才可以这样启动。 ~/mysql_installs/percona-8.0.18-bin-dbg/dba_tools$ ./startmysql.sh 4002
存储节点和元数据节点使用完全相同的程序,即kunlun-storage。kunlun-storage程序目录下的dba_tools 目录有一些DBA常用的脚本,包括这里用到的startmysql.sh和imysql.sh等。
cluster_mgr
最后,启动cluster_mgr进程,它负责维护昆仑数据库集群的运行状态,把目前独立运行的存储集群和元数据集群组成binlog复制集群。需要预先使用附带的配置模版文件写好配置文件 ./cluster_mgr_cfg.json ,然后执行这个命令: ~/cluster_mgr/bin/cluster_mgr_safe ./cluster_mgr_cfg.json &
集群的运行时任务(Task)状态
每个计算节点含有1个连接监听进程(postgres)和10个系统后台进程(daemon)以及若干个backend进程,每个backend进程专门服务一个客户端连接,示例入下面的列表。这些进程的功能如下:
postgres进程与PostgreSQL中完全相同,它负责监听客户端连接请求,并且在收到请求后建立TCP连接并且创建backend进程服务它。并且还负责在检测到其他后台进程退出后,把它拉起。它是一个计算节点实例的所有其他进程的父进程。kill掉这个进程即可关闭这个计算节点实例。
在10个后台进程中,有7个是PostgreSQL原本就自带的进程,其功能与之前完全相同。特别是checkpointer,background writer,walwriter, autovacuum launcher和logical replication launcher 这些进程在昆仑数据库集群中几乎完全处于空闲状态,因为用户数据并不存储在计算节点中而是存储在存储集群中。
昆仑数据库计算节点特有的后台进程
昆仑数据库中新增的后台进程包括一个GTSS,一个cluster_log_applier main worker以及每一个其他(非postgres)database一个的重放进程(cluster_log_applier applier for db)和一个global_deadlock_detector进程。
GTSS
负责处理分布式事务两阶段提交期间GTM在每个backend中发起的的commit log写入请求,批量写入commit log,成功后再通知每个等待的backend进程继续其第二阶段提交。GTSS会定期轮询处理请求并会被backend请求者唤醒。
global_deadlock_detector:负责全局死锁检测和解除,它会定期执行全局死锁检测和处理,并会被等待存储节点返回的 backend 唤醒开始新一轮 全局死锁检测和处理工作。
cluster_log_applier main worker
在本计算节点重放(replay)本集群其他计算节点在默认的postgres数据库中执行的 DDL 语句;执行create database/drop database创建和删除其它database并且启动/停止对应数据库的cluster_log_applier applier for db进程。同时还负责处理 postgres数据库中的序列的“下一组序列值” 预约请求,从该序列所在的存储集群预约其下一组序列值。
cluster_log_applier applier for db
每个database DBX 一个该进程,负责在本计算节点重放(replay)本集群其他计算节点在 DBX 数据库中执行的 DDL 语句;同时还负责处理 DBX数据库中的序列的“下一组序列值” 预约请求,从该序列所在的存储集群预约其下一组序列值。
dzw@dzw:~/blogs$ ps -ef|grep postgres
dzw 37684 1486 0 Sep22 pts/20 00:00:00 /home/dzw/mysql_installs/postgresql-11.5-dbg/bin/postgres -D /data/pg_data_dir-4003
dzw 37685 37684 0 Sep22 ? 00:00:17 postgres: kunlun: logger
dzw 37687 37684 0 Sep22 ? 00:00:00 postgres: kunlun: checkpointer
dzw 37688 37684 0 Sep22 ? 00:00:04 postgres: kunlun: background writer
dzw 37689 37684 0 Sep22 ? 00:00:36 postgres: kunlun: walwriter
dzw 37690 37684 0 Sep22 ? 00:00:00 postgres: kunlun: autovacuum launcher
dzw 37695 37684 0 Sep22 ? 00:00:00 postgres: kunlun: logical replication launcher
dzw 37691 37684 0 Sep22 ? 00:00:00 postgres: kunlun: stats collector
dzw 37692 37684 0 Sep22 ? 00:09:11 postgres: kunlun: global transaction state synchronizer(GTSS)
dzw 37693 37684 0 Sep22 ? 00:00:53 postgres: kunlun: cluster_log_applier main worker
dzw 37694 37684 0 Sep22 ? 00:00:20 postgres: kunlun: global_deadlock_detector worker
dzw 37696 37684 0 Sep22 ? 00:00:14 postgres: kunlun: cluster_log_applier applier for db regression
dzw 85620 37684 0 09:49 ? 00:00:00 postgres: kunlun: dzw postgres 127.0.0.1(39792) idle
backend进程以及连接状态
每个连接一个专属的backend进程,处理这个连接中客户端发送的请求,也就是执行客户端发送的SQL语句然后向其返回结果。上面列表中pid为 85620 的进程就是一个backend进程,可以看到它的客户端用户名dzw,连接的database是postgres,客户端ip地址和端口 是127.0.0.1(39792), 当时没有执行任何SQL语句,处于空闲状态,否则会显示其正在执行的SQL语句。
计算节点每个backend进程当它需要读写某个存储集群的表或者表分片时,就需要获得(或者发起)这个存储集群的MySQL连接。所以在存储集群中可以看到一个昆仑数据库集群的所有计算节点backend进程发起的所有连接。我们分别用mysql客户端程序连接存储集群的主节点,用show processlist命令看一下其中的连接和工作线程状态,如下面两个列表所示。其中的pthread_id,thread_tid,global_conn_id,comp_node_id 四列是昆仑数据库特有的列,社区版mysql中没有这些列。
它们的意义是:
- pthread_id:正在(或者上次)执行来自这个连接的SQL语句的工作线程的pthread句柄,DBA基本不需要使用;
- thread_tid:正在(或者上次)执行来自这个连接的SQL语句的工作线程的现场ID,DBA基本不需要使用;
- global_conn_id:计算节点中处理这个连接的backend进程的pid;在下面在两个存储集群中执行的show processlist 结果列表中都可以看到pid为 85620、37693和37694的3个进程发起的连接。backend进程与存储集群节点之间的每个连接可以访问其database中所有schema中的表和表分区在存储节点中的对应表分片,因此这样的mysql连接并不限定使用某个mysql database,所以这几行的db列都是NULL。而thread_tid 为37207和37710 的这两个连接是由cluster_mgr发起的因此它们的 global_conn_id和comp_node_id都是0.
- comp_node_id :发起这个连接的计算节点的ID。可以看到global_conn_id为 85620、37693和37694这3个连接都是ID为1的计算节点发起的。
通过comp_node_id、global_conn_id 和thread_tid 等字段就可以找到负责处理每个集群的客户端连接的计算节点及其backend进程以及存储节点线程。
mysql> show processlist;
+----+-----------------+-----------------+--------------------+---------+--------+------------------------+------------------+-----------+----------- ----+-----------------+------------+----------------+--------------+
| Id | User | Host | db | Command | Time | State | Info | Rows_sent | Rows_examined | pthread_id | thread_tid | global_conn_id | comp_node_id |
+----+-----------------+-----------------+--------------------+---------+--------+------------------------+------------------+-----------+---------------+-----------------+------------+----------------+--------------+
| 4 | event_scheduler | localhost | NULL | Daemon | 174108 | Waiting on empty queue | NULL | 0 | 0 | 140498270414592 | 34885 | 0 | 0 |
| 7 | system user | | NULL | Connect | 174108 | login | NULL | 0 | 0 | 140495938381568 | 34888 | 0 | 0 |
| 8 | system user | | NULL | Connect | 174108 | login | NULL | 0 | 0 | 140495921596160 | 34890 | 0 | 0 |
| 9 | system user | | NULL | Connect | 174108 | login | NULL | 0 | 0 | 140495929988864 | 34889 | 0 | 0 |
| 10 | system user | | NULL | Connect | 174108 | login | NULL | 0 | 0 | 140495913203456 | 34891 | 0 | 0 |
| 12 | pgx | 127.0.0.1:33788 | NULL | Sleep | 2 | | NULL | 0 | 0 | 140498269804288 | 37207 | 0 | 0 |
| 15 | pgx | 127.0.0.1:34220 | NULL | Sleep | 2 | | NULL | 0 | 0 | 140498269189888 | 37710 | 37693 | 1 |
| 16 | pgx | 127.0.0.1:56390 | NULL | Sleep | 2 | | NULL | 0 | 0 | 140498268985088 | 61800 | 37694 | 1 |
| 17 | root | localhost | postgres_$$_public | Query | 0 | starting | show processlist | 0 | 0 | 140498268780288 | 86063 | 0 | 0 |
| 18 | pgx | 127.0.0.1:57766 | NULL | Sleep | 6 | | NULL | 0 | 0 | 140498268575488 | 86635 | 85620 | 1 |
+----+-----------------+-----------------+--------------------+---------+--------+------------------------+------------------+-----------+----------- ----+-----------------+------------+----------------+--------------+
9 rows in set (0.00 sec)
mysql> show processlist;
+----+-----------------+-----------------+--------------------+---------+--------+------------------------+------------------+-----------+----------- ----+-----------------+------------+----------------+--------------+
| Id | User | Host | db | Command | Time | State | Info | Rows_sent | Rows_examined | pthread_id | thread_tid | global_conn_id | comp_node_id |
+----+-----------------+-----------------+--------------------+---------+--------+------------------------+------------------+-----------+----------- ----+-----------------+------------+----------------+--------------+
| 4 | event_scheduler | localhost | NULL | Daemon | 174159 | Waiting on empty queue | NULL | 0 | 0 | 139989471577856 | 34929 | 0 | 0 |
| 7 | system user | | NULL | Connect | 174159 | login | NULL | 0 | 0 | 139987131553536 | 34933 | 0 | 0 |
| 8 | system user | | NULL | Connect | 174159 | login | NULL | 0 | 0 | 139987114768128 | 34935 | 0 | 0 |
| 9 | system user | | NULL | Connect | 174159 | login | NULL | 0 | 0 | 139987123160832 | 34934 | 0 | 0 |
| 10 | system user | | NULL | Connect | 174159 | login | NULL | 0 | 0 | 139987139946240 | 34932 | 0 | 0 |
| 15 | pgx | 127.0.0.1:52576 | NULL | Sleep | 2 | | NULL | 0 | 0 | 139989470353152 | 61658 | 37693 | 1 |
| 16 | pgx | 127.0.0.1:52602 | NULL | Sleep | 0 | | NULL | 0 | 0 | 139989470148352 | 61795 | 0 | 0 |
| 17 | pgx | 127.0.0.1:52610 | NULL | Sleep | 0 | | NULL | 0 | 0 | 139989469943552 | 61799 | 37694 | 1 |
| 18 | root | localhost | postgres_$$_public | Query | 0 | starting | show processlist | 0 | 0 | 139989469738752 | 86346 | 0 | 0 |
| 19 | pgx | 127.0.0.1:53998 | NULL | Sleep | 33 | | NULL | 0 | 0 | 139989469533952 | 86636 | 85620 | 1 |
+----+-----------------+-----------------+--------------------+---------+--------+------------------------+------------------+-----------+---------------+-----------------+------------+----------------+--------------+
9 rows in set (0.00 sec)
使用集群
启动集群后,就可以正式使用集群了。可以用psql或者任何程序连接到计算节点然后 启动事务,执行查询若干语句,提交事务,以此类推即可。DBA用户需要参考这个文档了解一下集群的数据分片方面的方法和规则,应用程序猿则完全不需要了解这些内容,他们只要像使用单机数据库那样使用昆仑数据库做数据读写和事务提交即可。