# Security Considerations When Running ChaosBlade in Production: A Complete Guide

> Discover essential security considerations for running ChaosBlade in production Address root privileges, capability constraints, container isolation, and HTTP server risks for safe chaos engineering.

- Repository: [ChaosBlade/chaosblade](https://github.com/chaosblade-io/chaosblade)
- Tags: best-practices
- Published: 2026-02-27

---

**Running ChaosBlade in production requires root privileges or specific Linux capabilities for core functions like namespace manipulation and process injection, necessitating strict capability constraints, container isolation, and disabling of the built-in HTTP server to prevent unauthorized command execution.**

ChaosBlade is a powerful chaos engineering toolkit maintained at `chaosblade-io/chaosblade` that injects faults into processes, containers, and kernel resources. Because it manipulates namespaces, alters system resources, and executes low-level system calls, understanding the security considerations when running ChaosBlade in production is critical before deploying it to live environments.

## Core Architecture Privilege Requirements

ChaosBlade’s architecture inherently requires elevated privileges to execute experiments effectively. The following components demonstrate where the codebase enforces or relies on root-level access.

### Namespace Manipulation ([`nsexec.c`](https://github.com/chaosblade-io/chaosblade/blob/main/nsexec.c))

The [`nsexec.c`](https://github.com/chaosblade-io/chaosblade/blob/main/nsexec.c) file implements the `enter_ns` function, which uses the `setns(2)` syscall to join target process namespaces (IPC, UTS, NET, PID, or MNT). This operation requires the `CAP_SYS_ADMIN` capability, available only to root or processes with that capability in their effective set. When ChaosBlade attempts to enter a namespace without sufficient privileges, `setns` returns `-1` and the experiment aborts immediately.

### Java Agent Attachment ([`exec/jvm/sandbox.go`](https://github.com/chaosblade-io/chaosblade/blob/main/exec/jvm/sandbox.go))

When attaching a Java agent to a target JVM, the code in [`sandbox.go`](https://github.com/chaosblade-io/chaosblade/blob/main/sandbox.go) checks process ownership via `/proc/<pid>/status`. If the current user does not own the target process, ChaosBlade dynamically escalates privileges using `sudo -u <user>`, falling back to `su` if sudo is unavailable. This automatic privilege escalation creates a potential attack vector if environment variables like `PATH` are manipulated.

### HTTP Server Exposure ([`cli/cmd/server_start.go`](https://github.com/chaosblade-io/chaosblade/blob/main/cli/cmd/server_start.go))

The server mode implementation launches a background HTTP server that executes experiment commands received over the network. By default, the server returns a `CommandIllegal` error because the endpoint is disabled—the `Register` function returns "Server mode is disabled" unless explicitly enabled with the `--nohup` flag. When active, the server runs as the invoking user, meaning any compromise of the HTTP endpoint allows attackers to trigger privileged actions with the same rights as the server process.

### Container Privilege Requirements

The official demo image documented in [`README.md`](https://github.com/chaosblade-io/chaosblade/blob/main/README.md) requires the `--privileged` Docker flag because many experiments need raw socket access, cgroup manipulation, or namespace entry. However, this grants all capabilities to the container, which violates the principle of least privilege for production deployments.

## Threat Surface and Mitigation Strategies

Understanding specific attack vectors within ChaosBlade’s implementation allows you to implement targeted defenses.

### Kernel Namespace Entry Risks

The namespace entry mechanism in [`nsexec.c`](https://github.com/chaosblade-io/chaosblade/blob/main/nsexec.c) opens `/proc/<pid>/ns/<type>` files before calling `setns`. If an attacker gains access to the ChaosBlade binary, they could potentially enter arbitrary process namespaces and manipulate isolated environments. **Mitigation**: Run the `nsexec` helper inside containers granted only `CAP_SYS_ADMIN` for the specific namespace type, using Docker’s `--cap-add` instead of `--privileged`.

### Privilege Escalation in JVM Injection

The dynamic `sudo`/`su` escalation in [`sandbox.go`](https://github.com/chaosblade-io/chaosblade/blob/main/sandbox.go) assumes controlled environments. If users can modify their shell environment or PATH variable on the host, they could intercept the privilege escalation calls. **Mitigation**: Run ChaosBlade under a dedicated service account with restricted `/etc/sudoers` entries using `NOPASSWD: /path/to/blade` for specific commands only, or deploy in containers where JVM processes share the same user namespace to eliminate the need for sudo entirely.

### Network Exposure in Server Mode

The HTTP server implemented in [`server_start.go`](https://github.com/chaosblade-io/chaosblade/blob/main/server_start.go) listens on configurable IP/port combinations and parses blade CLI syntax from incoming requests. Without proper network controls, this exposes arbitrary command execution capabilities to anyone reaching the endpoint. **Mitigation**: Keep server mode disabled in production (do not use `--nohup`). If remote triggering is necessary, deploy behind an API gateway with TLS termination and mutual authentication, or use the Kubernetes operator which enforces RBAC policies.

## Production Hardening Best Practices

Implement these six strategies to safely run ChaosBlade in production environments:

1. **Create a Dedicated Service Account**  
   Create a system user `chaosblade` with a restricted login shell. Grant minimal sudo rights in `/etc/sudoers`:
   ```text
   chaosblade ALL=(root) NOPASSWD: /usr/local/bin/blade server start *
   ```

2. **Limit Linux Capabilities**  
   - For namespace experiments: `--cap-add=SYS_ADMIN` (or `SYS_PTRACE` for ptrace-based attacks)
   - For network experiments: `--cap-add=NET_ADMIN`
   - Avoid `--privileged` outside testing environments

3. **Implement Container-Level Isolation**  
   Deploy ChaosBlade inside minimal containers containing only the binary and static libraries. Enable Docker’s `userns-remap` to map container root to a non-root host UID.

4. **Disable the Built-In HTTP Server**  
   Do not enable server mode with `--nohup`. The default `blade server start` without this flag prints "Server mode is disabled" and exits safely.

5. **Enable Comprehensive Audit Logging**  
   Set `--log-level debug` and forward logs from `/var/log/chaosblade` (handled by `github.com/chaosblade-io/chaosblade-spec-go/log`) to your central SIEM.

6. **Maintain Security Patch Management**  
   Monitor [`SECURITY.md`](https://github.com/chaosblade-io/chaosblade/blob/main/SECURITY.md) for vulnerability disclosures and update promptly, especially for kernel-interacting components like [`nsexec.c`](https://github.com/chaosblade-io/chaosblade/blob/main/nsexec.c).

## Implementation Examples

### Minimal-Privilege Container Execution

Run ChaosBlade with only the capabilities required for CPU and network experiments:

```bash
docker run -it \
  --cap-add=SYS_ADMIN \
  --cap-add=NET_ADMIN \
  --user $(id -u):$(id -g) \
  chaosbladeio/chaosblade-demo \
  blade create cpu fullload --cpu-percent 50 --timeout 30

```

### Secure Sudo Configuration for JVM Experiments

Configure the service account to run blade without passwords for specific users:

```bash

# Add to /etc/sudoers

chaosblade ALL=(appuser) NOPASSWD: /usr/local/bin/blade

```

Then execute as the dedicated account:

```bash
sudo -u appuser blade create jvm delay --time 5000 --target-pid 12345

```

### Disabling Server Mode (Recommended)

Prevent accidental exposure of the HTTP API:

```bash

# This command intentionally fails to start the server in production

blade server start --port 9526

# Output: Server mode is disabled

```

### Kubernetes Operator Deployment

Use the ChaosBlade Operator to enforce RBAC-controlled experiments:

```yaml
apiVersion: chaosblade.io/v1alpha1
kind: ChaosBladeExperiment
metadata:
  name: cpu-fatigue
spec:
  scope: pod
  target: cpu
  action: fullload
  desc: "Inject 80% CPU load for 30s"
  mode: one
  selector:
    app: myservice

```

Apply with `kubectl apply -f experiment.yaml`. Only users with the `chaosblade-experiments` role can create these resources.

## Key Files for Security Audits

Review these source files when assessing ChaosBlade’s security posture:

- **[`SECURITY.md`](https://github.com/chaosblade-io/chaosblade/blob/main/SECURITY.md)** – Project-level security policy and vulnerability disclosure process
- **[`nsexec.c`](https://github.com/chaosblade-io/chaosblade/blob/main/nsexec.c)** – Implements namespace entry requiring `CAP_SYS_ADMIN`
- **[`exec/jvm/sandbox.go`](https://github.com/chaosblade-io/chaosblade/blob/main/exec/jvm/sandbox.go)** – Contains sudo/su escalation logic for JVM attachment
- **[`cli/cmd/server_start.go`](https://github.com/chaosblade-io/chaosblade/blob/main/cli/cmd/server_start.go)** – HTTP server implementation with potential remote execution surface
- **[`README.md`](https://github.com/chaosblade-io/chaosblade/blob/main/README.md)** – Documents privileged Docker usage patterns
- **`Makefile`** – Build scripts for multi-arch images that may register privileged QEMU binaries

## Summary

- ChaosBlade requires **root or specific capabilities** (`CAP_SYS_ADMIN`, `CAP_NET_ADMIN`) for namespace manipulation and process injection.
- The **Java agent attachment** mechanism in [`sandbox.go`](https://github.com/chaosblade-io/chaosblade/blob/main/sandbox.go) dynamically escalates via `sudo` or `su`, requiring careful service account configuration.
- The **built-in HTTP server** in [`server_start.go`](https://github.com/chaosblade-io/chaosblade/blob/main/server_start.go) should remain disabled in production to prevent unauthorized remote command execution.
- Use **capability constraints** (`--cap-add` vs `--privileged`) and user namespace remapping to minimize container attack surface.
- Deploy via the **Kubernetes operator** for RBAC-controlled, auditable experiment execution rather than standalone server mode.

## Frequently Asked Questions

### Does ChaosBlade require root access to run experiments?

Yes, most ChaosBlade experiments require root or specific Linux capabilities. The `setns(2)` syscall used in [`nsexec.c`](https://github.com/chaosblade-io/chaosblade/blob/main/nsexec.c) for namespace manipulation requires `CAP_SYS_ADMIN`, and network experiments require `CAP_NET_ADMIN`. However, you can run ChaosBlade as a non-root user inside containers that have these specific capabilities added, rather than granting full root access to the host.

### Is it safe to run ChaosBlade in server mode?

No, running ChaosBlade in server mode (`blade server start --nohup`) is not recommended for production without additional protections. The server executes arbitrary commands received via HTTP, and while it returns "Server mode is disabled" by default, enabling it exposes a remote command execution surface. If you must use remote triggering, deploy behind an API gateway with mutual TLS or use the Kubernetes operator which enforces RBAC.

### How do I minimize capabilities when running ChaosBlade in Docker?

Avoid the `--privileged` flag shown in the [`README.md`](https://github.com/chaosblade-io/chaosblade/blob/main/README.md) demos. Instead, use `--cap-add` to grant only specific capabilities: `SYS_ADMIN` for namespace experiments, `NET_ADMIN` for network chaos, and `SYS_PTRACE` for process injection. Combine this with `--user` directives or user namespace remapping to ensure the container root maps to a non-privileged host UID.

### What is the safest way to run ChaosBlade experiments in Kubernetes?

Use the **ChaosBlade Operator** rather than running the CLI directly in pods. The operator creates `ChaosBladeExperiment` custom resources that enforce Kubernetes RBAC policies, ensuring only authorized service accounts can create experiments. This approach eliminates the need for the built-in HTTP server and provides audit trails through the Kubernetes API server.