Kubernetes与容器设计模式

目录贴:Kubernetes学习系列

  在程序设计领域,面向对象设计和面向对象语言是你们最为熟悉和强大的工具,而面向对象除了其强大的核心特性以外,还有人们经过实践总结出来的一系列设计模式,能够用来解决实际应用设计中的一些复杂问题。html

  云原生应用运行的环境都是复杂的分布式环境,在这种状况下,一些有用的设计模式能够起到四两拨千斤的做用,而K8s社区推出的容器设计模式,则是结合了K8s集群的微服务模型提出的一系列可重用的解决典型分布式系统问题的模式。目前K8s社区推出的容器设计模式主要分为三大类:nginx

    1)        单容器管理模式;数据库

    2)        单节点多容器模式;编程

    3)        多节点多容器模式;后端

1、单容器管理模式

  K8s的最大特点是支持多容器的微服务实例。固然,单容器的模式也是支持的,只不过这种模式并不能突出K8s的特点和强大。不少人对K8s一直以来的印象是:功能强大,但入门较难。其实,单单就启动一个单容器微服务实例,K8s的命令行操做跟Docker原生命令同样简单。设计模式

[root@demo-k8s ~]# kubectl run nginx --image=nginx
deployment "nginx" created
[root@demo-k8s ~]# kubectl get deployment
NAME      DESIRED   CURRENT   UP-TO-DATE   AVAILABLE   AGE
nginx     1         1         1            1           24s
[root@demo-k8s ~]# kubectl get rs
NAME               DESIRED   CURRENT   AGE
nginx-3137573019   1         1         1m

  由上面的例子能够看到,K8s只要一个命令既能够启动以nginx为镜像的一个微服务实例。与此同时,K8s的强大之处在于,方便用户用一个命令的同时,仍然保证了K8s应用体系的完整性和规范性。也就是说,虽然用户只运行了一个命令,但K8s为用户自动建立了四种API对象,包括:Deployment,ReplicaSet(RS),Pod和Container。要想扩展伸缩同一服务的实例个数也很是简单。服务器

[root@demo-k8s ~]# kubectl scale deployment nginx --replicas=3
deployment "nginx" scaled
[root@demo-k8s ~]# kubectl get rs
NAME               DESIRED   CURRENT   AGE
nginx-3137573019   3         3         22m

  依靠这种兼顾易用性和模型一致性的设计理念,K8s使本身既适合简单场景也适合复杂场景。网络

2、单节点多容器模式

  从单节点多容器模式开始的容器设计模式,是真正体现K8s设计特色的地方,也就是基于多容器微服务模型的分布式应用模型。在K8s体系中,Pod是一个轻量级的节点,同一个Pod中的容器能够共享同一块存储空间和同一个网络地址空间,这使得咱们能够实现一些组合多个容器在同一节点工做的模式。既然Pod的特色是共享存储空间和网络地址,那么单节点多容器模式必定是利用这两种特性的。app

2.1 挎斗模式(Sidecar pattern)

  第一种单节点多容器模式是挎斗模式。这种模式主要是利用在同一Pod中的容器能够共享存储空间的能力。编程语言

  一个典型的挎斗应用场景如图所示:一个工具容器写文件到共享的文件目录,应用主容器从共享的文件目录读文件。例如,咱们能够用Nginx构建一个代码发布仓库,简单的将代码放到某个本地目录便可。为了保持同步,咱们同时用一个装有Git客户端的容器定时到原始代码仓库同步下拉最新的代码。这种模式的好处是,工具容器的镜像,也就是打包有Git客户端的镜像能够重用,而不须要跟应用的容器打包在一块儿。一样的应用,应用主容器不用Nginx也能够用Apache Httpd,均可以跟工具容器组合起来造成微服务。

  另外一个典型的挎斗模式如图所示:一个工具容器读文件,应用容器写文件。例如:一个基于Nginx的Web应用向系统文件系统写入日志,而一个收集日志的容器从共享目录读出日志,并输出到集群的日志系统。这一模式的好处在于,工具容器的镜像是能够重用的,不须要在每次更新应用容器打包的时候,把工具容器的执行文件打包进去。

2.2 外交官模式(Ambassador pattern)

  第二种单节点多容器模式是外交官模式。这种模式主要利用同一Pod中的容器能够共享网络地址空间的特性。如图所示,在一个Pod中给应用容器搭配一个工具容器做为代理服务器。工具容器帮助应用容器访问外部服务,使得应用容器访问服务时不须要使用外网的IP地址,而只须要用localhost访问本地服务。在这种模式下,做为代理服务器的工具容器好像外部服务派驻在Pod中的“外交官”,使得应用容器办理业务时只须要跟本Pod的外交官打交道,而不须要出国了,所以而得名。

2.2.1基于外交官模式的Redis访问案例

2.3 适配器模式(Adapter pattern)

  第三种单节点多容器模式是适配器模式。这种模式对于监控和管理分布式系统尤其重要。对分布式系统的一种理想设计目标,就是可以实现“分布地执行和存储,统一的监控和管理”。要想实现“统一的监控和管理”,应用和监控管理交互的接口须要是统一的,并且其接口是依照“统一的监控服务”的接口模式来实现。这和面向对象设计模式中的“适配器模式”也很是类似。

  一个典型的能够采用适配器模式的系统,是利用Prometheus做为监控服务的分布式系统。在Prometheus周边项目中,有诸多适用于不一样应用系统的监控数据输出器(Exporter),负责收集跟特定应用相关的监控数据,使得Prometheus服务能够以统一的数据模式收集不一样应用系统的监控数据,每一个Exporter同时也都是一个适配器模式的实现。

3、多节点组合模式

3.1 多节点选举模式

  多节点选举在分布式系统中是一种重要的模式,特别是对有状态服务来讲。在分布式系统中,通常来讲,无状态服务,能够随意的水平伸缩,只要把运行业务逻辑的实例复制出去运行就能够,这也就是K8s里ReplicationController和ReplicaSet所作的事情。

  对于有状态服务,人们也但愿可以水平的扩展,但由于每一个实例有本身的持久化状态,而这个持久化状态必需要延续它的生命,所以,有状态服务的水平伸缩模式就是状态的分片,其中机制跟数据库的分片是一致的。那么对于一个原生为分布式系统设计的有状态服务,每一个实例与分片数据的对应关系,就成为这个有状态服务的全局信息。对于任何服务,多个实例的全局信息都须要一个保存的地方。

  一个简单的办法是保存在外部的一个代理服务器上,这也就是MariaDB的Galera解决方案的作法,也是因此代理服务器为后端服务器所作的事情。但这种方式的问题在于,系统要依赖外部代理服务器,而代理服务器自己的高可用和水平伸缩仍是没有解决的问题。

  因此对于要原生本身解决高可用和水平伸缩问题的系统,例如Etcd和ElasticSearch,必定要有原生的主控节点选举机制。这样这个分布式系统就不须要依赖外部的系统来维护本身的状态了。对于一个分布式系统,最主要的系统全局信息,就是集群中有哪些节点,Master节点是哪一个,每一个节点对应哪一个分片。主控节点的任务,就是保存和分发这些信息。

   在K8s集群中,一个微服务实例Pod能够有多个容器。这一特性很好地提升了多节点选举机制的可重用性。它使得咱们能够专门开发一个用于选举的容器镜像,在实际部署中,将选举容器和普通应用容器组合起来,应用容器只须要从本地的选举容器读取状态,就能够获得选举结果。这样,使得应用容器能够只关注自身业务逻辑相关的代码。

3.2工做队列模式

  分布式系统的一个重要做用是可以充分利用多个物理计算资源的能力,特别是在动态按需调动计算资源完成计算任务。设想若是有大量的须要处理的任务随机的到来,对计算资源须要的容量是不肯定地;显然,按照最大可能计算量和最小可能计算量设置计算节点都是不合理的。

  这种状况下,能够把须要处理的任务放到一个待处理的队列里,根据须要启动计算节点从队列读取任务进行处理。在容器技术普遍应用以前,也有诸多的分布式处理系统依靠队列来处理大量计算任务,例如大数据处理系统Hadoop和Spark等。这些系统的一个限制是实现队列处理模式大多要遵循特定的编程模式和特定的编程语言,同时搭建基础设施也大多复杂而耗时。而基于容器和Kubernetes编排技术的工做队列模式的好处在于,利用很是简单的编排脚本就能够实现工做队列模式,而用Pod做为轻量级处理节点的模式,使得动态的调度计算资源变得很是容易。在Kubernetes中应用工做队列模式的逻辑示意图以下:

3.3 分散收集模式

  分散收集模式利用分布式系统弹性计算能力的容器设计模式。在这一模式中,计算服务的使用者,即服务的客户端,将初始计算请求发送给一个“根计算节点”。根计算节点对计算任务作出分割,将任务分割成大量的小计算任务,而后将小计算任务分配给大量计算服务器进行分布式平行计算 。每一个计算服务器都计算初始计算任务的一小块,将计算结果返回给根计算节点。根计算节点将全部计算结果合并起来,组成一个针对初始计算任务的一个统一的结果,返回给申请计算任务的客户端。

  这一系统中的分布式服务器很是适合用容器技术来实现,具体到K8s系统中,就是一个K8s的Pod;具体到Docker系统中,就是一个Docker容器。利用容器快速部署启动和运行时开销特别小的特色,任务能够被分到不少小服务器上并行处理,这些容器造成的小服务器跟其余任务共同使用基础设施计算节点的能力。

  一个典型的分散收集模式的分布式系统以下图所示。根节点接受到来自客户端的服务请求,将服务请求分配给不一样的业务模块分散处理,处理结果收集到根节点,通过必定的汇聚合并运算,产生一个合并的结果交付给客户端。

 

  声明:本文并不是原创,只是本人在学习容器设计模式过程当中,对一些网络资料的整理。主要参考于:《Kubernetes与云原生应用》系列之容器设计模式

相关文章
相关标签/搜索