pod: lable lable-selector
lable key=values
pod: pod可以叫做是有生命周期的对象。调度器将其调度到某节点运行后,他的任务终目也就被删除或停掉了。
自主式pod,(自我管理的POD)
控制器管理的pod。(建议使用这种POD)
ReplicationContrller 副本控制器。如果我们启动一个nginx_pod,
同一pod内多个容器通信,lo
各pod间有通信,
NMT:N:NGINX,M:MYSQL,T:TOMCAT
简单地说,kubernetes还是一个管理跨主机容器化应用的系统,实现了包括应用部署,高可用管理和弹性伸缩在内的一系列基了础功能并封装成为一套完整,简单易用的RESTful API对外提供服务,
kubernetes引入了专门的POD,从而建立了围绕着POD这个可以视作单个容器的“容器组”展开的,当容器组代替成了为系统中的主要粒度。
kubernetes提供了APIServer,scheduler,kubelet等底层枋心组件,从而使用得用户能够放心管理成行上万个容器实例,更提供了pod,replicagion controller,service等设计理念。
kubernetes提供了,容器组,跨主机网络,负载均衡,等一系列关键的上层容器服务。
在k8s之上我们运行了容器,同一类容器(同一类pod),
1、如果用户请求到达时我们该如何接入请求。到底给哪一类pod中的哪一个pod负责处理了。
2、POD本身是要有所为的控制器来管理的,尽量不要人手工去管理,在k8s上pod有两类,(1)自主式pod,(自我管理),我们创建以后仍然需要提交给APIserver,由APIserver接收以后
借助于调度器将它调度至指定的node节点,由node启动此pod,而后,如果pod中的容器出现故障,需要重启容器,那是由kubelet来完成的。但是如果节点故障了,这些pod也就消失不见了,
(2)控制器管理的pod,正是控制器这种机制的使用,在kubernetes集群的设计中,pod就被称为有生命令周期的对象,有调度器将其调度至集群中的某节点运行以后,他的任务结束后就被删除或停掉了。
但是有些任务,传统意义上的如ngxin、tomcat他们是做为守护进程运行的,这种要是运行成pod或容器的话,我们要确保他时刻得于运行状态。一旦出现故障必须要在第一时间发现,要么是取代他要么是重启他。
k8s为些提供的工具就叫pod控制器。
pod控制器有很多种,最早的一种就是replication controller,(副本控制器)
当我们要启动一个pod时,比如是启动一个nginx的pod,这个pod不够了,那我们再启一个pod,这个pod就叫做副本,其实每个pod都可以叫做是副本,那么控制器就专门控制着同一类pod资源的各种副本。
一旦副本数量少了,他会自动加一个补够,如果其中的一个pod被调度到第三个节点上运行,但是这个节点down机了,那么控制器会发现少了一个pod,控制器会重新请求apiserver借助于Scheduler调度以后找一个另外的节点
启动一个pod。还可以实现滚动更新,比如此前启动的容器是靠一个1.0版的镜像启动,后来我做了一个1.1版的镜像,需要把这些pod中对应的容器替换为1.1版本镜像,可以先关掉一个1.0镜像的容器或者先创建一个1.1镜像
的容器。可以在更新的过程中临时超出设定的副本数量,去掉一个1.0镜像的副本行了。以此类推,这就叫滚动更新,也支持滚动更新的逆反操作叫回滚。
到了新版时有了新的控制器,ReplicSet叫副本集,不直接使用,他有一个声明是更新的控制器,是Deployment来负责管理。我们用的最多的就是他,但是Deployment只能负责管理那些无状态的管理应用,有状态的应用使用statefulset
如果我们想在每一个node上运行一个副本,而不是随意运行,还需要一个DaemonSET,如果运行作业Job,如果运行周期性作业就叫Ctonjob
Deployment还支持二级控制器叫HPA,水平pod自动伸缩控制器。如:有两个nginx的pod不足以承载用户访问了,那就只有再加更多的pod了。
到底要加几个ngixn的pod,HPA会自动监控着的。HPA(HorizontalPodAutoscaler)是依据当前系统的可用资源不超某一个指定值的前提下自动增加pod数量。
比如有两个pod,pod有生命周期,也就是万一pod所在的节点down机了,pod有可能要在其他节点上重建,而重建完的pod和原来的pod不是同一个pod,里边运行的是同一个服务,但pod已经不是以前那个pod了,而且每一个容器都有一个ip地址吧,新建的
pod的ip地址和些前那个pod的ip地址也是不一样的,这么一来就有问题,我们客户端怎么去访问这些pod了,采用服务发现,客户端每一次去访问后端对应的服务时,他需要先去访问一个位置有没有这个服务。这个位置就叫中间层也叫Service,
Service只要不删除他的地址是固定的名称也是固定的,当客户端需要写在配置文件中访问某一个服务时,他不用发现也不用自动去发现某一个功能,他只需要要在配置文件中写明这个服务的地址或者名称就行,而这个服务是一个调度器还可以起到调度的功能。
不但能提供一个稳定的访问入口,还可以把请求送到后端的pod容器里。一旦pod死掉了,再新建一个pod,新建的pod立即会被service关联进来,把他作为service后端的可用pod资源, 客户端访问服务都是通过ip加端口或者是主机名加端口的。service关联后端的pod不是通过ip加端口或者是主机名加端口的方式,
而是通过在创建pod时的元数据lable来关联的,service把这个pod关联进来后,再动态探测这个pod的ip地址和端口,并做为自己动态调度后端可用的盈千用服务器主机对象。
在k8s上service并不是什么应用程序,也不是实体组件,他只不过是一个iptables的dnat规则,service作为一个kubernetes的对象来讲,有service的名称,service的名称也相当于是这个服务的名称。
而且名称可以被解析,可以把service的名称解析为service的ip地址,名称解析靠的是DNS,装完k8s集群时你会发现第一件事就需要在你的k8s集群上部署一个DNS的pod,以确保各service能被正确解析。这种服务是k8s自身服务就要用的pod,我们把它叫做基础级的系统架构所使用的pod,他们也被称为集群的附件(AADOns附加组件)
DNS只k8s众多附加组件中的一种,它可以动态改变,动态创建、动态删除、动态变动。比如你把service名称改一下,它会自动触发dns记录中的解析名称也会改变的,
客户端去访问某一服务时,可以直接访问服务的名称,然后由集群中专用的DNS来负责解析成service的地址,因此这个访问依然是由service做为代理访问实现的,而代理是由端口代理,就是由dnat实现的,dnat是多目标调度,对于linux来讲,iptables已经把负载均衡的主要功能交给ipvs来实现,因些如果service背后的同一类pod有好多是由dnat来实现的时,
在调度效果上可能不太尽人意,因此在1.11版的当中已经把其iptables的规则进一步改成了ipvs了,也就是意味着当你创建service时就相当于生成了一条ipvs,中不过是nat模型的ipvs,因此支持用户指定各种调度算法,
外接调度器已经脱离k8s的控制了,他不能基于k8s以命令的方式创建了。如果你是一个IAAS云计算环境,有一种服务叫LBaas负载均衡级服务,如果我们把k8s集群运行在阿里云或者是亚马逊云上,阿里云或者是AWS是支持LBaas的,我们k8s可以对外调用低层云计算环境API接口创建一个service这个service要对外开放,用他来创建一个外接调度器。
service只是调度流量的,控制器用来管理pod的。
整个k8s集群网络要有三种网络,
1、各pod运行在一个网络中,
2、Service是另外一个网络,service的地址和pod的地址是不同网段的,pod的地址是配置在pod内部网络名称空间上的,是可以ping通的正常的ip地址。
Service地址是虚拟的,只存在于iptables或ipvs中,
3、各节点又是一个网段,
节点网络,集群网络,pod网络。
外部访问时先到达节点网络,由节点网络代理至集群网络,再由集群网络代理至pod网络,
同一pod内多个容器间通信。使用lo本地通信。
各pod间通信。无论两个pod运行在哪个节点上,他们的地址是不能相同的,所以pod间可以直接使用对方地址通信。1、物理桥桥接,处于同一网段可以直接通信,但是这样有一个问题,比如,10个节点运行了三百个节点,每个容器都有一个固定的地址,结果是300个容器都处在同一个二层网络中。
做arp二层广播,所有的容器都能收到ARP请求,太乱了。
2、使用Overlay Network,叠加网络,通过隧道方式来转发二层报文使用pod之间通信,虽然夸主机但是感觉是在同一个二层网络中,
pod与service之间的通信。
pod有pod的网络,service有service的网络,各pod客户端是直接配置service的名称或地址就可以进行访问了,那怎么可达service呢,service的地址只不过是主机上的iptables的规则里的地址,
容器把目标地址指向网关,网关假如是docker0桥,iptables就在当前宿主机上有规则,每一个主机上都的有规则。只要创建service,这个service是要反应在整个集群上的每一个节点之上的,每一个node都应该有相关的iptables或ipvs,如果有一个容器试图去访问某一service地址时,它应该把请求送给网关。
docker0桥的地址。docker0桥收到请求后,他怎么知道docker0桥地址在哪呢,现在这就是一台主机上的事情了,他通过对应的iptables或ipvs规则表一检查就知道在哪里了。service怎么又能够所有节点上相关地址规则呢,这需要一个专门的组件来实现的。
在每一个node节点上运行一个组件,这个组件一般是运行node之上守护进程,被称之为kube-proxy,它负责随时和API-server进行通信,因为你的每一个pod发生变化以后这个结果要保存在api-server中的,这个通信内容发生改变后,会生成一个通知事件,这个事件中以被任何关联的组件接收到。
kube-proxy一旦发现某一service背后的pod发生改变地址发生改变,对应的由kube-proxy负责在本地把那个地址反应在iptables或者ipvs规则中,所以service的管理是靠kube-proxy,你创建service是要靠kube-proxy在每个节点上生成规则。每个service的变也需要靠kube-proxy反应到规则上
随时都有可能要变动,
API-server要存偖整个集群中所有对象状态信息,怎么存下的,各master之间要共享存储,对于master主机来讲,所有数据并不存储在master本地,而是放在共享存储当中,这种存储叫做k8s的etcd。是一个键值存储的数据库跟redis很类似,要把etcd做成多节点,一般至少有三节点。
etcd通过https通信的,etcd通有一特点,9300端口用于集群内部通信,9200用于集群外部通信。即于内部通信需要一个专门的证书叫点对点通信证书,向客户端通信要想加密使用另外一套证书实现,API-Server为了向客户端通信需要另一套证书。API-Server与kubelet通信要一套证书(https),
API-Server与kube-proxy需要一套证书,
K8s通过CNI(容器网络接口)插件体系来接近外部网络服务解决方案,只要你是一个网络服务提供商能遵巡CNI开发这个服务,那么就能够做为K8s的网络解决方案来使用。事实丰这些网络服务可以以附件的形式运行在k8s上的。
目前能运行为附件的CNI插件很多。
如果在一个k8s上托管了两万个pod,他们之间都可以直接通信的,假如这些pod属于同一个项目或者不属于同一家公司,别人可以访问你的服务甚至有可能劫持你的服务,
在多租户场景这是非常危险的,我们应该隔离,这是网络策略的功能,网络策略需要适加一些条件其实也是iptables的规则来隔离不同pod彼此之间不能访问。引入了k8s的另一个组件叫名称空间,
整个k8s是做为一个集群存在的,可以运行两万个pod在这个集群中,可以把他切割成多个空间,一类pod只允许在一个空间中,这个空间提供的不是真正意义上的网络边界,只是管理边界,意思是说第一个空间叫开发一,所有和开发有关的pod都放在这个空间中,第二个空间叫生产空间,所有和生产有关的pod都放在这个空间中。
我们要删除这样一个网络名称空间可以这个环境都移除掉,所以是提供了一个管理边界。但是pod之间并没有任何边界,开发环境中的pod访问生产环境中的pod没有任何问题。还是在同一个网络中的。
网络策略就是允许我们去定义名称空间和名称空间之间甚至是同一个名称空间中各pod间能否互相访问,通过生成iptables规则来隔离他们彼此互相访问,这就叫网络策略,
对于k8s来讲网络策略和网络功能是两个维度的概念。
flanner 支持网络配置,不支持网络策略。
calico 即支持网络配置,又支持网络策略。
部署和使用起来有些难,它能基于bgp协议来直接路由通信,是一个三层隧道网络,
canel 支持网络策略,和flanner结合个体。
这些是可以托管在k8s上之上做为容器去运行的,当然也可以做为附件运行的,也可以做节点上的守护进程运行的。
master:是集群的网关和中枢,负责诸如为用户端暴露API,跟综其他服务器的健康状态,以最优方式调度工作负载,它是用户或客户端与集群之间核心
联络点,并负责kubernetes系统的大多数集中式管控逻辑,单个Master节点即可完成其所有的功能,但出于冗余及负载均衡等目的,生产环境中通常
需要协同部署多个此类主机,Master节点类似于蜂群中的蜂王。
Node:是kuerbetes集群的工作节点,负责接收来自Master的工作指令并根据指令相应地创建或销毁pod对象,以及调整网络规则以合理地路由和转发流量等,
理论上讲,Node可以是任何形式的计算设备,不过Master会统一将其抽象为Node对象进行管理,Node类似于蜂群中的工蜂,生产环境中,它们通常数理
众多。
kubernetes将所有Node的资源集结于一处形成一台更加强大的服务器,在用户将诮用部署在其上时,Master会使用调度算法,将其自动指派至某个特定
的Node运秆,在Node加入集群或从集群中移除时,MaSter也会按需重新编排影响 到的POD(容器),于是,用户无须关心其应用究竟运行于何处,
pod:kubernetes并不直接运行容器,而是使用一个抽象的资源对象来封装一个或者多个容器,这个个抽象的对象即为POD,它也是kubernetes的最小
调度单元,同一个POD中的容器共享网络名称空间和存储资源,这些容器可经由本地回环口lo直接通信,但彼此之间又在Mount User 及PID等
名称空间上保持了隔离。尽管POD中可以包含多个容器,但是作为最小调度单元,它应该尽可能地保持小,即通常只应该包含一个主容器,以及必要
的辅助型容器。
资源标签:是将资源进行分类的标识符,资源标签其实就是一个健值型(Key/values)数据,标签旨在指定对象(如POD)辨识性的属性。
标签选择器:它是一种根据Label来过滤符合条件的资源对象的机制。
POD控制器:尽管POD是kubernetes最小调度单元,但用户通常并不会直接部署及管理POD对象,而是要借助于另一类抽象--控制器(Controller)
对其进行管理,用于工作负载的控制器是一种管理POD生命令周期的,它们是kubernetes上的一类对象,而非单个资源对象,包括ReplicationController
、ReplicaSet、Deployment、StatefulSet、Job等。负责确保指定的POD对象的副本数量精确符合定义,否则多退少补。使用控制器之后就不再需要手动管理
POD对象了,用户只需要声明应用的期望状态,控制器就会自动对其进行进程管理。
服务资源:是建立在一组POD对象之上的资源抽象,它通过标签选择器选定一组POD对象,关为这组POD对象定义一个统一的固定访问入口(通常是一个IP地址),若
kubernetes集群存在DNS附件,它就会在Service创建时为其自动配置一个DNS名称以便客户端进行服务发现。到在Service IP的请求将被负载均衡至其后端的节点,各个
POD对象之上,因此Service从本质上来讲是一个4层代理服务,另外,service还可以将集群外部流量引入到集群中来。
存储卷:是独立于容器文件系统之外的存储空间,常用于扩展容器的存储空间并为它提供持久存储能力。Kuernetes集群上的存储卷大体可分为临时卷,本地卷和网络卷。
临时卷和本地卷都位于Node本地,一旦POD被调度至其他POD,此种类型的存储卷将无法访问,因此临时卷和本地卷通常位于数据缓存,持久化的数据则需要放置于持久卷
(persistent volume)上。
Name和Namespace:是kubernetes集群中资源对象的标识符,它们的作用域通常是名称空间(Namespace),因此名称空间是名称的额外的限定机制,在同一个名称空间中,同一类
型资源对象的名称必须具有唯一性。名称空间通常用于实现租房或项目的资源隔离,从而形成逻辑分组。创建的POD和Service等资源对象都属于名称空间级别,未指定时,它们
都属于默认的名称空“default”