All Products
Search
Document Center

Container Service for Kubernetes:Use kritis-validation-hook to verify container image signatures

Last Updated:Mar 26, 2026

The kritis-validation-hook component enforces image signature verification at admission time, blocking the deployment of any container image not signed by a trusted authority. This topic demonstrates how to configure and test the component in an ACK cluster.

Prerequisites

Before you begin, make sure you have:

Background

kritis-validation-hook is built on the open source kritisContainer Registry (ACR)Key Management Service (KMS)Security Center software. It integrates with Alibaba Cloud Container Registry (ACR) and supports signature verification for images signed with Alibaba Cloud Key Management Service (KMS). Working together with Security Center, KMS, and ACR, the component provides fully automated image signing and signature verification to help you build a more secure runtime environment.

For information about automatically verifying container image signatures end-to-end, see Use the kritis-validation-hook component to automatically verify container image signatures.

Configure resource access permissions

For kritis-validation-hook to function, the cluster's RAM role must have the following permissions:

"cr:ListInstance",
"cr:ListMetadataOccurrences"
Important

For ACK managed clusters, grant these permissions to the Worker RAM role. For ACK dedicated clusters, grant them to both the Master RAM role and the Worker RAM role.

If the required permissions are missing, add them as follows.

  1. Create a custom policy with the following content. See Step 1: Create a custom policy.

    {
        "Statement": [
            {
                "Action": [
                    "cr:ListInstance",
                    "cr:ListMetadataOccurrences"
                ],
                "Effect": "Allow",
                "Resource": "*"
            }
        ],
        "Version": "1"
    }
  2. Grant the policy to the cluster's Worker RAM role. See Step 2: Grant permissions to the Worker RAM role of the cluster.

    For ACK dedicated clusters, also grant the policy to the Master RAM role.

Enable image signature verification

This example configures image signature verification for the default namespace. Image signing is outside the scope of kritis-validation-hook — this example assumes images are already signed. For signing steps, see Use container image signing.

The example uses the following signing information. Replace the sample values with your actual values.

Signing information Example value How to get YAML field
KMS public key (Base64) LS0tLS1CRUdJTiBQ*** Create an asymmetric key spec.publicKeyData
KMS key ID key-4a2ef103-5aa3-4220-**** Create a key spec.publicKeyId
Witness name demo-aa Configure a witness and a signature verification policy spec.noteReferencenamespaces/demo-aa references the witness named demo-aa
Signed image kritis-demo***.cn-hangzhou.cr.aliyuncs.com/kritis-demo***/alpine@sha256:ddba4d27a7ffc3f86dd6c2f92041af252a1f23a8e742c90e6e1297bfa1bc0c45 N/A N/A

Step 1: Declare the trusted authority

Create a file named AttestationAuthority.yaml with the following content.

apiVersion: kritis.grafeas.io/v1beta1
kind: AttestationAuthority
metadata:
  name: demo-aa
spec:
  noteReference: namespaces/demo-aa
  publicKeyData: LS0tLS1CRUdJTiBQ***
  publicKeyId: key-4a2ef103-5aa3-4220-****

Apply the resource.

kubectl apply -f AttestationAuthority.yaml

Step 2: Create a signature verification policy

Create a file named GenericAttestationPolicy.yaml with the following content. The policy references the AttestationAuthority created in Step 1.

apiVersion: kritis.grafeas.io/v1beta1
kind: GenericAttestationPolicy
metadata:
  name: demo-gap
spec:
  attestationAuthorityNames:
  - demo-aa

Apply the resource.

kubectl apply -f GenericAttestationPolicy.yaml

Step 3: Test with an unsigned image

Deploy an image that has not been signed by the trusted authority.

kubectl create deployment test-denied --image=anolis-registry.cn-zhangjiakou.cr.aliyuncs.com/openanolis/nginx:1.14.1-8.6

Expected output:

error: failed to create deployment: admission webhook "kritis-validation-hook-deployments.grafeas.io" denied the request: "ACROpenAPIError detail: <image anolis-registry.cn-zhangjiakou.cr.aliyuncs.com/openanolis/nginx:1.14.1-8.6 is not attested because of get resource url for anolis-registry.cn-zhangjiakou.cr.aliyuncs.com/openanolis/nginx:1.14.1-8.6: ListInstance failed, instanceName: "anolis", regionId: "cn-zhangjiakou", requstURL:error:****

The admission webhook denies the deployment because the image has no valid attestation from demo-aa.

Step 4: Test with a signed image

Deploy an image that is signed by the trusted authority. Replace the image address with your actual signed image.

kubectl create deployment test-allow --image=kritis-demo***.cn-hangzhou.cr.aliyuncs.com/kritis-demo***/alpine@sha256:ddba4d27a7ffc3f86dd6c2f92041af252a1f23a8e742c90e6e1297bfa1bc0c45

Expected output:

deployment.apps/test-allow created

The deployment succeeds because the image is attested by the trusted authority declared in demo-aa.

Configure an image signature verification allowlist

By default, kritis-validation-hook verifies every container image in its enforcement scope. In middleware or service mesh environments, sidecars injected by third-party components may not be signed, which causes pod creation to fail. Configure an allowlist to skip signature verification for specific images.

Define an admissionallowlists.kritis.grafeas.io resource to specify which images bypass verification.

apiVersion: kritis.grafeas.io/v1beta1   # Default value. Do not modify.
kind: AdmissionAllowlist                # Default value. Do not modify.
metadata:
  name: kritis-allowlist                # Must be unique within the cluster.
spec:
  patterns:                             # Define one or more allowlist entries.
  - namePattern: 'registry*.*.aliyuncs.com/acs/*'
  - namePattern: 'registry-vpc.cn-beijing.aliyuncs.com/arms-docker-repo/*'
    namespace: 'default'    # Optional. If omitted, the entry applies to all namespaces.

namePattern matching rules

Each namePattern value is matched against the full image reference, including registry host, repository path, and tag or digest. The following matching rules apply:

Rule Description Example
Exact match A value without * matches only that exact string. nginx:v0.1.0 matches only nginx:v0.1.0
Trailing * Matches any character except /. a.com/nginx* matches a.com/nginx:v0.1.0 but not a.com/nginx/test:v0.1.0
Mid-string * Matches letters, digits, hyphens (-), and underscores (_). registry-vpc.cn-*.aliyuncs.com/acs/pause:3.2 matches both registry-vpc.cn-hangzhou.aliyuncs.com/acs/pause:3.2 and registry-vpc.cn-beijing.aliyuncs.com/acs/pause:3.2

Add ACK system images to the allowlist

  1. Create a file named kritis-admission-allowlist-acs.yaml with the following content.

    apiVersion: kritis.grafeas.io/v1beta1
    kind: AdmissionAllowlist
    metadata:
      name: allow-acs-images
    spec:
      patterns:
      - namePattern: 'registry*.*.aliyuncs.com/acs/*'
      - namePattern: 'registry-*.ack.aliyuncs.com/acs/*'

    The following table lists common allowlist patterns you can add as needed.

    # Images used by ACK
    - namePattern: 'registry*.*.aliyuncs.com/acs/*'
    - namePattern: 'registry-*.ack.aliyuncs.com/acs/*'
    
    # Images used by ACK (China regions only)
    - namePattern: 'registry*.cn-*.aliyuncs.com/acs/*'
    - namePattern: 'registry-cn-*.ack.aliyuncs.com/acs/*'
    
    # Images used by ARMS
    - namePattern: 'registry*.*.aliyuncs.com/arms-docker-repo/*'
    
    # Images used by ARMS (China regions only)
    - namePattern: 'registry*.cn-*.aliyuncs.com/arms-docker-repo/*'
  2. Apply the allowlist.

    kubectl apply -f kritis-admission-allowlist-acs.yaml

    Expected output:

    admissionallowlist.kritis.grafeas.io/allow-acs-images created
  3. Verify the allowlist is active.

    kubectl get admissionallowlists.kritis.grafeas.io

    Expected output:

    NAME               AGE
    allow-acs-images   2m22s

What's next