4.3 使用ReplicaSet而不是ReplicationController
最初,ReplicationController是用于复制和在异常时重新调度节点的唯一Kubernetes组件,后来又引入了一个名为ReplicaSet的类似资源。它是新一代的ReplicationController,并且将其完全替换掉(ReplicationController最终将被弃用)。
你本可以通过创建一个ReplicaSet而不是一个ReplicationController来开始本章,但是笔者觉得从Kubernetes最初提供的组件开始是个好主意。另外,你仍然可以看到使用中的ReplicationController,所以你最好知道它们。也就是说从现在起,你应该始终创建ReplicaSet而不是ReplicationController。它们几乎完全相同,所以你不会碰到任何麻烦。
你通常不会直接创建它们,而是在创建更高层级的Deployment资源时(在第9章中会学到)自动创建它们。无论如何,你应该了解ReplicaSet,所以让我们看看它们与ReplicationController的区别。
4.3.1 比较ReplicaSet和ReplicationController
ReplicaSet的行为与ReplicationController完全相同,但pod选择器的表达能力更强。虽然ReplicationController的标签选择器只允许包含某个标签的匹配pod,但ReplicaSet的选择器还允许匹配缺少某个标签的pod,或包含特定标签名的pod,不管其值如何。
另外,举个例子,单个ReplicationController无法将pod与标签env=production和env=devel同时匹配。它只能匹配带有env=devel标签的pod或带有env=devel标签的pod。但是一个ReplicaSet可以匹配两组pod并将它们视为一个大组。
同样,无论ReplicationController的值如何,ReplicationController都无法仅基于标签名的存在来匹配pod,而ReplicaSet则可以。例如,ReplicaSet可匹配所有包含名为env的标签的pod,无论ReplicaSet的实际值是什么(可以理解为env=*)。
4.3.2 定义ReplicaSet
现在要创建一个ReplicaSet,并看看先前由ReplicationController创建稍后又被抛弃的无主pod,现在如何被ReplicaSet管理。首先,创建一个名为kubia-replicaset.yaml的新文件将你的ReplicationController改写为ReplicaSet,其中包含以下代码清单中的内容。
代码清单4.8 ReplicaSet的YAML定义:kubia-replicaset.yaml
apiVersion: apps/v1
kind: ReplicaSet
metadata:
name: kubia
labels:
app: kubia
tier: frontend
spec:
# modify replicas according to your case
replicas: 3
selector:
matchLabels:
app: kubia #简单的matchLabels选择器
template:
metadata:
labels:
app: kubia
spec: #期望Pod实现的功能(即在pod中部署)
containers:
- name: kubia
image: luksa/kubia:1.0
首先要注意的是ReplicaSet不是v1 API的一部分,因此你需要确保在创建资源时指定正确的apiVersion。你正在创建一个类型为ReplicaSet的资源,它的内容与你之前创建的ReplicationController的内容大致相同。
唯一的区别在选择器中。不必在selector属性中直接列出pod需要的标签,而是在selector.matchLabels下指定它们。这是在ReplicaSet中定义标签选择器的更简单(也更不具表达力)的方式。之后,你会看到表达力更强的选项。
因为你仍然有三个pod匹配从最初运行的 app=kubia
选择器,所以创建此ReplicaSet不会触发创建任何新的pod。ReplicaSet将把它现有的三个pod归为自己的管辖范围。
4.3.3 创建和检查ReplicaSet
使用kubectl create命令根据YAML文件创建ReplicaSet。之后,可以使用 kubectl get
和 kubectl describe
来检查ReplicaSet:
$ kubectl get rs
提示 rs是replicaset的简写。
$ kubectl describe rs
如你所见,ReplicaSet与ReplicationController没有任何区别。显示有三个与选择器匹配的副本。如果列出所有pod,你会发现它们仍然是你以前的三个pod。ReplicaSet没有创建任何新的pod。
4.3.4 使用ReplicaSet的更富表达力的标签选择器
ReplicaSet相对于ReplicationController的主要改进是它更具表达力的标签选择器。之前我们故意在第一个ReplicaSet示例中,用较简单的matchLabels选择器来确认ReplicaSet与ReplicationController没有区别。现在,你将用更强大的matchExpressions属性来重写选择器,如下面的代码清单所示。
代码清单4.9 一个matchExpressions选择器:kubia-replicasetmatchexpressions.yaml
[图片上传失败...(image-f763db-1626307243412)]
注意 仅显示了选择器。你会在本书的代码档案中找到整个ReplicaSet定义。
可以给选择器添加额外的表达式。如示例,每个表达式都必须包含一个key、一个operator(运算符),并且可能还有一个values的列表(取决于运算符)。你会看到四个有效的运算符:
- In:Label的值必须与其中一个指定的values匹配。
- NotIn:Label的值与任何指定的values不匹配。
- Exists:pod必须包含一个指定名称的标签(值不重要)。使用此运算符时,不应指定values字段。
- DoesNotExist:pod不得包含有指定名称的标签。values属性不得指定。
如果你指定了多个表达式,则所有这些表达式都必须为true才能使选择器与pod匹配。如果同时指定matchLabels和matchExpressions,则所有标签都必须匹配,并且所有表达式必须计算为true以使该pod与选择器匹配。
4.3.5 ReplicaSet小结
这是对ReplicaSet的快速介绍,将其作为ReplicationController的替代。请记住,始终使用它而不是ReplicationController,但你仍可以在其他人的部署中找到ReplicationController。
现在,删除ReplicaSet以清理你的集群。可以像删除ReplicationController一样删除ReplicaSet:
$ kubectl delete rs kubia
删除ReplicaSet会删除所有的pod。这种情况下是需要列出pod来确认的。
网友评论