概述

k8s中有需要的资源对象,不同的资源对象负载不同的功能,由多个资源对象相互配合组成可扩展,高可用的集群环境。

在前面已经提到过的一些对象 比如pod ,node ,service, deployment 都属于k8s中的对象。

基本上所有的对象都可以通过kubectl 命令进行增删改查操作。对象的信息是存储在etcd中的。

回忆一下在docker中的一个镜像可以由dockerFile来表示,而k8s中的资源对象也可以由一个一个的文件来表示,这个文件是yml 资源文件。

yml文件介绍

就以一个最简单的pod的文件为例

1
2
3
4
5
6
7
8
9
10
11
12
13
apiVersion: apps/v1
kind: Pod
metadata:
name: web
namespace: default
labels:
name:yweb
spec:
containers:
- name: web
image: tomcat:8.0
ports:
- containerPort:8080

简单说明:

  • apiVersion 和dockercompose 文件类似首先需要声明一个版本主要是为了解决版本升级的兼容性。
  • kind 表示当前的资源类型 比如 service pod namespace
  • metadata 可以定义元数据信息,比如标签等信息
  • sepc .containers 表示容器镜像的相关的定义信息
  • 当我们编写好这样的一个文件后可以使用 kubectl apply -f xx.yml 命令 ,使用定义的资源文件来创建资源
  • 也可以使用命令来生成这样的一个资源模板文件导出后对资源的文件进行修改,然后改成需要的格式

文件格式要求

  • yml 或yaml扩展名
  • 下一层级空出2个空格
  • : 或- 后一个空格

资源文件生成

kubectl create 命令用于生成一个资源,而一个资源的生成伴随着生成一个yml资源文件存储到etcd中,k8s支持试创建一个资源,而不运行,但是可以生成资源文件

示例:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
 //执行此命令创建一个名字为tomcat的部署
kubectl create deploy tomcat --image=tomcat:9.0 -o yaml --dry-run

//将信息输出到文件
kubectl create deploy tomcat --image=tomcat:9.0 -o yaml --dry-run > tomcat.yaml


=====输出信息


apiVersion: apps/v1
kind: Deployment
metadata:
creationTimestamp: null
labels:
app: tomcat
name: tomcat
spec:
replicas: 1
selector:
matchLabels:
app: tomcat
strategy: {}
template:
metadata:
creationTimestamp: null
labels:
app: tomcat
spec:
containers:
- image: tomcat:9.0
name: tomcat
resources: {}
status: {}


参数说明:
-o 输出格式
–dary-run 表示只是打印对象而不向apiServer 发送相关的请求

create 命令支持的操作资源有,具体也可以根据–help 命令查看

kubectl create –help

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
clusterrole         Create a ClusterRole.
clusterrolebinding 为一个指定的 ClusterRole 创建一个 ClusterRoleBinding
configmap 从本地 file, directory 或者 literal value 创建一个 configmap
cronjob Create a cronjob with the specified name.
deployment 创建一个指定名称的 deployment.
job Create a job with the specified name.
namespace 创建一个指定名称的 namespace
poddisruptionbudget 创建一个指定名称的 pod disruption budget.
priorityclass Create a priorityclass with the specified name.
quota 创建一个指定名称的 quota.
role Create a role with single rule.
rolebinding 为一个指定的 Role 或者 ClusterRole创建一个 RoleBinding
secret 使用指定的 subcommand 创建一个 secret
service 使用指定的 subcommand 创建一个 service.
serviceaccount 创建一个指定名称的 service account


node

node 对象简单的说就是物理机器。具有真实的ip ,并且区分master 节点和work节点。master节点用于整个集群的调度和协调,work节点内部的kubelet调用容器api,完成部署,升级等功能。
普通的node节点上包含有

  • kubelet 负载pod的创建,启停等管理
  • kube-proxy 实现k8s service的 通信和网络负载均衡
  • CNI 执行容器引擎,负载容器的创建和管理等
1
2
3
4
5
//查看node
kubectl get nodes -o wide
//查看详细信息
kubectl describe node [nodeName]

pod

在k8s中,部署的最小单位是一个叫做pod的对象,pod中包含了多个容器。(docker 中容器已经是最小的部署单元了)

其中每个pod中都有一个被称为pause 的根容器;其他的容器称为业务容器,业务容器共享pause 容器的网络,挂载,ip等;

pod 结构图

pod 里的多个业务容器共享pause容器的IP,共享pause容器的Volume。相当于pause的容器充当了业务容器的连接和共享的作用。
同时pause 的状态也代表了整个pod的状态,pause容器可以看做一个damon容器。

pod分类

分为普通的pod 和静态pod。主要的区别是是否首调度的统一管理,静态的pod 文件是存储在对应的node节点上的,可以看做是节点上的单独的pod。

静态Pod不需要 API 服务器 监管。比如master 上的api-service ,etcd 的pod都是静态pod。只在特定的节点上。

每一个pod拥有一个ip;后面会详细的介绍pod的相关信息。

1
2
kubectl get pod

pod的资源文件示例:

一般情况下我们不会直接创建pod,pod一般由控制器进行控制。

比如 deployment,satefulset

Replication Controller 和 Replica Set

这2个资源对象,都是用于管理pod的副本数量的.区别是在早期版本的的k8s的使用 Replication Controller 来管理,

不过现在已经不推荐使用Replication Controller 了,而是使用Replica Set ,一般Replica Set 通过deployment 来管理和使用;

replicaSet文件 示例

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
apiVersion: apps/v1
kind: ReplicaSet
metadata:
name: frontend
labels:
app: guestbook
tier: frontend
spec:
# modify replicas according to your case
replicas: 3
selector:
matchLabels:
tier: frontend
template:
metadata:
labels:
tier: frontend
spec:
containers:
- name: php-redis
image: gcr.io/google_samples/gb-frontend:v3

上面是一个replicaSet 文件.定义了版本,类型,标签等信息

replicaSet 的一个关键的属性是 spec.replicas 这个数量就决定了对应的pod的数量。

template 是pod template ,表示pod 的创建信息

那么rc 是如何控制那些pod呢?

是通过 spec.selector.matchLabels 通过标签的选择器 来选定特定标签的pod进行控制。

需要注意的是一般replicaSet 不单独使用,而是由控制器中进行管理使用

1
2
3
//设置副本数量
kubectl scale --replicas=3 rs/foo

namespace

通过 namespace可以对各种资源对象做多租户的区分管理;
默认的namespace 有 kube-system default 等

1
2
3
4
5
6
kubelctl get ns 查看
//过滤指定空间的对象
kubectl get pods -n kube-system
//创建namespace
kubectl create namespace test-namespace

namespace 使用

在创建资源的时候指定namepspace

创建一个自定义namepace的pod

1
2
kubectl run nginx --image=nginx --namespace=test-namespace

1
2
3
4
[root@master ~]# kubectl get pod -n test-namespace
NAME READY STATUS RESTARTS AGE
nginx 1/1 Running 0 47s

namespace切换

当不加 -n的参数的时候,执行命令的时候会使用default 的namespace。那么,当我们需要在不同的namespace中切换的时候,可以设置当前的namespace

当执行

1
2
kubectl get pod 
只显示default 下的数据
1
2
//设置当前的执行的namespace为 test-namespace
kubectl config set-context --current --namespace=test-namespace

再次执行

1
kubectl get pod 

将默认执行test-namespace 下的资源操作

1
kubectl config view | grep namespace:

此命令可以查看当前是在那个namespace下执行。

label 和 annotaion

label 是一个键值对的信息,用于给资源添加标签信息。
通过标签选择器来选择一组管理资源

比如 service 通过nodeSelector 来选择一组pod

annotaion也是key value 对不同的是 lebel 是系统特定标签数据,而 annotaion 可以任意自定义信息;

Deployment

deployment 定义了pod 的生成信息,比如镜像信息。也定义了 Replica Set 信息,设置pod的副本数量,通过修改deployment 完成pod的数量的扩容和缩减。

一般部署一个pod 都通过创建deployment来完成

1
2
kubectl create deploy --image=nginx

实例yml

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
apiVersion: apps/v1
kind: Deployment
metadata:
name: nginx-deployment
labels:
app: nginx
spec:
replicas: 3
selector:
matchLabels:
app: nginx
template:
metadata:
labels:
app: nginx
spec:
containers:
- name: nginx
image: nginx:1.14.2
ports:
- containerPort: 80

可以看到deployment 主要的信息包含:

spec.replicas 即 Replica Set 的关键配置信息;

spec.template 配置了模板pod的信息

spec.selector.matchLabels 表示此deployment的选择的pod的标签选择器配置

当我们需要更新一个deployment的镜像信息的时候,可以使用 kubectl set image

首先查看目前的部署信息

1
kubectl describe deploy  nginx

设置特定版本的镜像

1
kubectl set image deployment/nginx  nginx=nginx:1.17 --record

通过查看新创建的pod的详细信息可以看到镜像信息已经变化.后面会详细说明关于升级或回滚的信息

service

Service服务也是Kubernetes里的核心资源对象之一。

service 可以为一组具有相同功能的容器提供一个统一的入口和负载均衡策略,通过service 来访问一类pod 。

service 的概念很像微服务中的service的概念。属于同一类的服务资源的提供者。因为pod 是随时可能创建,扩容,销毁,所以ip 是一直动态变化的,为了解决这个问题,使用service的来解决同一类pod的访问和负载均衡问题。

​ service 和pod的关系

service 通过标签选择器来定义控制访问的一组pod

示例:

1
2
3
4
5
6
7
8
9
10
11
apiVersion: v1
kind: Service
metadata:
name: my-service
spec:
selector:
app: MyApp
ports:
- protocol: TCP
port: 80
targetPort: 9376

此service 访问将对所有的标签信息为 app:MyApp 的pod 起访问作用;

查看下service信息

1
kubectl get service

会看到每个service 都有一个CLUSTER_IP ,此IP 一旦service 创建将不再改变.

那么通过访问此 CLUSTER_IP :port 将能够访问到对应的映射的pod容器

configMap

保存配置参数的Map是 configmap 资源对象。

configmap 存储在etcd 中;

configMap 主要解决的是服务配置文件的集中存储的问题。

configMap 对象

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
apiVersion: v1
kind: ConfigMap
metadata:
name: game-demo
data:
# 类属性键;每一个键都映射到一个简单的值
player_initial_lives: "3"
ui_properties_file_name: "user-interface.properties"

# 类文件键
game.properties: |
enemy.types=aliens,monsters
player.maximum-lives=5
user-interface.properties: |
color.good=purple
color.bad=yellow
allow.textmode=true

一般configMap优先于应用程序生成,首先上传了configmap 再部署应用程序。后面将详细说明