极牛技术分享活动html
极牛技术实践分享系列活动是极牛联合顶级VC、技术专家,为企业、技术人提供的一种系统的线上技术分享活动。mysql
每期不一样的技术主题,和行业专家深度探讨,专一解决技术实践难点,推进技术创新。隔周三20点经过极牛线上技术分享群准时开课。欢迎各个机构、企业的行业专家、技术人报名参加。nginx
本期主题
Kubernetes 有状态集群服务部署与管理sql
嘉宾介绍docker
张寿红,从事软件研发工做十余年,目前从事基于Docker和Kubernetes的企业级容器云平台研发工做,主要包括容器服务、存储服务、CI/CD和镜像服务等。在加入时速云以前,前后在CA Technologies和Symantec担任Tech Lead和Principal Software Engineer。参与研发的软件产品有:企业数据保护软件、云平台上的服务管理系统、企业客户服务平台等。数据库
摘要:
在容器化时代,除了无状态的容器服务,好比Web服务器,用户也愈来愈多地使用容器部署有状态的应用,好比MySQL、Redis、Cassandra等。这些Pets(运行有状态服务的容器,须要特殊处理)就带来了新的需求,包括更长的生命周期,配置依赖,有状态的故障转移等。bootstrap
张寿红讲师深刻介绍Kubernetes如何知足有状态集群服务对容器编排系统提出的新需求,包括如何使用Kubernetes的动态存储请求与分配机制来实现服务状态的持久化存储,以及与高效部署和运行有状态集群服务相关的Kubernetes新特性,如Init Container、PetSet (StatefulSet)等。最后经过一个MySQL集群实例详解在Kubernetes中如何轻松部署一个高可用的有状态集群服务并实现自动化管理。缓存
大纲:
· Kubernetes简介和运行有状态集群服务的挑战
· Kubernetes存储系统
· Kubernetes有状态集群服务相关特性
· 实战:在Kubernetes上部署和管理MySQL集群服务器
你们晚上好,我是来自时速云的张寿红,很高兴有机会和你们作此次有关容器云的技术分享。网络
在容器化时代,除了无状态的容器服务,好比Web服务器,用户也愈来愈多地使用容器部署有状态的应用,这就对容器编排系统提出了新的需求。
我今天要和你们分享的主题就是如何在目前主流的容器云平台Kubernetes 上部署和管理有状态集群服务。此次分享的关键词有两个:一个是Kubernetes, 另外一个是有状态集群服务。
咱们会在第一部分了解一下什么是 Kubernetes,以及运行有状态集群服务面临的一些挑战。接下来的两部分咱们会重点介绍 Kubernetes 是如何应对这些挑战,以及经过哪些特性来解决有状态集群服务所特有的一些问题。最后一部分是实战,经过一个MySQL集群的例子来展现如何在Kubernetes上轻松地部署和管理一个有状态集群服务。
什么是Kubernetes?
简单一句话来讲,Kubernetes是一个运行和管理容器的平台。它在Docker、rkt等容器运行时之上,实现了容器的集群化和高可用。
Kubernetes简称K8S,来自Google,支持多种云计算环境,而且100% 开源,是云原生计算基金会的一部分,用Go语言开发的。
Kubernetes的一些基本概念:
其中最核心的一个概念是Pod,它是Kubernetes对容器进行的封装,是Kubernetes管理的最小单位。Pod经过Deployment来部署,Deployment会建立一个Replica Set 来保证Pod的个数始终是一个指定的值 。Pod通常不直接对外提供服务,而是经过Service对外提供一个稳定的访问接口,一个Service后面能够挂多个Pod实例 。
Service是如何找到它匹配的Pod呢?靠的是Label。Label是联系各个K8S资源的纽带。Replica Set 和它管理的Pod之间也是经过 Label 来关联的。若是Pod里的容器运行的是有状态服务,如数据库与缓存等,还须要挂载存储卷,用于存储服务状态。
讲完原理,咱们来看一个实例:
这是一个在K8S集群里运行的容器化应用案例,这个应用有本身的Web 客户端,同时还从Twitter采集数据,处理完后存储到本身的DB。
能够看到容器里跑的服务有两类,无状态和有状态。像Web服务器,流处理器等无状态服务出现问题后,直接杀掉,新建一个,管理起来很是简单。
可是对有状态服务,像数据库,它要求有更长的生命周期。在一个集群的状况下,集群成员之间如何能保持稳定的成员关系?这都对容器编排系统提出了新的挑战。
K8S是如何应对这些挑战的呢?
K8S运行的服务,从简单到复杂能够分红三类:无状态服务、普通有状态服务和有状态集群服务。下面分别来看K8S是如何运行这三类服务的。
无状态服务,K8S使用RC(或更新的ReplicaSet)来保证一个服务的实例数量。经过Service来对外提供一个稳定的访问接口。
普通有状态服务,它多了状态保存的需求。Kubernetes提供了以Volume和Persistent Volume为基础的存储系统,能够实现服务的状态保存。
状态集群服务,它又多了集群管理的需求。K8S为此开发了一套以Pet Set为核心的全新特性,方便了有状态集群服务在K8S上的部署和管理。
下面咱们来看Kubernetes如何知足“状态保存”的需求。
K8S的存储系统大体分为三个层次:普通Volume,Persistent Volume 和动态存储供应。
普通Volume
普通Volume,最简单的一种是“单节点存储卷”。它和Docker的存储卷相似,使用的是Pod所在K8S节点的本地目录。
具体有两种,一种是 emptyDir,是一个匿名的空目录,由Kubernetes在建立Pod时建立,删除Pod时删除。
另一种是 hostPath,与emptyDir的区别是,它在Pod以外独立存在,由用户指定路径名。
这类和节点绑定的存储卷在Pod迁移到其它节点后数据就会丢失,因此只能用于存储临时数据或用于在同一个Pod里的容器之间共享数据。
普通Volume,第二种类型是“跨节点存储卷”。这种存储卷不和某个具体的K8S节点绑定,而是独立于K8S节点存在的 。
跨节点存储卷因为能够在任何一个Kubernetes 节点上都可以被访问到,比较灵活,因此应用比较普遍。Kubernetes上的Volume是经过插件方式来实现的,因此可扩展性很强。
目前来讲几乎全部主流的存储在Kubernetes上都有相应的插件来支持。若是已有的存储不能知足要求,还能够开发本身的volume插件。
persistent volume,它和普通volume的区别是什么呢?
普通Volume和使用它的Pod之间是一种静态绑定关系,咱们没法单首创建一个普通volume,由于它不是一个独立的K8S资源对象。
而Persistent Volume 简称PV是一个K8S资源对象,因此咱们能够单首创建。它不和Pod直接发生关系,而是经过Persistent Volume Claim,简称PVC来实现动态绑定。
动态绑定过程是怎样的?
这是PV的生命周期,首先是Provision,即建立PV,这里建立PV有两种方式,静态和动态。
静态方式是管理员手动建立一堆PV,组成一个PV池,供PVC来绑定。动态方式是经过一个叫 storage class的对象由存储系统根据PVC的要求自动建立。
一个PV建立完后状态会变成Available,等待被PVC绑定。一旦被PVC邦定,PV的状态会变成Bound,就能够被相应的Pod使用。Pod使用完后会释放PV,PV的状态变成Released。
变成Released的PV会根据定义的回收策略作相应的回收工做。有三种回收策略,Retain、Delete 和Recycle。
Retain就是保留现场,K8S什么也不作。Delete 策略,K8S会自动删除该PV及里面的数据。Recycle方式,K8S会将PV里的数据删除,而后把PV的状态变成Available,又能够被新的PVC绑定使用。
动态方式是经过StorageClass来完成的,这是一种新的存储供应方式。
使用StorageClass有什么好处呢?除了由存储系统动态建立,节省了管理员的时间,还有一个好处是能够封装不一样类型的存储供PVC选用。
好比这里就有两个StorageClass,它们都是用谷歌的存储系统,可是一个使用的是普通磁盘,名字为slow。另外一个使用的是SSD,名字为fast。
在PVC里经过annotation指定了storageclass的名字为fast,这样这个PVC就会绑定一个SSD,而不会绑定一个普通的磁盘。
好,到这里Kubernetes的整个存储系统就都介绍完了。
下面进入Kubernetes与有状态集群服务相关的两个新特性:Init Container 和Pet Set。
什么是Init Container?
从名字来看就是作初始化工做的容器。能够有一个或多个,这些 Init Container 按照定义的顺序依次执行,只有全部的InitContainer 执行完后,主容器才启动。因为一个Pod里的存储卷是共享的,因此 Init Container 里产生的数据能够被主容器使用到。
Init Container的一个使用样例
这个例子建立一个Pod,这个Pod里跑的是一个nginx容器,Pod里有一个叫workdir的存储卷,访问nginx容器服务的时候,就会显示这个存储卷里的index.html 文件。而这个index.html 文件就是经过一个 busybox的初始化容器得到的。
介绍完Init Container,千呼万唤始出来,该今天的主角Pet Set出场了。
什么是Pet Set?
顾名思义是Pet的集合,那什么是Pet呢?它是一种须要特殊照顾的Pod。它有状态、有身份、固然也比普通的Pod要复杂一些。具体来讲,一个Pet有三个特征:
一是有稳定的存储,这是经过咱们前面介绍的PV/PVC 来实现的。
二是稳定的网络身份,这是经过一种叫 Headless Service 的特殊Service来实现的。 和普通Service相比,Headless Service没有Cluster IP,用于为一个集群内部的每一个成员提供一个惟一的DNS名字,用于集群内部成员之间通讯 。
三是序号命名规则, 好比 Pet Set 的名字叫 mysql,那么第一个启起来的Pet就叫mysql-0,第二个叫mysql-1,如此下去。当一个Pet down 掉后,新建立的Pet 会被赋予跟原来Pet同样的名字,经过这个名字就能匹配到原来的存储,实现状态保存。
好,与有状态服集群服务相关的K8S特性就介绍到这里。理论讲完了,下面进入实战,以Galera MySQL集群为例子,介绍如何在 Kubernetes如何上部署和管理一个有状态集群服务。
首先大体了解一下Galera MySQL:
![图片上传中...]
它不是那种主从式的集群,而是多Master集群,经过 Galera Replication 把多个MySQL实例关联起来组成一个集群。由Galera Replication 负责节点间的数据同步。
用户访问时能够链接到任何一个节点进行读写操做。每次写入的数据会被Galera Replication同步到整个集群,才算写入成功。节点之间没有数据延迟,在某个节点失效后,直接退出集群便可,无需失效转移。
如何在Kubernetes上部署和运行它?这是总体结构图:
左边的Headless Service用于为每一个MySQL Pet实例提供一个DNS名字,右边的PV池为MySQL提供存储。
这里有两个初始化容器,第一个用于安装须要的文件,第二个作MySQL的初始化工做 。
一个Pet Set里有多个Pet,每一个Pet对应MySQL集群里的一个节点。经过Pet Set能够管理整个MySQL集群。
部署MySQL集群具体的YAML文件
右边是一个Headless Service,名字是galera,左边是Pet Set,它用到了右边的Headless service。Replicas的数目为3,会建立3个Pet。
Pet Set 的annotation里定义了两个初始化容器:
Install容器安装的文件能够被bootstrap容器使用到;同时bootstrap容器生成的MySQL配置文件会放到config存储卷里,供后面的MySQL 容器使用。
主容器 Galera MySQL 的定义
除了常规的3306端口外,它还暴露了其它一些端口,用于集群内部的数据同步和状态转移等操做。这里MySQL启动参数里用到的文件,是在初始化容器里生成的,经过共享存储卷传递过来。
数据存储卷的定义
这里定义了三个存储卷,其中config、workdir就是简单的本地目录,而 datadir是一个PVC,它能够去绑定PV来存储MySQL数据库的数据 。
因此部署一个集群总共就须要两个YAML文件就能够了,一个Headless Service,一个 Pet Set。其中Pet Set里定义了初始化容器和存储卷。
用上面的方式部署完MySQL集群后,后面的运维工做是比较简单的。
假如某个集群节点因为某种缘由Crash掉了,Kubernetes 会自动建立一个新的Pet来替代,实现自动恢复。若是要扩容或缩容,也是一条命令、指定一下这个Pet Set 的Replicas的数目就好了。
若是要升级,只须要修改Pet Set 定义里 podTemplate 的image值,而后把老的Pet删除,新建立的Pet,就是最新版本的了。
对于在Kubernetes上部署有状态集群服务,咱们补充两点:
第一点是在最新发布的Kubernetes 1.5 里 PetSet 从新命名为StatefulSet。因此根据你使用的K8S版本不一样,可能看到的名字也不同。
第二点是简单介绍一下时速云提供的有状态集群服务:数据库与缓存。
务的建立工做,用户再也不须要了解咱们前面介绍的全部技术术语,只须要指定一下副本数目,存储的大小就能够了。
最后如下面这张图作为今天分享内容的总结:
有状态集群服务的两个需求:一个是存储需求,另外一个是集群需求。
对存储需求,Kubernetes的解决方案是:Volume、Persistent Volume 。对PV,除了手动建立PV池外,还能够经过Storage Class来让存储系统自动建立。
对集群需求,Kubernetes的解决方案是Pet Set。Pet Set 又经过Init Container来作集群初始化,经过Headless Service来为集群成员提供稳定 的网络身份。
最后咱们以MySQL集群为例,说明了如何在Kubernetes上部署和运行一个有状态集群服务。
目前有状态集群服务在Kubernetes上的部署还不是正式版,但彻底可用。若是您的项目中有容器化的需求,能够尝试。
Q&A
Q1:容器内的数据该保存在镜像里仍是宿主机中?
A1:一般数据是保存在独立的存储设备中,容器经过Volume挂载使用。简单的存储也能够用宿主机的目录。
Q2:k8s Resource 监控怎么作?
A2:有专门的容器监控工具,如Prometheus
Q3:Kubernetes和Mesos有啥区别,如何选择?
A3:Kubernetes为容器集群而生,Mesos除了容器集群,传统集群也能用。若是是纯容器云环境,推荐使用K8S。
Q4:在什么样的业务量下适合用Kubernetes?
A4: K8S 来自Google,经历了Google内部海量生产环境的检验,普通公司的业务量不是问题。
Q5:实际生产环境中对比k8s 和swarm 各有什么优劣,如何正确选型?
A5:swarm 是docker原生的容器管理系统,但相对K8S而言还比较新,不是很成熟。生产环境目前仍是推荐用K8S。
报名请关注极牛(ji-niu)公号回复技术分享