如何部署自己的webhook admission

如何部署自己的webhook admission_第1张图片

在之前的文章中,我们讲过webhook admission是什么以及如何在代码中实现一个webhook admission。今天我们主要讲下,如何在kubernetes中部署自己的webhook admission。

生成TLS验证的证书

为什么需要TLS验证:

  • 首先API服务器与其他程序通信需要保证安全性,所以他们之间要https加密通信。
  • webhook程序跟API服务器通信的时候可以理解为webhook程序是服务端,所以它要产生公私匙,将公匙交给客户端,让其加密后再发送数据。但是,客户端不知道服务端发公匙是不是伪造的,所以需要一个第三方机构CA进行证书签名。证书签名是使用CA的私匙加密,然后客户端用CA的公匙解密验证证书的真伪。

关于证书这块,可以两种方式实现,分为:

  • 由k8s自带的CA进行签名,因为这样api服务器就可以用自带CA的公匙进行验证。
  • 自己通过cfssl签发。

关于k8s自带的CA签名的,大家可以参照下面的脚本 webhook-create-signed-cert.sh

#!/bin/bash

set -e

usage() {
    cat <> ${tmpdir}/csr.conf
[req]
req_extensions = v3_req
distinguished_name = req_distinguished_name
[req_distinguished_name]
[ v3_req ]
basicConstraints = CA:FALSE
keyUsage = nonRepudiation, digitalSignature, keyEncipherment
extendedKeyUsage = serverAuth
subjectAltName = @alt_names
[alt_names]
DNS.1 = ${service}
DNS.2 = ${service}.${namespace}
DNS.3 = ${service}.${namespace}.svc
EOF

openssl genrsa -out ${tmpdir}/server-key.pem 2048
openssl req -new -key ${tmpdir}/server-key.pem -subj "/CN=${service}.${namespace}.svc" -out ${tmpdir}/server.csr -config ${tmpdir}/csr.conf

# clean-up any previously created CSR for our service. Ignore errors if not present.
kubectl delete csr ${csrName} 2>/dev/null || true

# create  server cert/key CSR and  send to k8s API
cat <&2
    exit 1
fi
echo ${serverCert} | openssl base64 -d -A -out ${tmpdir}/server-cert.pem


# create the secret with CA cert and server cert/key
kubectl create secret generic ${secret} \
        --from-file=key.pem=${tmpdir}/server-key.pem \
        --from-file=cert.pem=${tmpdir}/server-cert.pem \
        --dry-run -o yaml |
    kubectl -n ${namespace} apply -f -

但是有些特殊的托管集群,为了安全的内容,这种签发是行不通的。所以我们可以使用cfssl 自己签发。

安装cfssl

OS X

brew install cfssl

Linux

wget -q --show-progress --https-only --timestamping \\
  https://pkg.cfssl.org/R1.2/cfssl_linux-amd64 \\
  https://pkg.cfssl.org/R1.2/cfssljson_linux-amd64
chmod +x cfssl_linux-amd64 cfssljson_linux-amd64
sudo mv cfssl_linux-amd64 /usr/local/bin/cfssl
sudo mv cfssljson_linux-amd64 /usr/local/bin/cfssljson

创建CA cert

{

cat > ca-config.json < ca-csr.json <

Results:

ca-key.pem
ca.pem

创建 Server Cert

cat > server-csr.json <

PS: 最重要的是 -hostname 的值, {service-name}.{service-namespace}.svc, service-name代表你webhook 的service名字,service-namespace代表你webhook的命名空间。

Results:

server-key.pem
server.pem

创建WebhookConfiguration

Encode and trim the ca cert.

cat ca.pem | base64

Results:

LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSURvRENDQW9pZ0F3SUJBZ0lVVkZ0d2UwR09DMzRvbWppWUV6WGZKaGd4L244d0RRWUpLb1pJaHZjTkFRRUwKQlFBd2FERUxNQWtHQTFVRUJoTUNWVk14RHpBTkJnTlZCQWdUQms5eVpXZHZiakVSTUE4R0ExVUVCeE1JVUc5eQpkR3hoYm1ReEV6QVJCZ05WQkFvVENrdDFZbVZ5Ym1WMFpYTXhDekFKQmdOVkJBc1RBa05CTVJNd0VRWURWUVFECkV3cExkV0psY201bGRHVnpNQjRYRFRJd01EUXlPREEzTWprd01Gb1hEVEkxTURReU56QTNNamt3TUZvd2FERUwKTUFrR0ExVUVCaE1DVlZNeER6QU5CZ05WQkFnVEJrOXlaV2R2YmpFUk1BOEdBMVVFQnhNSVVHOXlkR3hoYm1ReApFekFSQmdOVkJBb1RDa3QxWW1WeWJtVjBaWE14Q3pBSkJnTlZCQXNUQWtOQk1STXdFUVlEVlFRREV3cExkV0psCmNtNWxkR1Z6TUlJQklqQU5CZ2txaGtpRzl3MEJBUUVGQUFPQ0FROEFNSUlCQ2dLQ0FRRUFydkF5Vzd0Umk0Zk8Ka21lQjFQRFhjN1VjeFRrVW1jSDBETkZ6NzJyVXN0cFdsbVV4SDZBRjNEYTRDU3ZpSHgrOUQ4Z2ZBaEdMcFVxSApzVklaT3NqTDVocVNuZzJEVzZRc2VUc3pHcWV1Z3NueFNlZXhLSzlYUi9RUnFmT3VrM3dqZWR3SGM2MU1BdWNBCndkT2h2SGlKQk5KR0NNSlF4ZGpkMTRaVk5KT2o1djJFHpkcWhzbjlXU3Ivc0ptOVFLRitPeTAyenN0MVUKd2NDSVN5dnpyMmJvRm5tbEgvWWVCRVRsTzJXQm95ZDZ0bHk0YmllRVV5Y0hBMzRnc3liUWVZcUFuSzF2S3UragpYVUxZQ3dXMzFwc1lxQTAxNURDbGlIcjgxNG50Q251NVVGYUJwUmtDTkMrM3A5aEU2WjdKRGVKQS9zVnBST3B5CmxWZ0RjTjEyT1FJREFRQUJvMEl3UURBT0JnTlZIUThCQWY4RUJBTUNBUVl3RHdZRFZSMFRBUUgvQkFVd0F3RUIKL3pBZEJnTlZIUTRFRmdRVUpmQVk2aW5uRXEveFdXSE9kOEJBWE9YdktCOHdEUVlKS29aSWh2Y05BUUVMQlFBRApnZ0VCQUFyQjBSZ1hzN1JhSU96Tk40QTFuVFg2d21keTdDaytSVEE4RXo4MkFPQnBJV2w3c2tCMUY1aFhJYWI5CjhvWi9UUzdhZTJuakJuK2lWVWpTbU5qdlM5M3BmRUxMR1lFZ2ZYYnJkdkNibnRDODRnQnlDM2YxSzJwR01zY1oKQ2N4OUUrSTFZekxDdFFQV2dPS0NEb3VJdGJCcmVTOVpodklNUkI2WjE3QW5CYWI1UGJodkNENjVIM0JYNlpsZgprVEJOUldFZFpDS0tBa2ZyUW1QaWVBRVpTbTd6eFFVZi85Rkx0RytkK3JHejAxeHZSUVFkSHZnbUNhSmx5TEE1CkZZbTRNSGtIb3dIa0I3aWxLVUhQc2ZzZ3ZFNlpweFpsdi9BbTVPcFhINllCZ0NuZVBha1c3RjdzanhxWVBUakMKei85RGNSSm5haDcvWXpROWZweFBha1o5c1dzPQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg==

创建webhook config:

cat mutaing.yaml <
kubectl create -f mutating.yaml

此处需要注意:failurePolicy: Fail定义了如何处理 admission webhook 中无法识别的错误和超时错误。允许的值为IgnoreFail

  • Ignore表示调用 webhook 的错误将被忽略并且允许 API 请求继续。
  • Fail表示调用 webhook 的错误导致准入失败并且 API 请求被拒绝。

创建 TLS secret for server

cat server.pem | base64

Result:

LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUVCVENDQXUyZ0F3SUJBZ0lVRUlOL1VvVGpnbWgwN3c2QnBmaDhQeVlCKzdzd0RRWUpLb1pJaHZjTkFRRUwKQlFBd2FERUxNQWtHQTFVRUJoTUNWVk14RHpBTkJnTlZCQWdUQms5eVpXZHZiakVSTUE4R0ExVUVCeE1JVUc5eQpkR3hoYm1ReEV6QVJCZ05WQkFvVENrdDFZbVZ5Ym1WMFpYTXhDekFKQmdOVkJBc1RBa05CTVJNd0VRWURWUVFECkV3cExkV0psY201bGRHVnpNQjRYRFRJd01EUXlPREE1TVRjd01Gb1hEVEl4TURReU9EQTVNVGN3TUZvd2J6RUwKTUFrR0ExVUVCaE1DVlZNeER6QU5CZ05WQkFnVEJrOXlaV2R2YmpFUk1BOEdBMVVFQnhNSVVHOXlkR3hoYm1ReApFekFSQmdOVkJBb1RDa3QxWW1WeWJtVjBaWE14RXpBUkJnTlZCQXNUQ2t0MVltVnlibVYwWlhNeEVqQVFCZ05WCkJBTVRDV0ZrYldsemMybHZiakNDQVNJd0RRWUpLb1pJaHZjTkFRRUJCUUFEZ2dFUEFEQ0NBUW9DZ2dFQkFLQkMKTnF5V3BSc1dmYi8yd3FGeU0vbmo1SGc0ZmJsY2YvQUNPNjFNejV5amIwVDB1NWFHd3pCeWNVMm1sN2ZqaGdscQo3N3BEWGlvaU9OYlY3N2NDNDIzZWV1MXdtajhVeENITDlNTGk5MjlNODBNWDN0NmZHWHVMUDUxTkVpaVY2YUt6Cncya2R4RFYwWklqUTd6YUNwOFExdFpDQXVpbzFzWkdlR205cUJOOHNhZjgvNkQraXRmN1dTUUZKVEt0K2k1ckMKRnVSQXo2ZEdqVmFmd2ZrS1YzeWNoT0IrRitxVm1oV3UyWFJCUjZmMDJESVNNVWFXei9DdUZ1MGpYN3pqcE1yVQpoZCtiU2lsaStodko2RHZYWkd5UUxIMlNuNG95enFSckozQktFcnhuRDBlbDYwRDVjaHUydFR1Q3pHVXhrS1NZCmRzVHNyOVpBRno5QVpFL0JvaHNDQXdFQUFhT0JuekNCbkRBT0JnTlZIUThCQWY4RUJBTUNCYUF3SFFZRFZSMGwKQkJZd0ZBWUlLd1lCQlFVSEF3RUdDQ3NHQVFVRkJ3TUNNQXdHQTFVZEV3RUIvd1FDTUFBd0hRWURWUjBPQkJZRQpGUFlTRTBiOEtKNVphaWpYbnJabjJjalB1dklMTUI4R0ExVWRJd1FZTUJhQUZDWHdHT29wNXhLdjhWbGh6bmZBClFGemw3eWdmTUIwR0ExVWRFUVFXTUJTQ0VtdHRjeTVyZFdKbExXRmtiV2x1TG5OMll6QU5CZ2txaGtpRW9EV2lvd3FWUTJzOUJRSnh2OVZEMEZpdi9Od1JjU2FSZHgrT0tQMHgvCnVyUmlkNHhIVnFBYjFlQ0wwQVF6Skh5MEV6YkU3bjV4NE1aSFhWYnhvdFA1b1RyR1R6T1VuZ0xqeWl0NFZ6UmgKUU9KSlRuVkIwY3MwZFpEVWduWTZ0VGFrSzFJY2d2ZndtVlMzN0FWZmZZcFlSNUdLTG50OGVlWEVwZFlTS1VQOApzdlNCRDRIenBqNGlVd2lLTU9LaGZja05INDM2N1k2S2pOUlhEaHp4OGVnVnp5Q3F6UGhoQWx5NlB0L1FER0ZwCk1RQmo2aFYzaUZ5NlY3UWowc0FZdDVBYzB5bERBT0RqaXc9PQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg==
cat server-key.pem | base64

Result:

LS0tLS1CRUdJTiBSU0EgUFJJVkFURSBLRVktLS0tLQpNSUlFb3dJQkFBS0NBUUVBb0VJMnJKYWxHeFo5di9iQ29YSXorZVBrZURoOXVWeC84QUk3clV6UG5LTnZSUFM3CmxvYkRNSEp4VGFhWHQrT0dDV3J2dWtOZUtpSTQxdFh2dHdMamJkNTY3WENhUHhURUljdjB3dUwzYjB6elF4ZmUKM3A4WmU0cy9uVTBTS0pYcG9yUERhUjNFTlhSa2lORHZOb0tueERXMWtJQzZLald4a1o0YWIyb0UzeXhwL3ovbwpQNksxL3RaSkFVbE1xMzZMbXNJVzVFRFBwMGFOVnAvQitRcFhmSnlFNEg0WDZwV2FGYTdaZEVGSHAvVFlNaEl4ClJwYlA4SzRXN1NOZnZPT2t5dFNGMzV0S0tXTDZHOG5vTzlka2JKQXNmWktmaWpMT3BHc25jRW9TdkdjUFI2WHIKUVBseUc3YTFPNExNWlRHUXBKaDJ4T3l2MWtBWFAwQmtUOEdpR3dJREFRQUJBb0lCQUF3dGUrSVpnR3BTaHpPegpHSThVRW9jR25qSFVlUmxBd2lnR3cyb2owQkxqQ0cyQSsxQXc1VndsRmg4RWJicjNleFAwSUV0VEd6Q3djUWxDCk1Ia0RxeXlLSDJVempVVUYydkdHZ2c3ZEdGaEl6S05vaVBMNXZBSDdUdFl4S1JRVWNEQ0E0SFI0WXBSOVI3WnQKeWYrbVpnRXU0NkViWndvV0Vtd3lTMmZ6OG5MUzJsek9qN1kvbFRPcDJPZnRYZ3Q5WGV4TXR2WXc4alNpVTBmSApJMk9UcG9oYlhvL2hkOThsdDNOei9DZzIrYU4waXRvZzAxZVV3TjY2UHh2MndtQ0VsVUd5cmh4enRyY2FaQVFiCjhqQWVWUUJyUnlpUmZpU1FSTXhTOWRPMGpseXhkdzVvNUs5YzFDMEhvRkxNSEJhVmxHNWpEWWNvVGJ2S0FDSzMKVmUydUdZRUNnWUVBd3QrbnVxYVd1WkFDb3k3Vi9remFRY3EyMWxiOUZxSUlEVTVSQ3Npa3l4WktWVmZRRXBQMQpJREV6TThOL1doSFE2bm5namUwdFBXWnhpQkFzcHM2VTB3V3ViQ0VZdmdnN2wvR3AyS2czODVEeTNDWnAwY3JBCkg3cXIrTlhBR2RRS0FrdDN3UDBuNE1rYk1Jd2k2ckZ1b2lKdW5hMWJ1YmEyNUd5U0hhcXJOREVDZ1lFQTBvYjUKbmRONjJFZzM5bFc1OEZzdEtRaDBYUHZrNlE0UEFYZHN4My9RK3dZeWsweWk3aEpIVHR0MjhCMlRrVmU1Z003VQpOYnRJcGs1eUlaQmdTc0VmMktUZWpjS0hVY3NsbEFDWGFOQkJOVXFpNHltdTc1SGhwajhYc2R3Q2tRRU1ERi9vCjZyYmpyNmpHQXpsVE1McDJGRmcrTllJd3J5MjgwRXIvUWhHbnBBc0NnWUJ5dFZZMC8zUi9mQzZoUWFPRFVsZXoKSEpFdGIvMEFRcFo4eHBuYndDbUl4ZkV4ZFVRc2UxMXgrcVFLRjB5eWh3UXowVlFHRnhObkxoTXNKV0V6T3l6TgpYbTNDaG1UYkQxdU00QnE3UnFIUXhJVEFZL2dzSHEyaXY2NFZCalZTdnNhNWZSVGJ5K2lhWDZhYW1CTEJsWG5yCkJGdWFndjRZUGw0LzdVekJHOEkxTVFLQmdHVU1KQU44M2hteGtDck1PdE1DOEVva4RjdNd09mNDJmNHhEOGRNd3ZwRm1rMFZYOE00cHlITENWQwowQW1rS1VxZlZ6Zmw3VWkrUDhFK3VIeWc1QWVNZ1Y4bktXSEd3RVFMMzhJanZVbEdrWlZkUjhETlV6TW16QjRLCkcwekJBb0dCQUxhQTdOb0ltblg4SFZoL1RRZlcxQ3Y0VytaSjdaNFRnb2FjYnZnd05nelFlNU1aMCt5Z3hsaVMKQ1BVdVBwVVV0ejU3MWhOTjI4Q1J2c2JVZFNxS2xyZ2RubGhONFJpZDAyK243R0h1RWYvZUE1NFZab2dQcURkMApnVVdVdnZiTXljTGFiS0c5dG1lQjQ4Q0xPektDSVlyVzJ6Y2RCK1YyeXdvQ29ZQUlSSnduCi0tLS0tRU5EIFJTQSBQUklWQVRFIEtFWS0tLS0tCg==
cat > secret.yaml <
kubectl create -f mutating.yaml

创建webhook deployment

将TLS密钥作为卷挂载,以便可以在Web服务中使用它来启动HTTPS服务器。

apiVersion: apps/v1
kind: Deployment
metadata:
  name: kms
  namespace: kube-admin
  labels:
    app: kms
spec:
  replicas: 2
  selector:
    matchLabels:
      app: kms
  template:
    metadata:
      labels:
        app: kms
    spec:
      containers:
      - name: kms
        image: xxx/mutation:v0.3.0
        imagePullPolicy: Always
        args:
        - -tlsCertFile=/etc/webhook/certs/cert.pem
        - -tlsKeyFile=/etc/webhook/certs/key.pem
        - -alsologtostderr
        - -v=4
        - 2>&1
        volumeMounts:
        - name: webhook-certs
          mountPath: /etc/webhook/certs
          readOnly: true
      volumes:
      - name: webhook-certs
        secret:
          secretName: kms

创建webhook service

apiVersion: v1
kind: Service
metadata:
  name: kms
  namespace: kube-admin
spec:
  selector:
    app: kms
  ports:
  - protocol: TCP
    port: 443
    targetPort: 443

你可能感兴趣的:(kubernetes,k8s)