Kubernetes架构的示例分析

发布时间:2021-08-21 17:40:31 作者:小新
来源:亿速云 阅读:127

这篇文章主要介绍Kubernetes架构的示例分析,文中介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们一定要看完!

首先,为什么要用Kubernetes? 使用一个工具先要梳理下使用这个工具的目标,我们不是为了工具而用工具。

Kubernetes的目标用一张被很多人引用过的图来说明最好: Kubernetes架构的示例分析
 

一句话,Kubernetes的目标是让你可以像管理牲畜一样管理你的服务,而不是像宠物一样,同时提高资源的利用率,让码农关注在应用开发本身,高可用的事情就交给Kubernetes吧。这个图本来是openstack提出的,但纯粹IaaS层的解决方案实现不了这个目标,于是有了Kubernetes。

Kubernetes和Borg系出同门,基本是Borg的开源改进版本,引用Google Borg论文里的说法:

it (1) hides the details of resource management and failure handling so its users can focus on application development instead; (2) operates with very high reliability and availability, and supports applica- tions that do the same; and (3) lets us run workloads across tens of thousands of machines effectively

我们如何验证是否达到这个目标了呢?

  1. 随机关掉一台机器,看你的服务能否正常

  2. 减少的应用实例能否自动迁移并恢复到其他节点

  3. 服务能否随着流量进行自动伸缩

我们从一个简单的多层应用的架构改进来探讨下: Kubernetes架构的示例分析

说明:

具体分析一下为了达到我们的目标,需要做到改进:

  1. Loadbalancer要调用后端应用服务节点,后端应用服务节点挂了或者迁移增加节点,都要变更Loadbalancer的配置。这样明显达不到目标,于是计划将Loadbalancer改造成Smart Loadbalancer,通过服务发现机制,应用实例启动或者销毁时自动注册到一个配置中心(etcd/zookeeper),Loadbalancer监听应用配置的变化自动修改自己的配置。

  2. Web应用对后端资源的依赖,比如Mysql和Memcached,对应资源的ip一般是写到配置文件的。资源节点变更或者增加都要变更应用配置。

  3. 应用节点迁移时依赖的系统和基础库不一样如何处理?部署方式不一样如何处理?磁盘路径,监听端口等冲突怎么办?这个可以通过Docker这样的容器技术,将应用部署运行的方式进行标准化,操作系统和基础库的依赖允许应用自定义,对磁盘路径以及端口的依赖通过Docker运行参数动态注入,而不需要变更应用配置。Docker的自定义变量以及参数,需要提供标准化的配置文件。

  4. 服务迁移问题 每种服务都需要一个master调度中心,来监控实例状态,确定要不要进行迁移,负责统一调度。并且每个服务器节点上要有个agent来执行具体的操作,监控该节点上的应用。另外还要提供接口以及工具去操作。

  5. 网络以及端口冲突的问题比较麻烦 需要引入类似SDN的解决方案。

  6. 内存,cpu,以及磁盘等硬件资源,原来的习惯是购买服务器的时候就根据服务器的上的应用类型进行规划,如果应用和硬件解耦,这种方式需要淘汰。但必须有一种调度机制让应用迁移的时候可进行筛选。

总结一下,通过分析得出,要达到目标,关键是解耦,应用进程和资源(包括 cpu,内存,磁盘,网络)的解耦,服务依赖关系的解耦。

我们上面的改造机制基本是按照个案进行设计,Kubernetes的则是要提供一套全面通用的机制。

然后,我们看看Kubernetes对以上问题的解决方案:

先上一张Kubernetes官方的架构图 Kubernetes架构的示例分析

  1. 调度中心master,主要有四个组件构成:

  2. 节点上的agent,主要有两个组件:

  3. Pods Kubernetes将应用的具体实例抽象为pod。每个pod首先会启动一个google_containers/pause docker容器,然后再启动应用真正的docker容器。这样做的目的是为了可以将多个docker容器封装到一个pod中,共享网络地址。

  4. Replication Controller 控制pod的副本数量,高可用就靠它了。

  5. Services service是对一组pods的抽象,通过kube-proxy的智能LoadBalancer机制,pods的销毁迁移不会影响services的功能以及上层的调用方。Kubernetes对service的抽象可以将底层服务和上层服务的依赖关系解耦,同时实现了和Docker links类似的环境变量注入机制(https://github.com/kubernetes/kubernetes/blob/release-1.0/docs/user-guide/services.md#environment-variables),但更灵活。如果配合dns的短域名解析机制,最终可实现完全解耦。

  6. Label key-value格式的标签,主要用于筛选,比如service和后端的pod是通过label进行筛选的,是弱关联的。

  7. Namespace Kubernetes中的namespace主要用来避免pod,service的名称冲突。同一个namespace内的pod,service的名称必须是唯一的。

  8. Kubectl Kubernetes的命令行工具,主要是通过调用apiserver来实现管理。

  9. Kube-dns dns是Kubernetes之上的应用,通过设置Pod的dns searchDomain(由kubelet启动pod时进行操作),可以实现同一个namespace中的service直接通过名称解析(这样带来的好处是开发测试正式环境可以共用同一套配置)。主要包含以下组件,这几个组件是打包到同一个pod中的。

  10. Networking Kubernetes的理念里,pod之间是可以直接通讯的(http://kubernetes.io/v1.1/docs/admin/networking.html),但实际上并没有内置解决方案,需要用户自己选择解决方案: Flannel,OpenVSwitch,Weave 等。我们测试用的是Flannel,比较简单。

  11. 配置文件 Kubernetes 支持yaml和json格式的配置文件,主要用来定义pod,replication controller,service,namespace等。

Kubernates 可能带来的改变

  1. 降低分布式应用开发运维的复杂度 纵观当前的各种分布式架构,hadoop,storm等,都是master-workers模式,框架很大一部分功能在节点的管理,处理程序的调度上,如果基于Kubernetes来实现类似功能,这些基本都可以交给Kubernetes完成,框架只需要负责核心数据的流转以及收集逻辑。当然,当前Kubernetes的pod还未像Borg一样直接支持batch job,但按照Kubernetes和Borg的关系,将来应该会支持(http://blog.kubernetes.io/2015/04/borg-predecessor-to-kubernetes.html)。

  2. 更完备的CI/CD(持续集成/持续交付)工具 CI是code-deploy的关键工具,但当前由于受限于部署环境的不一致,CI可做的事情有限,大多数还依赖用户的自定义脚本。有了Kubernetes这样的标准环境后,以后此类工具可以覆盖测试环境部署,集成测试,上线部署等环节,实现标准化的交付工作流。

  3. Kubernetes之上的分布式存储 Kubernetes官方提供了一个在Kubernetes上部署cassandra的例子,只需要重写一个基于Kubernetes apiserver的SeedProvider,就可以避免静态配置seed ip,享受Kubernetes带来的scale-out能力。再如前面我们提到的memcached的高可用例子,如果基于Kubernetes实现一个memcached的smart client,只需要改下客户端即可,非常简单。个人认为以后在Kubernetes上的支持多租户的分布式存储会更加流行。只要解决了存储服务的scale-out问题,应用的scale-out一般不会有太大问题。Hypernetes就是一个实现了多租户的Kubernetes版本。

  4. 企业应用的分发 当前SaaS(on-demand)比较流行的一个很大的原因是原来的on-premise应用的部署运维成本太高,如果Kubernetes等分布式操作系统得到广泛应用,on-premise的成本降低,on-premise以及托管云模式对SaaS的格局也会带来影响。这也是我们这样的创业公司关注Kubernetes的原因之一。

  5. 对IaaS的影响 当前的IaaS平台的组件逐渐有闭源的趋势,比如AWS尝试用Aurora替代Mysql,阿里云用KVStore替换Redis。用户主要关心的是服务的可靠性,自己运维的时候可能会倾向于开源方案,但如果使用云厂商的服务,就不太关心。按照这样的趋势,随着IaaS的普及,会对整个开源的生态产生影响。但有了Kubernetes这样的平台,IaaS厂商主要为Kubernetes提供运行的基础环境,Kubernetes接管上面的应用和服务,这样在IaaS厂商之间迁移也很容易。

  6. 微服务 微服务最近很热,但这个概念其实不新。主要一直受限于运维的复杂度,没有普及。如果运维系统跟不上,服务拆太细,很容易出现某个服务器的角落里部署着一个很古老的不常更新的服务,后来大家竟然忘记了,最后服务器迁移的时候给丢了,用户投诉才发现。而随着Docker以及Kubernetes这样的工具和平台逐渐成熟,微服务的时代也到来了。 在Kubernetes上的微服务治理框架可以一揽子解决微服务的rpc,监控,容灾问题,个人觉得可以期待。

遇到的一些问题

最后总结一下我遇到的一些问题

  1. 墙 gcr.io已被墙,如果在本地用脚本在虚拟机安装,请全程翻墙。如果在服务器上就自己想办法下载,然后在配置文件中指定镜像地址。

  2. 并发拉取镜像导致镜像文件破坏(https://github.com/kubernetes/kubernetes/issues/10623) 这个和docker也相关,建议先用脚本在各node上pull镜像再部署。

  3. 同一个pod内的多个容器启动顺序问题 同一个pod的多个容器定义中没有优先级,启动顺序不能保证。比如kube-dns中,etcd要先启动,然后skydns连接etcd创建基本的目录,最后kube2sky启动,将kube中已经定义的数据同步到dns中。如果顺序不对dns数据就不正常。如果遇到这种问题按顺序重启一下对应的容器即可。这种问题当前需要应用自己通过重试机制解决。

  4. 容器内访问外部网络 如果使用了Flannel方案,但容器内无法访问公网(node可以的情况),一般是iptables被搞坏了(https://github.com/coreos/flannel/issues/115)。

  5. 当前的Kubernetes没有应用的概念,我们的应用包含4个自己开发的服务组件,还有一些依赖(mysql,redis,mongodb等),定义下来一共要20多个yaml。要实现一键安装或者更新,还需要做不少工作。

  6. Kubernetes的公网负载均衡的解决方案依赖IaaS的实现,不够灵活。

  7. kube-proxy的性能问题,简单的压测结果如下: 10.254.2.99:80是service地址,后面有两个pod。11.1.16.15:3000是其中一个pod。代码是golang官方网站首页的那个helloword。

    ab -c 50 -n 100000 http://10.254.2.99:80/
    
     Server Hostname:		10.254.2.99
     Server Port:			80
    	
     Document Path:		  /
     Document Length:		43 bytes
    	
     Concurrency Level:	  50
     Time taken for tests:   346.442 seconds
     Complete requests:	  100000
     Failed requests:		0
     Write errors:		   0
     Total transferred:	  16000000 bytes
     HTML transferred:	   4300000 bytes
     Requests per second:	288.65 [#/sec] (mean)
     Time per request:	   173.221 [ms] (mean)
     Time per request:	   3.464 [ms] (mean, across all concurrent requests)
     Transfer rate:		  45.10 [Kbytes/sec] received
    	
     Connection Times (ms)
                   min  mean[+/-sd] median   max
     Connect:		0	1  39.9	  0	7015
     Processing:	 1  173 437.7	 22	5026
     Waiting:		1  172 437.7	 22	5026
     Total:		  3  173 440.4	 22   10070
    	
     Percentage of the requests served within a certain time (ms)
       50%	 22
       66%	 23
       75%	 24
       80%	 26
       90%   1022
       95%   1023
       98%   1031
       99%   2024
      100%  10070 (longest request)
    	
     ab -c 50 -n 100000 http://11.1.16.15:3000/
    	
     Server Hostname:		11.1.16.15
     Server Port:			3000
    	
     Document Path:		  /
     Document Length:		43 bytes
    	
     Concurrency Level:	  50
     Time taken for tests:   15.992 seconds
     Complete requests:	  100000
     Failed requests:		0
     Write errors:		   0
     Total transferred:	  16000000 bytes
     HTML transferred:	   4300000 bytes
     Requests per second:	6253.24 [#/sec] (mean)
     Time per request:	   7.996 [ms] (mean)
     Time per request:	   0.160 [ms] (mean, across all concurrent requests)
     Transfer rate:		  977.07 [Kbytes/sec] received
    	
     Connection Times (ms)
                   min  mean[+/-sd] median   max
     Connect:		0	0   0.0	  0	   2
     Processing:	 0	8   1.3	  7	  25
     Waiting:		0	8   1.3	  7	  24
     Total:		  1	8   1.3	  7	  25
    	
     Percentage of the requests served within a certain time (ms)
       50%	  7
       66%	  8
       75%	  8
       80%	  8
       90%	 11
       95%	 11
       98%	 11
       99%	 11
      100%	 25 (longest request)


以上是“Kubernetes架构的示例分析”这篇文章的所有内容,感谢各位的阅读!希望分享的内容对大家有帮助,更多相关知识,欢迎关注亿速云行业资讯频道!

推荐阅读:
  1. kubernetes概述的示例分析
  2. PHP架构的示例分析

免责声明:本站发布的内容(图片、视频和文字)以原创、转载和分享为主,文章观点不代表本网站立场,如果涉及侵权请联系站长邮箱:is@yisu.com进行举报,并提供相关证据,一经查实,将立刻删除涉嫌侵权内容。

kubernetes

上一篇:linux驱动中并发与竟态的示例分析

下一篇:MacOS下如何实现docker端口映射

相关阅读

您好,登录后才能下订单哦!

密码登录
登录注册
其他方式登录
点击 登录注册 即表示同意《亿速云用户服务条款》