x-anysync-daemon: &anysync-daemon restart: unless-stopped deploy: resources: limits: memory: ${ANY_SYNC_DAEMONS_MEMORY_LIMIT:-} x-anysync-node: &anysync-node image: "ghcr.io/anyproto/any-sync-node:${ANY_SYNC_NODE_VERSION}" depends_on: any-sync-coordinator: condition: service_started services: # refuse to start the stack while data from a previous MinIO install # has not been migrated to Garage yet (see the Upgrade Guide wiki page) s3-guard: restart: "no" build: context: . dockerfile: Dockerfile-any-sync-init entrypoint: ["bash", "/code/docker-generateconfig/s3-guard.sh"] volumes: - ./.env:/code/.env:ro,Z - ./docker-generateconfig:/code/docker-generateconfig:ro,Z - "${STORAGE_DIR}:/code/storage:Z" # generate and process any-sync configs any-sync-init: restart: "no" depends_on: s3-guard: condition: service_completed_successfully build: context: . dockerfile: Dockerfile-any-sync-init volumes: - ./.env:/code/.env:ro,Z - ./docker-generateconfig:/code/docker-generateconfig:ro,Z - ./etc:/code/etc:Z - "${STORAGE_DIR}:/code/storage:Z" mongo-1: depends_on: any-sync-init: condition: service_completed_successfully image: "mongo:${MONGO_VERSION}" restart: unless-stopped command: ["--replSet", "${MONGO_REPLICA_SET}", "--port", "${MONGO_1_PORT}"] volumes: - "${STORAGE_DIR}/mongo-1:/data/db:Z" healthcheck: test: test $$(mongosh --port ${MONGO_1_PORT} --quiet --eval "try {rs.initiate({_id:'${MONGO_REPLICA_SET}',members:[{_id:0,host:\"mongo-1:${MONGO_1_PORT}\"}]})} catch(e) {rs.status().ok}") -eq 1 interval: 10s start_period: 30s ports: - "127.0.0.1:${MONGO_1_PORT}:${MONGO_1_PORT}" redis: depends_on: any-sync-init: condition: service_completed_successfully image: "redis/redis-stack-server:${REDIS_VERSION}" restart: unless-stopped command: ["redis-server", "--port", "${REDIS_PORT}", "--dir", "/data/", "--appendonly", "yes", "--maxmemory", "${REDIS_MAXMEMORY}", "--maxmemory-policy", "noeviction", "--protected-mode", "no", "--loadmodule", "/opt/redis-stack/lib/redisbloom.so"] volumes: - "${STORAGE_DIR}/redis:/data:Z" healthcheck: test: [ "CMD", "redis-cli", "--raw", "-p", "${REDIS_PORT}", "incr", "ping" ] interval: 10s timeout: 30s retries: 3 ports: - "127.0.0.1:${REDIS_PORT}:${REDIS_PORT}" # S3-compatible object storage for any-sync-filenode. # The bucket and the access key are created automatically on first start. garage: image: "dxflrs/garage:${GARAGE_VERSION:?GARAGE_VERSION is not set - your .env is outdated, see https://github.com/anyproto/any-sync-dockercompose/wiki/Upgrade-Guide}" restart: unless-stopped command: ["/garage", "server", "--single-node", "--default-bucket", "--default-access-key"] environment: GARAGE_RPC_SECRET: "${GARAGE_RPC_SECRET:?GARAGE_RPC_SECRET is not set - your .env is outdated, see https://github.com/anyproto/any-sync-dockercompose/wiki/Upgrade-Guide}" GARAGE_DEFAULT_ACCESS_KEY: "${AWS_ACCESS_KEY_ID}" GARAGE_DEFAULT_SECRET_KEY: "${AWS_SECRET_ACCESS_KEY}" GARAGE_DEFAULT_BUCKET: "${S3_BUCKET:?S3_BUCKET is not set - your .env is outdated, see https://github.com/anyproto/any-sync-dockercompose/wiki/Upgrade-Guide}" volumes: - ./garage/garage.toml:/etc/garage.toml:ro,Z - "${STORAGE_DIR}/garage:/var/lib/garage:Z" healthcheck: test: ["CMD", "/garage", "status"] interval: 5s timeout: 10s retries: 5 start_period: 10s # --- one-off migration from MinIO to Garage, see the Upgrade Guide ----------- # Not started by "docker compose up"; only by: # docker compose --profile migrate run --rm s3-migrate minio-legacy: profiles: ["migrate"] # official MinIO images are no longer published; defaults to a community build image: "${MINIO_LEGACY_IMAGE:-pgsty/minio:RELEASE.2026-08-04T00-00-00Z}" restart: "no" command: ["server", "/data", "--address", ":9000"] environment: MINIO_ROOT_USER: "${AWS_ACCESS_KEY_ID}" MINIO_ROOT_PASSWORD: "${AWS_SECRET_ACCESS_KEY}" volumes: - "${STORAGE_DIR}/minio:/data:Z" healthcheck: test: bash -c ':> /dev/tcp/127.0.0.1/9000' || exit 1 interval: 5s timeout: 10s retries: 3 s3-migrate: profiles: ["migrate"] image: "rclone/rclone:${RCLONE_VERSION}" restart: "no" depends_on: minio-legacy: condition: service_healthy garage: condition: service_healthy environment: AWS_ACCESS_KEY_ID: "${AWS_ACCESS_KEY_ID}" AWS_SECRET_ACCESS_KEY: "${AWS_SECRET_ACCESS_KEY}" S3_BUCKET: "${S3_BUCKET}" S3_REGION: "${S3_REGION}" S3_LEGACY_BUCKET: "${S3_LEGACY_BUCKET}" entrypoint: ["/bin/sh", "/code/docker-generateconfig/migrate-s3.sh"] volumes: - ./docker-generateconfig:/code/docker-generateconfig:ro,Z - "${STORAGE_DIR}:/code/storage:Z" # --------------------------------------------------------------------------- any-sync-coordinator_bootstrap: image: "ghcr.io/anyproto/any-sync-coordinator:${ANY_SYNC_COORDINATOR_VERSION}" depends_on: any-sync-init: condition: service_completed_successfully mongo-1: condition: service_healthy volumes: - ./etc/any-sync-coordinator:/etc/any-sync-coordinator:Z restart: "no" command: ["/bin/any-sync-confapply", "-c", "/etc/any-sync-coordinator/config.yml", "-n", "/etc/any-sync-coordinator/network.yml", "-e"] any-sync-coordinator: <<: *anysync-daemon image: "ghcr.io/anyproto/any-sync-coordinator:${ANY_SYNC_COORDINATOR_VERSION}" depends_on: any-sync-init: condition: service_completed_successfully mongo-1: condition: service_healthy any-sync-coordinator_bootstrap: condition: service_completed_successfully ports: - "${ANY_SYNC_COORDINATOR_PORT}:${ANY_SYNC_COORDINATOR_PORT}" - "${ANY_SYNC_COORDINATOR_QUIC_PORT}:${ANY_SYNC_COORDINATOR_QUIC_PORT}/udp" - "${ANY_SYNC_COORDINATOR_METRIC_ADDR}:8000" volumes: - ./etc/any-sync-coordinator:/etc/any-sync-coordinator:Z - "${STORAGE_DIR}/networkStore/any-sync-coordinator:/networkStore:Z" any-sync-filenode: <<: *anysync-daemon image: "ghcr.io/anyproto/any-sync-filenode:${ANY_SYNC_FILENODE_VERSION}" depends_on: redis: condition: service_healthy garage: condition: service_healthy any-sync-coordinator: condition: service_started ports: - "${ANY_SYNC_FILENODE_PORT}:${ANY_SYNC_FILENODE_PORT}" - "${ANY_SYNC_FILENODE_QUIC_PORT}:${ANY_SYNC_FILENODE_QUIC_PORT}/udp" - "${ANY_SYNC_FILENODE_METRIC_ADDR}:8000" volumes: - ./etc/any-sync-filenode:/etc/any-sync-filenode:Z - ./etc/.aws:/root/.aws:ro - "${STORAGE_DIR}/networkStore/any-sync-filenode:/networkStore:Z" any-sync-node-1: <<: [*anysync-daemon, *anysync-node] ports: - "${ANY_SYNC_NODE_1_PORT}:${ANY_SYNC_NODE_1_PORT}" - "${ANY_SYNC_NODE_1_QUIC_PORT}:${ANY_SYNC_NODE_1_QUIC_PORT}/udp" - "${ANY_SYNC_NODE_1_API_SERVER_ADDR}:8080" - "${ANY_SYNC_NODE_1_METRIC_ADDR}:8000" volumes: - ./etc/any-sync-node-1:/etc/any-sync-node:Z - ./etc/.aws:/root/.aws:ro - "${STORAGE_DIR}/any-sync-node-1:/storage:Z" - "${STORAGE_DIR}/anyStorage/any-sync-node-1:/anyStorage:Z" - "${STORAGE_DIR}/networkStore/any-sync-node-1:/networkStore:Z" any-sync-node-2: <<: [*anysync-daemon, *anysync-node] ports: - "${ANY_SYNC_NODE_2_PORT}:${ANY_SYNC_NODE_2_PORT}" - "${ANY_SYNC_NODE_2_QUIC_PORT}:${ANY_SYNC_NODE_2_QUIC_PORT}/udp" - "${ANY_SYNC_NODE_2_API_SERVER_ADDR}:8080" - "${ANY_SYNC_NODE_2_METRIC_ADDR}:8000" volumes: - ./etc/any-sync-node-2:/etc/any-sync-node:Z - ./etc/.aws:/root/.aws:ro - "${STORAGE_DIR}/any-sync-node-2:/storage:Z" - "${STORAGE_DIR}/anyStorage/any-sync-node-2:/anyStorage:Z" - "${STORAGE_DIR}/networkStore/any-sync-node-2:/networkStore:Z" any-sync-node-3: <<: [*anysync-daemon, *anysync-node] ports: - "${ANY_SYNC_NODE_3_PORT}:${ANY_SYNC_NODE_3_PORT}" - "${ANY_SYNC_NODE_3_QUIC_PORT}:${ANY_SYNC_NODE_3_QUIC_PORT}/udp" - "${ANY_SYNC_NODE_3_API_SERVER_ADDR}:8080" - "${ANY_SYNC_NODE_3_METRIC_ADDR}:8000" volumes: - ./etc/any-sync-node-3:/etc/any-sync-node:Z - ./etc/.aws:/root/.aws:ro - "${STORAGE_DIR}/any-sync-node-3:/storage:Z" - "${STORAGE_DIR}/anyStorage/any-sync-node-3:/anyStorage:Z" - "${STORAGE_DIR}/networkStore/any-sync-node-3:/networkStore:Z" any-sync-consensusnode: <<: *anysync-daemon image: "ghcr.io/anyproto/any-sync-consensusnode:${ANY_SYNC_CONSENSUSNODE_VERSION}" depends_on: any-sync-coordinator: condition: service_started ports: - "${ANY_SYNC_CONSENSUSNODE_PORT}:${ANY_SYNC_CONSENSUSNODE_PORT}" - "${ANY_SYNC_CONSENSUSNODE_QUIC_PORT}:${ANY_SYNC_CONSENSUSNODE_QUIC_PORT}/udp" - "${ANY_SYNC_CONSENSUSNODE_METRIC_ADDR}:8000" volumes: - ./etc/any-sync-consensusnode:/etc/any-sync-consensusnode:Z - "${STORAGE_DIR}/networkStore/any-sync-consensusnode:/networkStore:Z" # any-sync-netcheck netcheck: image: "ghcr.io/anyproto/any-sync-tools:${ANY_SYNC_TOOLS_VERSION}" pull_policy: always restart: unless-stopped depends_on: - any-sync-consensusnode - any-sync-filenode - any-sync-coordinator - any-sync-node-1 - any-sync-node-2 - any-sync-node-3 volumes: - "${STORAGE_DIR}/docker-generateconfig:/conf:Z" entrypoint: ["/bin/sh", "-c"] command: - | while true; do echo "$(date): Running netcheck..." any-sync-netcheck -c /conf/nodes.yml 2>&1 | tee /tmp/netcheck-last.log echo "$(date): Netcheck completed, waiting 5 seconds..." sleep 5 done stop_signal: SIGTERM healthcheck: test: grep -qE 'netcheck\s+success' /tmp/netcheck-last.log interval: 5s start_period: 5s # optional services - uncomment if necessary # usage: https://github.com/anyproto/any-sync-dockercompose/wiki/Anytype-cli # anytype-cli bootstrap - create bot account on first run # anytype-cli_bootstrap: # image: "ghcr.io/anyproto/anytype-cli:${ANYTYPE_CLI_VERSION}" # restart: "no" # depends_on: # netcheck: # condition: service_healthy # volumes: # - ./etc/client.yml:/etc/anytype/network.yml:ro # - "${STORAGE_DIR}/anytype-cli:/root/.anytype:Z" # environment: # - ANYTYPE_CLI_ACCOUNT_NAME=${ANYTYPE_CLI_ACCOUNT_NAME:-anytype-bot} # entrypoint: > # /bin/sh -c " # if [ ! -f /root/.anytype/config.json ]; then # echo 'Creating bot account...'; # anytype serve & # SERVER_PID=$$!; # sleep 2; # anytype auth create $${ANYTYPE_CLI_ACCOUNT_NAME} --network-config /etc/anytype/network.yml || true; # echo 'Waiting for account initialization...'; # sleep 2; # kill $$SERVER_PID 2>/dev/null || true; # wait $$SERVER_PID 2>/dev/null || true; # else # echo 'Bot account already exists, skipping bootstrap'; # fi; # exit 0; # " # anytype-cli server # anytype-cli: # image: "ghcr.io/anyproto/anytype-cli:${ANYTYPE_CLI_VERSION}" # restart: unless-stopped # depends_on: # anytype-cli_bootstrap: # condition: service_completed_successfully # ports: # - "${ANYTYPE_CLI_GRPC_PORT}:31010" # - "${ANYTYPE_CLI_GRPC_WEB_PORT}:31011" # - "${ANYTYPE_CLI_API_PORT}:31012" # volumes: # - ./etc/client.yml:/etc/anytype/network.yml:ro # - "${STORAGE_DIR}/anytype-cli:/root/.anytype:Z" # healthcheck: # test: nc -z 127.0.0.1 31010 || exit 1 # interval: 30s # timeout: 5s # start_period: 15s # retries: 3