开发一个禁止删除 Namespace 的控制器

网站建设3年前发布
9 00

​大家好,我是乔克。,昨天收到一个朋友的信息,说不小心把集群的业务namespace干掉了,导致整个业务都停滞了,问我有没有禁止删除namespace的方案。,在我的记忆里,Kubernetes的准入里并没有这个控制器,所以我就给他说需要自己开发一个准入控制器来实现自己的目标。,作为人,何为正确!我不能只脱裤子,不放屁。所以这里也整理了一下如何自定义Kubernetes的准入控制器。,准入控制器(Admission Controller)位于 API Server 中,在对象被持久化之前,准入控制器拦截对 API Server 的请求,一般用来做身份验证和授权。其中包含两个特殊的控制器:MutatingAdmissionWebhook 和 ValidatingAdmissionWebhook。,整个准入控制器的流程如下:,当 API 请求进入时,mutating 和 validating 控制器使用配置中的外部 webhooks 列表并发调用,规则如下:,准入控制器是在 API Server 的启动参数中配置的。一个准入控制器可能属于以上两者中的一种,也可能两者都属于。,我们在部署 Kubernetes 集群的时候都会默认开启一系列准入控制器,如果没有设置这些准入控制器的话可以说你的 Kubernetes 集群就是在裸奔,应该叫管理员为集群添加准入控制器。,在开发之前先大致了解一下准入控制器的Webhook的大致实现逻辑:,AdmissionReview的结构体如下:,从代码的命名中可以很清晰的看出,在请求发送到 WebHook 时我们只需要关注内部的 AdmissionRequest(实际入参),在我们编写的 WebHook 处理完成后只需要返回包含有 AdmissionResponse(实际返回体) 的 AdmissionReview 对象即可;总的来说 AdmissionReview 对象是个套壳,请求是里面的 AdmissionRequest,响应是里面的 AdmissionResponse。,(1)首先创建一个HTTP Server,监听端口,接收请求。,由于准入控制器和Webhook之间需要使用TLS进行通信,所以上面监听的端口是TLS端口,通过server.ListenAndServeTLS实现,后续在部署服务的时候需要把证书挂到相应的目录中。,(2)定义Handler,将请求分发到具体的处理方法。,实现admissionHandler,主要作用是将http body的内容解析成AdmissionReview对象,然后调用具体的Hook处理,再将结果放到AdmissionReview中,返回给客户端。,上面处理是通过hook.Execute来处理请求,这是admissionController内部实现的一个结构体,它为每个操作定义了一个方法,如下:,我们就需要实现具体的AdmitFunc,并注册。,(3)将自己实现的方法注册到Hook中。,(4)实现具体的AdmitFunc。,这里实现很简单,如果Kind为Namespace,就拒绝操作。,上面完成了业务逻辑开发,下面就把它部署到Kubernetes集群测试一番。,(1)编写Dockerfile,将应用打包成镜像,(2)创建TLS证书,使用脚本进行创建。,(3)编写Deployment部署服务。,(4)部署Webhook,这里有一个${CA_BUNDLE}占位符,在创建Webhook的时候要将其替换掉,使用如下命令:,然后创建webhook.yaml即可。,上面的所有文件都在代码库里,可以直接使用脚本进行部署。,执行完成过后,可以查看具体的信息。,(1)首先打开webhook的pod日志。,(2)创建一个namespace并删除。,可以发现我们的删除操作被拒绝了,并且查看namespace还存在。,我们也可以到日志中查看,如下:,上面就是简单的实现了一个准入控制器。,https://www.qikqiak.com/post/k8s-admission-webhook,https://github.com/douglasmakey/admissioncontroller,https://mritd.com/2020/08/19/write-a-dynamic-admission-control-webhook/

© 版权声明

相关文章