services: bnkops.landing.server: image: lscr.io/linuxserver/nginx:latest container_name: bnkops.landing.server environment: - PUID=${USER_ID:-1000} # Uses USER_ID from your .env file, defaults to 1000 - PGID=${GROUP_ID:-1000} # Uses GROUP_ID from your .env file, defaults to 1000 - TZ=Etc/UTC volumes: - ./site:/config/www # Mounts your static site to Nginx's web root ports: - "4007:80" # Exposes Nginx's port 80 to host port 4001 restart: unless-stopped networks: - changemaker # Homepage App homepage-changemaker: image: ghcr.io/gethomepage/homepage:latest container_name: homepage-changemaker ports: - 3010:3000 volumes: - ./configs/homepage:/app/config - ./assets/icons:/app/public/icons - ./assets/images:/app/public/images - /var/run/docker.sock:/var/run/docker.sock environment: - PUID=1000 - PGID=1000 - TZ=Etc/UTC - HOMEPAGE_ALLOWED_HOSTS=* restart: unless-stopped networks: - changemaker homepage-changemaker-local: image: ghcr.io/gethomepage/homepage:latest container_name: homepage-changemaker-local ports: - 3011:3000 volumes: - ./configs/homepage-local:/app/config - ./assets/icons:/app/public/icons - ./assets/images:/app/public/images - /var/run/docker.sock:/var/run/docker.sock environment: - PUID=1000 - PGID=1000 - TZ=Etc/UTC - HOMEPAGE_ALLOWED_HOSTS=* restart: unless-stopped networks: - changemaker # n8n - Workflow Automation Tool n8n: image: docker.n8n.io/n8nio/n8n container_name: n8n-changemaker restart: unless-stopped ports: - "${N8N_PORT:-5678}:5678" environment: - N8N_HOST=${N8N_HOST:-n8n.${DOMAIN}} - N8N_PORT=5678 - N8N_PROTOCOL=https - NODE_ENV=production - WEBHOOK_URL=https://${N8N_HOST:-n8n.${DOMAIN}}/ - GENERIC_TIMEZONE=${GENERIC_TIMEZONE:-UTC} - N8N_ENCRYPTION_KEY=${N8N_ENCRYPTION_KEY:-changeMe} - N8N_USER_MANAGEMENT_DISABLED=false - N8N_DEFAULT_USER_EMAIL=${N8N_USER_EMAIL:-admin@example.com} - N8N_DEFAULT_USER_PASSWORD=${N8N_USER_PASSWORD:-changeMe} volumes: - n8n_data:/home/node/.n8n - ./local-files:/files networks: - changemaker # OpenWebUI - AI Chat Interface open-webui: image: ghcr.io/open-webui/open-webui:main container_name: open-webui-changemaker ports: - "${OPEN_WEBUI_PORT:-3005}:8080" volumes: - open-webui:/app/backend/data extra_hosts: - "host.docker.internal:host-gateway" restart: unless-stopped networks: - changemaker depends_on: - ollama # Excalidraw services excalidraw: image: kiliandeca/excalidraw container_name: excalidraw-changemaker healthcheck: disable: true ports: - "${EXCALIDRAW_PORT:-3333}:80" environment: BACKEND_V2_GET_URL: ${EXCALIDRAW_PUBLIC_URL:-http://localhost:3333}/api/v2/scenes/ BACKEND_V2_POST_URL: ${EXCALIDRAW_PUBLIC_URL:-http://localhost:3333}/api/v2/scenes/ LIBRARY_URL: ${EXCALIDRAW_LIBRARY_URL:-https://libraries.excalidraw.com} LIBRARY_BACKEND: ${EXCALIDRAW_LIBRARY_BACKEND:-https://us-central1-excalidraw-room-persistence.cloudfunctions.net/libraries} SOCKET_SERVER_URL: ${EXCALIDRAW_PUBLIC_SOCKET_URL:-http://localhost:3333}/ STORAGE_BACKEND: "http" HTTP_STORAGE_BACKEND_URL: ${EXCALIDRAW_PUBLIC_URL:-http://localhost:3333}/api/v2 restart: unless-stopped networks: - changemaker depends_on: - excalidraw-storage-backend - excalidraw-room - redis-excalidraw excalidraw-storage-backend: image: kiliandeca/excalidraw-storage-backend container_name: excalidraw-storage-backend-changemaker restart: unless-stopped environment: STORAGE_URI: redis://redis-excalidraw:6379 networks: - changemaker depends_on: - redis-excalidraw excalidraw-room: image: excalidraw/excalidraw-room container_name: excalidraw-room-changemaker restart: unless-stopped networks: - changemaker redis-excalidraw: image: redis:6.2-alpine container_name: redis-excalidraw-changemaker restart: unless-stopped volumes: - redis_excalidraw_data:/data networks: - changemaker # listmonk app listmonk-app: image: listmonk/listmonk:latest container_name: listmonk_app restart: unless-stopped ports: - "9000:9000" networks: - changemaker hostname: ${LISTMONK_HOSTNAME} depends_on: - listmonk-db command: [sh, -c, "./listmonk --install --idempotent --yes --config '' && ./listmonk --upgrade --yes --config '' && ./listmonk --config ''"] environment: LISTMONK_app__address: 0.0.0.0:9000 LISTMONK_db__user: ${POSTGRES_USER} LISTMONK_db__password: ${POSTGRES_PASSWORD} LISTMONK_db__database: ${POSTGRES_DB} LISTMONK_db__host: listmonk-db LISTMONK_db__port: 5432 LISTMONK_db__ssl_mode: disable LISTMONK_db__max_open: 25 LISTMONK_db__max_idle: 25 LISTMONK_db__max_lifetime: 300s TZ: Etc/UTC LISTMONK_ADMIN_USER: ${LISTMONK_ADMIN_USER:-} LISTMONK_ADMIN_PASSWORD: ${LISTMONK_ADMIN_PASSWORD:-} volumes: - ./assets/uploads:/listmonk/uploads:rw # Postgres database listmonk-db: image: postgres:17-alpine container_name: listmonk-db restart: unless-stopped ports: - "0.0.0.0:5432:5432" networks: - changemaker environment: POSTGRES_USER: ${POSTGRES_USER} POSTGRES_PASSWORD: ${POSTGRES_PASSWORD} POSTGRES_DB: ${POSTGRES_DB} healthcheck: test: ["CMD-SHELL", "pg_isready -U ${POSTGRES_USER}"] interval: 10s timeout: 5s retries: 6 volumes: - type: volume source: listmonk-data target: /var/lib/postgresql/data # Monica CRM monica-app: image: monica container_name: monica-app-changemaker depends_on: - monica-db ports: - 8085:80 environment: - APP_KEY=${MONICA_APP_KEY} - DB_HOST=monica-db - DB_USERNAME=${MONICA_DB_USERNAME} - DB_PASSWORD=${MONICA_DB_PASSWORD} volumes: - data:/var/www/html/storage restart: unless-stopped networks: - changemaker # Monica Database monica-db: image: mariadb:11 container_name: monica-db-changemaker environment: - MYSQL_RANDOM_ROOT_PASSWORD=true - MYSQL_DATABASE=${MONICA_MYSQL_DATABASE} - MYSQL_USER=${MONICA_MYSQL_USER} - MYSQL_PASSWORD=${MONICA_MYSQL_PASSWORD} volumes: - mysql:/var/lib/mysql restart: unless-stopped networks: - changemaker # MkDocs Documentation mkdocs: image: squidfunk/mkdocs-material container_name: mkdocs-changemaker volumes: - ./mkdocs:/docs:rw - ./assets/images:/docs/assets/images:rw user: "${USER_ID:-1000}:${GROUP_ID:-1000}" ports: - "${MKDOCS_PORT:-4000}:8000" environment: - SITE_URL=${BASE_DOMAIN:-https://changeme.org} command: serve --dev-addr=0.0.0.0:8000 --watch-theme --livereload networks: - changemaker restart: unless-stopped mkdocs-site-server: image: lscr.io/linuxserver/nginx:latest container_name: mkdocs-site-server-changemaker environment: - PUID=${USER_ID:-1000} # Uses USER_ID from your .env file, defaults to 1000 - PGID=${GROUP_ID:-1000} # Uses GROUP_ID from your .env file, defaults to 1000 - TZ=Etc/UTC volumes: - ./mkdocs/site:/config/www # Mounts your static site to Nginx's web root ports: - "4001:80" # Exposes Nginx's port 80 to host port 4001 restart: unless-stopped networks: - changemaker # Flatnotes - Note-taking app flatnotes: container_name: flatnotes-changemaker image: dullage/flatnotes:latest environment: PUID: ${FLATNOTES_PUID:-1000} PGID: ${FLATNOTES_PGID:-1000} FLATNOTES_AUTH_TYPE: ${FLATNOTES_AUTH_TYPE:-password} FLATNOTES_USERNAME: ${FLATNOTES_USERNAME} FLATNOTES_PASSWORD: ${FLATNOTES_PASSWORD} FLATNOTES_SECRET_KEY: ${FLATNOTES_SECRET_KEY} volumes: - ./mkdocs/docs/notes:/data ports: - "${FLATNOTES_PORT:-8080}:8080" restart: unless-stopped networks: - changemaker code-server: build: context: . dockerfile: Dockerfile.code-server container_name: code-server-changemaker environment: - DOCKER_USER=${USER_NAME:-coder} - DEFAULT_WORKSPACE=/home/coder/mkdocs user: "${USER_ID:-1000}:${GROUP_ID:-1000}" volumes: - ./configs/code-server/.config:/home/coder/.config - ./configs/code-server/.local:/home/coder/.local - ./mkdocs:/home/coder/mkdocs/ - ./site:/home/coder/site/ ports: - "${CODE_SERVER_PORT:-8888}:8080" restart: unless-stopped networks: - changemaker ollama: image: ollama/ollama container_name: ollama-changemaker volumes: - ollama:/root/.ollama ports: - "11435:11434" restart: unless-stopped networks: - changemaker # Gitea - Git service gitea-app: image: docker.gitea.com/gitea:1.23.7 container_name: gitea_changemaker environment: - USER_UID=${USER_ID} - USER_GID=${GROUP_ID} - GITEA__database__DB_TYPE=${GITEA_DB_TYPE} - GITEA__database__HOST=${GITEA_DB_HOST} - GITEA__database__NAME=${GITEA_DB_NAME} - GITEA__database__USER=${GITEA_DB_USER} - GITEA__database__PASSWD=${GITEA_DB_PASSWD} - GITEA__server__ROOT_URL=${GITEA_ROOT_URL} - GITEA__server__HTTP_PORT=${GITEA_WEB_PORT} - GITEA__server__PROTOCOL=http - GITEA__server__DOMAIN=${GITEA_DOMAIN} - GITEA__server__ENABLE_GZIP=true - GITEA__server__PROXY_PROTOCOL=true - GITEA__server__PROXY_PROXY_PROTOCOL_TLS=true - GITEA__server__PROXY_ALLOW_SUBNET=0.0.0.0/0 restart: always networks: - gitea volumes: - gitea_data:/data - /etc/timezone:/etc/timezone:ro - /etc/localtime:/etc/localtime:ro ports: - "${GITEA_WEB_PORT}:3030" - "${GITEA_SSH_PORT}:22" depends_on: - gitea-db gitea-db: image: mysql:8 container_name: gitea_mysql_changemaker restart: always environment: - MYSQL_ROOT_PASSWORD=${GITEA_DB_ROOT_PASSWORD} - MYSQL_USER=${GITEA_DB_USER} - MYSQL_PASSWORD=${GITEA_DB_PASSWD} - MYSQL_DATABASE=${GITEA_DB_NAME} networks: - gitea volumes: - mysql_data:/var/lib/mysql healthcheck: test: ["CMD", "mysqladmin", "ping", "-h", "localhost", "-u", "${GITEA_DB_USER}", "-p${GITEA_DB_PASSWD}"] interval: 10s timeout: 5s retries: 5 portainer: image: portainer/portainer-ce:lts container_name: portainer-changemaker restart: always environment: - DISABLE_HTTP_REDIRECT=true networks: - changemaker ports: - "8005:8000" - "9444:9443" volumes: - /var/run/docker.sock:/var/run/docker.sock - portainer_data:/data # Mini-QR - QR Code Generator mini-qr: image: ghcr.io/lyqht/mini-qr:latest container_name: mini-qr ports: - 8081:8080 restart: unless-stopped networks: - changemaker # Ferdium - Multiple messaging app client ferdium: image: lscr.io/linuxserver/ferdium:latest container_name: ferdium-changemaker security_opt: - seccomp:unconfined #optional environment: - PUID=1000 - PGID=1000 - TZ=Etc/UTC - CUSTOM_PORT=3009 - CUSTOM_HTTPS_PORT=3006 volumes: - ./configs/ferdium:/config ports: - 3009:3009 - 3006:3006 shm_size: "1gb" restart: unless-stopped networks: - changemaker # Apache Answer - Q&A Platform answer: image: apache/answer container_name: answer-changemaker restart: unless-stopped environment: - DB_TYPE=sqlite3 - PAGINATION_PAGE_SIZE=10 - LANGUAGE=en-US - TZ=Etc/UTC ports: - "${ANSWER_APP_PORT:-9080}:80" volumes: - ./answer-data:/data networks: - changemaker # NocoDB - Open Source Airtable Alternative nocodb: depends_on: root_db: condition: service_healthy environment: NC_DB: "pg://root_db:5432?u=postgres&p=password&d=root_db" image: "nocodb/nocodb:latest" ports: - "8090:8080" restart: always volumes: - "nc_data:/usr/app/data" networks: - changemaker root_db: environment: POSTGRES_DB: root_db POSTGRES_PASSWORD: password POSTGRES_USER: postgres healthcheck: interval: 10s retries: 10 test: "pg_isready -U \"$$POSTGRES_USER\" -d \"$$POSTGRES_DB\"" timeout: 2s image: postgres:16.6 restart: always volumes: - "db_data:/var/lib/postgresql/data" networks: - changemaker # ConvertX - File Conversion Tool convertx: image: ghcr.io/c4illin/convertx container_name: convertx-changemaker restart: unless-stopped ports: - "${CONVERTX_PORT:-3100}:3000" environment: - JWT_SECRET=${CONVERTX_JWT_SECRET:-aLongAndSecretStringUsedToSignTheJSONWebToken1234} volumes: - ./convertx-data:/app/data networks: - changemaker # Rocket.Chat - Team Chat Platform rocketchat: image: ${ROCKETCHAT_IMAGE:-registry.rocket.chat/rocketchat/rocket.chat}:${ROCKETCHAT_RELEASE:-latest} container_name: rocketchat-changemaker restart: unless-stopped environment: MONGO_URL: "mongodb://${ROCKETCHAT_MONGODB_HOST:-mongodb-rocketchat}:${ROCKETCHAT_MONGODB_PORT:-27017}/${ROCKETCHAT_MONGODB_DATABASE:-rocketchat}?replicaSet=${ROCKETCHAT_MONGODB_REPLICA_SET:-rs0}" MONGO_OPLOG_URL: "mongodb://${ROCKETCHAT_MONGODB_HOST:-mongodb-rocketchat}:${ROCKETCHAT_MONGODB_PORT:-27017}/local?replicaSet=${ROCKETCHAT_MONGODB_REPLICA_SET:-rs0}" ROOT_URL: ${ROCKETCHAT_ROOT_URL:-http://localhost:${ROCKETCHAT_PORT:-3004}} PORT: ${ROCKETCHAT_CONTAINER_PORT:-3000} DEPLOY_METHOD: docker DEPLOY_PLATFORM: ${ROCKETCHAT_DEPLOYMENT_ENVIRONMENT:-changemaker} ports: - "${ROCKETCHAT_PORT:-3004}:${ROCKETCHAT_CONTAINER_PORT:-3000}" depends_on: - mongodb-rocketchat healthcheck: test: ["CMD", "curl", "-f", "http://localhost:${ROCKETCHAT_CONTAINER_PORT:-3000}/api/info"] interval: 30s timeout: 10s retries: 5 start_period: 60s networks: - changemaker # MongoDB for Rocket.Chat mongodb-rocketchat: image: docker.io/bitnami/mongodb:${ROCKETCHAT_MONGODB_VERSION:-6.0} container_name: mongodb-rocketchat-changemaker restart: unless-stopped volumes: - mongodb_rocketchat_data:/bitnami/mongodb environment: MONGODB_REPLICA_SET_MODE: primary MONGODB_REPLICA_SET_NAME: ${ROCKETCHAT_MONGODB_REPLICA_SET:-rs0} MONGODB_PORT_NUMBER: ${ROCKETCHAT_MONGODB_PORT:-27017} MONGODB_INITIAL_PRIMARY_HOST: ${ROCKETCHAT_MONGODB_HOST:-mongodb-rocketchat} MONGODB_INITIAL_PRIMARY_PORT_NUMBER: ${ROCKETCHAT_MONGODB_PORT:-27017} MONGODB_ADVERTISED_HOSTNAME: ${ROCKETCHAT_MONGODB_HOST:-mongodb-rocketchat} MONGODB_ENABLE_JOURNAL: ${ROCKETCHAT_MONGODB_ENABLE_JOURNAL:-true} ALLOW_EMPTY_PASSWORD: ${ROCKETCHAT_MONGODB_ALLOW_EMPTY_PASSWORD:-yes} networks: - changemaker networks: changemaker: driver: bridge gitea: external: false volumes: listmonk-data: data: name: data mysql: name: mysql ollama: gitea_data: driver: local mysql_data: driver: local portainer_data: name: portainer_data_changemaker redis_excalidraw_data: driver: local open-webui: driver: local notused: nocodb_db_data: driver: local n8n_data: driver: local mongodb_rocketchat_data: driver: local db_data: {} nc_data: {}