mirror of
https://github.com/kyverno/kyverno.git
synced 2025-03-28 18:38:40 +00:00
NK-14: Updated documentation, added examples.
This commit is contained in:
parent
c126da313c
commit
807dc1f23c
45 changed files with 1021 additions and 12 deletions
35
README.md
35
README.md
|
@ -6,13 +6,14 @@ A Kubernetes native policy engine
|
|||
## How it works
|
||||
The solution provides a possibility to validate the custom Kubernetes resources and modify them before their creation.
|
||||
### Components
|
||||
|
||||
* **Policy Controller** (`/controller`) allows defining custom resources which can be used in your Kubernetes cluster
|
||||
* **WebHooks Server** (`/server`) implements the connection between Kubernetes API server and **Mutation WebHook**
|
||||
* **WebHooks Server** (`/server`) implements connection between Kubernetes API server and **Mutation WebHook**
|
||||
* **Mutation WebHook** (`/webhooks`) allows applying Nirmata policies for validation and mutation of the certain types of resources (see the list below)
|
||||
* **Kube Client** (`/kubeclient`) allows other components to communicate with Kubernetes API server for resource management in a cluster
|
||||
* **Initialization functions** (`/init.go`, `/utils`) allow running the controller inside the cluster without deep pre-tuning
|
||||
|
||||
The program initializes the configuration of the client API Cubernetis and creates a HTTPS server with a webhook for resource mutation. When a resource is created in a cluster for various reasons, the Kerbernetes core sends a request for a mutation of this resource to the web hook. The policy controller manages the objects of the politicians created in the cluster and is always aware of what policies are currently in effect: information about the policies is available on the webhook thanks to the policy controller. The request to create a resource contains its full definition. If the resource matches one or more of the current policies, the resource mutates in accordance with them.
|
||||
The program initializes the configuration of the client API Kubernetes and creates an HTTPS server with a webhook for resource mutation. When a resource is created in a cluster for various reasons, the Kerbernetes core sends a request for a mutation of this resource to the webhook. The policy controller manages the objects of the policies created in the cluster and is always aware of which policies are currently in effect: information on the policies is available on the webhook due to the policy controller. The request to create a resource contains its full definition. If the resource matches to one or more of the current policies, the resource is mutated in accordance with them.
|
||||
|
||||
### Policy application
|
||||
|
||||
|
@ -39,13 +40,14 @@ The program initializes the configuration of the client API Cubernetis and creat
|
|||
When a request for a resource creation is received (i.e. a YAML file), it will be checked against the corresponding Nirmata policies.
|
||||
The policy for a resource is looked up either by the resource name, or with the help of selector.
|
||||
In case the data in the YAML file does not conform to the policy, the resource will be mutated with the help of the **Mutation WebHook**, which can perform one of the following:
|
||||
|
||||
* **add**: either add a lacking key and its value or replace a value of the already existing key;
|
||||
* **replace**: either replace a value of the already existing key or add a lacking key and its value;
|
||||
* **remove**: remove an unnecessary key and its value.
|
||||
|
||||
**NOTE**: **add** and **replace** behave in the same way, so they can be used interchangeably. But there is the difference between 'add' and 'replace' operations in case of mutating an array. In this case 'add' operation will add an element to the list 'replace' operation replaces whole list.
|
||||
**NOTE**: **add** and **replace** behave in the same way, so they can be used interchangeably. However, there is the difference between the **add** and **replace** operations when mutating an array. In this case **add** will add an element to the list, whereas **replace** will replace the whole list.
|
||||
|
||||
After the resource YAMP file is validated and mutated, the required object is created in the Kubernetes cluster.
|
||||
After the resource YAML file is mutated, the required object is created in the Kubernetes cluster.
|
||||
|
||||
## Examples
|
||||
|
||||
|
@ -80,14 +82,19 @@ spec :
|
|||
```
|
||||
|
||||
In the **name** parameter, you should specify the policy name.
|
||||
The **failurePolicy** parameter is optional. It is set to **stopOnError** by default. Other possible value is **continueOnError**. If **continueOnError** is specified, the resource will be created despite the errors occured in web hook.
|
||||
The **rules** section consists of mandatory **resource** sub-section and optional **patch** sub-section.
|
||||
|
||||
The **failurePolicy** parameter is optional. It is set to **stopOnError** by default. Other possible value is **continueOnError**. If **continueOnError** is specified, the resource will be created despite the errors that may have occurred in the webhook.
|
||||
|
||||
The **rules** section consists of the mandatory **resource** sub-section and an optional **patch** sub-section.
|
||||
|
||||
The **resource** sub-section defines to which kind of the supported resources a Nirmata policy has to be applied:
|
||||
|
||||
* In the **kind** parameter, you should specify the resource type. You can find the list of the supported types in the **How it works** section.
|
||||
* In the **name** parameter, you should specify the name of the resource the policy has to be applied to. This parameter can be omitted if **selector** is specified.
|
||||
* In the **selector** parameter, you should specify conditions based on which the resources will be chosen for the policy to be applied to. This parameter is optional if **name** is specified.
|
||||
|
||||
The **patch** sub-section defines what needs to be changed (i.e. mutated) before resource creation can take place. This section contains multiple entries of the path, operation, and value.
|
||||
|
||||
* In the **path** parameter, you should specify the required path.
|
||||
* In the **op** parameter, you should specify the required operation (Add | Replace | Delete).
|
||||
* In the **value** parameter, you should specify either a number, a YAML string, or text.
|
||||
|
@ -127,12 +134,16 @@ spec :
|
|||
name: some-other-secrets
|
||||
data: # data is optional
|
||||
```
|
||||
The **rules** section in this example have mandatory **resource** sub-section, additional **secretGenerator** and **configMapGenerator** sub-sections, and has no and optional **patch** sub-section.
|
||||
**configMapGenerator** sub-section defines the contents of the config-map which will be created in future namespace.
|
||||
**copyFrom** contains information about template config-map. **data** describes the contents of created config-map. **copyFrom** and **data** are optional, but at least one of these fields must be specified. If both the **copyFrom** and the **data** are specified, then the template **copyFrom** will be used for the configuration, and then the specified **data** will be added to config-map.
|
||||
**secretGenerator** acts exactly as **configMapGenerator**, but creates the secret insted of config-map.
|
||||
In this example, the **rules** section has the mandatory **resource** sub-section, additional **secretGenerator** and **configMapGenerator** sub-sections, and no optional **patch** sub-section.
|
||||
|
||||
The **configMapGenerator** sub-section defines the contents of the config-map which will be created in the future namespace.
|
||||
|
||||
The **copyFrom** parameter contains information about template config-map. The **data** parameter describes the contents of the created config-map. **copyFrom** and **data** are optional, but at least one of these fields must be specified. If both **copyFrom** and **data** are specified, then the template **copyFrom** will be used for the configuration, and then the specified **data** will be added to the config-map.
|
||||
|
||||
**secretGenerator** acts exactly as **configMapGenerator**, but creates a secret instead of the config-map.
|
||||
|
||||
### More examples
|
||||
An example of a policy that uses all available features: `definitions/policy-example.yaml`.
|
||||
See the contents of `/examples`: there are definitions and policies for every supported type of resource.
|
||||
|
||||
# Build
|
||||
|
@ -140,7 +151,7 @@ See the contents of `/examples`: there are definitions and policies for every su
|
|||
## Prerequisites
|
||||
|
||||
You need to have the go and dep utils installed on your machine.
|
||||
Ensure that GOPATH environment variable is set to the desired location.
|
||||
Ensure that the GOPATH environment variable is set to the desired location.
|
||||
Code generation for the CRD controller depends on kubernetes/hack, so before using code generation, execute:
|
||||
|
||||
`go get k8s.io/kubernetes/hack`
|
||||
|
@ -188,4 +199,4 @@ _At the time of creation of these instructions, only this installation method wo
|
|||
## For production
|
||||
|
||||
_To be implemented_
|
||||
The scripts for "development installation method" will be moved to the controller's code. The solution will perform the preparation inside the cluster automatically. Yuo should be able to use `definitions/install.yaml` to install the controller.
|
||||
The scripts for "development installation method" will be moved to the controller's code. The solution will perform the preparation inside the cluster automatically.
|
14
examples/ConfigMap/configMap.yaml
Normal file
14
examples/ConfigMap/configMap.yaml
Normal file
|
@ -0,0 +1,14 @@
|
|||
apiVersion: v1
|
||||
kind: ConfigMap
|
||||
metadata:
|
||||
name: game-config
|
||||
namespace: default
|
||||
data:
|
||||
secretData: "very sensitive data"
|
||||
secretDatatoreplace: "data is not changed"
|
||||
game.properties: |
|
||||
enemies=aliens
|
||||
lives=3
|
||||
ui.properties: |
|
||||
color.good=purple
|
||||
color.bad=yellow
|
19
examples/ConfigMap/policy-ConfigMap.yaml
Normal file
19
examples/ConfigMap/policy-ConfigMap.yaml
Normal file
|
@ -0,0 +1,19 @@
|
|||
apiVersion : policy.nirmata.io/v1alpha1
|
||||
kind : Policy
|
||||
metadata :
|
||||
name : policy-test
|
||||
spec :
|
||||
failurePolicy: stopOnError
|
||||
rules:
|
||||
- resource:
|
||||
kind : ConfigMap
|
||||
name: "game-config"
|
||||
patch:
|
||||
- path : "/data/newKey"
|
||||
op : add
|
||||
value : newValue
|
||||
- path : "/data/secretData"
|
||||
op : remove
|
||||
- path : "/data/secretDatatoreplace"
|
||||
op : replace
|
||||
value : "data is replaced"
|
20
examples/ConfigMapGenerator,SecretGenerator/configMap.yaml
Normal file
20
examples/ConfigMapGenerator,SecretGenerator/configMap.yaml
Normal file
|
@ -0,0 +1,20 @@
|
|||
apiVersion: v1
|
||||
kind: ConfigMap
|
||||
metadata:
|
||||
name: game-config
|
||||
namespace: default
|
||||
labels:
|
||||
originalLabel : isHere
|
||||
data:
|
||||
ui.properties : |
|
||||
color.good=green
|
||||
color.bad=red
|
||||
|
||||
game.properties : |
|
||||
enemies=predators
|
||||
lives=3
|
||||
|
||||
configmap.data: |
|
||||
ns=default
|
||||
labels=originalLabel
|
||||
labelscount=1
|
|
@ -0,0 +1,7 @@
|
|||
kind: Namespace
|
||||
apiVersion: v1
|
||||
metadata:
|
||||
name: "ns2"
|
||||
labels:
|
||||
LabelForSelector : "namespace2"
|
||||
|
|
@ -0,0 +1,83 @@
|
|||
# This is a test-policy with patch, configMapGenerator with and without "copyFrom" option,
|
||||
# secretGenerator with and without "copyFrom" option.
|
||||
# To apply this policy you need to create secret and configMap in "default" namespace
|
||||
# and then create a namespace
|
||||
|
||||
apiVersion : policy.nirmata.io/v1alpha1
|
||||
kind : Policy
|
||||
metadata :
|
||||
name : "policy-ns-patch-cmg-sg"
|
||||
spec :
|
||||
failurePolicy: stopOnError
|
||||
rules:
|
||||
- resource :
|
||||
kind : Namespace
|
||||
selector:
|
||||
matchLabels:
|
||||
LabelForSelector : "namespace2"
|
||||
patch:
|
||||
- path: "/metadata/labels/isMutatedByPolicy"
|
||||
op: add
|
||||
value: "true"
|
||||
|
||||
- resource :
|
||||
kind : Namespace
|
||||
selector:
|
||||
matchLabels:
|
||||
LabelForSelector : "namespace2"
|
||||
configMapGenerator :
|
||||
name : copied-cm
|
||||
copyFrom :
|
||||
namespace : default
|
||||
name : game-config
|
||||
data :
|
||||
secretData: "data from cmg"
|
||||
|
||||
- resource :
|
||||
kind : Namespace
|
||||
selector:
|
||||
matchLabels:
|
||||
LabelForSelector : "namespace2"
|
||||
configMapGenerator :
|
||||
name : generated-cm
|
||||
data :
|
||||
secretData: "very sensitive data from cmg"
|
||||
database: mongodb
|
||||
database_uri: mongodb://localhost:27017
|
||||
|
||||
keys: |
|
||||
image.public.key=771
|
||||
rsa.public.key=42
|
||||
|
||||
- resource :
|
||||
kind : Namespace
|
||||
selector:
|
||||
matchLabels:
|
||||
LabelForSelector : "namespace2"
|
||||
|
||||
secretGenerator :
|
||||
name : generated-secrets
|
||||
data :
|
||||
foo : bar
|
||||
app.properties : /
|
||||
foo1=bar1
|
||||
foo2=bar2
|
||||
ui.properties : /
|
||||
foo1=bar1
|
||||
foo2=bar2
|
||||
|
||||
- resource :
|
||||
kind : Namespace
|
||||
selector:
|
||||
matchLabels:
|
||||
LabelForSelector : "namespace2"
|
||||
|
||||
secretGenerator :
|
||||
name : copied-secrets
|
||||
copyFrom :
|
||||
namespace : default
|
||||
name : mysecret
|
||||
data :
|
||||
foo : bar
|
||||
secretData: "data from sg"
|
||||
|
10
examples/ConfigMapGenerator,SecretGenerator/secrets.yaml
Normal file
10
examples/ConfigMapGenerator,SecretGenerator/secrets.yaml
Normal file
|
@ -0,0 +1,10 @@
|
|||
apiVersion: v1
|
||||
kind: Secret
|
||||
metadata:
|
||||
name: mysecret
|
||||
labels:
|
||||
originalLabel : isHere
|
||||
type: Opaque
|
||||
data:
|
||||
username: dXNlcg==
|
||||
password: cGFzc3dvcmQ=
|
21
examples/CronJob/cronjob.yaml
Normal file
21
examples/CronJob/cronjob.yaml
Normal file
|
@ -0,0 +1,21 @@
|
|||
apiVersion: batch/v1beta1
|
||||
kind: CronJob
|
||||
metadata:
|
||||
name: hello
|
||||
labels :
|
||||
label : "original"
|
||||
|
||||
spec:
|
||||
schedule: "*/1 * * * *"
|
||||
jobTemplate:
|
||||
spec:
|
||||
template:
|
||||
spec:
|
||||
containers:
|
||||
- name: hello
|
||||
image: busybox
|
||||
args:
|
||||
- /bin/sh
|
||||
- -c
|
||||
- date; echo Hello from the Kubernetes cluster
|
||||
restartPolicy: OnFailure
|
20
examples/CronJob/policy-CronJob.yaml
Normal file
20
examples/CronJob/policy-CronJob.yaml
Normal file
|
@ -0,0 +1,20 @@
|
|||
apiVersion : policy.nirmata.io/v1alpha1
|
||||
kind : Policy
|
||||
metadata :
|
||||
name : policy-cronjob
|
||||
|
||||
spec :
|
||||
failurePolicy: stopOnError
|
||||
rules:
|
||||
- resource:
|
||||
kind : CronJob
|
||||
name: "hello"
|
||||
patch:
|
||||
- path: "/metadata/labels/isMutated"
|
||||
op: add
|
||||
value: "true"
|
||||
- path : "/spec/schedule"
|
||||
op : replace
|
||||
value : "* */1 * * *"
|
||||
|
||||
|
43
examples/DaemonSet/DaemonSet.yaml
Normal file
43
examples/DaemonSet/DaemonSet.yaml
Normal file
|
@ -0,0 +1,43 @@
|
|||
apiVersion: apps/v1
|
||||
kind: DaemonSet
|
||||
metadata:
|
||||
name: fluentd-elasticsearch
|
||||
namespace: kube-system
|
||||
labels:
|
||||
k8s-app: fluentd-logging
|
||||
originalLabel : isHere
|
||||
spec:
|
||||
selector:
|
||||
matchLabels:
|
||||
name: fluentd-elasticsearch
|
||||
template:
|
||||
metadata:
|
||||
labels:
|
||||
name: fluentd-elasticsearch
|
||||
spec:
|
||||
tolerations:
|
||||
- key: node-role.kubernetes.io/master
|
||||
effect: NoSchedule
|
||||
containers:
|
||||
- name: fluentd-elasticsearch
|
||||
image: k8s.gcr.io/fluentd-elasticsearch:1.20
|
||||
resources:
|
||||
limits:
|
||||
memory: 200Mi
|
||||
requests:
|
||||
cpu: 100m
|
||||
memory: 200Mi
|
||||
volumeMounts:
|
||||
- name: varlog
|
||||
mountPath: /var/log
|
||||
- name: varlibdockercontainers
|
||||
mountPath: /var/lib/docker/containers
|
||||
readOnly: true
|
||||
terminationGracePeriodSeconds: 30
|
||||
volumes:
|
||||
- name: varlog
|
||||
hostPath:
|
||||
path: /var/log
|
||||
- name: varlibdockercontainers
|
||||
hostPath:
|
||||
path: /var/lib/docker/containers
|
21
examples/DaemonSet/policy-ds.yaml
Normal file
21
examples/DaemonSet/policy-ds.yaml
Normal file
|
@ -0,0 +1,21 @@
|
|||
apiVersion : policy.nirmata.io/v1alpha1
|
||||
kind : Policy
|
||||
metadata :
|
||||
name : policy-daemonset
|
||||
spec :
|
||||
failurePolicy: stopOnError
|
||||
rules:
|
||||
- resource:
|
||||
kind : DaemonSet
|
||||
selector:
|
||||
matchLabels:
|
||||
originalLabel: isHere
|
||||
patch:
|
||||
- path: "/metadata/labels/isMutated"
|
||||
op: add
|
||||
value: "true"
|
||||
- path: "/metadata/labels/originalLabel"
|
||||
op: remove
|
||||
- path : "/spec/template/spec/containers/0/image"
|
||||
op : replace
|
||||
value: "k8s.gcr.io/fluentd-elasticsearch:latest"
|
34
examples/Deployment/ghost-deployment.yaml
Normal file
34
examples/Deployment/ghost-deployment.yaml
Normal file
|
@ -0,0 +1,34 @@
|
|||
kind: "Deployment"
|
||||
apiVersion: "extensions/v1beta1"
|
||||
metadata:
|
||||
name: "ghost"
|
||||
labels:
|
||||
nirmata.io/deployment.name: "ghost"
|
||||
nirmata.io/application.name: "ghost"
|
||||
nirmata.io/component: "ghost"
|
||||
spec:
|
||||
replicas: 1
|
||||
revisionHistoryLimit: 5
|
||||
selector:
|
||||
matchLabels:
|
||||
nirmata.io/application.name: "ghost"
|
||||
nirmata.io/component: "ghost"
|
||||
strategy:
|
||||
type: "RollingUpdate"
|
||||
rollingUpdate:
|
||||
maxSurge: 1
|
||||
maxUnavailable: 0
|
||||
template:
|
||||
metadata:
|
||||
labels:
|
||||
nirmata.io/deployment.name: "ghost"
|
||||
nirmata.io/application.name: "ghost"
|
||||
nirmata.io/component: "ghost"
|
||||
spec:
|
||||
containers:
|
||||
- name: "ghost"
|
||||
image: "ghost:2.9.1-alpine"
|
||||
ports:
|
||||
- containerPort: 8080
|
||||
protocol: "TCP"
|
||||
|
21
examples/Deployment/nginx-deployment.yaml
Normal file
21
examples/Deployment/nginx-deployment.yaml
Normal file
|
@ -0,0 +1,21 @@
|
|||
apiVersion: apps/v1
|
||||
kind: Deployment
|
||||
metadata:
|
||||
name: nginx-deployment
|
||||
labels:
|
||||
app: nginx
|
||||
spec:
|
||||
replicas: 3
|
||||
selector:
|
||||
matchLabels:
|
||||
app: nginx
|
||||
template:
|
||||
metadata:
|
||||
labels:
|
||||
app: nginx
|
||||
spec:
|
||||
containers:
|
||||
- name: nginx
|
||||
image: nginx:1.7.9
|
||||
ports:
|
||||
- containerPort: 80
|
24
examples/Deployment/policy-deployment-ghost.yaml
Normal file
24
examples/Deployment/policy-deployment-ghost.yaml
Normal file
|
@ -0,0 +1,24 @@
|
|||
apiVersion : policy.nirmata.io/v1alpha1
|
||||
kind : Policy
|
||||
metadata :
|
||||
name : policy-deployment-ghost
|
||||
spec :
|
||||
failurePolicy: stopOnError
|
||||
rules:
|
||||
- resource:
|
||||
kind : Deployment
|
||||
selector :
|
||||
matchLabels :
|
||||
nirmata.io/deployment.name: "ghost"
|
||||
patch:
|
||||
- path: /metadata/labels/isMutated
|
||||
op: add
|
||||
value: "true"
|
||||
- path: "/spec/strategy/rollingUpdate/maxSurge"
|
||||
op: add
|
||||
value: 5
|
||||
- path: "/spec/template/spec/containers/0/ports/0"
|
||||
op: replace
|
||||
value:
|
||||
containerPort: 2368
|
||||
protocol: TCP
|
20
examples/Deployment/policy-deployment.yaml
Normal file
20
examples/Deployment/policy-deployment.yaml
Normal file
|
@ -0,0 +1,20 @@
|
|||
apiVersion : policy.nirmata.io/v1alpha1
|
||||
kind : Policy
|
||||
metadata :
|
||||
name : policy-deployment
|
||||
spec :
|
||||
failurePolicy: stopOnError
|
||||
rules:
|
||||
- resource:
|
||||
kind : Deployment
|
||||
name: nginx-deployment
|
||||
patch:
|
||||
- path: /metadata/labels/isMutated
|
||||
op: add
|
||||
value: "true"
|
||||
- path: /metadata/labels/app
|
||||
op: replace
|
||||
value: "nginx_is_mutated"
|
||||
|
||||
|
||||
|
13
examples/Endpoints/endpoints.yaml
Normal file
13
examples/Endpoints/endpoints.yaml
Normal file
|
@ -0,0 +1,13 @@
|
|||
apiVersion: v1
|
||||
kind: Endpoints
|
||||
metadata:
|
||||
name: test-endpoint
|
||||
labels:
|
||||
label : test
|
||||
subsets:
|
||||
- addresses:
|
||||
- ip: 192.168.10.171
|
||||
ports:
|
||||
- name: secure-connection
|
||||
port: 443
|
||||
protocol: TCP
|
25
examples/Endpoints/policy-endpoints.yaml
Normal file
25
examples/Endpoints/policy-endpoints.yaml
Normal file
|
@ -0,0 +1,25 @@
|
|||
apiVersion : policy.nirmata.io/v1alpha1
|
||||
kind : Policy
|
||||
metadata :
|
||||
name : policy-endpoints
|
||||
spec :
|
||||
failurePolicy: stopOnError
|
||||
rules:
|
||||
- resource:
|
||||
kind : Endpoints
|
||||
selector:
|
||||
matchLabels:
|
||||
label : test
|
||||
patch:
|
||||
- path : "/subsets/0/ports/0/port"
|
||||
op : replace
|
||||
value: 9663
|
||||
- path : "/subsets/0"
|
||||
op: add
|
||||
value:
|
||||
addresses:
|
||||
- ip: "192.168.10.171"
|
||||
ports:
|
||||
- name: load-balancer-connection
|
||||
port: 80
|
||||
protocol: UDP
|
|
@ -0,0 +1,20 @@
|
|||
apiVersion: autoscaling/v2beta1
|
||||
kind: HorizontalPodAutoscaler
|
||||
metadata:
|
||||
name: wildfly-example
|
||||
spec:
|
||||
scaleTargetRef:
|
||||
apiVersion: extensions/v1beta1
|
||||
kind: Deployment
|
||||
name: wildfly-example
|
||||
minReplicas: 1
|
||||
maxReplicas: 5
|
||||
metrics:
|
||||
- type: Resource
|
||||
resource:
|
||||
name: cpu
|
||||
targetAverageUtilization: 80
|
||||
- type: Resource
|
||||
resource:
|
||||
name: memory
|
||||
targetAverageValue: 1000Mi
|
20
examples/HorizontalPodAutoscaler/policy-hpa.yaml
Normal file
20
examples/HorizontalPodAutoscaler/policy-hpa.yaml
Normal file
|
@ -0,0 +1,20 @@
|
|||
apiVersion : policy.nirmata.io/v1alpha1
|
||||
kind : Policy
|
||||
metadata :
|
||||
name : policy-hpa
|
||||
spec :
|
||||
failurePolicy: stopOnError
|
||||
rules:
|
||||
- resource:
|
||||
kind : HorizontalPodAutoscaler
|
||||
selector:
|
||||
matchLabels:
|
||||
originalLabel: isHere
|
||||
patch:
|
||||
- path: "/metadata/labels"
|
||||
op: add
|
||||
value:
|
||||
isMutated: "true"
|
||||
- op: replace
|
||||
path: "/spec/metrics/1/resource/targetAverageValue"
|
||||
value: "959Mi"
|
14
examples/Ingress/ingress.yaml
Normal file
14
examples/Ingress/ingress.yaml
Normal file
|
@ -0,0 +1,14 @@
|
|||
apiVersion: extensions/v1beta1
|
||||
kind: Ingress
|
||||
metadata:
|
||||
name: test-ingress
|
||||
annotations:
|
||||
nginx.ingress.kubernetes.io/rewrite-target: /
|
||||
spec:
|
||||
rules:
|
||||
- http:
|
||||
paths:
|
||||
- path: /testpath
|
||||
backend:
|
||||
serviceName: test
|
||||
servicePort: 80
|
19
examples/Ingress/policy-ingess.yaml
Normal file
19
examples/Ingress/policy-ingess.yaml
Normal file
|
@ -0,0 +1,19 @@
|
|||
apiVersion : policy.nirmata.io/v1alpha1
|
||||
kind : Policy
|
||||
metadata :
|
||||
name : policy-ingress
|
||||
spec :
|
||||
failurePolicy: stopOnError
|
||||
rules:
|
||||
- resource:
|
||||
kind : Ingress
|
||||
selector:
|
||||
matchLabels:
|
||||
originalLabel: isHere
|
||||
patch:
|
||||
- path: "/metadata/labels/isMutated"
|
||||
op: add
|
||||
value: "true"
|
||||
- path : "/spec/rules/0/http/paths/0/path"
|
||||
op : replace
|
||||
value: "/mutatedpath"
|
14
examples/Job/job.yaml
Normal file
14
examples/Job/job.yaml
Normal file
|
@ -0,0 +1,14 @@
|
|||
apiVersion: batch/v1
|
||||
kind: Job
|
||||
metadata:
|
||||
name: pi
|
||||
spec:
|
||||
template:
|
||||
spec:
|
||||
containers:
|
||||
- name: pi
|
||||
image: perl
|
||||
command: ["perl"]
|
||||
restartPolicy: Never
|
||||
backoffLimit: 4
|
||||
|
17
examples/Job/policy-job.yaml
Normal file
17
examples/Job/policy-job.yaml
Normal file
|
@ -0,0 +1,17 @@
|
|||
apiVersion : policy.nirmata.io/v1alpha1
|
||||
kind : Policy
|
||||
metadata :
|
||||
name : policy-job-perl-bigInt
|
||||
spec :
|
||||
failurePolicy: stopOnError
|
||||
rules:
|
||||
- resource:
|
||||
kind : Job
|
||||
name: pi
|
||||
patch:
|
||||
- path : "/spec/template/spec/containers/0/command"
|
||||
op : add
|
||||
value: [ "-Mbignum=bpi", "-wle", "print bpi(2000)" ]
|
||||
- path : "/spec/backoffLimit"
|
||||
op: add
|
||||
value: 10
|
13
examples/LimitRange/limitrange.yaml
Normal file
13
examples/LimitRange/limitrange.yaml
Normal file
|
@ -0,0 +1,13 @@
|
|||
apiVersion: v1
|
||||
kind: LimitRange
|
||||
metadata:
|
||||
name: test-mem-limit-range
|
||||
labels:
|
||||
containerSize: minimal
|
||||
spec:
|
||||
limits:
|
||||
- default:
|
||||
memory: 512Mi
|
||||
defaultRequest:
|
||||
memory: 256Mi
|
||||
type: Container
|
16
examples/LimitRange/policy-limitrange.yaml
Normal file
16
examples/LimitRange/policy-limitrange.yaml
Normal file
|
@ -0,0 +1,16 @@
|
|||
apiVersion : policy.nirmata.io/v1alpha1
|
||||
kind : Policy
|
||||
metadata :
|
||||
name : policy-limitrange
|
||||
spec :
|
||||
failurePolicy: stopOnError
|
||||
rules:
|
||||
- resource:
|
||||
kind : LimitRange
|
||||
selector:
|
||||
matchLabels:
|
||||
containerSize: minimal
|
||||
patch:
|
||||
- path : "/spec/limits/0/default/memory"
|
||||
op : replace
|
||||
value: "384Mi"
|
8
examples/Namespace/namespace.yaml
Normal file
8
examples/Namespace/namespace.yaml
Normal file
|
@ -0,0 +1,8 @@
|
|||
kind: Namespace
|
||||
apiVersion: v1
|
||||
metadata:
|
||||
name: "namespace-not-modified"
|
||||
labels:
|
||||
LabelForSelector : "namespace"
|
||||
replaced : "no"
|
||||
|
25
examples/Namespace/policy-namespace-by-name.yaml
Normal file
25
examples/Namespace/policy-namespace-by-name.yaml
Normal file
|
@ -0,0 +1,25 @@
|
|||
apiVersion : policy.nirmata.io/v1alpha1
|
||||
|
||||
kind : Policy
|
||||
|
||||
metadata :
|
||||
name : policy-namespace
|
||||
|
||||
spec :
|
||||
failurePolicy: stopOnError
|
||||
|
||||
rules:
|
||||
- resource:
|
||||
kind : Namespace
|
||||
name : "namespace-not-modified"
|
||||
|
||||
patch:
|
||||
- path: "/metadata/labels/isMutated"
|
||||
op: add
|
||||
value: "true"
|
||||
- path: "/metadata/name"
|
||||
op: replace
|
||||
value: "modified-namespace"
|
||||
|
||||
|
||||
|
27
examples/Namespace/policy-namespace.yaml
Normal file
27
examples/Namespace/policy-namespace.yaml
Normal file
|
@ -0,0 +1,27 @@
|
|||
apiVersion : policy.nirmata.io/v1alpha1
|
||||
|
||||
kind : Policy
|
||||
|
||||
metadata :
|
||||
name : policy-namespace
|
||||
|
||||
spec :
|
||||
failurePolicy: stopOnError
|
||||
|
||||
rules:
|
||||
- resource:
|
||||
kind : Namespace
|
||||
selector:
|
||||
matchLabels:
|
||||
LabelForSelector : "namespace"
|
||||
|
||||
patch:
|
||||
- path: "/metadata/labels/replaced"
|
||||
op: add
|
||||
value: "yes"
|
||||
- path: "/metadata/name"
|
||||
op: replace
|
||||
value: "modified-namespace-name"
|
||||
|
||||
|
||||
|
36
examples/NetworkPolicy/networkpolicy.yaml
Normal file
36
examples/NetworkPolicy/networkpolicy.yaml
Normal file
|
@ -0,0 +1,36 @@
|
|||
apiVersion: networking.k8s.io/v1
|
||||
kind: NetworkPolicy
|
||||
metadata:
|
||||
name: test-network-policy
|
||||
labels:
|
||||
originalLabel : isHere
|
||||
namespace: default
|
||||
spec:
|
||||
podSelector:
|
||||
matchLabels:
|
||||
role: db
|
||||
policyTypes:
|
||||
- Ingress
|
||||
- Egress
|
||||
ingress:
|
||||
- from:
|
||||
- ipBlock:
|
||||
cidr: 172.17.0.0/16
|
||||
except:
|
||||
- 172.17.129.0/24
|
||||
- namespaceSelector:
|
||||
matchLabels:
|
||||
project: myproject
|
||||
- podSelector:
|
||||
matchLabels:
|
||||
role: frontend
|
||||
ports:
|
||||
- protocol: TCP
|
||||
port: 6379
|
||||
egress:
|
||||
- to:
|
||||
- ipBlock:
|
||||
cidr: 10.0.0.0/24
|
||||
ports:
|
||||
- protocol: TCP
|
||||
port: 5978
|
21
examples/NetworkPolicy/policy-networkpolicy.yaml
Normal file
21
examples/NetworkPolicy/policy-networkpolicy.yaml
Normal file
|
@ -0,0 +1,21 @@
|
|||
apiVersion : policy.nirmata.io/v1alpha1
|
||||
kind : Policy
|
||||
metadata :
|
||||
name : policy-network-policy
|
||||
spec :
|
||||
failurePolicy: stopOnError
|
||||
rules:
|
||||
- resource:
|
||||
kind : NetworkPolicy
|
||||
selector:
|
||||
matchLabels:
|
||||
originalLabel: isHere
|
||||
patch:
|
||||
- path: "/metadata/labels/isMutated"
|
||||
op: add
|
||||
value: "true"
|
||||
- path: "/metadata/labels/originalLabel"
|
||||
op: remove
|
||||
- path : "/spec/ingress/0/from/0/ipBlock/cidr"
|
||||
op : replace
|
||||
value: "172.17.128.0/17"
|
19
examples/PersistentVolumeClaim/PVC.yaml
Normal file
19
examples/PersistentVolumeClaim/PVC.yaml
Normal file
|
@ -0,0 +1,19 @@
|
|||
kind: PersistentVolumeClaim
|
||||
apiVersion: v1
|
||||
metadata:
|
||||
name: game-myclaim
|
||||
labels:
|
||||
originalLabel : isHere
|
||||
spec:
|
||||
accessModes:
|
||||
- ReadWriteOnce
|
||||
volumeMode: Filesystem
|
||||
resources:
|
||||
requests:
|
||||
storage: 8Gi
|
||||
storageClassName: slow
|
||||
selector:
|
||||
matchLabels:
|
||||
release: "stable"
|
||||
matchExpressions:
|
||||
- {key: environment, operator: In, values: [dev]}
|
17
examples/PersistentVolumeClaim/policy-PVC.yaml
Normal file
17
examples/PersistentVolumeClaim/policy-PVC.yaml
Normal file
|
@ -0,0 +1,17 @@
|
|||
apiVersion : policy.nirmata.io/v1alpha1
|
||||
kind : Policy
|
||||
metadata :
|
||||
name : policy-pvc
|
||||
spec :
|
||||
failurePolicy: stopOnError
|
||||
rules:
|
||||
- resource:
|
||||
kind : PersistentVolumeClaim
|
||||
matchLabels:
|
||||
originalLabel: isHere
|
||||
patch:
|
||||
- path: "/metadata/labels/originalLabel"
|
||||
op: remove
|
||||
- path : "/spec/resources/requests/storage"
|
||||
op : replace
|
||||
value: "6Gi"
|
9
examples/PodDisruptionBudget/pdb.yaml
Normal file
9
examples/PodDisruptionBudget/pdb.yaml
Normal file
|
@ -0,0 +1,9 @@
|
|||
apiVersion: policy/v1beta1
|
||||
kind: PodDisruptionBudget
|
||||
metadata:
|
||||
name: game-pdb
|
||||
spec:
|
||||
minAvailable: 2
|
||||
selector:
|
||||
matchLabels:
|
||||
app: zookeeper
|
17
examples/PodDisruptionBudget/policy-pdb.yaml
Normal file
17
examples/PodDisruptionBudget/policy-pdb.yaml
Normal file
|
@ -0,0 +1,17 @@
|
|||
apiVersion : policy.nirmata.io/v1alpha1
|
||||
kind : Policy
|
||||
metadata :
|
||||
name : policy-pdb
|
||||
spec :
|
||||
failurePolicy: stopOnError
|
||||
rules:
|
||||
- resource:
|
||||
kind : PodDisruptionBudget
|
||||
name: "game-pdb"
|
||||
patch:
|
||||
- path: "/metadata/labels/isMutated"
|
||||
op: add
|
||||
value: "true"
|
||||
- path : "/spec/minAvailable"
|
||||
op : replace
|
||||
value: "5%"
|
18
examples/PodTemplate/PodTemplate.yaml
Normal file
18
examples/PodTemplate/PodTemplate.yaml
Normal file
|
@ -0,0 +1,18 @@
|
|||
apiVersion: v1
|
||||
kind: PodTemplate
|
||||
metadata:
|
||||
name: nginx-test
|
||||
labels:
|
||||
app: nginx
|
||||
originalLabel: isHere
|
||||
template:
|
||||
spec:
|
||||
containers:
|
||||
- name: redis
|
||||
image: redis
|
||||
ports:
|
||||
- containerPort: 80
|
||||
protocol: TCP
|
||||
restartPolicy: Always
|
||||
terminationGracePeriodSeconds: 30
|
||||
dnsPolicy: ClusterFirst
|
21
examples/PodTemplate/policy-PodTemplate.yaml
Normal file
21
examples/PodTemplate/policy-PodTemplate.yaml
Normal file
|
@ -0,0 +1,21 @@
|
|||
apiVersion : policy.nirmata.io/v1alpha1
|
||||
kind : Policy
|
||||
metadata :
|
||||
name : test-podtemplate
|
||||
spec :
|
||||
failurePolicy: stopOnError
|
||||
rules:
|
||||
- resource:
|
||||
kind : PodTemplate
|
||||
selector:
|
||||
matchLabels:
|
||||
originalLabel: isHere
|
||||
patch:
|
||||
- path: "/metadata/labels/app"
|
||||
op : replace
|
||||
value : mutedApp
|
||||
- path: "/template/spec/containers/0/name"
|
||||
op : replace
|
||||
value : my-mutated-app
|
||||
- path: "/metadata/labels/originalLabel"
|
||||
op : remove
|
81
examples/README.md
Normal file
81
examples/README.md
Normal file
|
@ -0,0 +1,81 @@
|
|||
# Examples
|
||||
Examples of policies and resources with which you can play to see the kube-policy in action. There are definitions for each supported resource type and an example policy for the corresponding resource.
|
||||
## How to play
|
||||
First of all, **build and install the policy controller**: see README file in the project's root.
|
||||
Each folder contains a pair of files, one of which is the definition of the resource, and the second is the definition of the policy for this resource. Let's look at an example of the endpoints mutation. Endpoints are listed in file `example/Endpoints/endpoints.yaml`:
|
||||
|
||||
```apiVersion: v1
|
||||
kind: Endpoints
|
||||
metadata:
|
||||
name: test-endpoint
|
||||
labels:
|
||||
label : test
|
||||
subsets:
|
||||
- addresses:
|
||||
- ip: 192.168.10.171
|
||||
ports:
|
||||
- name: secure-connection
|
||||
port: 443
|
||||
protocol: TCP
|
||||
```
|
||||
Create this resource:
|
||||
|
||||
```
|
||||
> kubectl create -f example/Endpoints/endpoints.yaml
|
||||
endpoints/test-endpoint created
|
||||
> kubectl get -f example/Endpoints/endpoints.yaml
|
||||
NAME ENDPOINTS AGE
|
||||
test-endpoint 192.168.10.171:443 6s
|
||||
```
|
||||
We just created an endpoints resource and made sure that it was created without changes. Let's remove it now and try to create it again, but with an active policy for endpoints resources.
|
||||
```
|
||||
> kubectl delete -f test/endpoints.yaml
|
||||
endpoints "test-endpoint" deleted
|
||||
```
|
||||
We have this a policy for enpoints (`examples/Endpoints/policy-endpoint.yaml`):
|
||||
|
||||
```
|
||||
apiVersion : policy.nirmata.io/v1alpha1
|
||||
kind : Policy
|
||||
metadata :
|
||||
name : policy-endpoints
|
||||
spec :
|
||||
failurePolicy: stopOnError
|
||||
rules:
|
||||
- resource:
|
||||
kind : Endpoints
|
||||
selector:
|
||||
matchLabels:
|
||||
label : test
|
||||
patch:
|
||||
- path : "/subsets/0/ports/0/port"
|
||||
op : replace
|
||||
value: 9663
|
||||
- path : "/subsets/0"
|
||||
op: add
|
||||
value:
|
||||
addresses:
|
||||
- ip: "192.168.10.171"
|
||||
ports:
|
||||
- name: additional-connection
|
||||
port: 80
|
||||
protocol: UDP
|
||||
```
|
||||
This policy does 2 patches:
|
||||
|
||||
- **replaces** the first port of the first connection to 6443
|
||||
- **adds** new endpoint with IP 192.168.10.171 and port 80 (UDP)
|
||||
|
||||
Let's apply this policy and create the endpoints again to see the changes:
|
||||
```
|
||||
> kubectl create -f examples/Endpoints/policy-endpoints.yaml
|
||||
policy.policy.nirmata.io/policy-endpoints created
|
||||
> kubectl create -f examples/Endpoints/endpoints.yaml
|
||||
endpoints/test-endpoint created
|
||||
> kubectl get -f examples/Endpoints/endpoints.yaml
|
||||
NAME ENDPOINTS AGE
|
||||
test-endpoint 192.168.10.171:80,192.168.10.171:9663 30s
|
||||
```
|
||||
As you can see, the endpoints resource was created with changes: a new port 80 was added, and port 443 was changed to 6443.
|
||||
|
||||
**Enjoy :)**
|
17
examples/ResourceQuota/policy-quota.yaml
Normal file
17
examples/ResourceQuota/policy-quota.yaml
Normal file
|
@ -0,0 +1,17 @@
|
|||
apiVersion : policy.nirmata.io/v1alpha1
|
||||
kind : Policy
|
||||
metadata :
|
||||
name : policy-quota
|
||||
spec :
|
||||
failurePolicy: stopOnError
|
||||
rules:
|
||||
- resource:
|
||||
kind : ResourceQuota
|
||||
name: "pods-high"
|
||||
patch:
|
||||
- path: "/metadata/labels/isMutated"
|
||||
op: add
|
||||
value: "true"
|
||||
- path : "/spec/hard/cpu"
|
||||
op : replace
|
||||
value : "7"
|
18
examples/ResourceQuota/quota.yaml
Normal file
18
examples/ResourceQuota/quota.yaml
Normal file
|
@ -0,0 +1,18 @@
|
|||
apiVersion: v1
|
||||
kind: List
|
||||
items:
|
||||
- apiVersion: v1
|
||||
kind: ResourceQuota
|
||||
metadata:
|
||||
name: pods-high
|
||||
spec:
|
||||
hard:
|
||||
cpu: 100
|
||||
memory: 200Gi
|
||||
pods: "10"
|
||||
scopeSelector:
|
||||
matchExpressions:
|
||||
- operator : In
|
||||
scopeName: PriorityClass
|
||||
values: ["high"]
|
||||
|
22
examples/Secrets/policy-secrets.yaml
Normal file
22
examples/Secrets/policy-secrets.yaml
Normal file
|
@ -0,0 +1,22 @@
|
|||
apiVersion : policy.nirmata.io/v1alpha1
|
||||
kind : Policy
|
||||
metadata :
|
||||
name : policy-secrets
|
||||
spec :
|
||||
failurePolicy: stopOnError
|
||||
rules:
|
||||
- resource:
|
||||
kind : Secret
|
||||
name: "mysecret"
|
||||
patch:
|
||||
- path: "/metadata/labels/isMutated"
|
||||
op: add
|
||||
value: "true"
|
||||
- path: "/metadata/labels/originalLabel"
|
||||
op: remove
|
||||
- path : "/data/newPass"
|
||||
op : add
|
||||
value : "bmV3UmFuZG9tUGFzcwo="
|
||||
- path : "/data/password"
|
||||
op : replace
|
||||
value : "Y29tcHJvbWlzZWQK"
|
11
examples/Secrets/secrets.yaml
Normal file
11
examples/Secrets/secrets.yaml
Normal file
|
@ -0,0 +1,11 @@
|
|||
apiVersion: v1
|
||||
kind: Secret
|
||||
metadata:
|
||||
name: mysecret
|
||||
labels:
|
||||
originalLabel : isHere
|
||||
|
||||
type: Opaque
|
||||
data:
|
||||
username: QXByaW9yaXQK
|
||||
password: cXVlc3QxIQo=
|
17
examples/Services/Services.yaml
Normal file
17
examples/Services/Services.yaml
Normal file
|
@ -0,0 +1,17 @@
|
|||
kind: Service
|
||||
apiVersion: v1
|
||||
metadata:
|
||||
name: game-service
|
||||
labels:
|
||||
originalLabel : isHere
|
||||
|
||||
secretLabel : thisIsMySecret
|
||||
spec:
|
||||
selector:
|
||||
app: MyApp
|
||||
ports:
|
||||
- name: http
|
||||
|
||||
protocol: TCP
|
||||
port: 80
|
||||
targetPort: 9376
|
23
examples/Services/policy-Service.yaml
Normal file
23
examples/Services/policy-Service.yaml
Normal file
|
@ -0,0 +1,23 @@
|
|||
apiVersion : policy.nirmata.io/v1alpha1
|
||||
kind : Policy
|
||||
metadata :
|
||||
name : policy-service
|
||||
spec :
|
||||
failurePolicy: stopOnError
|
||||
rules:
|
||||
- resource:
|
||||
kind: Service
|
||||
name: game-service
|
||||
patch:
|
||||
- path: "/metadata/labels/isMutated"
|
||||
op: add
|
||||
value: "true"
|
||||
- path : "/metadata/labels/secretLabel"
|
||||
op : replace
|
||||
value : "weKnow"
|
||||
- path : "/metadata/labels/originalLabel"
|
||||
op : remove
|
||||
- path: "/spec/selector/app"
|
||||
op: replace
|
||||
value: "mutedApp"
|
||||
|
39
examples/StatefulSet/StatefulSet.yaml
Normal file
39
examples/StatefulSet/StatefulSet.yaml
Normal file
|
@ -0,0 +1,39 @@
|
|||
apiVersion: apps/v1
|
||||
kind: StatefulSet
|
||||
metadata:
|
||||
name: game-web
|
||||
|
||||
labels:
|
||||
|
||||
originalLabel : isHere
|
||||
|
||||
spec:
|
||||
selector:
|
||||
matchLabels:
|
||||
app: nginx-but-no # has to match .spec.template.metadata.labels
|
||||
serviceName: "nginx-but-no"
|
||||
replicas: 3 # by default is 1
|
||||
template:
|
||||
metadata:
|
||||
labels:
|
||||
app: nginx-but-no # has to match .spec.selector.matchLabels
|
||||
spec:
|
||||
terminationGracePeriodSeconds: 10
|
||||
containers:
|
||||
- name: nginx-but-no
|
||||
image: k8s.gcr.io/nginx-but-no-slim:0.8
|
||||
ports:
|
||||
- containerPort: 8780
|
||||
name: webp
|
||||
volumeMounts:
|
||||
- name: www
|
||||
mountPath: /usr/share/nginx-but-no/html
|
||||
volumeClaimTemplates:
|
||||
- metadata:
|
||||
name: www
|
||||
spec:
|
||||
accessModes: [ "ReadWriteOnce" ]
|
||||
storageClassName: "my-storage-class"
|
||||
resources:
|
||||
requests:
|
||||
storage: 1Gi
|
24
examples/StatefulSet/policy-StatefulSet.yaml
Normal file
24
examples/StatefulSet/policy-StatefulSet.yaml
Normal file
|
@ -0,0 +1,24 @@
|
|||
apiVersion : policy.nirmata.io/v1alpha1
|
||||
kind : Policy
|
||||
metadata :
|
||||
name : policy-statefulset
|
||||
spec :
|
||||
failurePolicy: stopOnError
|
||||
rules:
|
||||
- resource:
|
||||
kind : StatefulSet
|
||||
selector:
|
||||
matchLabels:
|
||||
originalLabel: isHere
|
||||
patch:
|
||||
- path: "/spec/template/metadata/labels/isMutated"
|
||||
op: add
|
||||
value: "true"
|
||||
- path: "/metadata/labels/isMutated"
|
||||
op: add
|
||||
value: "true"
|
||||
- path : "/metadata/labels/originalLabel"
|
||||
op : remove
|
||||
- path : "/spec/serviceName"
|
||||
op : replace
|
||||
value : "not-a-nginx"
|
Loading…
Add table
Reference in a new issue