docker-compose.yml
Rama main · réplica de lectura del repositorio original.
# =====================================================
# Skiff — one-command self-hosted deploy
#
# Usage:
# mkdir -p data
# cp .env.example .env
# # edit .env and set SKIFF_COOKIE_SECRET
# docker compose up -d --build
#
# Then visit http://localhost:8080 (or your reverse proxy).
#
# PORT BINDING SECURITY:
# By default Skiff binds to 127.0.0.1 only. This means it is
# NOT reachable from other machines on the network, which is the
# safe default — especially important before the vault is initialized,
# since /api/vault/setup is unauthenticated (first caller sets the
# master password).
#
# To expose on a LAN/public IP, set HOST_ADDR in your .env:
# HOST_ADDR=0.0.0.0 # all interfaces
# HOST_ADDR=192.168.1.x # specific NIC
# Then put Skiff behind a reverse proxy (nginx/Caddy) with TLS.
#
# DATA DIRECTORY:
# Create ./data as your own user before first run. If Docker
# creates it, it will be owned by root and the container's
# unprivileged node user cannot write the database.
# =====================================================
services:
skiff:
build: .
image: skiff:latest
container_name: skiff
restart: unless-stopped
ports:
# FIX: bind to 127.0.0.1 by default so the setup endpoint is not
# reachable from the network before the vault is initialized.
# Override by setting HOST_ADDR=0.0.0.0 in .env for reverse-proxy setups.
- "${HOST_ADDR:-127.0.0.1}:${HOST_PORT:-8080}:8080"
volumes:
- ./data:/app/data
environment:
SKIFF_PORT: 8080
SKIFF_HOST: 0.0.0.0
SKIFF_DATA_DIR: /app/data
SKIFF_COOKIE_SECRET: "${SKIFF_COOKIE_SECRET:?required - generate with: openssl rand -hex 32}"
SKIFF_TRUSTED_ORIGINS: ${SKIFF_TRUSTED_ORIGINS:-}
SKIFF_SETUP_TOKEN: ${SKIFF_SETUP_TOKEN:-}
SKIFF_TRUST_PROXY: ${SKIFF_TRUST_PROXY:-}
SKIFF_MAX_SESSIONS_PER_USER: ${SKIFF_MAX_SESSIONS_PER_USER:-}
NODE_ENV: production
healthcheck:
test: ["CMD", "node", "-e", "fetch('http://127.0.0.1:8080/api/health').then(r=>r.ok?process.exit(0):process.exit(1)).catch(()=>process.exit(1))"]
interval: 30s
timeout: 5s
retries: 3
start_period: 5s