mirror of
https://github.com/maziggy/bambuddy.git
synced 2026-09-30 11:12:35 +02:00
The 50000-51000 docker-compose port range spawned ~2000 docker-proxy host processes (~3.5 GB RSS) under Docker's default userland-proxy. The 1001-port pool was symptom treatment — collisions only matter for multi-VP-on-shared-bind, but the cost was paid by every install. Each VP now gets a non-overlapping 10-port slice computed from its id (VP 1 -> 50000-50009, VP 2 -> 50010-50019, ...). Class constants are gone; VirtualPrinterFTPServer takes passive_port_min/max instance args. Wraps modulo PASSIVE_MAX_SLOTS = 100, with the existing 10-attempt random retry as same-slot collision fallback. Compose default narrowed to 50000-50029 (3 VPs). Proxy-mode VPs forward the real printer's full range and stay on the separate TCPProxy constants. Compose comment rewritten to acknowledge Linux multi-service hosts as a primary bridge-mode audience and drop an over-stated "confirmed by reporter" claim about userland-proxy=false.
170 lines
8.5 KiB
YAML
170 lines
8.5 KiB
YAML
services:
|
||
bambuddy:
|
||
image: ghcr.io/maziggy/bambuddy:latest
|
||
build: .
|
||
# Usage:
|
||
# docker compose up -d → pulls pre-built image from ghcr.io
|
||
# docker compose up -d --build → builds locally from source
|
||
container_name: bambuddy
|
||
# File ownership inside the data and logs volumes is normalised by the
|
||
# entrypoint at startup (chowns to PUID:PGID and drops privileges via
|
||
# gosu before running the app). Override PUID / PGID below to match
|
||
# your host user if needed — defaults to 1000:1000 to match the
|
||
# historical compose `user:` directive.
|
||
#
|
||
# Allow binding to privileged ports (322, 990) as non-root user — required
|
||
# for FTPS in every VP mode and for the RTSPS camera proxy in proxy mode +
|
||
# non-proxy modes that have a target printer configured. Without this, the
|
||
# FTP and RTSP listeners silently fail.
|
||
cap_add:
|
||
- NET_BIND_SERVICE
|
||
#
|
||
# LINUX: Use host mode for printer discovery and camera streaming
|
||
network_mode: host
|
||
#
|
||
# macOS/WINDOWS: Docker Desktop doesn't support host mode.
|
||
# Comment out "network_mode: host" above and uncomment "ports:" below.
|
||
# Note: Printer discovery won't work - add printers manually by IP.
|
||
#ports:
|
||
# - "${PORT:-8000}:8000"
|
||
# - "3000:3000" # Virtual printer bind/detect
|
||
# - "3002:3002" # Virtual printer bind/detect
|
||
# - "8883:8883" # Virtual printer MQTT
|
||
# - "990:990" # Virtual printer FTP control
|
||
# - "6000:6000" # Virtual printer file transfer tunnel
|
||
# - "322:322" # Virtual printer RTSP camera (X1/H2/P2; proxy mode + non-proxy modes with a target printer)
|
||
# - "2024-2026:2024-2026" # Virtual printer proprietary ports (A1/P1S)
|
||
# - "50000-50029:50000-50029" # Virtual printer FTP passive data (3 VPs × 10-port slice)
|
||
#
|
||
# FTP passive-mode port slicing (#1646): non-proxy VPs (Archive / Review /
|
||
# Queue modes) get a 10-port slice each, allocated by VP id — VP 1 →
|
||
# 50000-50009, VP 2 → 50010-50019, VP 3 → 50020-50029, etc. The default
|
||
# exposure above covers 3 VPs; widen the range to cover more
|
||
# (`50000-500N9` where N = vp_count - 1). Proxy-mode VPs forward the
|
||
# real printer's full 50000-50100 range — if you use proxy mode, expose
|
||
# `50000-50100:50000-50100` instead.
|
||
#
|
||
# Why narrow this matters on bridge mode: with Docker's default
|
||
# userland-proxy (true), every exposed port spawns one docker-proxy host
|
||
# process per address family (IPv4 + IPv6). The original 1001-port range
|
||
# spawned ~2000 such processes, pinning ~3.5 GB of host RAM that doesn't
|
||
# appear in `docker stats` (host-level, not container-level). 30 ports
|
||
# → ~60 processes → ~210 MB instead.
|
||
#
|
||
# Bridge mode is the normal setup for any Linux host that runs
|
||
# Bambuddy alongside other services (NAS, multi-tenant Docker VM,
|
||
# Synology DSM, Unraid) — `network_mode: host` would conflict with
|
||
# ports those other services already bind. Bambuddy uses host mode by
|
||
# default because SSDP printer discovery needs L2 multicast, but it's
|
||
# a deliberate trade-off, not a security-blind default; setups that
|
||
# forgo discovery (add printers by IP) can stay on bridge with the
|
||
# narrowed range above.
|
||
volumes:
|
||
- bambuddy_data:/app/data
|
||
- bambuddy_logs:/app/logs
|
||
#
|
||
# OPTIONAL — only needed if you ALSO run a native install of Bambuddy
|
||
# on the same host and want both installs to share the same Virtual
|
||
# Printer CA certificate (so the slicer only has to trust one CA).
|
||
# Most Docker-only users should leave this commented out — the
|
||
# entrypoint will keep the VP data inside the named volume above.
|
||
# If uncommented, the entrypoint chowns the host directory to
|
||
# PUID:PGID on first start so the container user can write to it.
|
||
#- ./virtual_printer:/app/data/virtual_printer
|
||
#
|
||
# Mount scheduled backup output to NAS or external storage
|
||
# Backups default to DATA_DIR/backups/ inside the data volume.
|
||
# Uncomment to store them externally (e.g. on a NAS share).
|
||
#- /path/to/nas/bambuddy-backups:/app/data/backups
|
||
#
|
||
# Tailscale integration (optional): mount the host's tailscaled socket
|
||
# so Bambuddy can request Let's Encrypt certs for virtual printers via
|
||
# your tailnet's MagicDNS name. Requires:
|
||
# 1. Tailscale installed + `tailscale up` completed on the host
|
||
# 2. `sudo tailscale set --operator=<container-user>` on the host so
|
||
# the user running the container can call `tailscale cert`
|
||
# Without this mount, the Tailscale toggle in the UI is harmless —
|
||
# Bambuddy falls back to self-signed certs.
|
||
#- /var/run/tailscale/tailscaled.sock:/var/run/tailscale/tailscaled.sock
|
||
#
|
||
# Using a self signed certificate for Home Assistant
|
||
# Add your certificate to certs directory and mount it to the container.
|
||
# The certificate will be added to the system trust store on container startup.
|
||
# Enable the system trust store with the USE_SYSTEM_TRUST_STORE env var to
|
||
# have Bambuddy trust the certificate.
|
||
# - /path/to/certs:/usr/local/share/ca-certificates
|
||
#
|
||
# External library folders. Mount the host paths the operator wants
|
||
# users to be able to register as external folders. The in-container
|
||
# paths chosen here MUST appear in BAMBUDDY_EXTERNAL_ROOTS below.
|
||
# Read-only (:ro) is recommended unless you want users uploading
|
||
# files back to the host share.
|
||
#- /mnt/nas/3d-prints:/external/nas:ro
|
||
#- /srv/library:/external/projects:ro
|
||
environment:
|
||
- TZ=${TZ:-Europe/Berlin}
|
||
# User/group the container drops to after the entrypoint normalises
|
||
# ownership on /app/data and /app/logs. Match your host user (run
|
||
# `id -u` / `id -g`) if you want files written by the container to
|
||
# show up as your user on the host. Defaults to 1000:1000.
|
||
- PUID=${PUID:-1000}
|
||
- PGID=${PGID:-1000}
|
||
# Port BamBuddy runs on (default: 8000)
|
||
# Usage: PORT=8080 docker compose up -d
|
||
- PORT=${PORT:-8000}
|
||
# Virtual printer: Set to the Docker host's IP when using bridge mode (ports:).
|
||
# Required for FTP passive mode to work behind NAT.
|
||
# Example: VIRTUAL_PRINTER_PASV_ADDRESS=192.168.1.100
|
||
#- VIRTUAL_PRINTER_PASV_ADDRESS=
|
||
#
|
||
# External PostgreSQL (optional — uses SQLite by default)
|
||
# Example: DATABASE_URL=postgresql+asyncpg://bambuddy:password@db-host:5432/bambuddy
|
||
#- DATABASE_URL=
|
||
#
|
||
# Slicer API sidecar (optional — Settings → "Use Slicer API" toggles this on).
|
||
# Default points at the OrcaSlicer sidecar on the docker host; change if you
|
||
# run the sidecar on a different host/port. The matching docker-compose.yml
|
||
# for the sidecars lives in the orca-slicer-api fork
|
||
# (https://github.com/maziggy/orca-slicer-api).
|
||
#- SLICER_API_URL=http://localhost:3003
|
||
#
|
||
# MFA at-rest encryption key (#1219). Auto-generated to
|
||
# DATA_DIR/.mfa_encryption_key on first startup if unset. Override here
|
||
# to manage the key out-of-band (e.g. via a secret manager).
|
||
#- MFA_ENCRYPTION_KEY=
|
||
#
|
||
# External library folders (GHSA-r2qv follow-up). Empty default
|
||
# disables the "Add external folder" feature; set to one or more
|
||
# colon-separated absolute paths INSIDE THE CONTAINER to opt in.
|
||
# The paths must also be bind-mounted from the host — uncomment
|
||
# the matching volume snippet below.
|
||
# Example for a single NAS mount:
|
||
#- BAMBUDDY_EXTERNAL_ROOTS=/external/nas
|
||
# Example for two roots:
|
||
#- BAMBUDDY_EXTERNAL_ROOTS=/external/nas:/external/projects
|
||
#
|
||
# Enable System Trust Store for certificate validation (e.g. for local Home Assistant)
|
||
# You also need to mount your certificates to the container (see volumes section above).
|
||
# - USE_SYSTEM_TRUST_STORE=true
|
||
restart: unless-stopped
|
||
|
||
# Optional: External PostgreSQL database
|
||
# Uncomment to run Postgres alongside Bambuddy (or use an external Postgres host)
|
||
#postgres:
|
||
# image: postgres:16-alpine
|
||
# container_name: bambuddy-db
|
||
# restart: unless-stopped
|
||
# environment:
|
||
# POSTGRES_USER: bambuddy
|
||
# POSTGRES_PASSWORD: changeme
|
||
# POSTGRES_DB: bambuddy
|
||
# volumes:
|
||
# - bambuddy_pgdata:/var/lib/postgresql/data
|
||
# ports:
|
||
# - "5432:5432"
|
||
|
||
volumes:
|
||
bambuddy_data:
|
||
bambuddy_logs:
|
||
#bambuddy_pgdata:
|