services: postersplus: build: context: . dockerfile: ./dockerfile args: # Bake the PP-OCRv5 Mobile detector into the image (default). Set # BAKE_PPOCR_MODEL=false in your .env for a lean image that downloads the # model once at runtime instead. BAKE_PPOCR_MODEL: "${BAKE_PPOCR_MODEL:-true}" image: postersplus ports: - "8000:8000" restart: unless-stopped volumes: # Named volume (not a host bind) so a fresh `compose up` works with the # non-root uid 568 the image runs as: Docker seeds a new named volume's # ownership from the image's /app/cache (owned by 568), whereas a fresh # host bind dir is created root-owned and would be unwritable. Holds the # cache DB, TMDB posters/logos, and composites. # To supply discovery_overrides.json, copy it in after first start: # docker compose cp ./discovery_overrides.json postersplus:/app/cache/ - postersplus-cache:/app/cache env_file: - .env # see this file for an explanation of what each flag does environment: - TMDB_API_KEY=${TMDB_API_KEY:-} - MDBLIST_API_KEY=${MDBLIST_API_KEY:-} - TVDB_API_KEY=${TVDB_API_KEY:-} - TVDB_SUBSCRIBER_PIN=${TVDB_SUBSCRIBER_PIN:-} - TVDB_USE_LOGOS=${TVDB_USE_LOGOS:-true} - TVDB_USE_BACKDROPS=${TVDB_USE_BACKDROPS:-true} - TVDB_USE_POSTERS=${TVDB_USE_POSTERS:-false} - TVDB_LOGO_PRIORITY=${TVDB_LOGO_PRIORITY:-3} - ACCESS_KEY=${ACCESS_KEY:-} - WORKERS=${WORKERS:-1} - TEXTLESS_DETECTION_CONCURRENCY=${TEXTLESS_DETECTION_CONCURRENCY:-2} - TEXTLESS_DETECTION_MAX_VOTES=${TEXTLESS_DETECTION_MAX_VOTES:-3000} - AIOSTREAMS_URL=${AIOSTREAMS_URL:-} - AIOSTREAMS_AUTH=${AIOSTREAMS_AUTH:-} - QUALITY_OLD_CACHE_DURATION=${QUALITY_OLD_CACHE_DURATION:-90} - QUALITY_BG_CONCURRENCY=${QUALITY_BG_CONCURRENCY:-5} - CDN_CACHE_TTL=${CDN_CACHE_TTL:-0} - COMPOSITE_CACHE_TTL=${COMPOSITE_CACHE_TTL:-604800} - COMPOSITE_MAX_ENTRIES=${COMPOSITE_MAX_ENTRIES:-0} - DEFAULT_LOGO_LANGUAGE=${DEFAULT_LOGO_LANGUAGE:-en} # --- ElfHosted fork: hosted-mode backends (all opt-in; unset = upstream) --- # Postgres / Redis / S3 backends. Leave unset for SQLite + in-process + # local FS. See .env / .env.example for the commented postgres/redis/minio # sidecar recipes and full descriptions. - DATABASE_URL=${DATABASE_URL:-} - REDIS_URL=${REDIS_URL:-} - OBJECT_STORE_URL=${OBJECT_STORE_URL:-} - OBJECT_STORE_PUBLIC_URL=${OBJECT_STORE_PUBLIC_URL:-} # Static-preset moat + observability + limits. - PRESET_ENABLED=${PRESET_ENABLED:-} - PRESET_CDN_CACHE_TTL=${PRESET_CDN_CACHE_TTL:-86400} - ANONYMOUS_TMDB_RPS=${ANONYMOUS_TMDB_RPS:-5} - RATE_LIMIT_RPS=${RATE_LIMIT_RPS:-0} - RENDER_CONCURRENCY=${RENDER_CONCURRENCY:-0} - RENDER_QUEUE_TIMEOUT=${RENDER_QUEUE_TIMEOUT:-30} - METRICS_ACCESS_KEY=${METRICS_ACCESS_KEY:-} - LOG_FORMAT=${LOG_FORMAT:-text} # The image runs as the non-root uid 568; the named volume below is seeded # writable for it automatically (see the volumes: note). healthcheck: # Exec form (no shell) so a probe that overruns is killed outright rather # than leaving an orphaned python3 behind; see the HEALTHCHECK note in # the dockerfile. test: ["CMD", "python3", "-c", "import http.client; c = http.client.HTTPConnection('localhost', 8000, timeout=8); c.request('GET', '/health'); r = c.getresponse(); raise SystemExit(0 if r.status == 200 else 1)"] interval: 30s timeout: 10s retries: 3 start_period: 15s volumes: postersplus-cache: