-

9 min read

Kubernetes Cluster Security - Nuclei Templates v9.9.0 šŸŽ‰

Kubernetes Cluster Security - Nuclei Templates v9.9.0 šŸŽ‰

We're excited to tell you about Nuclei Templates release v9.9.0! This new version includes newly added Kubernetes Cluster Security templates. In this blog post, we'll discuss automating Kubernetes security review, creating custom k8s security checks, and sharing results on the PDCP Cloud for review.

Kubernetes is often discussed for its complexity and steep learning curve. Its challenging nature has made it a frequent topic for memes in the developer community

Hence, we've opted to simplify the process of reviewing its misconfiguration by crafting security checks for k8s using the straightforward YAML format.

For those particularly interested in using the Kubernetes security templates, feel free to skip to the end of the blog

Kubernetes Cluster Security Review, often referred to simply as Kubernetes Security Audit, is a crucial process for evaluating the security measures in place within your Kubernetes clusters. It involves a thorough review of configurations, policies, and setups to ensure they align with security best practices and compliance requirements.

Kubernetes Cluster Security Review

Key activities in a Kubernetes Cluster Security Review typically include:

  1. Deployment Configurations Review: This involves examining deployment settings to ensure aspects like resource limits and security contexts are properly configured. For example, checking that containers don't run as root or have privilege escalation disabled.
  2. Network Policies Enforcement: This check ensures that network policies are effectively isolating components and controlling the flow of traffic to minimize the risk of breaches through network routes.
  3. Pod Security Standards: Reviewing pod configurations for security-related settings such as whether containers prevent privilege escalation, use read-only root filesystems, or share host namespaces.
  4. Compliance and Configuration Management: This involves ensuring Kubernetes setups adhere to compliance mandates specific to the industry, and that configuration management practices are robust.
  5. Security Contexts and Roles: Examining the security contexts applied to pods and deployments to ensure they restrict permissions and capabilities appropriately.
  6. Logging and Monitoring: Ensuring that logging and monitoring configurations are set up to capture necessary information for security auditing and incident response.
  7. Secrets Management: Checking how secrets are managed and accessed within the cluster to prevent unauthorized access or leakage.
  8. Vulnerability Scanning and Patch Management: Regularly scanning for vulnerabilities and applying necessary patches to Kubernetes components and container images.

The added templates perform essential checks around k8s security and compliance statuses, making reviews more efficient for Pentesters, devOps engineers and security teams alike.

These templates uses kubectl that interact with the Kubernetes API, providing flexibility to tailor security checks or automate specific security tasks. Templates offer extensive control over Kubernetes resources, aiding in deep security checks and configurations. We have used code protocols to write Kubernetes cluster security templates.

What are Code Protocol Templates?

Nuclei empowers users to execute external code on the host operating system, granting security researchers, pentesters, and developers the flexibility to expand its capabilities beyond standard protocol-based testing. This functionality enables interaction with the underlying OS, facilitating the execution of custom scripts or commands for a diverse array of tasks including system configurations, file operations, and network interactions. Such control and adaptability empower users to customize their security testing workflows to meet precise needs. Explore the Code protocol templates in our documentation for more details.

Because code templates can execute commands on hosts, users must first sign the template using their keys, and these are not included in default scans. To use these templates, you need to sign them using the -sign flag. After signing, you can run the templates by providing the -code flag.

In the example below, you'll notice that we can easily run an kubectl command directly into the template. However, unlike other templates that execute on target hosts, this one will run the command on our own host.

yaml

1id: kubernetes-code-env
2info:
3  name: Kubernetes Cluster Validation
4  author: princechaddha
5  severity: info
6  description: |
7    Checks if kubernetes CLI is set up and all necessary tools are installed on the environment.
8  reference:
9    - https://kubernetes.io/
10  tags: cloud,devops,kubernetes,k8s,k8s-cluster-security
11
12self-contained: true
13code:
14  - engine:
15      - sh
16      - bash
17    source: |
18      kubectl version
19
20    extractors:
21      - type: regex
22        internal: true
23        name: server_version
24        group: 1
25        regex:
26          - 'Server Version:\s*(v[0-9]+\.[0-9]+\.[0-9]+)'
27
28      - type: dsl
29        dsl:
30          - '"kubectl is successfully connected to the Kubernetes API Server Version: " + server_version'

Example #1:

In this example, we will create a template that identifies privileged containers in deployments ā€” a common security risk:

  • In the example below, we've set self-contained: true because this Nuclei template operates independently of any specific host, using local Kubernetes configurations to fetch and analyze deployment data.
  • The first code block specifies the sh and bash engines to execute the kubectl command to retrieve all deployments across all namespaces in JSON format. This block includes an extractor that extracts the list of deployments and stores it in the items array.
  • We've utilized the flow property to orchestrate the execution sequence of the template. It starts with executing code(1) to fetch deployment data, followed by iterating over each deployment using a for loop. Within this loop, the set function assigns the current deployment to a variable, and then javascript(1) is executed for further processing.
  • Second Code Block (JavaScript) processes each deployment by parsing the deployment data and examining each container within the deployment. It specifically checks if any container is running in privileged mode, has runAsUser set below 1000, or has allowPrivilegeEscalation enabled.
  • There is no matcher used here as the logic is embedded within the JavaScript. The results are extracted using a DSL type that directly formats and outputs the response indicating whether a container meets the risky criteria

yaml

1id: k8s-privileged-container
2
3info:
4  name: Privileged Containers Found in Deployments
5  author: princechaddha
6  severity: critical
7  description: Checks for containers running in privileged mode within Kubernetes Deployments, and now also checks for user privileges and privilege escalation settings.
8  impact: |
9    Running containers in privileged mode, as the root user, or with privilege escalation enabled can grant them access to host resources and could lead to security breaches if the container is compromised.
10  remediation: |
11    Ensure that no container in Kubernetes Deployments runs in privileged mode, as the root user, or with privilege escalation enabled. Modify the security context for each container to set `privileged: false`, `runAsUser` appropriately, and `allowPrivilegeEscalation: false`.
12  reference:
13    - https://kubernetes.io/docs/concepts/policy/pod-security-policy/#privileged
14  tags: cloud,devops,kubernetes,k8s,devsecops,deployments,k8s-cluster-security
15
16flow: |
17  code(1);
18  for (let deployment of template.items) {
19    set("deployment", deployment)
20    javascript(1);
21  }
22
23self-contained: true
24code:
25  - engine:
26      - sh
27      - bash
28    source: kubectl get deployments --all-namespaces --output=json
29    extractors:
30      - type: json
31        name: items
32        internal: true
33        json:
34          - '.items[]'
35
36javascript:
37  - code: |
38        deployment = JSON.parse(template.deployment);
39        for (let container of deployment.spec.template.spec.containers) {
40          let sc = container.securityContext || {};
41          if (sc.privileged || sc.runAsUser < 1000 || sc.allowPrivilegeEscalation) {
42            let result = (`Deployment '${deployment.metadata.name}' in namespace '${deployment.metadata.namespace}' is running container '${container.name}' with insecure settings: Privileged=${sc.privileged}, runAsUser=${sc.runAsUser}, allowPrivilegeEscalation=${sc.allowPrivilegeEscalation}.`);
43            Export(result);
44            break;
45          }
46        }
47
48    extractors:
49      - type: dsl
50        dsl:
51          - response

Example #2:

Similarly, in the following template we are checking for Pods running with root user ID.

yaml

1id: k8s-root-user-id
2
3info:
4  name: Pods run with root user ID
5  author: princechaddha
6  severity: low
7  description: Checks for pods running with the user ID of the root user, increasing security risks.
8  impact: |
9    Running pods with the root user ID can allow malicious entities to gain unnecessary privileges, leading to potential compromises in the Kubernetes environment.
10  remediation: Configure pods to run with a non-root user ID by setting the 'securityContext' for each container and the pod itself.
11  reference:
12    - https://kubernetes.io/docs/tasks/configure-pod-container/security-context/
13  tags: cloud,devops,kubernetes,devsecops,pods,k8s,k8s-cluster-security
14
15flow: |
16  code(1);
17  for (let pod of template.items) {
18    set("pod", pod)
19    javascript(1);
20  }
21
22self-contained: true
23code:
24  - engine:
25      - sh
26      - bash
27    source: kubectl get pods --all-namespaces --output=json
28    extractors:
29      - type: json
30        name: items
31        internal: true
32        json:
33          - '.items[] | {pod: .metadata.name, containers: .spec.containers}'
34
35javascript:
36  - code: |
37        let podData = JSON.parse(template.pod);
38        podData.containers.forEach(container => {
39          if (container.securityContext && container.securityContext.runAsUser === 0) {
40            let result = (`Container '${container.name}' in pod '${podData.pod}' is running with root user ID.`);
41            Export(result);
42          }
43        });
44
45    extractors:
46      - type: dsl
47        dsl:
48          - response

Example #3:

In the following template we are checking if the seccomp profile is set to docker/default or runtime/default in Kubernetes Deployments

yaml

1id: k8s-seccomp-profile-set
2
3info:
4  name: Set appropriate seccomp profile
5  author: princechaddha
6  severity: medium
7  description: Checks if the seccomp profile is set to docker/default or runtime/default in Kubernetes Deployments.
8  impact: |
9    Using a default seccomp profile helps in reducing the attack surface of the container by limiting the syscalls containers can make, which can prevent certain types of exploits.
10  remediation: |
11    Ensure that all containers in Kubernetes Deployments have a seccomp profile of docker/default or runtime/default set in their security contexts.
12  reference:
13    - https://kubernetes.io/docs/tutorials/clusters/seccomp/
14  tags: cloud,devops,kubernetes,devsecops,containers,k8s,k8s-cluster-security
15
16flow: |
17  code(1);
18  for (let deployment of template.items) {
19    set("deployment", deployment)
20    javascript(1);
21  }
22
23self-contained: true
24code:
25  - engine:
26      - sh
27      - bash
28    source: kubectl get deployments --all-namespaces --output=json
29    extractors:
30      - type: json
31        name: items
32        internal: true
33        json:
34          - '.items[]'
35
36javascript:
37  - code: |
38        deployment = JSON.parse(template.deployment);
39        deployment.spec.template.spec.containers.forEach(container => {
40          if (container.securityContext && container.securityContext.seccompProfile &&
41              (container.securityContext.seccompProfile.type === 'RuntimeDefault' || container.securityContext.seccompProfile.type === 'DockerDefault')) {
42            // No action needed, configured properly
43          } else {
44            let result = (`Deployment '${deployment.metadata.name}' in namespace '${deployment.metadata.namespace}' does not have an appropriate seccomp profile set.`);
45            Export(result);
46          }
47        });
48
49    extractors:
50      - type: dsl
51        dsl:
52          - response

Check out all the other k8s templates by visiting the Nuclei Templates GitHub repository.

Custom Templates for Specific Use Cases

Similar to the above template, users can create their own custom Kubernetes security checks for their environment. This flexibility allows security teams, pentesters, and DevOps professionals to address unique security concerns and operational practices within their Kubernetes clusters. Here are a few scenarios where creating custom Kubernetes Nuclei templates might be particularly beneficial:

  1. Custom Resource Checks: Organizations using custom resources in Kubernetes can develop templates to ensure these resources adhere to security best practices. For example, a template could check if custom Operators are granted minimal permissions necessary for their function.
  2. Specific Compliance Audits: For industries with specific regulatory requirements, custom templates can help enforce compliance through continuous monitoring. For instance, a template could verify that all deployments comply with HIPAA or PCI DSS requirements by checking encryption configurations and access controls.
  3. Cluster-Specific Security Policies: Each Kubernetes cluster might have its own set of security policies based on its role and exposure. Custom templates can help ensure that each cluster adheres to its specific policies, such as enforcing network policies that isolate sensitive workloads.
  4. Integration with CI/CD Pipelines: Custom templates can be integrated into CI/CD pipelines to automatically check for security issues before new deployments are rolled out. For example, a template might scan new images for vulnerabilities or check configurations for compliance before they are applied to production environments.
  5. Advanced Network Policy Testing: While basic checks for network policies are common, custom templates can perform more sophisticated testing to ensure that the implemented policies effectively segregate and protect different parts of the cluster.
  6. Performance and Resource Optimization: Beyond security, custom templates can also help optimize cluster performance and resource usage. For instance, a template might identify over-provisioned resources or pods that are not using resource limits effectively.

Running Kubernetes Security Templates

To utilize these templates, ensure your environment is set up correctly. You need to install kubectl and configure its contexts or specific access permissions.

In Nuclei-Templates, we've introduced the concept of profiles, which allow users to run a specific set of templates tailored for a particular use case. For running Kubernetes Security templates, we have a profile named k8s-cluster-security.

Once the environment is properly configured, users can execute the following template to ensure everything is set up correctly before running the profile.

cli

1nuclei -id kubernetes-code-env -code

If the template matches, this indicates that the environment has all the necessary tools installed and the CLI is set up.

Uploading Results to ProjectDiscovery Cloud Platform

Now, we'll run a scan using our k8s scan profile. Before we start, it's very useful for pentesters or companies to save the scan results for reporting or remediation purposes. To facilitate this, you can use the -cloud-upload flag to upload the results to PDCP.

To upload results to the cloud, you need to obtain an authentication token. Here are the steps to follow:

  • Go to PDCP Cloud and log in to your account.
  • Click on your profile picture in the top-right corner and select API key.
  • Copy your API key, and in your terminal, type nuclei -auth <your-api-key>.

Now you're all set to run the templates!

cli

1nuclei -profile k8s-cluster-security -cloud-upload

Now that we have numerous results, it would be very convenient to view these on the Cloud. Simply log into PDCP Cloud, and you will find a scan created with the results.

We have added 35 templates categorized by type, including checks for deployments, network policies, pods, and compliance. We invite the community to share their feedback. We anticipate this number will grow as the security community continues to contribute and collaborate.

Conclusion

The Nuclei templates for Kubernetes provide users with significant creativity and flexibility, enabling them to craft checks that cater to their particular workflow and environment. This approach can not only assist in identifying and resolving security misconfigurations but also facilitate the monitoring of their overall k8s environment.


You can also join our Discord server. It's a great place to connect with fellow contributors and stay updated with the latest developments. Thank you, once again!

By leveraging Nuclei and actively engaging with the open-source community, or by becoming a part of the ProjectDiscovery Cloud Platform, companies can enhance their security measures, proactively address emerging threats, and establish a more secure digital landscape. Security represents a shared endeavor, and by collaborating, we can consistently adapt and confront the ever-evolving challenges posed by cyber threats.