services:
  mockapi:
    image: wiremock/wiremock:3.9.1
    ports:
      - '8088:8080'
    volumes:
      - ${MOCK_API_DATA_PATH}/mappings:/home/wiremock/mappings

  redis:
    image: redis:6.2.14-alpine
    restart: always
    ports:
      - 6379:6379
    healthcheck:
      test: ['CMD', 'redis-cli', 'ping']
      interval: 1s
      timeout: 3s

  postgres:
    image: postgres:16.4
    restart: always
    environment:
      - POSTGRES_DB=n8n
      - POSTGRES_USER=postgres
      - POSTGRES_PASSWORD=password
      - PGDATA=/var/lib/postgresql/data/pgdata
    volumes:
      - ${RUN_DIR}/postgres:/var/lib/postgresql/data
    healthcheck:
      test: ['CMD-SHELL', 'pg_isready -U postgres']
      interval: 5s
      timeout: 5s
      retries: 10

  n8n_worker1:
    image: ghcr.io/n8n-io/n8n:${N8N_VERSION:-latest}
    environment:
      - N8N_DIAGNOSTICS_ENABLED=false
      - N8N_USER_FOLDER=/n8n/worker1
      - N8N_ENCRYPTION_KEY=${N8N_ENCRYPTION_KEY}
      - N8N_LICENSE_CERT=${N8N_LICENSE_CERT}
      - N8N_LICENSE_ACTIVATION_KEY=${N8N_LICENSE_ACTIVATION_KEY}
      - N8N_LICENSE_TENANT_ID=${N8N_LICENSE_TENANT_ID}
      # Scaling mode config
      - EXECUTIONS_MODE=queue
      - QUEUE_BULL_REDIS_HOST=redis
      - QUEUE_HEALTH_CHECK_ACTIVE=true
      - N8N_CONCURRENCY_PRODUCTION_LIMIT=10
      # DB config
      - DB_TYPE=postgresdb
      - DB_POSTGRESDB_HOST=postgres
      - DB_POSTGRESDB_PASSWORD=password
      # Task Runner config
      - N8N_RUNNERS_ENABLED=true
      - N8N_RUNNERS_MODE=external
      - N8N_RUNNERS_BROKER_LISTEN_ADDRESS=0.0.0.0
      - N8N_RUNNERS_AUTH_TOKEN=test
    command: worker
    volumes:
      - ${RUN_DIR}/n8n-worker1:/n8n
    depends_on:
      postgres:
        condition: service_healthy
      redis:
        condition: service_healthy
    healthcheck:
      test: ['CMD-SHELL', 'wget --spider -q http://localhost:5678/healthz || exit 1']
      interval: 5s
      timeout: 5s
      retries: 10

  n8n_worker1_runners:
    image: ghcr.io/n8n-io/runners:${N8N_VERSION:-latest}
    environment:
      - N8N_RUNNERS_TASK_BROKER_URI=http://n8n_worker1:5679
      - N8N_RUNNERS_AUTH_TOKEN=test
      - NO_COLOR=1
    depends_on:
      n8n_worker1:
        condition: service_healthy

  n8n_worker2:
    image: ghcr.io/n8n-io/n8n:${N8N_VERSION:-latest}
    environment:
      - N8N_DIAGNOSTICS_ENABLED=false
      - N8N_USER_FOLDER=/n8n/worker2
      - N8N_ENCRYPTION_KEY=${N8N_ENCRYPTION_KEY}
      - N8N_LICENSE_CERT=${N8N_LICENSE_CERT}
      - N8N_LICENSE_ACTIVATION_KEY=${N8N_LICENSE_ACTIVATION_KEY}
      - N8N_LICENSE_TENANT_ID=${N8N_LICENSE_TENANT_ID}
      # Scaling mode config
      - EXECUTIONS_MODE=queue
      - QUEUE_BULL_REDIS_HOST=redis
      - QUEUE_HEALTH_CHECK_ACTIVE=true
      - N8N_CONCURRENCY_PRODUCTION_LIMIT=10
      # DB config
      - DB_TYPE=postgresdb
      - DB_POSTGRESDB_HOST=postgres
      - DB_POSTGRESDB_PASSWORD=password
      # Task Runner config
      - N8N_RUNNERS_ENABLED=true
      - N8N_RUNNERS_MODE=external
      - N8N_RUNNERS_BROKER_LISTEN_ADDRESS=0.0.0.0
      - N8N_RUNNERS_AUTH_TOKEN=test
    command: worker
    volumes:
      - ${RUN_DIR}/n8n-worker2:/n8n
    depends_on:
      # We let the worker 1 start first so it can run the DB migrations
      n8n_worker1:
        condition: service_healthy
      postgres:
        condition: service_healthy
      redis:
        condition: service_healthy
    healthcheck:
      test: ['CMD-SHELL', 'wget --spider -q http://localhost:5678/healthz || exit 1']
      interval: 5s
      timeout: 5s
      retries: 10

  n8n_worker2_runners:
    image: ghcr.io/n8n-io/runners:${N8N_VERSION:-latest}
    environment:
      - N8N_RUNNERS_TASK_BROKER_URI=http://n8n_worker2:5679
      - N8N_RUNNERS_AUTH_TOKEN=test
      - NO_COLOR=1
    depends_on:
      n8n_worker2:
        condition: service_healthy

  n8n_main2:
    image: ghcr.io/n8n-io/n8n:${N8N_VERSION:-latest}
    environment:
      - N8N_DIAGNOSTICS_ENABLED=false
      - N8N_USER_FOLDER=/n8n
      - N8N_ENCRYPTION_KEY=${N8N_ENCRYPTION_KEY}
      - N8N_LICENSE_CERT=${N8N_LICENSE_CERT}
      - N8N_LICENSE_ACTIVATION_KEY=${N8N_LICENSE_ACTIVATION_KEY}
      - N8N_LICENSE_TENANT_ID=${N8N_LICENSE_TENANT_ID}
      # Scaling mode config
      - N8N_PROXY_HOPS=1
      - EXECUTIONS_MODE=queue
      - QUEUE_BULL_REDIS_HOST=redis
      - N8N_MULTI_MAIN_SETUP_ENABLED=true
      # DB config
      - DB_TYPE=postgresdb
      - DB_POSTGRESDB_HOST=postgres
      - DB_POSTGRESDB_PASSWORD=password
      - N8N_METRICS=true
    volumes:
      - ${RUN_DIR}/n8n-main2:/n8n
    depends_on:
      n8n_worker1:
        condition: service_healthy
      n8n_worker2:
        condition: service_healthy
      postgres:
        condition: service_healthy
      redis:
        condition: service_healthy
      mockapi:
        condition: service_started
    healthcheck:
      test: ['CMD-SHELL', 'wget --spider -q http://n8n_main2:5678/healthz || exit 1']
      interval: 5s
      timeout: 5s
      retries: 10

  n8n_main1:
    image: ghcr.io/n8n-io/n8n:${N8N_VERSION:-latest}
    environment:
      - N8N_DIAGNOSTICS_ENABLED=false
      - N8N_USER_FOLDER=/n8n
      - N8N_ENCRYPTION_KEY=${N8N_ENCRYPTION_KEY}
      - N8N_LICENSE_CERT=${N8N_LICENSE_CERT}
      - N8N_LICENSE_ACTIVATION_KEY=${N8N_LICENSE_ACTIVATION_KEY}
      - N8N_LICENSE_TENANT_ID=${N8N_LICENSE_TENANT_ID}
      # Scaling mode config
      - N8N_PROXY_HOPS=1
      - EXECUTIONS_MODE=queue
      - QUEUE_BULL_REDIS_HOST=redis
      - N8N_MULTI_MAIN_SETUP_ENABLED=true
      # DB config
      - DB_TYPE=postgresdb
      - DB_POSTGRESDB_HOST=postgres
      - DB_POSTGRESDB_PASSWORD=password
      - N8N_METRICS=true
    volumes:
      - ${RUN_DIR}/n8n-main1:/n8n
    depends_on:
      n8n_worker1:
        condition: service_healthy
      n8n_worker2:
        condition: service_healthy
      postgres:
        condition: service_healthy
      redis:
        condition: service_healthy
      mockapi:
        condition: service_started
    healthcheck:
      test: ['CMD-SHELL', 'wget --spider -q http://n8n_main1:5678/healthz || exit 1']
      interval: 5s
      timeout: 5s
      retries: 10

  # Load balancer that acts as an entry point for n8n
  n8n:
    image: nginx:1.27.2
    ports:
      - '5678:80'
    volumes:
      - ./nginx.conf:/etc/nginx/nginx.conf
    depends_on:
      n8n_main1:
        condition: service_healthy
      n8n_main2:
        condition: service_healthy

  benchmark:
    image: ghcr.io/n8n-io/n8n-benchmark:${N8N_BENCHMARK_VERSION:-latest}
    depends_on:
      - n8n
    environment:
      - N8N_BASE_URL=http://n8n:80
      - K6_API_TOKEN=${K6_API_TOKEN}
      - BENCHMARK_RESULT_WEBHOOK_URL=${BENCHMARK_RESULT_WEBHOOK_URL}
      - BENCHMARK_RESULT_WEBHOOK_AUTH_HEADER=${BENCHMARK_RESULT_WEBHOOK_AUTH_HEADER}
      - COLLECT_APP_METRICS=true
