Kubernetes管理pod资源对象
更新:HHH   时间:2023-1-7


这篇文章主要为大家分享Kubernetes管理pod资源对象的方法。文中还介绍了Kubernetes中的Namespace,希望大家通过这篇文章能有所收获。

一,k8s的资源对象

Deployment、Service、Pod是k8s最核心的3个资源对象

Deployment:最常见的无状态应用的控制器,支持应用的扩缩容、滚动升级等操作。

Service:为弹性变动且存在生命周期的Pod对象提供了一个固定的访问接口,用于服务发现和服务访问。

Pod:是运行容器以及调度的最小单位。同一个pod可以同时运行多个容器,这些容器共享net、UTS、IPC,除此之外还有USER、PID、MOUNT。

ReplicationController:用于确保每个Pod副本在任意时刻都能满足目标数量,简单来说,它用于每个容器或容器组总是运行并且可以访问的:老一代无状态的Pod应用控制器。

RwplicatSet:新一代的无状态的Pod应用控制器,它与RC的不同之处在于支持的标签选择器不同,RC只支持等值选择器(键值对),RS还额外支持基于集合的选择器。

StatefulSet:用于管理有状态的持久化应用,如database服务程序,它与Deployment不同之处在于,它会为每一个pod创建一个独有的持久性标识符,并确保每个pod之间的顺序性。

DaemonSet:用于确保每一个节点都运行了某个pod的一个副本,新增的节点一样会被添加到此类pod,在节点移除时,此pod会被回收。

Job:用于管理运行完成后即可终止的应用,例如批量处理做作业任务;

1.Pod的生命周期被定义为以下几个阶段。

  • Pending:Pod已经被创建,但是一个或者多个容器还未创建,这包括Pod调度阶段,以及容器镜像的下载过程。
  • Running:Pod已经被调度到Node,所有容器已经创建,并且至少一个容器在运行或者正在重启。
  • Succeeded:Pod中所有容器正常退出。
  • Failed:Pod中所有容器退出,至少有一个容器是一次退出的。

2.特点

Pod是能够被创建、调度和管理的最小单元;
每个Pod都有一个独立的IP;
一个Pod由一个或多个容器构成,并共享命名空间和共享存储等;Pod所有容器在同一个Node上;
容器生命周期管理;
对资源使用进行限制,resources(requests、limits);
对容器进行探测:livenessProbe;
集群内的Pod之间都可以任意访问,这一般是通过一个二层网络来实现的。

3.Pod与容器

在Docker中,容器是最小的处理单元,增删改查的对象是容器,容器是一种虚拟化技术,容器之间是隔离的,隔离是基于Linux Namespace实现的。
而在K8S中,Pod包含一个或者多个相关的容器,Pod可以认为是容器的一种延伸扩展,一个Pod也是一个隔离体,而Pod内部包含的一组容器又是共享的(包括PID、Network、IPC、UTS)。除此之外,Pod中的容器可以访问共同的数据卷来实现文件系统的共享。

4.资源请求与限制

创建Pod时,可以指定计算资源(目前支持的资源类型有CPU和内存),即指定每个容器的资源请求(Request)和资源限制(Limit),资源请求是容器所需的最小资源需求,资源限制则是容器不能超过的资源上限。关系是: 0<=request<=limit<=infinity
Pod的资源请求就是Pod中所有容器资源请求之和。K8S在调度Pod时,会根据Node中的资源总量(通过cAdvisor接口获得),以及该Node上已使用的计算资源,来判断该Node是否满足需求。
资源请求能够保证Pod有足够的资源来运行,而资源限制则是防止某个Pod无限制地使用资源,导致其他Pod崩溃。特别是在公有云场景,往往会有恶意软件通过抢占内存来平台。
具体配置请见http://blog.csdn.net/liyingke112/article/details/77452630

5.一pod多容器

Pod主要是在容器化环境中建立一个面向应用的“逻辑主机”模型,它可以包含一个或多个相互间紧密联系的容器。当其中任一容器异常时,该Pod也随之异常。

一pod多容器,让多个同应用的单一容器整合到一个类虚拟机中,使其所有容器共用一个vm的资源,提高耦合度,从而方便副本的复制,提高整体的可用性。

一pod多容器的优势:

同个Pod下的容器之间能更方便的共享数据和通信,使用相同的网络命名空间、IP地址和端口区间,相互之间能通过localhost来发现和通信。

在同个Pod内运行的容器共享存储空间(如果设置),存储卷内的数据不会在容器重启后丢失,同时能被同Pod下别的容器读取。

相比原生的容器接口,Pod通过提供更高层次的抽象,简化了应用的部署和管理,不同容器提供不同服务。Pod就像一个管理横向部署的单元,主机托管、资源共享、协调复制和依赖管理都可以自动处理。

6.Pod-使用

核心原则是:将多个应用分散到多个Pod中
原因:基于资源的合理应用;扩缩容,不同应用应该有不同的扩缩容策略等。
如果容器之间不是必须运行在一起的话,那么就放到不同的Pod里
如果容器之前是相互独立的组件,那么就放到不同的Pod里
如果容器之前扩缩容策略不一样,那么就放到不同的Pod里
结论:单Pod单容器应用,除非特殊原因

实验环境

主机IP地址服务
master192.168.1.21k8s
node01192.168.1.22k8s
node02192.168.1.23k8s

基于https://blog.51cto.com/14320361/2464655 的实验继续进行

二,Namespace:名称空间

默认的名称空间:Default

Namespace(命名空间)是kubernetes系统中的另一个重要的概念,通过将系统内部的对象“分配”到不同的Namespace中,形成逻辑上分组的不同项目、小组或用户组,便于不同的分组在共享使用整个集群的资源的同时还能被分别管理。

Kubernetes集群在启动后,会创建一个名为“default”的Namespace,如果不特别指明Namespace,则用户创建的Pod、RC、Service都被系统创建到“default”的Namespace中。

1.查看名称空间

[root@master ~]# kubectl get namespaces

2.查看名称空间详细信息

[root@master ~]# kubectl describe ns default

3.创建名称空间

[root@master ~]# kubectl create ns bdqn

查看一下

[root@master ~]# kubectl get namespaces

4.创建namespace的yaml文件

(1)查看格式

[root@master ~]# kubectl explain ns
//查看nasespace的yaml文件的格式

(2)创建namespace的yaml文件

[root@master ~]# vim test-ns.yaml
apiVersion: v1
kind: Namespace
metadata:
  name: test

(3)运行namespace的yaml文件

[root@master ~]# kubectl apply -f test-ns.yaml 

(4)查看一下

[root@master ~]# kubectl get ns

4.删除名称空间

[root@master ~]# kubectl delete ns test 
[root@master ~]# kubectl delete -f test-ns.yaml 

注意:namespace资源对象进用于资源对象的隔离,并不能隔绝不同名称空间的Pod之间的通信。那是网络策略资源的功能。

5.查看指定名称空间

可使用--namespace或-n选项

[root@master ~]# kubectl get pod -n kube-system 
[root@master ~]# kubectl get pod --namespace kube-system 

三,Pod

1.编写一个pod的yaml文件

[root@master ~]# vim pod.yaml
kind: Pod
apiVersion: v1
metadata:
  name: test-pod
spec:
  containers:
  - name: test-app
    image: 192.168.1.21:5000/web:v1

pod的yaml文件不支持replicas字段

(1)运行一下

[root@master ~]# kubectl apply -f pod.yaml 

(2)查看一下

[root@master ~]# kubectl get pod

ps:这个pod因为是自己创建的,所以删除之后k8s并不会自动生成,相当于docker中创建

2.指定pod的namespace名称空间

(1)修改pod的yaml文件

[root@master ~]# vim pod.yaml
kind: Pod        #资源类型
apiVersion: v1   #api版本
metadata:
  name: test-pod    #指定控制器名称
  namespace: bdqn   #指定namespace(名称空间)
spec:
  containers:      #容器
  - name: test-app  #容器名称
    image: 192.168.1.21:5000/web:v1  #镜像
执行一下
[root@master ~]# kubectl apply -f pod.yaml 

(2)查看一下

[root@master ~]#  kubectl get pod -n bdqn 
//根据namespace名称查看

3.pod中镜像获取策略

Always:镜像标签为“laster”或镜像不存在时,总是从指定的仓库中获取镜像。

IfNotPresent:仅当本地镜像不存在时才从目标仓库下载。

Never:禁止从仓库中下载镜像,即只使用本地镜像。

注意:对于标签为“laster”或者标签不存在,其默认的镜像下载策略为“Always”,而对于其他的标签镜像,默认策略为“IfNotPresent”。

4.观察pod和service的不同并关联

(1)pod的yaml文件(指定端口)

[root@master ~]# vim pod.yaml 
kind: Pod          #资源类型
apiVersion: v1      #api版本
metadata:
  name: test-pod       #指定控制器名称
  namespace: bdqn   #指定namespace(名称空间)
spec:
  containers:                          #容器
  - name: test-app                    #容器名称
    image: 192.168.1.21:5000/web:v1   #镜像
    imagePullPolicy: IfNotPresent   #获取的策略
    ports:
    - protocol: TCP
      containerPort: 80  
<1>删除之前的pod
[root@master ~]# kubectl delete pod -n bdqn test-pod 
<2>执行一下
[root@master ~]# kubectl apply -f pod.yaml 
<3>查看一下
[root@master ~]# kubectl get pod -n bdqn 

(2)pod的yaml文件(修改端口)

[root@master ~]# vim pod.yaml 
kind: Pod
apiVersion: v1
metadata:
  name: test-pod
  namespace: bdqn
spec:
  containers:
  - name: test-app
    image: 192.168.1.21:5000/web:v1
    imagePullPolicy: IfNotPresent
    ports:
    - protocol: TCP
      containerPort: 90   #改一下端口
<1>删除之前的pod
[root@master ~]# kubectl delete pod -n bdqn test-pod 
<2>执行一下
[root@master ~]# kubectl apply -f pod.yaml 
<3>查看一下
[root@master ~]# kubectl get pod -n bdqn -o wide

<4>访问一下

会发现修改的90端口并不生效,他只是一个提示字段并不生效。

(3)pod的yaml文件(添加标签)

[root@master ~]# vim pod.yaml 
kind: Pod
apiVersion: v1
metadata:
  name: test-pod
  namespace: bdqn
  labels:                 #标签
    app: test-web          #标签名称
spec:
  containers:
  - name: test-app
    image: 192.168.1.21:5000/web:v1
    imagePullPolicy: IfNotPresent
    ports:
    - protocol: TCP
      containerPort: 90   #改一下端口
--------------------------------------pod---------------------------------------------

(4)编写一个service的yaml文件

[root@master ~]# vim test-svc.yaml 
apiVersion: v1      #api版本
kind: Service          #资源类型
metadata:
  name: test-svc       #指定控制器名称
  namespace: bdqn   #指定namespace(名称空间)
spec:
  selector:          #标签
    app: test-web    #标签名称(须和pod的标签名称一致)
  ports:              
  - port: 80          #宿主机端口
    targetPort: 80    #容器端口

会发现添加的80端口生效了,所以不能乱改。

<1>执行一下
[root@master ~]# kubectl apply -f test-svc.yaml
<2>查看一下
[root@master ~]# kubectl get svc -n bdqn 

[root@master ~]# kubectl describe svc -n bdqn test-svc 

<4>访问一下
[root@master ~]# curl 10.98.57.97 

--------------------------------------service---------------------------------------------

四,容器的重启策略

Pod的重启策略(RestartPolicy)应用与Pod内所有容器,并且仅在Pod所处的Node上由kubelet进行判断和重启操作。当某个容器异常退出或者健康检查失败时,kubelet将根据RestartPolicy的设置来进行相应的操作。

Always:(默认情况下使用)但凡Pod对象终止就将其重启;
OnFailure:仅在Pod对象出现错误时才将其重启;
Never:从不重启;

五,pod的默认健康检查

每个容器启动时都会执行一个进程,此进程由 Dockerfile 的 CMD 或 ENTRYPOINT 指定。如果进程退出时返回码非零,则认为容器发生故障,Kubernetes 就会根据 restartPolicy 重启容器。

(1)编写健康检查的yaml文件

下面我们模拟一个容器发生故障的场景,Pod 配置文件如下:

[root@master ~]# vim healcheck.yaml 
apiVersion: v1
kind: Pod
metadata:
  labels:
    test: healcheck
  name:  healcheck
spec:
  restartPolicy: OnFailure  #指定重启策略
  containers:
  - name:  healcheck
    image: busybox:latest
    args:                   #生成pod时运行的命令
    - /bin/sh
    - -c
    - sleep 20; exit 1 

<1>执行一下

[root@master ~]# kubectl apply -f  healcheck.yaml

<2>查看一下

[root@master ~]# kubectl get pod -o wide

[root@master ~]# kubectl get pod -w | grep healcheck

在上面的例子中,容器进程返回值非零,Kubernetes 则认为容器发生故障,需要重启。但有不少情况是发生了故障,但进程并不会退出。

六,小实验

1)以自己的名称创建一个k8s名称空间,以下所有操作都在此名称空间中。

(1)创建名称空间

[root@master ~]# kubectl create ns xgp

(2)查看一下

[root@master ~]# kubectl get ns xgp 

2)创建一个Pod资源对象,使用的是私有仓库中私有镜像,其镜像的下载策略为:NEVER。 Pod的重启策略为: Never.

[root@master ~]# vim pod.yaml
kind: Pod
apiVersion: v1
metadata:
  name: test-pod
  namespace: xgp
  labels:
    app: test-web
spec:
  restartPolicy: Never
  containers:
  - name: www
    image: 192.168.1.21:5000/web:v1
    imagePullPolicy: Never
    args:                   
    - /bin/sh
    - -c
    - sleep 90; exit 1
    ports:
    - protocol: TCP
      containerPort: 80

3)创建出容器之后,执行非正常退出,查看Pod的最终状态。

(1)执行一下上面pod的yaml文件

[root@master ~]# kubectl apply -f pod.yaml 

(2)动态查看ns中test-pod的信息

[root@master ~]# kubectl get pod -n xgp  -w | grep test-pod

删除test-pod

[root@master ~]# kubectl delete pod -n xgp test-pod 

4) 创建一个Service资源对象,与上述Pod对象关联,验证他们的关联性。

(1)修改pod的yaml文件

[root@master ~]# vim pod.yaml
kind: Pod
apiVersion: v1
metadata:
  name: test-pod
  namespace: xgp
  labels:
    app: test-web
spec:
  restartPolicy: Never
  containers:
  - name: www
    image: 192.168.1.21:5000/web:v1
    imagePullPolicy: Never
    ports:
    - protocol: TCP
      containerPort: 80

(1)编写service的yaml文件

[root@master ~]# vim svc.yaml 
apiVersion: v1
kind: Service
metadata:
  name: test-svc
  namespace: xgp
spec:
  selector:
    app: test-web
  ports:
  - port: 80
    targetPort: 80

(2)执行一下

[root@master ~]# kubectl apply -f svc.yaml 

(3)查看一下

[root@master ~]# kubectl get  pod -o wide -n xgp 

(4)访问一下

[root@master ~]# curl 10.244.1.21

看完上述内容,你们对pod资源对象有进一步的了解吗?如果还想学到更多技能或想了解更多相关内容,欢迎关注天达云行业资讯频道,感谢各位的阅读。

返回云计算教程...