Detect and respond to threats inside running containers using Falco.
Interactive Wizard (fires when no arguments are provided)
When invoked with no arguments, ask before proceeding:
Q1 — Mode?
What do you need? 1. install — deploy Falco on Kubernetes (EKS or GKE) with eBPF driver 2. rules — write and test a custom Falco rule 3. alerts — configure Falcosidekick to route alerts (Slack, webhook, etc.) 4. debug — diagnose why a Falco rule is not firing 5. harden — map runtime Falco alerts to Kyverno admission policies Alerts on behaviour a container never showed while learning (profile-based, no rule writing), or Kubescape already runs → /platform-skills:kubescape-operator runtime Enter 1–5 or mode name:
Before install, check for another eBPF agent: kubectl get ds -A | grep -iE 'node-agent|tetragon'. Kubescape's node-agent with runtimeDetection overlaps with Falco on the same nodes; pick one per node pool, or disable Kubescape's runtimeDetection and keep its posture and CVE capabilities.
Q2 — Context (after mode selected, one at a time):
- install:
Which cloud platform? EKS / GKE / other (specify node OS if known): - rules:
Describe the behaviour to detect (e.g. "shell spawned in a container", "unexpected outbound connection"): - alerts:
Which output destination? Slack / webhook / PagerDuty / other: - debug:
Describe the symptom — which rule is not firing, and what event should trigger it? - harden:
Which Falco alert or rule output should block re-admission? (paste the alert or rule name):
Then proceed into the relevant mode below.
Mode: install
Deploy Falco on Kubernetes (EKS or GKE) using the eBPF driver via Helm.
Prerequisites:
- Helm 3.x
kubectlaccess to the target cluster- Node OS: Amazon Linux 2/2023 (EKS) or Container-Optimized OS (GKE) — both support eBPF
Steps:
- Add the Falco Helm repository:
bash
helm repo add falcosecurity https://falcosecurity.github.io/charts helm repo update - Install Falco with eBPF driver (never kernel module on managed K8s):
bash
helm install falco falcosecurity/falco \ --namespace falco \ --create-namespace \ -f examples/runtime-security/falco-values.yaml - Verify DaemonSet is running on all nodes:
bash
kubectl rollout status daemonset/falco -n falco kubectl get pods -n falco -o wide - Confirm Falco is receiving events:
Expected: lines likebashkubectl logs -n falco -l app.kubernetes.io/name=falco --tail=20Notice A shell was spawned...(from the default ruleset test events)
EKS-specific note: if using Bottlerocket nodes, set driver.kind: modern_ebpf in Helm values — Bottlerocket does not ship kernel headers for the classic eBPF probe.
GKE-specific note: COS nodes require driver.kind: modern_ebpf. GKE Autopilot does not support Falco (no DaemonSet scheduling).
Mode: rules
Write and test custom Falco rules.
Steps:
- Explain the rule structure:
yaml
- rule: Shell spawned in container desc: A shell was spawned inside a container — potential interactive intrusion condition: > spawned_process and container and shell_procs and not container.image.repository in (allowed_shell_images) output: > Shell spawned in container (user=%user.name user_id=%user.uid container=%container.name image=%container.image.repository shell=%proc.name parent=%proc.pname cmdline=%proc.cmdline) priority: WARNING tags: [container, shell, mitre_execution] - Key condition fields:
spawned_process— a new process was exec'dcontainer— event is inside a container (not on the host)proc.name— process namecontainer.image.repository— image name without tagfd.net— network file descriptor (for connection events)
- Test with falco-event-generator:
Then check logs:bashkubectl run event-generator \ --image=falcosecurity/event-generator \ --restart=Never \ --rm -it -- run syscallkubectl logs -n falco -l app.kubernetes.io/name=falco | grep WARNING - Load custom rules via Helm values:
yaml
customRules: custom-rules.yaml: |- - rule: Shell spawned in container ...
Mode: alerts
Configure Falcosidekick to route Falco alerts to Slack, webhooks, or other outputs.
Steps:
- Install Falcosidekick alongside Falco:
bash
helm upgrade --install falco falcosecurity/falco \ --namespace falco \ --create-namespace \ --set falcosidekick.enabled=true \ --set falcosidekick.webui.enabled=true \ -f examples/runtime-security/falcosidekick-values.yaml - Configure Slack output in Falcosidekick values:
yaml
falcosidekick: config: slack: webhookurl: "https://hooks.slack.com/services/<token>" minimumpriority: warning messageformat: > Alert: *{{ .Rule }}* (Priority: {{ .Priority }}) Container: `{{ index .OutputFields "container.name" }}` Image: `{{ index .OutputFields "container.image.repository" }}` - Verify alerts are routing:
bash
kubectl port-forward -n falco svc/falco-falcosidekick-ui 2802:2802 # Open http://localhost:2802 — events appear in the UI - Deduplication: set
slack.minimumpriority: warningto suppress DEBUG/INFO noise
Mode: debug
If you need deeper context on any Falco component, load references/runtime-security.md.
Diagnose why a Falco rule is not firing.
Checklist (work through in order):
- Is Falco running?
bash
kubectl get pods -n falco -o wide kubectl logs -n falco -l app.kubernetes.io/name=falco | tail -20 - Is the rule loaded?
bash
kubectl logs -n falco -l app.kubernetes.io/name=falco | grep -i "Loading rules" kubectl exec -n falco daemonset/falco -- cat /etc/falco/rules.d/custom-rules.yaml 2>/dev/null \ || kubectl exec -n falco daemonset/falco -- ls /etc/falco/ - Is the condition correct? Test the event type:
bash
kubectl exec -n falco daemonset/falco -- falco --validate /etc/falco/rules.d/custom-rules.yaml - Is the event being generated? Use event-generator for syscall rules:
bash
kubectl run test --image=falcosecurity/event-generator --rm -it -- run syscall - Is the priority too low? If
falcosidekick.config.slack.minimumpriority: error, rules withpriority: WARNINGare silently dropped. Adjust priority or threshold. - Is there a macro override? Check if a built-in macro like
never_trueis shadowing your condition:bashkubectl exec -n falco daemonset/falco -- cat /etc/falco/falco_rules.yaml | grep -A3 "macro: <macro name>" kubectl exec -n falco daemonset/falco -- ls /etc/falco/rules.d/
Mode: harden
Map Falco runtime alerts to Kyverno admission policies to prevent redeployment of flagged workloads.
Steps:
- Explain the bridge pattern: Falco detects a runtime violation → alert metadata is added as a label/annotation to the offending Pod or Deployment → Kyverno admission policy blocks future admission of workloads with that label
- Label the offending workload (from an alert webhook handler or manual response):
bash
kubectl label deployment <name> -n <namespace> \ security.platform/falco-alert=critical - Apply the Kyverno policy to block re-admission:
yaml
apiVersion: policies.kyverno.io/v1 kind: ValidatingPolicy metadata: name: block-falco-flagged-workloads spec: validationActions: [Deny] matchConstraints: resourceRules: - apiGroups: ["apps"] apiVersions: ["v1"] operations: ["CREATE", "UPDATE"] resources: ["deployments"] validations: - expression: > !has(object.metadata.labels) || !('security.platform/falco-alert' in object.metadata.labels) || object.metadata.labels['security.platform/falco-alert'] != 'critical' message: "Deployment is flagged by a Falco critical alert and cannot be re-admitted. Remove the flag after remediation." -
Important: Kyverno blocks new pod admissions only — it does not terminate existing running pods that violate the policy. After applying the policy, manually identify and terminate flagged pods:
bash# Find pods matching the label that triggered the alert kubectl get pods -n <namespace> -l <label-key>=<label-value> # Terminate with grace period to allow in-flight requests to drain kubectl delete pod <name> -n <namespace> --grace-period=30
- Remediation workflow: fix the workload → remove the label → re-admit
Recovery: If a Kyverno policy blocks a legitimate workload, remove the triggering label immediately:
bashkubectl label deployment <name> -n <namespace> security.platform/falco-alert-
The workload will be re-admitted on next rollout. Fix the underlying security issue, then re-apply the label to re-admit under policy enforcement.
After completing this task, log errors and learnings via /platform-skills:self-improve log.


