# Installation – web UI This guide sets up the web UI on a Docker host, step by step. The agents on your fail2ban hosts are covered in [agent.md](agent.md); you need both. - Source: - Image: `git.retronerd.at/schiwagoa/fail2ban-webui` (`amd64`, `arm64`) - Tags: `1.0.0` (exact), `1` (latest 1.x), `latest` ## 1. Prerequisites - Docker Engine with Compose v2 (`docker compose version`) - Outgoing SSH (TCP 22 or your port) from the Docker host to every fail2ban host - A DNS name and a reverse proxy with TLS for the UI (see [reverse-proxy.md](reverse-proxy.md)) Check that the subnet used in the example (`172.23.51.0/24`) is free: ```bash docker network inspect $(docker network ls -q) --format '{{.Name}} {{range .IPAM.Config}}{{.Subnet}}{{end}}' | grep 172.23.51 \ || echo "172.23.51.0/24 is free" ``` If it is taken, pick another `/24` and change it in step 3. ## 2. Directories ```bash mkdir -p /opt/fail2ban-webui/config /opt/fail2ban-webui/data cd /opt/fail2ban-webui # the container runs as UID 10050 and needs to write to data/ chown -R 10050:10050 data chmod 700 data ``` | Path | Content | |---|---| | `docker-compose.yaml` | the service | | `.env` | settings and secrets (password hash, OIDC secret) | | `config/hosts.yaml` | the fail2ban hosts (mounted read-only) | | `data/` | SSH key, `known_hosts`, session secret, audit log, GeoIP database | ## 3. docker-compose.yaml ```bash nano docker-compose.yaml ``` ```yaml # ===================================================================== # fail2ban-webui – example docker-compose.yaml # # mkdir -p fail2ban-webui/{config,data} && cd fail2ban-webui # (copy this file, .env.example as .env and hosts.yaml.example as config/hosts.yaml) # chown -R 10050:10050 data # # The UI listens on 127.0.0.1:8080 only – put a reverse proxy with TLS in front of it. # The network uses its own /24 subnet; change it if it collides with an existing one # (docker network inspect $(docker network ls -q) | grep Subnet). # ===================================================================== name: fail2ban-webui services: fail2ban-webui: image: git.retronerd.at/schiwagoa/fail2ban-webui:latest # build: { context: .., dockerfile: docker/Dockerfile } # build from the repository instead container_name: fail2ban-webui restart: unless-stopped env_file: .env environment: TZ: ${TZ:-Europe/Vienna} read_only: true tmpfs: - /tmp cap_drop: - ALL security_opt: - no-new-privileges:true volumes: - ./config:/config:ro - ./data:/data ports: - "127.0.0.1:8080:8080" extra_hosts: # lets the container reach an agent on the Docker host itself (address: host.docker.internal) - "host.docker.internal:host-gateway" deploy: resources: limits: memory: 256M networks: fail2ban-webui.dockernetwork.local: ipv4_address: 172.23.51.10 networks: fail2ban-webui.dockernetwork.local: name: fail2ban-webui.dockernetwork.local driver: bridge ipam: config: - subnet: 172.23.51.0/24 gateway: 172.23.51.1 ip_range: 172.23.51.128/25 ``` If the reverse proxy runs on another machine, bind the port to the LAN address instead, e.g. `"192.168.1.10:8080:8080"` – never to `0.0.0.0` without a firewall in front. ## 4. .env Start with this minimal file; every option is described in [configuration.md](configuration.md) and in [`examples/.env.example`](../examples/.env.example). ```bash nano .env chmod 600 .env ``` ```ini PUBLIC_URL=https://fail2ban.example.org DEFAULT_LANG=en TRUSTED_PROXY_HOPS=1 AUTH_MODE=local AUTH_USER=admin AUTH_PASSWORD_HASH='set in the next step' SSH_USER=f2bweb MANUAL_JAIL=manual-block GEOIP_AUTO_DOWNLOAD=1 ``` ### Password hash ```bash docker compose run --rm -it fail2ban-webui hash-password ``` Copy the printed line (`AUTH_PASSWORD_HASH='scrypt:…'`) into `.env` and replace the placeholder. **Keep the single quotes** – the hash contains `$` signs that Docker Compose would otherwise try to expand. For single sign-on instead see [authentication.md](authentication.md). ## 5. SSH key ```bash docker compose run --rm fail2ban-webui keygen ``` The command creates `data/ssh/id_ed25519` and prints the public key (`ssh-ed25519 AAAA… fail2ban-webui`). Copy it – you need it for the agent installer. ## 6. Agents Install the agent on every fail2ban host as described in [agent.md](agent.md). In short: ```bash # on each fail2ban host, as root git clone https://git.retronerd.at/schiwagoa/fail2ban-webui.git /tmp/fail2ban-webui echo 'ssh-ed25519 AAAA… fail2ban-webui' > /tmp/webui.pub bash /tmp/fail2ban-webui/agent/install.sh --key-file /tmp/webui.pub --from ``` ## 7. config/hosts.yaml ```bash nano config/hosts.yaml ``` ```yaml hosts: - name: web01 address: web01.example.org - name: lxc-proxy address: 192.168.1.20 port: 2222 # fail2ban on the Docker host itself - name: dockerhost address: host.docker.internal ``` `user` defaults to `SSH_USER` (`f2bweb`). Set `user: root` for hosts where the agent was installed with `--user root`. ## 8. Host keys and connection test ```bash docker compose run --rm -it fail2ban-webui keyscan ``` `keyscan` shows the fingerprint of every host and asks before writing `data/ssh/known_hosts`. Compare the fingerprints with the hosts: ```bash # on the fail2ban host ssh-keygen -lf /etc/ssh/ssh_host_ed25519_key.pub ``` Then test every agent: ```bash docker compose run --rm fail2ban-webui check ``` ``` OK web01 agent 1.0.0, 3 jails, 12 bans OK lxc-proxy agent 1.0.0, 2 jails, 0 bans OK dockerhost agent 1.0.0, 4 jails, 7 bans ``` Every host must show `OK` – see [operations.md](operations.md#troubleshooting) otherwise. ## 9. Start ```bash docker compose up -d docker compose ps # STATUS: Up … (healthy) docker compose logs -f fail2ban-webui # Ctrl+C to leave ``` The log shows a summary like `fail2ban-webui 1.0.0 – hosts: web01, lxc-proxy, dockerhost – auth: local – loki: off – geoip: on`. Local test without the proxy: ```bash curl -s http://127.0.0.1:8080/healthz # ok ``` ## 10. Reverse proxy Publish `http://127.0.0.1:8080` (or the LAN address from step 3) under your DNS name with TLS – examples for Nginx Proxy Manager, Caddy, Traefik and nginx are in [reverse-proxy.md](reverse-proxy.md). Then open `PUBLIC_URL` and sign in. ## Next steps - [Protect the login with fail2ban](operations.md#protecting-the-login-with-fail2ban) - [Updates and backups](operations.md) - Optional: [Loki history and Grafana links](configuration.md#loki-and-grafana)