一、前言
很多地方都有 webhook 的概念,就是在需要的地方预留些钩子作为事件的回调通知。不管是 k8s 自带的资源、还是我们声明的 CRD 资源都可以定义对应的 webhook。
二、k8s webhook
k8s 的 webhook 主要有 2 种:mutating-webhook、validating-webhook,前者可以在资源的创建、更新时候修改 yaml 定义的内容(比如设置一些默认值),后者可以对资源进行一些校验。
2.1 创建
kubebuilder create webhook --group webapp --version v1 --kind Guestbook --defaulting --programmatic-validation
上面的命令同时创建 2 种 webhook
- 会将你声明的 webhook 注册到 manager 里面,在 main.go 里面
api/v1/guestbook_webhook.go
里面生成回调的相对应入口,你要你在里面填充相关的代码逻辑。config
里面也会生成 webhook 需要部署声明的一些 yaml(默认生成的 yaml 需要自己调整部分内容)
a. default/kustomization.yaml 里面将../webhook
../certmanager
注释去除
b. certmanager 证书声明的内容要调整
c. webhook manifests.yaml 回调地址如果是部署在集群外的需要调整
2.2 证书认证
根据 K8S文档描述, Kubernetes API Server 通过 HTTPS POST 访问 Webhook Server, 也就是说 Webhook Server 必须要监听在HTTPS协议上。
这边使用 cert-manager 来提供 https 所需要的证书。
证书声明
修改 config/certmanager/certificate.yaml
,当前实验服务是部署在本地,所以证书里面添加了本机的 ip 地址。正常是要填写服务端(webhook-server)的域名
# The following manifests contain a self-signed issuer CR and a certificate CR.
# More document can be found at https://docs.cert-manager.io
# WARNING: Targets CertManager v1.0. Check https://cert-manager.io/docs/installation/upgrading/ for breaking changes.
apiVersion: cert-manager.io/v1
kind: Issuer
metadata:
name: selfsigned-issuer
namespace: system
spec:
selfSigned: {}
---
apiVersion: cert-manager.io/v1
kind: Certificate
metadata:
name: serving-cert # this name should match the one appeared in kustomizeconfig.yaml
namespace: system
spec:
# $(SERVICE_NAME) and $(SERVICE_NAMESPACE) will be substituted by kustomize
commonName: 10.130.161.13
dnsNames:
#- $(SERVICE_NAME).$(SERVICE_NAMESPACE).svc
#- $(SERVICE_NAME).$(SERVICE_NAMESPACE).svc.cluster.local
- 10.130.161.13
ipAddresses:
- 10.130.161.13
issuerRef:
kind: Issuer
name: selfsigned-issuer
secretName: webhook-server-cert # this secret will not be prefixed, since it's not managed by kustomize
2.3 调试
通过webhook 修改资源的参数值
路径:api/v1/guestbook_webhook.go
func (r *Guestbook) Default() {
guestbooklog.Info("default", "name", r.Name)
// 如果参数 == hello a ,就改成 hello b
if r.Spec.Foo == "hello a" {
r.Spec.Foo = "hello b"
}
}
测试
- 通过 kubectl 修改 guestbook 的 spec.foo 值
- 本地服务断点调试,有触发
- 查看值被我们改成
b
了
发表评论 取消回复