commit 9e4d9727e4cf0003614b54d45da888a0b2951f03
parent b2940b50161bf8af99cda0f0f277b40e12a1f9ef
Author: Robin Bron <robin.bron@yourhosting.nl>
Date: Tue, 3 Mar 2026 10:15:51 +0100
Docker-specific readme
Diffstat:
2 files changed, 124 insertions(+), 2 deletions(-)
diff --git a/.github/workflows/docker.yml b/.github/workflows/docker.yml
@@ -152,5 +152,5 @@ jobs:
username: ${{ secrets.DOCKERHUB_USERNAME }}
password: ${{ secrets.DOCKERHUB_TOKEN }}
repository: finwo/udphole
- short-description: "UDP hole punching proxy with RESP2 API"
- readme-filepath: README.md
+ short-description: "UDP hole punching proxy with RESP2 API | Source: https://github.com/finwo/udphole"
+ readme-filepath: DOCKER.md
diff --git a/DOCKER.md b/DOCKER.md
@@ -0,0 +1,122 @@
+# UDPHOLE Docker
+
+Run udphole as a Docker container.
+
+## Quick Start
+
+```bash
+docker run -p 6379:6379 -p 7000-7999:7000-7999/udp finwo/udphole
+```
+
+## Environment Variables
+
+| Variable | Default | Description |
+|----------|---------|-------------|
+| `API_PORT` | `6379` | TCP port for the RESP2 API server |
+| `UDP_PORTS` | `7000-7999` | UDP port range for UDP sockets |
+| `LOG_LEVEL` | `info` | Log verbosity: fatal, error, warn, info, debug, trace |
+| `API_ADMIN_USER` | `admin` | Username for admin user |
+| `API_ADMIN_PASS` | `supers3cret` | Password for admin user |
+| `CLUSTER` | | Comma-separated list of cluster node names (enables cluster mode) |
+| `CLUSTER_<NAME>` | | Connection string for cluster node `<NAME>` (e.g., `tcp://user:pass@host:port`) |
+
+## Configuration
+
+### Auto-generated Config
+
+If no config file is mounted, the container auto-generates `/etc/udphole.conf` from environment variables:
+
+```yaml
+[udphole]
+ports = 7000-7999
+listen = :6379
+
+[user:admin]
+permit = *
+secret = supers3cret
+```
+
+### Custom Config
+
+Mount your own config file to override defaults:
+
+```bash
+docker run -p 6379:6379 -p 7000-7999:7000-7999/udp \
+ -v /path/to/udphole.conf:/etc/udphole.conf:ro \
+ finwo/udphole
+```
+
+## Cluster Mode
+
+To run in cluster mode, set the `CLUSTER` environment variable and define node addresses:
+
+```bash
+docker run -p 6379:6379 -p 7000-7999:7000-7999/udp \
+ -e CLUSTER=node1,node2 \
+ -e CLUSTER_NODE1=tcp://user:pass@192.168.1.10:6379 \
+ -e CLUSTER_NODE2=tcp://user:pass@192.168.1.11:6379 \
+ finwo/udphole
+```
+
+This generates:
+
+```ini
+[udphole]
+ports = 7000-7999
+listen = :6379
+cluster = node1
+cluster = node2
+
+[user:admin]
+permit = *
+secret = supers3cret
+
+[cluster:node1]
+address = tcp://user:pass@192.168.1.10:6379
+username = user
+password = pass
+
+[cluster:node2]
+address = tcp://user:pass@192.168.1.11:6379
+username = user
+password = pass
+```
+
+## Docker Compose
+
+```yaml
+services:
+ udphole:
+ image: finwo/udphole
+ ports:
+ - "6379:6379"
+ - "7000-7999:7000-7999/udp"
+ environment:
+ - API_PORT=6379
+ - UDP_PORTS=7000-7999
+ - LOG_LEVEL=info
+ - API_ADMIN_USER=admin
+ - API_ADMIN_PASS=supers3cret
+ healthcheck:
+ test: ["CMD", "nc", "-z", "localhost", "6379"]
+ interval: 10s
+ timeout: 5s
+ retries: 3
+```
+
+## Healthcheck
+
+The container includes a healthcheck using `nc` to verify the API port is listening:
+
+```bash
+nc -z localhost 6379
+```
+
+## Architecture
+
+The container is available for:
+- `linux/amd64`
+- `linux/arm64/v8` (e.g., Raspberry Pi 4+, M1 Mac)
+- `linux/riscv64`
+
+Docker automatically selects the correct variant for your host architecture.