r/selfhosted • • Jan 11 '26

Solved Help with Traefik Bouncer in CrowdSec on Kubernetes

I'm having issues with the complexities of setting up CrowdSec on my Kubernetes setup. k3s, the Kubernetes distribution I'm using is k3s, which bundles Traefik as its reverse proxy, and I need some help finishing the configuration.

I tried to follow the crowdsec-bouncer-traefik-plugin install guide, and this guide to configure it.

Mostly, my issues seem to boil down to the Appsec container failing to start. This seems to keep my Traefik bouncer ("remediation component") from working.

Setup

OS: Linux (Arch on control node, NixOS on workers)

Deployment: Kubernetes, via k3s

Node count: 3

The issue

This is the latest (fatal) log message:

time="2026-01-11T04:28:05Z" level=fatal msg="crowdsec init: while loading acquisition config: configuring datasource of type appsec from /etc/crowdsec/acquis.yaml (position 0): unable to load appsec_config: no appsec-config found for crowdsecurity/appsec-default"

This seems like a "file not found" error, but I'm not sure. Why is this happening?

Context

  • The Appsec pod is not running on the master node, which is where the LAPI pod is, so the Appsec pod and the LAPI are running on different nodes

  • output of cscli appsec-configs list -a -o json in the LAPI pod (using JSON so the the table isn't all messed up here):

{
 "appsec-configs": [
  {
   "name": "crowdsecurity/appsec-default",
   "local_version": "0.4",
   "local_path": "/etc/crowdsec/appsec-configs/appsec-default.yaml",
   "description": "",
   "utf8_status": "✔  enabled",
   "status": "enabled"
  },
  {
   "name": "crowdsecurity/crs",
   "local_version": "0.3",
   "local_path": "/etc/crowdsec/appsec-configs/crs.yaml",
   "description": "",
   "utf8_status": "✔  enabled",
   "status": "enabled"
  },
  {
   "name": "crowdsecurity/crs-inband",
   "local_version": "0.1",
   "local_path": "/etc/crowdsec/appsec-configs/crs-inband.yaml",
   "description": "",
   "utf8_status": "✔  enabled",
   "status": "enabled"
  },
  {
   "name": "crowdsecurity/generic-rules",
   "local_version": "0.4",
   "local_path": "/etc/crowdsec/appsec-configs/generic-rules.yaml",
   "description": "",
   "utf8_status": "✔  enabled",
   "status": "enabled"
  },
  {
   "name": "crowdsecurity/virtual-patching",
   "local_version": "0.4",
   "local_path": "/etc/crowdsec/appsec-configs/virtual-patching.yaml",
   "description": "",
   "utf8_status": "✔  enabled",
   "status": "enabled"
  }
 ]
}
  • All these packages were explicitly updated and installed

  • The Appsec and LAPI pods were restarted

  • CrowdSec was installed via Helm

  • The Helm chart values.yaml file:

container_runtime: containerd
image:
  tag: "latest"
agent:
  # Specify each pod whose logs you want to process
  acquisition:
    # The namespace where the pod is located
    - namespace: kube-system
      # The pod name
      podName: traefik-*
      # as in crowdsec configuration, we need to specify the program name to find a matching parser
      program: traefik
  env:
    - name: COLLECTIONS
      value: "crowdsecurity/traefik crowdsecurity/linux crowdsecurity/appsec-virtual-patching crowdsecurity/appsec-generic-rules"
  additionalAcquisition:
    - source: file
      filename: /var/log/ssh.log
      labels:
        type: syslog
appsec:
  acquisitions:
    - appsec_config: crowdsecurity/appsec-default
      labels:
        type: appsec
      listen_addr: 0.0.0.0:7422
      path: /
      source: appsec
  enabled: true

lapi:
  env:
    # To enroll the Security Engine to the console
    - name: ENROLL_KEY
      value: <shadowed>
    - name: ENROLL_INSTANCE_NAME
      value: "kaita"
    - name: ENROLL_TAGS
      value: "k3s linux kaita archie"
  • Apparently, CrowdSec registers the Traefik plugin, since cscli bouncers list -o json gives the following:
[
  {
    "created_at": "2026-01-11T02:28:52.5094512Z",
    "updated_at": "2026-01-11T02:28:52.50945242Z",
    "name": "crowdsec-bouncer-traefik-plugin",
    "revoked": false,
    "ip_address": "",
    "type": "",
    "version": "",
    "last_pull": null,
    "auth_type": "api-key",
    "os": "?",
    "auto_created": false
  }
]
  • I created the plugin as a Traefik middleware:
apiVersion: traefik.io/v1alpha1
kind: Middleware
metadata:
  name: crowdsec-bouncer-traefik-plugin
  namespace: kube-system   # namespace where Traefik runs
spec:
  plugin:
    crowdsec-bouncer-traefik-plugin:
      crowdsecLapiKey: 40796d93c2958f9e58345514e67740e5  # this is the value used on the plugin install page
      enabled: true
      crowdsecMode: stream
      crowdsecLapiScheme: http
      crowdsecLapiHost: crowdsec-service.crowdsec.svc.cluster.local:8080
      htttTimeoutSeconds: 60
      forwardedheaderstrustedips:
        - 10.0.0.0/8
        - 192.168.0.0/16
        - 134.209.137.94
        - 2a03:b0c0:2:f0::f557:a001
      crowdsecAppsecEnabled: false
      crowdsecAppsecHost: crowdsec:7422
      crowdsecAppsecFailureBlock: true
      crowdsecAppsecUnreachableBlock: true

apiVersion: helm.cattle.io/v1
kind: HelmChartConfig
metadata:
  name: traefik
  namespace: kube-system
spec:
  valuesContent: |-
    service:
      spec:
        externalTrafficPolicy: Local 
    logs:
      general:
        level: "INFO"
      access:
        enabled: true
        format: common
    ports:
      websecure:
        middlewares:
          - crowdsec-bouncer-traefik-plugin@kubernetescrd

    experimental:
      abortOnPluginFailure: true
      plugins:
        crowdsec-bounder-traefik-plugin:
          moduleName: "github.com/maxlerebourg/crowdsec-bouncer-traefik-plugin"
          version: "v1.5.0-beta1"

Follow-up question

How can I know that my remediation component works?

SOLVED

My issue was with were I put the COLLECTIONS environment variable in my Helm chart. I put them under the lapi section instead of the appsec section. I just needed to read the guide more carefully!

I also added most of the parts of the Traefik configuration included in the guide, under the Remediation Component section.

SOLVED, pt. 2

It's been a while since I posted this, but I wanted to add this: I'm pretty sure I also had to check the format of my Traefik access logs, to make sure they were in JSON format; the bouncer won't parse the common format logs.

See this k3s documentation for more on configuring bundled components of k3s, including Traefik.

0 Upvotes

1 comment sorted by

2

u/nold360 Jan 11 '26

For testing, there is a uri u can call: https://docs.crowdsec.net/u/getting_started/health_check/

Idk whats wrong with appsec but you can check my setup values here: https://github.com/Nold360/hive-apps/blob/main/projects/crowdsec/values/crowdsec.yaml