1、对于update 请求,需要将整个修改后的对象提交给apiserver,并且apiserver会校验用户提交的resourceVersion是否和当前k8s中这个对象的resourceVersion一致,一致才能接受本次update,否则发生版本冲突。
2、对于patch请求,只需要将对象中某些字段的修改提交给apiserver,并且apiserver 不会考虑版本问题,而是直接将patch打到对象上,然后再更新版本号。
(1)json patch: 需要指定操作类型,且修改列表时要通过元素序号来指定元素;
(2)merge patch:无法单独更新一个列表中的某个元素,会整个覆盖列表;
(3)strategic merge patch: 更新列表时,不需要指定序号,而是以name 作为 key 来计算 merge,同时strategic只适用于原生 K8s 资源以及Aggregated API方式的自定义资源,对于 CRD 定义的资源对象是无法使用的;
(4)apply patch:包括client-side apply和server-side apply,kubectl apply时默认是client-side apply patch,同时kubectl edit也是patch;
– 首先解析用户提交的数据(YAML/JSON)为一个对象 A;然后调用 Get 接口从 K8s 中查询这个资源对象:
– 如果查询结果不存在,kubectl 将本次用户提交的数据记录到对象 A 的 annotation 中(key 为 kubectl.kubernetes.io/last–applied–configuration),最后将对象 A提交给 K8s 创建;
– 如果查询到 K8s 中已有这个资源,假设为对象 B,kubectl 尝试从对象 B 的 annotation 中取出 kubectl.kubernetes.io/last–applied–configuration 的值(对应了上一次 apply 提交的内容);