Use CIS Kubernetes Benchmark policy constraints
Policy Controller comes with a default library of constraint templates that can be used with the CIS bundle to audit the compliance of your cluster against the CIS Kubernetes Benchmark. This benchmark is a set of recommendations for configuring Kubernetes to support a strong security posture.
This bundle of constraints addresses and enforces policies in the following domains:
- RBAC and service accounts
- Pod Security Policies
- Network policies and CNI
- Secrets management
- General policies
These have not yet been certified by CIS.
The bundle includes these constraints to satisfy corresponding controls in the CIS benchmark:
Constraint | Control ID | Control description |
---|---|---|
psp-privileged-container | 5.2.1 | Minimize the admission of privileged containers |
psp-host-namespace | 5.2.2 | Minimize the admission of containers wanting to share the host process ID namespace |
5.2.3 | Minimize the admission of containers wanting to share the host IPC namespace | |
psp-host-network-ports | 5.2.4 | Minimize the admission of containers wanting to share the host network namespace |
psp-allow-privilege-escalation-container | 5.2.5 | Minimize the admission of containers with allowPrivilegeEscalation |
psp-pods-must-run-as-nonroot | 5.2.6 | Minimize the admission of root containers |
psp-capabilities | 5.2.7 | Minimize the admission of containers with the NET_RAW capability |
5.2.8 | Minimize the admission of containers with added capabilities | |
5.2.9 | Minimize the admission of containers with capabilities assigned | |
require-namespace-network-policies | 5.3.2 | Ensure that all namespaces have Network Policies defined |
no-secrets-as-env-vars | 5.4.1 | Prefer using Secrets as files over Secrets as environment variables |
psp-seccomp-docker-default | 5.7.2 | Ensure that the seccomp profile is set to docker/default in your Pod definitions |
pods-require-security-context | 5.7.3 | Apply Security Context to your Pods and containers |
Before you begin
- Install and initialize the
Google Cloud CLI,
which provides the
gcloud
andkubectl
commands used in these instructions. If you use Cloud Shell, Google Cloud CLI comes pre-installed. - Install and setup kpt. kpt is used in these instructions to customize and deploy Kubernetes resources.
- If you are using Anthos Config Management for the first time, enable Anthos Config Management.
- Create, or make sure you have access to, a cluster running Kubernetes version of 1.14.x or later with Policy Controller installed on the cluster. For details on Policy Controller installation refer to Install Policy Controller.
- Optional: Install Config Sync and sync your cluster to the Google sample repository. This repository comes pre-populated with CIS constraints for Policy Controller. To learn more, see Install Config Sync.
Audit CIS policies with Policy Controller
Policy Controller lets you enforce policies for your Kubernetes cluster. To help test your workloads and their compliance with regard to the CIS policies outlined in the preceding table, you can deploy these constraints in "audit" mode to reveal violations and more importantly give yourself a chance to fix them before enforcing on your Kubernetes cluster.
You can apply these policies with spec.enforcementAction
set to dryrun
using
kpt
or
Config Sync.
kpt
Download the CIS policy bundle from GitHub using kpt:
kpt pkg get https://github.com/GoogleCloudPlatform/acm-policy-controller-library.git/bundles/cis-k8s-v1.5.1
Run the
set-enforcement-action
kpt function to set the policies' enforcement action todryrun
:kpt fn eval cis-k8s-v1.5.1 -i gcr.io/kpt-fn/set-enforcement-action:v0.1 \ -- enforcementAction=dryrun
Initialize the working directory with kpt, which creates a resource to track changes:
cd cis-k8s-v1.5.1 kpt live init
Apply the policy constraints with kpt:
kpt live apply
The output is the following:
k8spspseccomp.constraints.gatekeeper.sh/psp-seccomp-docker-default created k8spodsrequiresecuritycontext.constraints.gatekeeper.sh/pods-require-security-context created k8sprohibitrolewildcardaccess.constraints.gatekeeper.sh/prohibit-role-wildcard-access created k8srequirenamespacenetworkpolicies.constraints.gatekeeper.sh/require-namespace-network-policies created k8snoenvvarsecrets.constraints.gatekeeper.sh/no-secrets-as-env-vars created k8spspallowprivilegeescalationcontainer.constraints.gatekeeper.sh/psp-allow-privilege-escalation-container created k8spspallowedusers.constraints.gatekeeper.sh/psp-pods-must-run-as-nonroot created k8spsphostnetworkingports.constraints.gatekeeper.sh/psp-host-network-ports created k8srestrictrolebindings.constraints.gatekeeper.sh/restrict-clusteradmin-rolebindings created k8spspcapabilities.constraints.gatekeeper.sh/psp-capabilities created k8spsphostnamespace.constraints.gatekeeper.sh/psp-host-namespace created k8spspprivilegedcontainer.constraints.gatekeeper.sh/psp-privileged-container created 13 resource(s) applied. 13 created, 0 unchanged, 0 configured, 0 failed
Verify that policy constraints have been installed and check if violations exist across the cluster:
kpt live status --output table --poll-until current
A status of
CURRENT
confirms successful installation of the constraints.
Config Sync
Operators using Config Sync to deploy policies to their clusters can use the following instructions:
Change into the sync directory for Config Sync:
cd SYNC_ROOT_DIR
Download the CIS policy bundle from GitHub using kpt:
kpt pkg get git@github.com:GoogleCloudPlatform/acm-policy-controller-library.git/bundles/cis-k8s-v1.5.1 policy/cis
Run the
set-enforcement-action
kpt function to set the policies' enforcement action todryrun
:kpt fn eval policy/cis/cis-k8s-v1.5.1 -i gcr.io/kpt-fn/set-enforcement-action:v0.1 -- enforcementAction=dryrun
Preview the policy constraints that will be created:
kpt live init policy/cis/cis-k8s-v1.5.1 kpt live apply --dry-run policy/cis/cis-k8s-v1.5.1
The output is the following:
k8spsphostnamespace.constraints.gatekeeper.sh/psp-host-namespace created (dry-run) k8spodsrequiresecuritycontext.constraints.gatekeeper.sh/pods-require-security-context created (dry-run) k8srestrictnamespaces.constraints.gatekeeper.sh/restrict-default-namespace created (dry-run) k8srestrictrolebindings.constraints.gatekeeper.sh/restrict-clusteradmin-rolebindings created (dry-run) k8snoenvvarsecrets.constraints.gatekeeper.sh/no-secrets-as-env-vars created (dry-run) k8spspallowedusers.constraints.gatekeeper.sh/psp-pods-must-run-as-nonroot created (dry-run) k8spsphostnetworkingports.constraints.gatekeeper.sh/psp-host-network-ports created (dry-run) k8spspprivilegedcontainer.constraints.gatekeeper.sh/psp-privileged-container created (dry-run) k8spspseccomp.constraints.gatekeeper.sh/psp-seccomp-docker-default created (dry-run) k8sprohibitrolewildcardaccess.constraints.gatekeeper.sh/prohibit-role-wildcard-access created (dry-run) k8srequirenamespacenetworkpolicies.constraints.gatekeeper.sh/require-namespace-network-policies created (dry-run) k8spspallowprivilegeescalationcontainer.constraints.gatekeeper.sh/psp-allow-privilege-escalation-container created (dry-run) k8spspcapabilities.constraints.gatekeeper.sh/psp-capabilities created (dry-run) 13 resource(s) applied. 13 created, 0 unchanged, 0 configured, 0 failed (dry-run)
Push changes to the Config Sync repo:
git add SYNC_ROOT_DIR/policy/cis git commit -m 'Adding CIS policy audit enforcement' git push
Verify the status of the installation:
watch gcloud beta container hub config-management status --project PROJECT_ID
A status of
SYNCED
confirms the installation of the policies.
View policy violations
Once the policy constraints are installed in audit mode, violations on the cluster can be viewed using the following command:
kubectl get constraint -o json | jq -cC '.items[]| [.kind,.status.totalViolations]'
If you prefer to view the violations in Cloud Logging, go to the Logs Explorer page.
Use the following filters in the Query editor to monitor the violations logs:
resource.type="k8s_container" resource.labels.location=CLUSTER_LOCATION resource.labels.namespace_name="gatekeeper-system" resource.labels.pod_name:"gatekeeper-audit-" jsonPayload.process: "audit" jsonPayload.event_type: "violation_audited" jsonPayload.constraint_name:* jsonPayload.constraint_namespace:*
Enforce CIS policies
Once you've reviewed policy violations on your cluster, the next step is to enforce these policies so that the Admission Controller blocks any non-compliant resource from getting applied to the cluster.
kpt
Run the
set-enforcement-action
kpt function to set the policies' enforcement action todeny
:kpt fn eval -i gcr.io/kpt-fn/set-enforcement-action:v0.1 -- enforcementAction=deny
Apply the policy constraints:
kpt live apply
Config Sync
Operators using Config Sync to deploy policies to their clusters can use the following instructions:
Change into the sync directory for Config Sync:
cd SYNC_ROOT_DIR
Run the
set-enforcement-action
kpt function to set the policies' enforcement action todeny
:kpt fn eval policy/cis/cis-k8s-v1.5.1 -i gcr.io/kpt-fn/set-enforcement-action:v0.1 -- enforcementAction=deny
Push changes to the Config Sync repo:
git add SYNC_ROOT_DIR/policy/cis git commit -m 'Enforcing CIS policies for GKE' git push
Verify the status of the installation:
gcloud alpha anthos config sync repo list --project PROJECT_ID
Your repo showing up in the
SYNCED
column confirms the installation of the policies.
Test policy enforcement
Perform a quick test to confirm the policy enforcement and blocking of non-compliant resources on the cluster.
Create a non-compliant resource on the cluster using the following command:
cat <<EOF | kubectl apply -f -
apiVersion: v1
kind: Pod
metadata:
namespace: wp
name: wp-non-compliant
labels:
app: wordpress
spec:
containers:
- image: wordpress
name: wordpress
ports:
- containerPort: 80
name: wordpress
EOF
The admission controller should produce an error listing out the policy violations that this resource violates.