利用Kubernetes搭建mysql主从复制集群

之前相关的文章请参考:
Docker集群管理方案Kubernetes之部署
Docker集群管理方案Kubernetes之组件

通过本文的实践,我们可以了解一下k8s能带给我们什么。另外,实际生产环境中mysql的主从复制考虑的事情会更多。

mysql主从复制

mysql的主从复制可以通过如下方式实现。

  1. master
    在master主机上修改配置文件,比如通常是修改my.cnf。
    [mysqld] server-id=1 log-bin
    在mysql上创建同步账号并授权。
    如下,创建用户名为repl,密码为1234567:
    create user 'repl'@'%' identified by '1234567';
    如下,给repl用户授权允许同步:
    grant replication slave on *.* to 'repl'@'%' identified by '1234567';

  2. slave
    同样,在slave主机上修改配置文件。
    [mysqld] server-id=2 log-bin
    接着配置如下,其中x.x.x.x为master主机ip地址。
    change master to master_host='x.x.x.x',master_user='repl',master_password='1234567';

注意server-id为主机标识,不能重复。

利用Docker实现主从复制

本节介绍利用Docker官网镜像文件实现上述的各项配置,这是为了接下来k8s的使用。利用Docker实现mysql的方式有很多种,可以参考其他文章。

mysql官网Docker镜像文件地址:https://hub.docker.com/_/mysql/
这里用的是8.0 Dockerfile,包括两个文件Dockerfile, docker-entrypoint.sh。

  1. 准备master的镜像
    将Dockerfile, docker-entrypoint.sh复制一份作为master的镜像。
    在Dockerfile中添加如下:
    RUN sed -i '/\[mysqld\]/a server-id=1\nlog-bin' /etc/mysql/mysql.conf.d/mysqld.cnf
    在docker-entrypoint.sh中添加如下:
    echo "CREATE USER '$MYSQL_REPLICATION_USER'@'%' IDENTIFIED BY '$MYSQL_REPLICATION_PASSWORD' ;" | "${mysql[@]}" echo "GRANT REPLICATION SLAVE ON *.* TO '$MYSQL_REPLICATION_USER'@'%' IDENTIFIED BY '$MYSQL_REPLICATION_PASSWORD' ;" | "${mysql[@]}" echo 'FLUSH PRIVILEGES ;' | "${mysql[@]}"
    可以看到上面添加了两个环境变量MYSQL_REPLICATION_USER和MYSQL_REPLICATION_PASSWORD,用作主从复制的账号和密码。
    通过下面的截图可以看到上面添加内容所在的位置。

    Dockerfile.png

    docker-entrypoint.sh.png

  2. 准备slave的镜像
    将Dockerfile, docker-entrypoint.sh复制一份作为slave的镜像。
    在Dockerfile中添加如下:
    RUN RAND="$(date +%s | rev | cut -c 1-2)$(echo ${RANDOM})" && sed -i '/\[mysqld\]/a server-id='$RAND'\nlog-bin' /etc/mysql/mysql.conf.d/mysqld.cnf
    这里server-id用的是随机数。
    在docker-entrypoint.sh中添加如下:
    echo "STOP SLAVE;" | "${mysql[@]}" echo "CHANGE MASTER TO master_host='$MYSQL_MASTER_SERVICE_HOST', master_user='$MYSQL_REPLICATION_USER', master_password='$MYSQL_REPLICATION_PASSWORD' ;" | "${mysql[@]}" echo "START SLAVE;" | "${mysql[@]}"
    通过下面的截图可以看到上面添加内容所在的位置。

    Dockerfile.png

    docker-entrypoint.sh.png

    重要的来了,上面slave的配置中,master_host一项用的是$MYSQL_MASTER_SERVICE_HOST,这个环境变量(enviromnent variable)是由k8s生成的。
    k8s的service创建后,会自动分配一个cluster ip,这个cluster ip是动态的,我们没法直接使用或硬编码,k8s为了service对容器的可见,生成了一组环境变量,这些环境变量用于记录service name到cluster ip地址的映射关系,这样容器中就可以使用这些变量来使用service。(类似的,Docker中提供了links。)

举例:如果service的名称为foo,则生成的环境变量如下:
FOO_SERVICE_HOST
FOO_SERVICE_PORT
更多介绍请参考k8s官方资料:http://kubernetes.io/docs/user-guide/container-environment/

  1. 构建镜像并上传至docker hub
    分别构建用于mysql master和mysql slave的Docker镜像,并上传至docker hub,地址为https://hub.docker.com/ (这是因为当我们用k8s去做mysql集群部署的时候,k8s默认会去docker hub下载镜像。通常在生产环境中服务器是不运行连接internet的,因此通常会搭建自己的docker hub服务器。)。

构建master镜像

切换到master Dockerfile所在的目录,执行命令:
docker build -t paulliu/mysql-master:0.1 .

构建slave镜像

切换到slave Dockerfile所在的目录,执行命令:
docker build -t paulliu/mysql-slave:0.1 .

镜像推送

然后将构建好的镜像文件推送到docker hub,首先使用下面的命令登陆,如果没有注册,需要先到官网注册一下。
docker login
接着执行推送命令:
docke push paulliu/mysql-master:0.1
docke push paulliu/mysql-slave:0.1

如果感觉上面的一堆配置太麻烦,可以直接使用我构建好的镜像,地址为:
https://hub.docker.com/u/paulliu/

k8s部署

终于进入到正题,接下来开始利用k8s构建mysql集群。
首先声明,由于yaml格式的问题,没法直接贴源代码,只能贴截图,见谅。

  1. mysql master的部署
    replication controller和service的yaml文件如下,文件名分别为mysql-master-rc.yaml和mysql-master-service.yaml。
    replication controller:

    mysql-master-rc.yaml.png

    可以看到在env中添加了mysql需要的环境变量。
    service:
    mysql-master-service.yaml.png

    切换到yaml文件所在目录,执行命令以部署mysql master服务:
    kubectl create -f mysql-master-rc.yaml
    kubectl create -f mysql-master-service.yaml

  2. mysql slave的部署
    replication controller和service的yaml文件如下,文件名分别为mysql-slave-rc.yaml和mysql-slave-service.yaml。
    replication controller:

    mysql-slave-rc.yaml.png

    service:
    mysql-slave-service.yaml.png

    切换到yaml文件所在目录,执行命令以部署mysql slave服务:
    kubectl create -f mysql-slave-rc.yaml
    kubectl create -f mysql-slave-service.yaml

  3. 查看运行状态
    执行命令,查看k8s各资源的运行情况:
    kubectl get pods,service,rc
    我的环境的运行截图,各资源运行正常。

    k8s.png

  4. 测试mysql的主从复制
    到目前为止,mysql的一主一从均运行在k8s的pod中。由于上面service创建并没有使用type: NodePort方式,所以service只能在kubernetes的pods中引用,外界是无法使用的。

mysql master上的操作

通过如下命令连接到pods中的容器,其中mysql-master-pe18a为pod名称。
kubectl exec -it mysql-master-pe18a /bin/bash
接着连接本地mysql master服务器:
mysql -uroot -p
至此进入到mysql命令模式。
执行命令show master status;查看状态。
执行下面的命令创建数据库以及表,以测试数据同步:
create database paul_test_sync_db; use paul_test_sync_db; create table test_tb(id int(3),name char(10)); insert into test_tb values(001,'ok');

mysql slave上的操作

按照上面相同的方式进入到mysql slave的命令行,执行以下命令:
show slave status\G;
通过该命令可以查看主从同步的情况,通常利用该命令来检查主从配置是否有问题。

mysql-slave-running.png

执行以下命令,可以看到刚才在master上创建的库表已经同步过来了:
show databases; use paul_test_sync_db; select * from test_tb;

  1. 集群伸缩
    上面仅仅是一主一从,那接下来看看如何利用k8s对从服务器进行扩展。
    此处将原先的1台从服务器扩展为3台,执行命令:
    kubectl scale rc mysql-slave --replicas=3
    上面命令的意思是将名称为mysql-slave的rc控制的pod副本数量变更为3。
    执行kubectl get pods命令可以看到扩展后的结果。

总结

本文假设你已经对kubernetes有一定了解,因此并没有对一些命令、文件进行解释。
本文搭建的mysql一主多从集群环境,并没有考虑外部卷的挂载,因此当集群服务重启后,在mysql中创建的数据库、添加的数据会全部丢失。

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 158,560评论 4 361
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 67,104评论 1 291
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 108,297评论 0 243
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 43,869评论 0 204
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 52,275评论 3 287
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 40,563评论 1 216
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 31,833评论 2 312
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 30,543评论 0 197
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 34,245评论 1 241
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 30,512评论 2 244
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 32,011评论 1 258
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 28,359评论 2 253
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 33,006评论 3 235
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 26,062评论 0 8
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 26,825评论 0 194
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 35,590评论 2 273
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 35,501评论 2 268

推荐阅读更多精彩内容