Files
public/stacks/productivity/postiz/docker-compose.yaml
T
thesabear bebcd714af Restructure compose mirror: stacks/ grouped by purpose, not by host
Replaces rocky-docker-lxc/, caddy-vm/, monitoring-vm/, and automation/
with a single stacks/ tree grouped by function (identity-and-security,
platform, media, productivity, dev-tools) - 55 stacks total, every one
a real directory in the private repos today.

Resolves all outstanding drift: adds Wazuh (previously entirely
missing), Firefly III and Postiz (never mirrored), the internal-zone
Caddy instance and the Cron Scheduler's separate NocoDB instance
(both previously conflated with their counterparts under one shared
folder); renames Calibre-Web to calibre-web-automated and splits
Kodi-MariaDB into kodi + mariadb-latest to match what the private
repos actually run now; drops the decommissioned NetBox stack.

Also removes automation/iac/old-content/ and
automation/ansible/old-playbooks/ in the same pass - both folders
were entirely stale content describing a superseded architecture
(GitLab instead of Gitea, HAProxy+mTLS SSO instead of the current
Caddy+Authentik setup), now replaced by docs/iac-pipeline.md.
2026-08-22 07:44:11 +03:00

158 lines
4.8 KiB
YAML

services:
postiz:
image: ghcr.io/gitroomhq/postiz-app:latest
container_name: postiz
restart: unless-stopped
env_file:
- .env.secrets # JWT_SECRET, DATABASE_URL, social-platform client IDs/secrets — never committed
environment:
TZ: ${TZ}
MAIN_URL: ${MAIN_URL}
FRONTEND_URL: ${FRONTEND_URL}
NEXT_PUBLIC_BACKEND_URL: ${NEXT_PUBLIC_BACKEND_URL}
BACKEND_INTERNAL_URL: ${BACKEND_INTERNAL_URL}
REDIS_URL: redis://postiz-redis:6379
TEMPORAL_ADDRESS: temporal:7233
IS_GENERAL: "true"
DISABLE_REGISTRATION: ${DISABLE_REGISTRATION}
STORAGE_PROVIDER: ${STORAGE_PROVIDER}
UPLOAD_DIRECTORY: ${UPLOAD_DIRECTORY}
NEXT_PUBLIC_UPLOAD_DIRECTORY: ${UPLOAD_DIRECTORY}
MASTODON_URL: ${MASTODON_URL}
volumes:
- /path/to/postiz/config:/config/
- /path/to/postiz/uploads:/uploads/
ports:
- "${HTTP_PORT}:5000"
depends_on:
postiz-postgres:
condition: service_healthy
postiz-redis:
condition: service_healthy
networks:
- postiz-net
postiz-postgres:
image: postgres:18-alpine
container_name: postiz-postgres
restart: unless-stopped
env_file:
- .env.secrets # POSTGRES_PASSWORD — never committed
environment:
TZ: ${TZ}
POSTGRES_USER: ${POSTIZ_POSTGRES_USER}
POSTGRES_DB: ${POSTIZ_POSTGRES_DB}
volumes:
- /path/to/postiz/postgres_data:/var/lib/postgresql
healthcheck:
test: ["CMD-SHELL", "pg_isready -U ${POSTIZ_POSTGRES_USER} -d ${POSTIZ_POSTGRES_DB}"]
interval: 10s
timeout: 3s
retries: 3
networks:
- postiz-net
postiz-redis:
image: valkey/valkey:9.0-alpine
container_name: postiz-redis
restart: unless-stopped
healthcheck:
test: ["CMD-SHELL", "valkey-cli ping"]
interval: 10s
timeout: 3s
retries: 3
volumes:
- /path/to/postiz/redis_data:/data
networks:
- postiz-net
# Temporal stack: required since Postiz v2.12.0 for all background jobs
# (scheduled posting, OAuth token refresh, email digests) — not optional,
# a real surprise in this app's actual deployment footprint.
temporal-elasticsearch:
image: elasticsearch:7.17.27
container_name: postiz-temporal-elasticsearch
restart: unless-stopped
environment:
- cluster.routing.allocation.disk.threshold_enabled=true
- cluster.routing.allocation.disk.watermark.low=512mb
- cluster.routing.allocation.disk.watermark.high=256mb
- cluster.routing.allocation.disk.watermark.flood_stage=128mb
- discovery.type=single-node
- ES_JAVA_OPTS=-Xms256m -Xmx256m
- xpack.security.enabled=false
volumes:
- /path/to/postiz/temporal_elasticsearch_data:/usr/share/elasticsearch/data
networks:
- postiz-net
temporal-postgres:
image: postgres:18-alpine
container_name: postiz-temporal-postgres
restart: unless-stopped
env_file:
- .env.secrets.temporal-postgres # POSTGRES_PASSWORD — never committed; separate file, avoids a collision with postiz-postgres
environment:
TZ: ${TZ}
POSTGRES_USER: ${TEMPORAL_POSTGRES_USER}
volumes:
- /path/to/postiz/temporal_postgres_data:/var/lib/postgresql
networks:
- postiz-net
temporal:
image: temporalio/auto-setup:1.28.1
container_name: postiz-temporal
restart: unless-stopped
depends_on:
- temporal-postgres
- temporal-elasticsearch
env_file:
- .env.secrets # POSTGRES_PWD — never committed
environment:
- DB=postgres12
- DB_PORT=5432
- POSTGRES_USER=${TEMPORAL_POSTGRES_USER}
- POSTGRES_SEEDS=temporal-postgres
- DYNAMIC_CONFIG_FILE_PATH=config/dynamicconfig/development-sql.yaml
- ENABLE_ES=true
- ES_SEEDS=temporal-elasticsearch
- ES_VERSION=v7
- TEMPORAL_NAMESPACE=default
ports:
- "127.0.0.1:${TEMPORAL_PORT}:7233" # gRPC control plane, unauthenticated by default — localhost-only
volumes:
- ./dynamicconfig:/etc/temporal/config/dynamicconfig
networks:
- postiz-net
temporal-admin-tools:
image: temporalio/admin-tools:1.28.1-tctl-1.18.4-cli-1.4.1
container_name: postiz-temporal-admin-tools
restart: unless-stopped
environment:
- TEMPORAL_ADDRESS=temporal:7233
- TEMPORAL_CLI_ADDRESS=temporal:7233
depends_on:
- temporal
stdin_open: true
tty: true
networks:
- postiz-net
temporal-ui:
image: temporalio/ui:2.34.0
container_name: postiz-temporal-ui
restart: unless-stopped
environment:
- TEMPORAL_ADDRESS=temporal:7233
- TEMPORAL_CORS_ORIGINS=http://127.0.0.1:${TEMPORAL_UI_PORT}
ports:
- "127.0.0.1:${TEMPORAL_UI_PORT}:8080" # unauthenticated by default — localhost-only, SSH-tunnel to debug
networks:
- postiz-net
networks:
postiz-net:
external: true