mirror of
https://github.com/kyverno/kyverno.git
synced 2025-03-15 20:20:22 +00:00
feat: configure webhook scope based on resource and policy type (#8065)
* feat: configure webhook scope based on policy type Signed-off-by: Florian Hopfensperger <florian.hopfensperger@allianz.de> * Update pkg/controllers/webhook/controller.go Co-authored-by: Charles-Edouard Brétéché <charles.edouard@nirmata.com> Signed-off-by: shuting <shuting@nirmata.com> * feat: configure webhook scope based on resource type Signed-off-by: Florian Hopfensperger <florian.hopfensperger@allianz.de> * review comments Signed-off-by: Florian Hopfensperger <florian.hopfensperger@allianz.de> * sorting of webhooks Signed-off-by: Florian Hopfensperger <florian.hopfensperger@allianz.de> * Update pkg/controllers/webhook/utils.go Signed-off-by: Charles-Edouard Brétéché <charles.edouard@nirmata.com> * fix imports Signed-off-by: Florian Hopfensperger <florian.hopfensperger@allianz.de> --------- Signed-off-by: Florian Hopfensperger <florian.hopfensperger@allianz.de> Signed-off-by: shuting <shuting@nirmata.com> Signed-off-by: Charles-Edouard Brétéché <charles.edouard@nirmata.com> Co-authored-by: shuting <shuting@nirmata.com> Co-authored-by: Charles-Edouard Brétéché <charles.edouard@nirmata.com>
This commit is contained in:
parent
e6c39f31a5
commit
8781a38849
63 changed files with 970 additions and 22 deletions
|
@ -853,6 +853,17 @@ func (c *controller) getLease() (*coordinationv1.Lease, error) {
|
||||||
return c.leaseLister.Leases(config.KyvernoNamespace()).Get("kyverno-health")
|
return c.leaseLister.Leases(config.KyvernoNamespace()).Get("kyverno-health")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// GroupVersionResourceScope adds the resource scope to the GVR
|
||||||
|
type GroupVersionResourceScope struct {
|
||||||
|
schema.GroupVersionResource
|
||||||
|
Scope admissionregistrationv1.ScopeType
|
||||||
|
}
|
||||||
|
|
||||||
|
// String puts / between group/version/resource and scope
|
||||||
|
func (gvs GroupVersionResourceScope) String() string {
|
||||||
|
return gvs.GroupVersion().String() + "/" + gvs.Resource + "/" + string(gvs.Scope)
|
||||||
|
}
|
||||||
|
|
||||||
// mergeWebhook merges the matching kinds of the policy to webhook.rule
|
// mergeWebhook merges the matching kinds of the policy to webhook.rule
|
||||||
func (c *controller) mergeWebhook(dst *webhook, policy kyvernov1.PolicyInterface, updateValidate bool) {
|
func (c *controller) mergeWebhook(dst *webhook, policy kyvernov1.PolicyInterface, updateValidate bool) {
|
||||||
var matchedGVK []string
|
var matchedGVK []string
|
||||||
|
@ -873,31 +884,43 @@ func (c *controller) mergeWebhook(dst *webhook, policy kyvernov1.PolicyInterface
|
||||||
matchedGVK = append(matchedGVK, rule.MatchResources.GetKinds()...)
|
matchedGVK = append(matchedGVK, rule.MatchResources.GetKinds()...)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
var gvrsList []schema.GroupVersionResource
|
var gvrsList []GroupVersionResourceScope
|
||||||
for _, gvk := range matchedGVK {
|
for _, gvk := range matchedGVK {
|
||||||
// NOTE: webhook stores GVR in its rules while policy stores GVK in its rules definition
|
// NOTE: webhook stores GVR in its rules while policy stores GVK in its rules definition
|
||||||
group, version, kind, subresource := kubeutils.ParseKindSelector(gvk)
|
group, version, kind, subresource := kubeutils.ParseKindSelector(gvk)
|
||||||
|
|
||||||
|
// if kind or group is `*` we use the scope of the policy
|
||||||
|
policyScope := admissionregistrationv1.AllScopes
|
||||||
|
if policy.IsNamespaced() {
|
||||||
|
policyScope = admissionregistrationv1.NamespacedScope
|
||||||
|
}
|
||||||
|
|
||||||
// if kind is `*` no need to lookup resources
|
// if kind is `*` no need to lookup resources
|
||||||
if kind == "*" && subresource == "*" {
|
if kind == "*" && subresource == "*" {
|
||||||
gvrsList = append(gvrsList, schema.GroupVersionResource{Group: group, Version: version, Resource: "*/*"})
|
gvrsList = append(gvrsList, GroupVersionResourceScope{GroupVersionResource: schema.GroupVersionResource{Group: group, Version: version, Resource: "*/*"}, Scope: policyScope})
|
||||||
} else if kind == "*" && subresource == "" {
|
} else if kind == "*" && subresource == "" {
|
||||||
gvrsList = append(gvrsList, schema.GroupVersionResource{Group: group, Version: version, Resource: "*"})
|
gvrsList = append(gvrsList, GroupVersionResourceScope{GroupVersionResource: schema.GroupVersionResource{Group: group, Version: version, Resource: "*"}, Scope: policyScope})
|
||||||
} else if kind == "*" && subresource != "" {
|
} else if kind == "*" && subresource != "" {
|
||||||
gvrsList = append(gvrsList, schema.GroupVersionResource{Group: group, Version: version, Resource: "*/" + subresource})
|
gvrsList = append(gvrsList, GroupVersionResourceScope{GroupVersionResource: schema.GroupVersionResource{Group: group, Version: version, Resource: "*/" + subresource}, Scope: policyScope})
|
||||||
} else {
|
} else {
|
||||||
gvrss, err := c.discoveryClient.FindResources(group, version, kind, subresource)
|
gvrss, err := c.discoveryClient.FindResources(group, version, kind, subresource)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
logger.Error(err, "unable to find resource", "group", group, "version", version, "kind", kind, "subresource", subresource)
|
logger.Error(err, "unable to find resource", "group", group, "version", version, "kind", kind, "subresource", subresource)
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
for gvrs := range gvrss {
|
for gvrs, resource := range gvrss {
|
||||||
gvrsList = append(gvrsList, gvrs.GroupVersion.WithResource(gvrs.ResourceSubresource()))
|
resourceScope := admissionregistrationv1.AllScopes
|
||||||
|
if resource.Namespaced {
|
||||||
|
resourceScope = admissionregistrationv1.NamespacedScope
|
||||||
|
}
|
||||||
|
gvrsList = append(gvrsList, GroupVersionResourceScope{GroupVersionResource: gvrs.GroupVersion.WithResource(gvrs.ResourceSubresource()), Scope: resourceScope})
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
for _, gvr := range gvrsList {
|
for _, gvrs := range gvrsList {
|
||||||
dst.set(gvr)
|
dst.set(gvrs)
|
||||||
}
|
}
|
||||||
|
|
||||||
spec := policy.GetSpec()
|
spec := policy.GetSpec()
|
||||||
if spec.WebhookTimeoutSeconds != nil {
|
if spec.WebhookTimeoutSeconds != nil {
|
||||||
if dst.maxWebhookTimeout < *spec.WebhookTimeoutSeconds {
|
if dst.maxWebhookTimeout < *spec.WebhookTimeoutSeconds {
|
||||||
|
|
|
@ -12,26 +12,39 @@ import (
|
||||||
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
|
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
|
||||||
"k8s.io/apimachinery/pkg/runtime/schema"
|
"k8s.io/apimachinery/pkg/runtime/schema"
|
||||||
"k8s.io/apimachinery/pkg/util/sets"
|
"k8s.io/apimachinery/pkg/util/sets"
|
||||||
|
"k8s.io/utils/ptr"
|
||||||
)
|
)
|
||||||
|
|
||||||
// webhook is the instance that aggregates the GVK of existing policies
|
// webhook is the instance that aggregates the GVK of existing policies
|
||||||
// based on kind, failurePolicy and webhookTimeout
|
// based on group, kind, scopeType, failurePolicy and webhookTimeout
|
||||||
type webhook struct {
|
type webhook struct {
|
||||||
maxWebhookTimeout int32
|
maxWebhookTimeout int32
|
||||||
failurePolicy admissionregistrationv1.FailurePolicyType
|
failurePolicy admissionregistrationv1.FailurePolicyType
|
||||||
rules map[schema.GroupVersion]sets.Set[string]
|
rules map[groupVersionScope]sets.Set[string]
|
||||||
|
}
|
||||||
|
|
||||||
|
// groupVersionScope contains the GV and scopeType of a resource
|
||||||
|
type groupVersionScope struct {
|
||||||
|
schema.GroupVersion
|
||||||
|
scopeType admissionregistrationv1.ScopeType
|
||||||
|
}
|
||||||
|
|
||||||
|
// String puts / between group/version and scope
|
||||||
|
func (gvs groupVersionScope) String() string {
|
||||||
|
return gvs.GroupVersion.String() + "/" + string(gvs.scopeType)
|
||||||
}
|
}
|
||||||
|
|
||||||
func newWebhook(timeout int32, failurePolicy admissionregistrationv1.FailurePolicyType) *webhook {
|
func newWebhook(timeout int32, failurePolicy admissionregistrationv1.FailurePolicyType) *webhook {
|
||||||
return &webhook{
|
return &webhook{
|
||||||
maxWebhookTimeout: timeout,
|
maxWebhookTimeout: timeout,
|
||||||
failurePolicy: failurePolicy,
|
failurePolicy: failurePolicy,
|
||||||
rules: map[schema.GroupVersion]sets.Set[string]{},
|
rules: map[groupVersionScope]sets.Set[string]{},
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (wh *webhook) buildRulesWithOperations(ops ...admissionregistrationv1.OperationType) []admissionregistrationv1.RuleWithOperations {
|
func (wh *webhook) buildRulesWithOperations(ops ...admissionregistrationv1.OperationType) []admissionregistrationv1.RuleWithOperations {
|
||||||
var rules []admissionregistrationv1.RuleWithOperations
|
var rules []admissionregistrationv1.RuleWithOperations
|
||||||
|
|
||||||
for gv, resources := range wh.rules {
|
for gv, resources := range wh.rules {
|
||||||
// if we have pods, we add pods/ephemeralcontainers by default
|
// if we have pods, we add pods/ephemeralcontainers by default
|
||||||
if (gv.Group == "" || gv.Group == "*") && (gv.Version == "v1" || gv.Version == "*") && (resources.Has("pods") || resources.Has("*")) {
|
if (gv.Group == "" || gv.Group == "*") && (gv.Version == "v1" || gv.Version == "*") && (resources.Has("pods") || resources.Has("*")) {
|
||||||
|
@ -42,6 +55,7 @@ func (wh *webhook) buildRulesWithOperations(ops ...admissionregistrationv1.Opera
|
||||||
APIGroups: []string{gv.Group},
|
APIGroups: []string{gv.Group},
|
||||||
APIVersions: []string{gv.Version},
|
APIVersions: []string{gv.Version},
|
||||||
Resources: sets.List(resources),
|
Resources: sets.List(resources),
|
||||||
|
Scope: ptr.To(gv.scopeType),
|
||||||
},
|
},
|
||||||
Operations: ops,
|
Operations: ops,
|
||||||
})
|
})
|
||||||
|
@ -67,16 +81,38 @@ func (wh *webhook) buildRulesWithOperations(ops ...admissionregistrationv1.Opera
|
||||||
if x, match := less(a.Resources, b.Resources); match {
|
if x, match := less(a.Resources, b.Resources); match {
|
||||||
return x
|
return x
|
||||||
}
|
}
|
||||||
|
if x := strings.Compare(string(*a.Scope), string(*b.Scope)); x != 0 {
|
||||||
|
return x
|
||||||
|
}
|
||||||
return 0
|
return 0
|
||||||
})
|
})
|
||||||
return rules
|
return rules
|
||||||
}
|
}
|
||||||
|
|
||||||
func (wh *webhook) set(gvrs schema.GroupVersionResource) {
|
func (wh *webhook) set(gvrs GroupVersionResourceScope) {
|
||||||
gv := gvrs.GroupVersion()
|
gvs := groupVersionScope{
|
||||||
resources := wh.rules[gv]
|
GroupVersion: gvrs.GroupVersion(),
|
||||||
|
scopeType: gvrs.Scope,
|
||||||
|
}
|
||||||
|
|
||||||
|
// check if the resource contains wildcard and is already added as all scope
|
||||||
|
// in that case, we do not need to add it again as namespaced scope
|
||||||
|
if (gvrs.Resource == "*" || gvrs.Group == "*") && gvs.scopeType == admissionregistrationv1.NamespacedScope {
|
||||||
|
allScopeResource := groupVersionScope{
|
||||||
|
GroupVersion: gvs.GroupVersion,
|
||||||
|
scopeType: admissionregistrationv1.AllScopes,
|
||||||
|
}
|
||||||
|
resources := wh.rules[allScopeResource]
|
||||||
|
if resources != nil {
|
||||||
|
// explicitly do nothing as the resource is already added as all scope
|
||||||
|
return
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// check if the resource is already added
|
||||||
|
resources := wh.rules[gvs]
|
||||||
if resources == nil {
|
if resources == nil {
|
||||||
wh.rules[gv] = sets.New(gvrs.Resource)
|
wh.rules[gvs] = sets.New(gvrs.Resource)
|
||||||
} else {
|
} else {
|
||||||
resources.Insert(gvrs.Resource)
|
resources.Insert(gvrs.Resource)
|
||||||
}
|
}
|
||||||
|
|
|
@ -15,8 +15,9 @@ func Test_webhook_isEmpty(t *testing.T) {
|
||||||
empty := newWebhook(DefaultWebhookTimeout, admissionregistrationv1.Ignore)
|
empty := newWebhook(DefaultWebhookTimeout, admissionregistrationv1.Ignore)
|
||||||
assert.Equal(t, empty.isEmpty(), true)
|
assert.Equal(t, empty.isEmpty(), true)
|
||||||
notEmpty := newWebhook(DefaultWebhookTimeout, admissionregistrationv1.Ignore)
|
notEmpty := newWebhook(DefaultWebhookTimeout, admissionregistrationv1.Ignore)
|
||||||
notEmpty.set(schema.GroupVersionResource{
|
notEmpty.set(GroupVersionResourceScope{
|
||||||
Group: "", Version: "v1", Resource: "pods",
|
GroupVersionResource: schema.GroupVersionResource{Group: "", Version: "v1", Resource: "pods"},
|
||||||
|
Scope: admissionregistrationv1.NamespacedScope,
|
||||||
})
|
})
|
||||||
assert.Equal(t, notEmpty.isEmpty(), false)
|
assert.Equal(t, notEmpty.isEmpty(), false)
|
||||||
}
|
}
|
||||||
|
|
|
@ -0,0 +1,9 @@
|
||||||
|
## Description
|
||||||
|
|
||||||
|
This test verifies the resource validation webhook is configured correctly when a ClusterPolicy targets all `*` resources.
|
||||||
|
|
||||||
|
## Steps
|
||||||
|
|
||||||
|
1. - Create a ClusterPolicy targeting `*`
|
||||||
|
- Assert ClusterPolicy gets ready
|
||||||
|
1. - Assert that the resource validation webhook is configured correctly and the scope is set to "*"
|
17
test/conformance/chainsaw/webhooks/clusterpolicy/chainsaw-test.yaml
Executable file
17
test/conformance/chainsaw/webhooks/clusterpolicy/chainsaw-test.yaml
Executable file
|
@ -0,0 +1,17 @@
|
||||||
|
apiVersion: chainsaw.kyverno.io/v1alpha1
|
||||||
|
kind: Test
|
||||||
|
metadata:
|
||||||
|
creationTimestamp: null
|
||||||
|
name: clusterpolicy
|
||||||
|
spec:
|
||||||
|
steps:
|
||||||
|
- name: step-01
|
||||||
|
try:
|
||||||
|
- apply:
|
||||||
|
file: policy.yaml
|
||||||
|
- assert:
|
||||||
|
file: policy-assert.yaml
|
||||||
|
- name: step-02
|
||||||
|
try:
|
||||||
|
- assert:
|
||||||
|
file: webhooks.yaml
|
|
@ -18,4 +18,4 @@ webhooks:
|
||||||
resources:
|
resources:
|
||||||
- pods
|
- pods
|
||||||
- pods/ephemeralcontainers
|
- pods/ephemeralcontainers
|
||||||
scope: '*'
|
scope: 'Namespaced'
|
||||||
|
|
|
@ -25,4 +25,4 @@ webhooks:
|
||||||
- pods/portforward
|
- pods/portforward
|
||||||
- pods/proxy
|
- pods/proxy
|
||||||
- pods/status
|
- pods/status
|
||||||
scope: '*'
|
scope: 'Namespaced'
|
||||||
|
|
|
@ -0,0 +1,9 @@
|
||||||
|
## Description
|
||||||
|
|
||||||
|
This test verifies the resource validation webhook is configured correctly when a ClusterPolicy targets CustomResourceDefinition resources and a Policy targets `ConfigMap`.
|
||||||
|
|
||||||
|
## Steps
|
||||||
|
|
||||||
|
1. - Create a policy targeting `*`
|
||||||
|
- Assert policy gets ready
|
||||||
|
1. - Assert that the resource validation webhook is configured correctly two rules for `ConfigMap` and `CustomResourceDefinition` created
|
|
@ -0,0 +1,23 @@
|
||||||
|
apiVersion: chainsaw.kyverno.io/v1alpha1
|
||||||
|
kind: Test
|
||||||
|
metadata:
|
||||||
|
creationTimestamp: null
|
||||||
|
name: policy-clusterpolicy-different-resource-group
|
||||||
|
spec:
|
||||||
|
steps:
|
||||||
|
- name: step-01
|
||||||
|
try:
|
||||||
|
- apply:
|
||||||
|
file: policy-1.yaml
|
||||||
|
- assert:
|
||||||
|
file: policy-1-assert.yaml
|
||||||
|
- name: step-2
|
||||||
|
try:
|
||||||
|
- apply:
|
||||||
|
file: policy-2.yaml
|
||||||
|
- assert:
|
||||||
|
file: policy-2-assert.yaml
|
||||||
|
- name: step-3
|
||||||
|
try:
|
||||||
|
- assert:
|
||||||
|
file: webhooks.yaml
|
|
@ -0,0 +1,9 @@
|
||||||
|
apiVersion: kyverno.io/v1
|
||||||
|
kind: ClusterPolicy
|
||||||
|
metadata:
|
||||||
|
name: policy-1
|
||||||
|
status:
|
||||||
|
conditions:
|
||||||
|
- reason: Succeeded
|
||||||
|
status: "True"
|
||||||
|
type: Ready
|
|
@ -0,0 +1,22 @@
|
||||||
|
apiVersion: kyverno.io/v1
|
||||||
|
kind: ClusterPolicy
|
||||||
|
metadata:
|
||||||
|
name: policy-1
|
||||||
|
annotations:
|
||||||
|
pod-policies.kyverno.io/autogen-controllers: none
|
||||||
|
spec:
|
||||||
|
validationFailureAction: Audit
|
||||||
|
background: false
|
||||||
|
rules:
|
||||||
|
- name: require-team
|
||||||
|
match:
|
||||||
|
any:
|
||||||
|
- resources:
|
||||||
|
kinds:
|
||||||
|
- 'CustomResourceDefinition'
|
||||||
|
validate:
|
||||||
|
message: 'The label `team` is required.'
|
||||||
|
pattern:
|
||||||
|
metadata:
|
||||||
|
labels:
|
||||||
|
team: '?*'
|
|
@ -0,0 +1,9 @@
|
||||||
|
apiVersion: kyverno.io/v1
|
||||||
|
kind: Policy
|
||||||
|
metadata:
|
||||||
|
name: policy-2
|
||||||
|
status:
|
||||||
|
conditions:
|
||||||
|
- reason: Succeeded
|
||||||
|
status: "True"
|
||||||
|
type: Ready
|
|
@ -0,0 +1,22 @@
|
||||||
|
apiVersion: kyverno.io/v1
|
||||||
|
kind: Policy
|
||||||
|
metadata:
|
||||||
|
name: policy-2
|
||||||
|
annotations:
|
||||||
|
pod-policies.kyverno.io/autogen-controllers: none
|
||||||
|
spec:
|
||||||
|
validationFailureAction: Audit
|
||||||
|
background: false
|
||||||
|
rules:
|
||||||
|
- name: require-team
|
||||||
|
match:
|
||||||
|
any:
|
||||||
|
- resources:
|
||||||
|
kinds:
|
||||||
|
- 'ConfigMap'
|
||||||
|
validate:
|
||||||
|
message: 'The label `team` is required.'
|
||||||
|
pattern:
|
||||||
|
metadata:
|
||||||
|
labels:
|
||||||
|
team: '?*'
|
|
@ -0,0 +1,33 @@
|
||||||
|
apiVersion: admissionregistration.k8s.io/v1
|
||||||
|
kind: ValidatingWebhookConfiguration
|
||||||
|
metadata:
|
||||||
|
labels:
|
||||||
|
webhook.kyverno.io/managed-by: kyverno
|
||||||
|
name: kyverno-resource-validating-webhook-cfg
|
||||||
|
webhooks:
|
||||||
|
- failurePolicy: Fail
|
||||||
|
rules:
|
||||||
|
- apiGroups:
|
||||||
|
- ""
|
||||||
|
apiVersions:
|
||||||
|
- v1
|
||||||
|
operations:
|
||||||
|
- CREATE
|
||||||
|
- UPDATE
|
||||||
|
- DELETE
|
||||||
|
- CONNECT
|
||||||
|
resources:
|
||||||
|
- configmaps
|
||||||
|
scope: Namespaced
|
||||||
|
- apiGroups:
|
||||||
|
- apiextensions.k8s.io
|
||||||
|
apiVersions:
|
||||||
|
- v1
|
||||||
|
operations:
|
||||||
|
- CREATE
|
||||||
|
- UPDATE
|
||||||
|
- DELETE
|
||||||
|
- CONNECT
|
||||||
|
resources:
|
||||||
|
- customresourcedefinitions
|
||||||
|
scope: '*'
|
|
@ -0,0 +1,9 @@
|
||||||
|
## Description
|
||||||
|
|
||||||
|
This test verifies the resource validation webhook is configured correctly when a ClusterPolicy targets the `ConfigMap` and `CustomResourceDefinition` resource.
|
||||||
|
|
||||||
|
## Steps
|
||||||
|
|
||||||
|
1. - Create a ClusterPolicy targeting `ConfigMap` and `CustomResourceDefinition`
|
||||||
|
- Assert polices get ready
|
||||||
|
1. - Assert that the resource validation webhook is configured correctly
|
|
@ -0,0 +1,17 @@
|
||||||
|
apiVersion: chainsaw.kyverno.io/v1alpha1
|
||||||
|
kind: Test
|
||||||
|
metadata:
|
||||||
|
creationTimestamp: null
|
||||||
|
name: policy-clusterpolicy-namespaced-clusterscoped-resources
|
||||||
|
spec:
|
||||||
|
steps:
|
||||||
|
- name: step-01
|
||||||
|
try:
|
||||||
|
- apply:
|
||||||
|
file: clusterpolicy.yaml
|
||||||
|
- assert:
|
||||||
|
file: clusterpolicy-assert.yaml
|
||||||
|
- name: step-02
|
||||||
|
try:
|
||||||
|
- assert:
|
||||||
|
file: webhooks.yaml
|
|
@ -0,0 +1,9 @@
|
||||||
|
apiVersion: kyverno.io/v1
|
||||||
|
kind: ClusterPolicy
|
||||||
|
metadata:
|
||||||
|
name: require-labels
|
||||||
|
status:
|
||||||
|
conditions:
|
||||||
|
- reason: Succeeded
|
||||||
|
status: "True"
|
||||||
|
type: Ready
|
|
@ -0,0 +1,23 @@
|
||||||
|
apiVersion: kyverno.io/v1
|
||||||
|
kind: ClusterPolicy
|
||||||
|
metadata:
|
||||||
|
name: require-labels
|
||||||
|
annotations:
|
||||||
|
pod-policies.kyverno.io/autogen-controllers: none
|
||||||
|
spec:
|
||||||
|
validationFailureAction: Audit
|
||||||
|
background: false
|
||||||
|
rules:
|
||||||
|
- name: require-team
|
||||||
|
match:
|
||||||
|
any:
|
||||||
|
- resources:
|
||||||
|
kinds:
|
||||||
|
- 'ConfigMap'
|
||||||
|
- 'CustomResourceDefinition'
|
||||||
|
validate:
|
||||||
|
message: 'The label `team` is required.'
|
||||||
|
pattern:
|
||||||
|
metadata:
|
||||||
|
labels:
|
||||||
|
team: '?*'
|
|
@ -0,0 +1,33 @@
|
||||||
|
apiVersion: admissionregistration.k8s.io/v1
|
||||||
|
kind: ValidatingWebhookConfiguration
|
||||||
|
metadata:
|
||||||
|
labels:
|
||||||
|
webhook.kyverno.io/managed-by: kyverno
|
||||||
|
name: kyverno-resource-validating-webhook-cfg
|
||||||
|
webhooks:
|
||||||
|
- failurePolicy: Fail
|
||||||
|
rules:
|
||||||
|
- apiGroups:
|
||||||
|
- ""
|
||||||
|
apiVersions:
|
||||||
|
- v1
|
||||||
|
operations:
|
||||||
|
- CREATE
|
||||||
|
- UPDATE
|
||||||
|
- DELETE
|
||||||
|
- CONNECT
|
||||||
|
resources:
|
||||||
|
- configmaps
|
||||||
|
scope: Namespaced
|
||||||
|
- apiGroups:
|
||||||
|
- apiextensions.k8s.io
|
||||||
|
apiVersions:
|
||||||
|
- v1
|
||||||
|
operations:
|
||||||
|
- CREATE
|
||||||
|
- UPDATE
|
||||||
|
- DELETE
|
||||||
|
- CONNECT
|
||||||
|
resources:
|
||||||
|
- customresourcedefinitions
|
||||||
|
scope: '*'
|
|
@ -0,0 +1,10 @@
|
||||||
|
## Description
|
||||||
|
|
||||||
|
This test verifies the resource validation webhook is configured correctly when a Policy targets the `Secret` resource and ClusterPolicy targets the `ConfigMap` resource.
|
||||||
|
|
||||||
|
## Steps
|
||||||
|
|
||||||
|
1. - Create a Policy targeting `Secret`
|
||||||
|
- Create a ClusterPolicy targeting `ConfigMap`
|
||||||
|
- Assert polices get ready
|
||||||
|
1. - Assert that the resource validation webhook is configured correctly
|
|
@ -0,0 +1,21 @@
|
||||||
|
apiVersion: chainsaw.kyverno.io/v1alpha1
|
||||||
|
kind: Test
|
||||||
|
metadata:
|
||||||
|
creationTimestamp: null
|
||||||
|
name: policy-clusterpolicy-namespaced-resources
|
||||||
|
spec:
|
||||||
|
steps:
|
||||||
|
- name: step-01
|
||||||
|
try:
|
||||||
|
- apply:
|
||||||
|
file: policy.yaml
|
||||||
|
- apply:
|
||||||
|
file: clusterpolicy.yaml
|
||||||
|
- assert:
|
||||||
|
file: policy-assert.yaml
|
||||||
|
- assert:
|
||||||
|
file: clusterpolicy-assert.yaml
|
||||||
|
- name: step-02
|
||||||
|
try:
|
||||||
|
- assert:
|
||||||
|
file: webhooks.yaml
|
|
@ -0,0 +1,9 @@
|
||||||
|
apiVersion: kyverno.io/v1
|
||||||
|
kind: ClusterPolicy
|
||||||
|
metadata:
|
||||||
|
name: require-labels
|
||||||
|
status:
|
||||||
|
conditions:
|
||||||
|
- reason: Succeeded
|
||||||
|
status: "True"
|
||||||
|
type: Ready
|
|
@ -0,0 +1,22 @@
|
||||||
|
apiVersion: kyverno.io/v1
|
||||||
|
kind: ClusterPolicy
|
||||||
|
metadata:
|
||||||
|
name: require-labels
|
||||||
|
annotations:
|
||||||
|
pod-policies.kyverno.io/autogen-controllers: none
|
||||||
|
spec:
|
||||||
|
validationFailureAction: Audit
|
||||||
|
background: false
|
||||||
|
rules:
|
||||||
|
- name: require-team
|
||||||
|
match:
|
||||||
|
any:
|
||||||
|
- resources:
|
||||||
|
kinds:
|
||||||
|
- 'ConfigMap'
|
||||||
|
validate:
|
||||||
|
message: 'The label `team` is required.'
|
||||||
|
pattern:
|
||||||
|
metadata:
|
||||||
|
labels:
|
||||||
|
team: '?*'
|
|
@ -0,0 +1,9 @@
|
||||||
|
apiVersion: kyverno.io/v1
|
||||||
|
kind: Policy
|
||||||
|
metadata:
|
||||||
|
name: require-labels
|
||||||
|
status:
|
||||||
|
conditions:
|
||||||
|
- reason: Succeeded
|
||||||
|
status: "True"
|
||||||
|
type: Ready
|
|
@ -0,0 +1,22 @@
|
||||||
|
apiVersion: kyverno.io/v1
|
||||||
|
kind: Policy
|
||||||
|
metadata:
|
||||||
|
name: require-labels
|
||||||
|
annotations:
|
||||||
|
pod-policies.kyverno.io/autogen-controllers: none
|
||||||
|
spec:
|
||||||
|
validationFailureAction: Audit
|
||||||
|
background: false
|
||||||
|
rules:
|
||||||
|
- name: require-team
|
||||||
|
match:
|
||||||
|
any:
|
||||||
|
- resources:
|
||||||
|
kinds:
|
||||||
|
- 'Secret'
|
||||||
|
validate:
|
||||||
|
message: 'The label `team` is required.'
|
||||||
|
pattern:
|
||||||
|
metadata:
|
||||||
|
labels:
|
||||||
|
team: '?*'
|
|
@ -0,0 +1,22 @@
|
||||||
|
apiVersion: admissionregistration.k8s.io/v1
|
||||||
|
kind: ValidatingWebhookConfiguration
|
||||||
|
metadata:
|
||||||
|
labels:
|
||||||
|
webhook.kyverno.io/managed-by: kyverno
|
||||||
|
name: kyverno-resource-validating-webhook-cfg
|
||||||
|
webhooks:
|
||||||
|
- failurePolicy: Fail
|
||||||
|
rules:
|
||||||
|
- apiGroups:
|
||||||
|
- ''
|
||||||
|
apiVersions:
|
||||||
|
- 'v1'
|
||||||
|
operations:
|
||||||
|
- CREATE
|
||||||
|
- UPDATE
|
||||||
|
- DELETE
|
||||||
|
- CONNECT
|
||||||
|
resources:
|
||||||
|
- 'configmaps'
|
||||||
|
- 'secrets'
|
||||||
|
scope: 'Namespaced'
|
|
@ -0,0 +1,10 @@
|
||||||
|
## Description
|
||||||
|
|
||||||
|
This test verifies the resource validation webhook is configured correctly when a Policy and ClusterPolicy target the `ConfigMap` resource.
|
||||||
|
|
||||||
|
## Steps
|
||||||
|
|
||||||
|
1. - Create a Policy targeting `ConfigMap`
|
||||||
|
- Create a ClusterPolicy targeting `ConfigMap`
|
||||||
|
- Assert polices get ready
|
||||||
|
1. - Assert that the resource validation webhook is configured correctly
|
|
@ -0,0 +1,21 @@
|
||||||
|
apiVersion: chainsaw.kyverno.io/v1alpha1
|
||||||
|
kind: Test
|
||||||
|
metadata:
|
||||||
|
creationTimestamp: null
|
||||||
|
name: policy-clusterpolicy-same-resource
|
||||||
|
spec:
|
||||||
|
steps:
|
||||||
|
- name: step-01
|
||||||
|
try:
|
||||||
|
- apply:
|
||||||
|
file: policy.yaml
|
||||||
|
- apply:
|
||||||
|
file: clusterpolicy.yaml
|
||||||
|
- assert:
|
||||||
|
file: policy-assert.yaml
|
||||||
|
- assert:
|
||||||
|
file: clusterpolicy-assert.yaml
|
||||||
|
- name: step-02
|
||||||
|
try:
|
||||||
|
- assert:
|
||||||
|
file: webhooks.yaml
|
|
@ -0,0 +1,9 @@
|
||||||
|
apiVersion: kyverno.io/v1
|
||||||
|
kind: ClusterPolicy
|
||||||
|
metadata:
|
||||||
|
name: require-labels
|
||||||
|
status:
|
||||||
|
conditions:
|
||||||
|
- reason: Succeeded
|
||||||
|
status: "True"
|
||||||
|
type: Ready
|
|
@ -0,0 +1,22 @@
|
||||||
|
apiVersion: kyverno.io/v1
|
||||||
|
kind: ClusterPolicy
|
||||||
|
metadata:
|
||||||
|
name: require-labels
|
||||||
|
annotations:
|
||||||
|
pod-policies.kyverno.io/autogen-controllers: none
|
||||||
|
spec:
|
||||||
|
validationFailureAction: Audit
|
||||||
|
background: false
|
||||||
|
rules:
|
||||||
|
- name: require-team
|
||||||
|
match:
|
||||||
|
any:
|
||||||
|
- resources:
|
||||||
|
kinds:
|
||||||
|
- 'ConfigMap'
|
||||||
|
validate:
|
||||||
|
message: 'The label `team` is required.'
|
||||||
|
pattern:
|
||||||
|
metadata:
|
||||||
|
labels:
|
||||||
|
team: '?*'
|
|
@ -0,0 +1,9 @@
|
||||||
|
apiVersion: kyverno.io/v1
|
||||||
|
kind: Policy
|
||||||
|
metadata:
|
||||||
|
name: require-labels
|
||||||
|
status:
|
||||||
|
conditions:
|
||||||
|
- reason: Succeeded
|
||||||
|
status: "True"
|
||||||
|
type: Ready
|
|
@ -0,0 +1,22 @@
|
||||||
|
apiVersion: kyverno.io/v1
|
||||||
|
kind: Policy
|
||||||
|
metadata:
|
||||||
|
name: require-labels
|
||||||
|
annotations:
|
||||||
|
pod-policies.kyverno.io/autogen-controllers: none
|
||||||
|
spec:
|
||||||
|
validationFailureAction: Audit
|
||||||
|
background: false
|
||||||
|
rules:
|
||||||
|
- name: require-team
|
||||||
|
match:
|
||||||
|
any:
|
||||||
|
- resources:
|
||||||
|
kinds:
|
||||||
|
- 'ConfigMap'
|
||||||
|
validate:
|
||||||
|
message: 'The label `team` is required.'
|
||||||
|
pattern:
|
||||||
|
metadata:
|
||||||
|
labels:
|
||||||
|
team: '?*'
|
|
@ -0,0 +1,21 @@
|
||||||
|
apiVersion: admissionregistration.k8s.io/v1
|
||||||
|
kind: ValidatingWebhookConfiguration
|
||||||
|
metadata:
|
||||||
|
labels:
|
||||||
|
webhook.kyverno.io/managed-by: kyverno
|
||||||
|
name: kyverno-resource-validating-webhook-cfg
|
||||||
|
webhooks:
|
||||||
|
- failurePolicy: Fail
|
||||||
|
rules:
|
||||||
|
- apiGroups:
|
||||||
|
- ''
|
||||||
|
apiVersions:
|
||||||
|
- 'v1'
|
||||||
|
operations:
|
||||||
|
- CREATE
|
||||||
|
- UPDATE
|
||||||
|
- DELETE
|
||||||
|
- CONNECT
|
||||||
|
resources:
|
||||||
|
- 'configmaps'
|
||||||
|
scope: 'Namespaced'
|
|
@ -0,0 +1,10 @@
|
||||||
|
## Description
|
||||||
|
|
||||||
|
This test verifies the resource validation webhook is configured correctly when a Policy and ClusterPolicy target all `*` resources.
|
||||||
|
|
||||||
|
## Steps
|
||||||
|
|
||||||
|
1. - Create a Policy targeting `*`
|
||||||
|
- Create a ClusterPolicy targeting `*`
|
||||||
|
- Assert policies get ready
|
||||||
|
1. - Assert that the resource validation webhook is configured correctly
|
|
@ -0,0 +1,21 @@
|
||||||
|
apiVersion: chainsaw.kyverno.io/v1alpha1
|
||||||
|
kind: Test
|
||||||
|
metadata:
|
||||||
|
creationTimestamp: null
|
||||||
|
name: policy-clusterpolicy-wildcard-resource
|
||||||
|
spec:
|
||||||
|
steps:
|
||||||
|
- name: step-01
|
||||||
|
try:
|
||||||
|
- apply:
|
||||||
|
file: policy.yaml
|
||||||
|
- apply:
|
||||||
|
file: clusterpolicy.yaml
|
||||||
|
- assert:
|
||||||
|
file: policy-assert.yaml
|
||||||
|
- assert:
|
||||||
|
file: clusterpolicy-assert.yaml
|
||||||
|
- name: step-02
|
||||||
|
try:
|
||||||
|
- assert:
|
||||||
|
file: webhooks.yaml
|
|
@ -0,0 +1,9 @@
|
||||||
|
apiVersion: kyverno.io/v1
|
||||||
|
kind: ClusterPolicy
|
||||||
|
metadata:
|
||||||
|
name: require-labels
|
||||||
|
status:
|
||||||
|
conditions:
|
||||||
|
- reason: Succeeded
|
||||||
|
status: "True"
|
||||||
|
type: Ready
|
|
@ -0,0 +1,22 @@
|
||||||
|
apiVersion: kyverno.io/v1
|
||||||
|
kind: ClusterPolicy
|
||||||
|
metadata:
|
||||||
|
name: require-labels
|
||||||
|
annotations:
|
||||||
|
pod-policies.kyverno.io/autogen-controllers: none
|
||||||
|
spec:
|
||||||
|
validationFailureAction: Audit
|
||||||
|
background: false
|
||||||
|
rules:
|
||||||
|
- name: require-team
|
||||||
|
match:
|
||||||
|
any:
|
||||||
|
- resources:
|
||||||
|
kinds:
|
||||||
|
- '*'
|
||||||
|
validate:
|
||||||
|
message: 'The label `team` is required.'
|
||||||
|
pattern:
|
||||||
|
metadata:
|
||||||
|
labels:
|
||||||
|
team: '?*'
|
|
@ -0,0 +1,9 @@
|
||||||
|
apiVersion: kyverno.io/v1
|
||||||
|
kind: Policy
|
||||||
|
metadata:
|
||||||
|
name: require-labels
|
||||||
|
status:
|
||||||
|
conditions:
|
||||||
|
- reason: Succeeded
|
||||||
|
status: "True"
|
||||||
|
type: Ready
|
|
@ -0,0 +1,22 @@
|
||||||
|
apiVersion: kyverno.io/v1
|
||||||
|
kind: Policy
|
||||||
|
metadata:
|
||||||
|
name: require-labels
|
||||||
|
annotations:
|
||||||
|
pod-policies.kyverno.io/autogen-controllers: none
|
||||||
|
spec:
|
||||||
|
validationFailureAction: Audit
|
||||||
|
background: false
|
||||||
|
rules:
|
||||||
|
- name: require-team
|
||||||
|
match:
|
||||||
|
any:
|
||||||
|
- resources:
|
||||||
|
kinds:
|
||||||
|
- '*'
|
||||||
|
validate:
|
||||||
|
message: 'The label `team` is required.'
|
||||||
|
pattern:
|
||||||
|
metadata:
|
||||||
|
labels:
|
||||||
|
team: '?*'
|
|
@ -0,0 +1,22 @@
|
||||||
|
apiVersion: admissionregistration.k8s.io/v1
|
||||||
|
kind: ValidatingWebhookConfiguration
|
||||||
|
metadata:
|
||||||
|
labels:
|
||||||
|
webhook.kyverno.io/managed-by: kyverno
|
||||||
|
name: kyverno-resource-validating-webhook-cfg
|
||||||
|
webhooks:
|
||||||
|
- failurePolicy: Fail
|
||||||
|
rules:
|
||||||
|
- apiGroups:
|
||||||
|
- '*'
|
||||||
|
apiVersions:
|
||||||
|
- '*'
|
||||||
|
operations:
|
||||||
|
- CREATE
|
||||||
|
- UPDATE
|
||||||
|
- DELETE
|
||||||
|
- CONNECT
|
||||||
|
resources:
|
||||||
|
- '*'
|
||||||
|
- pods/ephemeralcontainers
|
||||||
|
scope: '*'
|
|
@ -0,0 +1,4 @@
|
||||||
|
## Description
|
||||||
|
|
||||||
|
This test tries to create a Policy which targets a clusterscoped resource.
|
||||||
|
The policy should be rejected.
|
|
@ -0,0 +1,14 @@
|
||||||
|
apiVersion: chainsaw.kyverno.io/v1alpha1
|
||||||
|
kind: Test
|
||||||
|
metadata:
|
||||||
|
creationTimestamp: null
|
||||||
|
name: policy-clusterscope-resource
|
||||||
|
spec:
|
||||||
|
steps:
|
||||||
|
- name: step-01
|
||||||
|
try:
|
||||||
|
- apply:
|
||||||
|
expect:
|
||||||
|
- check:
|
||||||
|
($error != null): true
|
||||||
|
file: policy.yaml
|
|
@ -0,0 +1,22 @@
|
||||||
|
apiVersion: kyverno.io/v1
|
||||||
|
kind: Policy
|
||||||
|
metadata:
|
||||||
|
name: require-labels
|
||||||
|
annotations:
|
||||||
|
pod-policies.kyverno.io/autogen-controllers: none
|
||||||
|
spec:
|
||||||
|
validationFailureAction: Audit
|
||||||
|
background: false
|
||||||
|
rules:
|
||||||
|
- name: require-team
|
||||||
|
match:
|
||||||
|
any:
|
||||||
|
- resources:
|
||||||
|
kinds:
|
||||||
|
- 'CustomResourceDefinition'
|
||||||
|
validate:
|
||||||
|
message: 'The label `team` is required.'
|
||||||
|
pattern:
|
||||||
|
metadata:
|
||||||
|
labels:
|
||||||
|
team: '?*'
|
|
@ -0,0 +1,10 @@
|
||||||
|
## Description
|
||||||
|
|
||||||
|
This test verifies the resource validation webhook is configured correctly when a Policy targets all `*` resources.
|
||||||
|
|
||||||
|
## Steps
|
||||||
|
|
||||||
|
1. - Create a policy targeting `Deployment`
|
||||||
|
Create a policy targeting `Configmap`
|
||||||
|
- Assert policies gets ready
|
||||||
|
1. - Assert that the resource validation webhook is configured correctly and two rules are created with scope is set to "namespaced"
|
|
@ -0,0 +1,23 @@
|
||||||
|
apiVersion: chainsaw.kyverno.io/v1alpha1
|
||||||
|
kind: Test
|
||||||
|
metadata:
|
||||||
|
creationTimestamp: null
|
||||||
|
name: policy-different-resource-group
|
||||||
|
spec:
|
||||||
|
steps:
|
||||||
|
- name: step-01
|
||||||
|
try:
|
||||||
|
- apply:
|
||||||
|
file: policy-1.yaml
|
||||||
|
- assert:
|
||||||
|
file: policy-1-assert.yaml
|
||||||
|
- name: step-2
|
||||||
|
try:
|
||||||
|
- apply:
|
||||||
|
file: policy-2.yaml
|
||||||
|
- assert:
|
||||||
|
file: policy-2-assert.yaml
|
||||||
|
- name: step-3
|
||||||
|
try:
|
||||||
|
- assert:
|
||||||
|
file: webhooks.yaml
|
|
@ -0,0 +1,9 @@
|
||||||
|
apiVersion: kyverno.io/v1
|
||||||
|
kind: Policy
|
||||||
|
metadata:
|
||||||
|
name: policy-1
|
||||||
|
status:
|
||||||
|
conditions:
|
||||||
|
- reason: Succeeded
|
||||||
|
status: "True"
|
||||||
|
type: Ready
|
|
@ -0,0 +1,22 @@
|
||||||
|
apiVersion: kyverno.io/v1
|
||||||
|
kind: Policy
|
||||||
|
metadata:
|
||||||
|
name: policy-1
|
||||||
|
annotations:
|
||||||
|
pod-policies.kyverno.io/autogen-controllers: none
|
||||||
|
spec:
|
||||||
|
validationFailureAction: Audit
|
||||||
|
background: false
|
||||||
|
rules:
|
||||||
|
- name: require-team
|
||||||
|
match:
|
||||||
|
any:
|
||||||
|
- resources:
|
||||||
|
kinds:
|
||||||
|
- 'Deployment'
|
||||||
|
validate:
|
||||||
|
message: 'The label `team` is required.'
|
||||||
|
pattern:
|
||||||
|
metadata:
|
||||||
|
labels:
|
||||||
|
team: '?*'
|
|
@ -0,0 +1,9 @@
|
||||||
|
apiVersion: kyverno.io/v1
|
||||||
|
kind: Policy
|
||||||
|
metadata:
|
||||||
|
name: policy-2
|
||||||
|
status:
|
||||||
|
conditions:
|
||||||
|
- reason: Succeeded
|
||||||
|
status: "True"
|
||||||
|
type: Ready
|
|
@ -0,0 +1,22 @@
|
||||||
|
apiVersion: kyverno.io/v1
|
||||||
|
kind: Policy
|
||||||
|
metadata:
|
||||||
|
name: policy-2
|
||||||
|
annotations:
|
||||||
|
pod-policies.kyverno.io/autogen-controllers: none
|
||||||
|
spec:
|
||||||
|
validationFailureAction: Audit
|
||||||
|
background: false
|
||||||
|
rules:
|
||||||
|
- name: require-team
|
||||||
|
match:
|
||||||
|
any:
|
||||||
|
- resources:
|
||||||
|
kinds:
|
||||||
|
- 'ConfigMap'
|
||||||
|
validate:
|
||||||
|
message: 'The label `team` is required.'
|
||||||
|
pattern:
|
||||||
|
metadata:
|
||||||
|
labels:
|
||||||
|
team: '?*'
|
|
@ -0,0 +1,33 @@
|
||||||
|
apiVersion: admissionregistration.k8s.io/v1
|
||||||
|
kind: ValidatingWebhookConfiguration
|
||||||
|
metadata:
|
||||||
|
labels:
|
||||||
|
webhook.kyverno.io/managed-by: kyverno
|
||||||
|
name: kyverno-resource-validating-webhook-cfg
|
||||||
|
webhooks:
|
||||||
|
- failurePolicy: Fail
|
||||||
|
rules:
|
||||||
|
- apiGroups:
|
||||||
|
- ""
|
||||||
|
apiVersions:
|
||||||
|
- v1
|
||||||
|
operations:
|
||||||
|
- CREATE
|
||||||
|
- UPDATE
|
||||||
|
- DELETE
|
||||||
|
- CONNECT
|
||||||
|
resources:
|
||||||
|
- configmaps
|
||||||
|
scope: Namespaced
|
||||||
|
- apiGroups:
|
||||||
|
- apps
|
||||||
|
apiVersions:
|
||||||
|
- v1
|
||||||
|
operations:
|
||||||
|
- CREATE
|
||||||
|
- UPDATE
|
||||||
|
- DELETE
|
||||||
|
- CONNECT
|
||||||
|
resources:
|
||||||
|
- deployments
|
||||||
|
scope: Namespaced
|
|
@ -1,9 +1,9 @@
|
||||||
## Description
|
## Description
|
||||||
|
|
||||||
This test verifies the resource validation webhook is configured correctly when a policy targets all `*` resources.
|
This test verifies the resource validation webhook is configured correctly when a ClusterPolicy targets all `*` resources.
|
||||||
|
|
||||||
## Steps
|
## Steps
|
||||||
|
|
||||||
1. - Create a policy targeting `*`
|
1. - Create a ClusterPolicy targeting `*`
|
||||||
- Assert policy gets ready
|
- Assert policy gets ready
|
||||||
1. - Assert that the resource validation webhook is configured correctly
|
1. - Assert that the resource validation webhook is configured correctly
|
|
@ -0,0 +1,17 @@
|
||||||
|
apiVersion: chainsaw.kyverno.io/v1alpha1
|
||||||
|
kind: Test
|
||||||
|
metadata:
|
||||||
|
creationTimestamp: null
|
||||||
|
name: policy-wildcard-resource
|
||||||
|
spec:
|
||||||
|
steps:
|
||||||
|
- name: step-01
|
||||||
|
try:
|
||||||
|
- apply:
|
||||||
|
file: policy.yaml
|
||||||
|
- assert:
|
||||||
|
file: policy-assert.yaml
|
||||||
|
- name: step-02
|
||||||
|
try:
|
||||||
|
- assert:
|
||||||
|
file: webhooks.yaml
|
|
@ -0,0 +1,9 @@
|
||||||
|
apiVersion: kyverno.io/v1
|
||||||
|
kind: ClusterPolicy
|
||||||
|
metadata:
|
||||||
|
name: require-labels
|
||||||
|
status:
|
||||||
|
conditions:
|
||||||
|
- reason: Succeeded
|
||||||
|
status: "True"
|
||||||
|
type: Ready
|
|
@ -0,0 +1,22 @@
|
||||||
|
apiVersion: kyverno.io/v1
|
||||||
|
kind: ClusterPolicy
|
||||||
|
metadata:
|
||||||
|
name: require-labels
|
||||||
|
annotations:
|
||||||
|
pod-policies.kyverno.io/autogen-controllers: none
|
||||||
|
spec:
|
||||||
|
validationFailureAction: Audit
|
||||||
|
background: false
|
||||||
|
rules:
|
||||||
|
- name: require-team
|
||||||
|
match:
|
||||||
|
any:
|
||||||
|
- resources:
|
||||||
|
kinds:
|
||||||
|
- '*'
|
||||||
|
validate:
|
||||||
|
message: 'The label `team` is required.'
|
||||||
|
pattern:
|
||||||
|
metadata:
|
||||||
|
labels:
|
||||||
|
team: '?*'
|
|
@ -0,0 +1,22 @@
|
||||||
|
apiVersion: admissionregistration.k8s.io/v1
|
||||||
|
kind: ValidatingWebhookConfiguration
|
||||||
|
metadata:
|
||||||
|
labels:
|
||||||
|
webhook.kyverno.io/managed-by: kyverno
|
||||||
|
name: kyverno-resource-validating-webhook-cfg
|
||||||
|
webhooks:
|
||||||
|
- failurePolicy: Fail
|
||||||
|
rules:
|
||||||
|
- apiGroups:
|
||||||
|
- '*'
|
||||||
|
apiVersions:
|
||||||
|
- '*'
|
||||||
|
operations:
|
||||||
|
- CREATE
|
||||||
|
- UPDATE
|
||||||
|
- DELETE
|
||||||
|
- CONNECT
|
||||||
|
resources:
|
||||||
|
- '*'
|
||||||
|
- pods/ephemeralcontainers
|
||||||
|
scope: '*'
|
9
test/conformance/chainsaw/webhooks/policy/README.md
Normal file
9
test/conformance/chainsaw/webhooks/policy/README.md
Normal file
|
@ -0,0 +1,9 @@
|
||||||
|
## Description
|
||||||
|
|
||||||
|
This test verifies the resource validation webhook is configured correctly when a Policy targets all `*` resources.
|
||||||
|
|
||||||
|
## Steps
|
||||||
|
|
||||||
|
1. - Create a Policy targeting `*`
|
||||||
|
- Assert Policy gets ready
|
||||||
|
1. - Assert that the resource validation webhook is configured correctly and scope is set to "namespaced"
|
|
@ -2,7 +2,7 @@ apiVersion: chainsaw.kyverno.io/v1alpha1
|
||||||
kind: Test
|
kind: Test
|
||||||
metadata:
|
metadata:
|
||||||
creationTimestamp: null
|
creationTimestamp: null
|
||||||
name: wildcard
|
name: policy
|
||||||
spec:
|
spec:
|
||||||
steps:
|
steps:
|
||||||
- name: step-01
|
- name: step-01
|
|
@ -0,0 +1,9 @@
|
||||||
|
apiVersion: kyverno.io/v1
|
||||||
|
kind: Policy
|
||||||
|
metadata:
|
||||||
|
name: require-labels
|
||||||
|
status:
|
||||||
|
conditions:
|
||||||
|
- reason: Succeeded
|
||||||
|
status: "True"
|
||||||
|
type: Ready
|
22
test/conformance/chainsaw/webhooks/policy/policy.yaml
Normal file
22
test/conformance/chainsaw/webhooks/policy/policy.yaml
Normal file
|
@ -0,0 +1,22 @@
|
||||||
|
apiVersion: kyverno.io/v1
|
||||||
|
kind: Policy
|
||||||
|
metadata:
|
||||||
|
name: require-labels
|
||||||
|
annotations:
|
||||||
|
pod-policies.kyverno.io/autogen-controllers: none
|
||||||
|
spec:
|
||||||
|
validationFailureAction: Audit
|
||||||
|
background: false
|
||||||
|
rules:
|
||||||
|
- name: require-team
|
||||||
|
match:
|
||||||
|
any:
|
||||||
|
- resources:
|
||||||
|
kinds:
|
||||||
|
- '*'
|
||||||
|
validate:
|
||||||
|
message: 'The label `team` is required.'
|
||||||
|
pattern:
|
||||||
|
metadata:
|
||||||
|
labels:
|
||||||
|
team: '?*'
|
22
test/conformance/chainsaw/webhooks/policy/webhooks.yaml
Normal file
22
test/conformance/chainsaw/webhooks/policy/webhooks.yaml
Normal file
|
@ -0,0 +1,22 @@
|
||||||
|
apiVersion: admissionregistration.k8s.io/v1
|
||||||
|
kind: ValidatingWebhookConfiguration
|
||||||
|
metadata:
|
||||||
|
labels:
|
||||||
|
webhook.kyverno.io/managed-by: kyverno
|
||||||
|
name: kyverno-resource-validating-webhook-cfg
|
||||||
|
webhooks:
|
||||||
|
- failurePolicy: Fail
|
||||||
|
rules:
|
||||||
|
- apiGroups:
|
||||||
|
- '*'
|
||||||
|
apiVersions:
|
||||||
|
- '*'
|
||||||
|
operations:
|
||||||
|
- CREATE
|
||||||
|
- UPDATE
|
||||||
|
- DELETE
|
||||||
|
- CONNECT
|
||||||
|
resources:
|
||||||
|
- '*'
|
||||||
|
- pods/ephemeralcontainers
|
||||||
|
scope: 'Namespaced'
|
Loading…
Add table
Reference in a new issue