Question 23: ImagePolicyWebhook

Problem Statement

Solve this question on: ssh cks4024

Team White created an ImagePolicyWebhook solution at /opt/course/23/webhook on cks4024 which needs to be enabled for the cluster. There is an existing and working webhook-backend Service in Namespace team-white which will be the ImagePolicyWebhook backend.

Tasks:

  1. Create an AdmissionConfiguration at /opt/course/23/webhook/admission-config.yaml with the specified ImagePolicyWebhook configuration
  2. Configure the apiserver to:
    • Mount /opt/course/23/webhook at /etc/kubernetes/webhook
    • Use the AdmissionConfiguration at path /etc/kubernetes/webhook/admission-config.yaml
    • Enable the ImagePolicyWebhook admission plugin
  3. Ensure the ImagePolicyWebhook backend prevents container images containing "danger-danger" from being used
Create a backup of /etc/kubernetes/manifests/kube-apiserver.yaml outside of /etc/kubernetes/manifests so you can revert back in case of issues
Use sudo -i to become root which may be required for this question

Solution

Step 1: Check Existing Webhook Backend

First, let's verify the existing webhook backend:

➜ ssh cks4024

➜ candidate@cks4024:~$ k -n team-white get pod,svc,secret
NAME                                   READY   STATUS    RESTARTS   AGE
pod/webhook-backend-669f74bf8d-2vgnd   1/1     Running   0          18s

NAME                      TYPE        CLUSTER-IP      EXTERNAL-IP   PORT(S)   AGE
service/webhook-backend   ClusterIP   10.111.10.111           443/TCP   67m

NAME                     TYPE                DATA   AGE
secret/webhook-backend   kubernetes.io/tls   2      59s
Step 2: Create AdmissionConfiguration

Create the AdmissionConfiguration file with the specified ImagePolicyWebhook configuration:

➜ candidate@cks4024:~$ sudo -i

➜ root@cks4024:~# vim /opt/course/23/webhook/admission-config.yaml
# cks4024:/opt/course/23/webhook/admission-config.yaml
apiVersion: apiserver.config.k8s.io/v1
kind: AdmissionConfiguration
plugins:
  - name: ImagePolicyWebhook
    configuration:
      imagePolicy:
        kubeConfigFile: /etc/kubernetes/webhook/webhook.yaml
        allowTTL: 10
        denyTTL: 10
        retryBackoff: 20
        defaultAllow: true
Step 3: Configure API Server

First, create a backup of the API server manifest:

➜ root@cks4024:~# cp /etc/kubernetes/manifests/kube-apiserver.yaml ~/s23_kube-apiserver.yaml

Update the API server configuration:

➜ root@cks4024:~# vim /etc/kubernetes/manifests/kube-apiserver.yaml
# cks4024:/etc/kubernetes/manifests/kube-apiserver.yaml
apiVersion: v1
kind: Pod
metadata:
  name: kube-apiserver
  namespace: kube-system
spec:
  containers:
  - command:
    - kube-apiserver
    - --advertise-address=192.168.100.11
    - --allow-privileged=true
    - --authorization-mode=Node,RBAC
    - --client-ca-file=/etc/kubernetes/pki/ca.crt
    - --enable-admission-plugins=NodeRestriction,ImagePolicyWebhook
    - --admission-control-config-file=/etc/kubernetes/webhook/admission-config.yaml
    - --enable-bootstrap-token-auth=true
    - --etcd-cafile=/etc/kubernetes/pki/etcd/ca.crt
    - --etcd-certfile=/etc/kubernetes/pki/apiserver-etcd-client.crt
    - --etcd-keyfile=/etc/kubernetes/pki/apiserver-etcd-client.key
    ...
    volumeMounts:
    - mountPath: /etc/kubernetes/webhook
      name: webhook
      readOnly: true
    ...
  volumes:
  - hostPath:
      path: /opt/course/23/webhook
      type: DirectoryOrCreate
    name: webhook
  ...
Step 4: Verify Configuration

Wait for the API server to restart and verify the webhook is working:

➜ root@cks4024:~# k run test1 --image=something/danger-danger
Error from server (Forbidden): pods "test1" is forbidden: image policy webhook backend denied one or more images: Images containing danger-danger are not allowed

➜ root@cks4024:~# k run test2 --image=nginx:alpine
pod/test2 created

➜ root@cks4024:~# k get pod
NAME                                  READY   STATUS    RESTARTS   AGE
test2                                 1/1     Running   0          7s

Check the webhook backend logs:

➜ root@cks4024:~# k -n team-white logs deploy/webhook-backend
POST request received with body: {"kind":"ImageReview","apiVersion":"imagepolicy.k8s.io/v1alpha1","metadata":{"creationTimestamp":null},"spec":{"containers":[{"image":"something/danger-danger"}],"namespace":"default"},"status":{"allowed":false}}
POST request check image name: something/danger-danger
POST image name FORBIDDEN

POST request received with body: {"kind":"ImageReview","apiVersion":"imagepolicy.k8s.io/v1alpha1","metadata":{"creationTimestamp":null},"spec":{"containers":[{"image":"nginx:alpine"}],"namespace":"default"},"status":{"allowed":false}}
POST request check image name: nginx:alpine
Summary of changes:
  • Created AdmissionConfiguration with ImagePolicyWebhook settings
  • Configured API server to use the webhook
  • Verified webhook prevents images containing "danger-danger"
  • Confirmed other images are allowed
Security Note: ImagePolicyWebhook is a powerful security feature that can prevent the deployment of potentially harmful container images. Always test the configuration thoroughly to ensure it doesn't block legitimate images or affect system components.
Back to Questions List