Example Scenarios
Example: Trigger a PolicyReport
By default, a PolicyReport
object (Namespaced) is created in the same Namespace where resources apply to one or more Kyverno policies, be they Policy
or ClusterPolicy
policies.
A single Kyverno ClusterPolicy exists with a single rule which ensures Pods cannot mount Secrets as environment variables.
1apiVersion: kyverno.io/v1
2kind: ClusterPolicy
3metadata:
4 name: secrets-not-from-env-vars
5spec:
6 background: true
7 validationFailureAction: Audit
8 rules:
9 - name: secrets-not-from-env-vars
10 match:
11 any:
12 - resources:
13 kinds:
14 - Pod
15 validate:
16 message: "Secrets must be mounted as volumes, not as environment variables."
17 pattern:
18 spec:
19 containers:
20 - name: "*"
21 =(env):
22 - =(valueFrom):
23 X(secretKeyRef): "null"
Creating a Pod in this Namespace which does not use any Secrets (and thereby does not violate the secrets-not-from-env-vars
rule in the ClusterPolicy) will generate the first entry in the PolicyReport, but listed as a PASS
.
1$ kubectl run busybox --image busybox:1.28 -- sleep 9999
2pod/busybox created
3
4$ kubectl get po
5NAME READY STATUS RESTARTS AGE
6busybox 1/1 Running 0 66s
7
8$ kubectl get polr
9NAME PASS FAIL WARN ERROR SKIP AGE
10cpol-secrets-not-from-env-vars 1 0 0 0 0 6s
Inspect the PolicyReport in the default
Namespace to view its contents. Notice that the busybox
Pod is listed as having passed.
1$ kubectl get polr cpol-secrets-not-from-env-vars -o yaml
2
3<snipped>
4results:
5- message: validation rule 'secrets-not-from-env-vars' passed.
6 policy: secrets-not-from-env-vars
7 resources:
8 - apiVersion: v1
9 kind: Pod
10 name: busybox
11 namespace: default
12 uid: 0dd94825-cc6e-435b-982b-fb76ac2fdc2a
13 result: pass
14 rule: secrets-not-from-env-vars
15 scored: true
16 source: kyverno
17 timestamp:
18 nanos: 0
19 seconds: 1666097147
20summary:
21 error: 0
22 fail: 0
23 pass: 1
24 skip: 0
25 warn: 0
Create another Pod which violates the rule in the sample policy. Because the rule is written with validationFailureAction: Audit
, resources are allowed to be created which violate the rule. If this occurs, another entry will be created in the PolicyReport which denotes this condition as a FAIL. By contrast, if validationFailureAction: Enforce
and an offending resource was attempted creation, it would be immediately blocked and therefore would not generate another entry in the report. However, if the resource passed then a PASS result would be created in the report.
1apiVersion: v1
2kind: Pod
3metadata:
4 name: secret-pod
5spec:
6 containers:
7 - name: busybox
8 image: busybox:1.28
9 env:
10 - name: SECRET_STUFF
11 valueFrom:
12 secretKeyRef:
13 name: mysecret
14 key: mysecretname
Since the above Pod spec was allowed and it violated the rule, there should now be a failure entry in the PolicyReport in the default
Namespace.
1$ kubectl get polr polr-ns-default -o yaml
2
3<snipped>
4- message: 'validation error: Secrets must be mounted as volumes, not as environment
5 variables. rule secrets-not-from-env-vars failed at path /spec/containers/0/env/0/valueFrom/secretKeyRef/'
6 policy: secrets-not-from-env-vars
7 resources:
8 - apiVersion: v1
9 kind: Pod
10 name: secret-pod
11 namespace: default
12 uid: 72a7422c-fb6f-486f-b274-1ca0de55d49d
13 result: fail
14 rule: secrets-not-from-env-vars
15 scored: true
16 source: kyverno
17 timestamp:
18 nanos: 0
19 seconds: 1666098438
20summary:
21 error: 0
22 fail: 1
23 pass: 1
24 skip: 0
25 warn: 0
Lastly, delete the Pod called secret-pod
and once again check the PolicyReport object.
1$ kubectl delete po secret-pod
2pod "secret-pod" deleted
3
4$ kubectl get polr cpol-secrets-not-from-env-vars
5NAME PASS FAIL WARN ERROR SKIP AGE
6cpol-secrets-not-from-env-vars 1 0 0 0 0 2m21s
Notice how the PolicyReport has removed the previously-failed entry when the violating Pod was deleted.
Example: Trigger a ClusterPolicyReport
A ClusterPolicyReport is the same concept as a PolicyReport only it contains resources which are cluster scoped rather than Namespaced.
As an example, create the following sample ClusterPolicy containing a single rule which validates that all new Namespaces should contain the label called thisshouldntexist
and have some value. Notice how validationFailureAction: Audit
and background: true
in this ClusterPolicy.
1apiVersion: kyverno.io/v1
2kind: ClusterPolicy
3metadata:
4 name: require-ns-labels
5spec:
6 validationFailureAction: Audit
7 background: true
8 rules:
9 - name: check-for-labels-on-namespace
10 match:
11 any:
12 - resources:
13 kinds:
14 - Namespace
15 validate:
16 message: "The label `thisshouldntexist` is required."
17 pattern:
18 metadata:
19 labels:
20 thisshouldntexist: "?*"
After creating this sample ClusterPolicy, check for the existence of a ClusterPolicyReport object.
1$ kubectl get cpolr
2NAME PASS FAIL WARN ERROR SKIP AGE
3cpol-require-ns-labels 0 5 0 0 0 76m
Notice that a ClusterPolicyReport named cpol-require-ns-labels
exists with five failures. The number of combined results here will depend on the number of Namespaces in your cluster. At the moment the policy was created, Kyverno began inspecting existing Namespaces to evaluate them against the policy.
The ClusterPolicyReport, when inspected, has the same structure as the PolicyReport object and contains entries in the results
and summary
objects with the outcomes of a policy audit.
1results:
2- message: 'validation error: The label `thisshouldntexist` is required. rule check-for-labels-on-namespace
3 failed at path /metadata/labels/thisshouldntexist/'
4 policy: require-ns-labels
5 resources:
6 - apiVersion: v1
7 kind: Namespace
8 name: kube-node-lease
9 uid: 06e5056f-76a3-461a-8d45-2793b8bd5bbc
10 result: fail
11 rule: check-for-labels-on-namespace
12 scored: true
13 source: kyverno
14 timestamp:
15 nanos: 0
16 seconds: 1666098654
17- message: 'validation error: The label `thisshouldntexist` is required. rule check-for-labels-on-namespace
18 failed at path /metadata/labels/thisshouldntexist/'
19 policy: require-ns-labels
20 resources:
21 - apiVersion: v1
22 kind: Namespace
23 name: default
24 uid: 4ffe22fd-0927-4ed1-8b04-50ca7ed58626
25 result: fail
26 rule: check-for-labels-on-namespace
27 scored: true
28 source: kyverno
29 timestamp:
30 nanos: 0
31 seconds: 1666098654
32- message: 'validation error: The label `thisshouldntexist` is required. rule check-for-labels-on-namespace
33 failed at path /metadata/labels/thisshouldntexist/'
34 policy: require-ns-labels
35 resources:
36 - apiVersion: v1
37 kind: Namespace
38 name: kyverno
39 uid: 5d87cd66-ce30-4abc-b863-f3b97715a5f1
40 result: fail
41 rule: check-for-labels-on-namespace
42 scored: true
43 source: kyverno
44 timestamp:
45 nanos: 0
46 seconds: 1666098654
47- message: 'validation error: The label `thisshouldntexist` is required. rule check-for-labels-on-namespace
48 failed at path /metadata/labels/thisshouldntexist/'
49 policy: require-ns-labels
50 resources:
51 - apiVersion: v1
52 kind: Namespace
53 name: kube-public
54 uid: c077ee71-435b-4921-9e05-8751fee71b64
55 result: fail
56 rule: check-for-labels-on-namespace
57 scored: true
58 source: kyverno
59 timestamp:
60 nanos: 0
61 seconds: 1666098654
62- message: 'validation error: The label `thisshouldntexist` is required. rule check-for-labels-on-namespace
63 failed at path /metadata/labels/thisshouldntexist/'
64 policy: require-ns-labels
65 resources:
66 - apiVersion: v1
67 kind: Namespace
68 name: kube-system
69 uid: e63fabde-b572-4b07-b899-b2230f4eac69
70 result: fail
71 rule: check-for-labels-on-namespace
72 scored: true
73 source: kyverno
74 timestamp:
75 nanos: 0
76 seconds: 1666098654
77summary:
78 error: 0
79 fail: 5
80 pass: 0
81 skip: 0
82 warn: 0