patch的类型
kubernetes的patch一般有以下几种:
json patch:在请求中指定操作类型,例如:add、replace,再指定json内容进行操作,请参考:https://tools.ietf.org/html/rfc6902
merge patch:合并操作,可以提交整个资源的信息,与现有信息进行合并后生效,也可以提交部分信息用于替换,请参考:https://tools.ietf.org/html/rfc7386
strategic merge patch:k8s默认的patch类型。json patch和merge patch都遵守rfc标准,但是strategic merge patch却是kubernetes独有的,官方中文文档中称为策略性合并,也是merge的一种,但是真正执行时kubernetes会做合并还是替换是和具体的资源定义相关的(具体策略由 Kubernetes 源代码中字段标记中的 patchStrategy 键的值指定),以Pod的Container为例,下面是其源码:
(源码可以在Github的kubernetes/api下面查看,比如Pod源码在/core/v1/types.go中,Daemonset源码在/apps/v1/types.go中),红框中显示其Container节点的patchStrategy属性是merge,也就是说如果您提交了一份strategic merge patch,里面的内容是关于Pod的Container的,那么原有的Container不会被替换,而是合并(例如以前只有nginx,提交的strategic merge patch是redis,那么最终pod下会有两个container:nginx和redis)。而没有指定patchStrategy属性的则会被替换,比如tolerations就没有指定patchStrategy,那么到时候tolerations的改动就会被直接替换,而不是合并。
通过源码查看资源的patchStrategy属性是很麻烦的事情,因此也可以通过Kubernetes API 文档来查看,如下图,地址是:https://kubernetes.io/docs/reference/generated/kubernetes-api/v1.18/#podspec-v1-core
例子
deployment-patch.yaml
apiVersion: apps/v1 # for versions before 1.9.0 use apps/v1beta2
kind: Deployment
metadata:
name: patch-demo
spec:
replicas: 2
selector:
matchLabels:
app: nginx
template:
metadata:
labels:
app: nginx
spec:
containers:
- name: patch-demo-ctr
image: nginx
tolerations:
- effect: NoSchedule
key: dedicated
value: test-team
创建deployment:
kubectl apply -f deployment-patch.yaml
patch-file-containers.yaml 文件内容:
spec:
template:
spec:
containers:
- name: patch-demo-ctr-2
image: redis
执行patch操作,
kubectl patch deployment patch-demo --patch "$(cat patch-file-containers.yaml)"
kubectl get deployment patch-demo -o yaml
根据之前的分析,默认的patch类型是strategic merge patch,而containers字段指定了patchStrategy属性,因此redis会被合并,此时每个Pod中会有两个容器,一个是原有的nginx,一个是合并过来的redis。
下面是kubectl get deployment patch-demo -o yaml命令的输出结果。
patch-file-tolerations.yaml 文件内容:
spec:
template:
spec:
tolerations:
- effect: NoSchedule
key: dedicated222
value: test-team111111
执行patch操作,
kubectl patch deployment patch-demo --patch "$(cat patch-file-tolerations.yaml)"
kubectl get deployment patch-demo -o yaml
根据之前的分析,默认的patch类型是strategic merge patch,而tolerations字段没有指定patchStrategy属性,因此原来的tolerations字段中的值会被替换。
下面是kubectl get deployment patch-demo -o yaml命令的输出结果。可以看到,原来的tolerations字段的值已经被替换。
参考文章
https://blog.csdn.net/boling_cavalry/article/details/107885697
https://blog.csdn.net/li_101357/article/details/90546907