services:

  # ── Identity init containers ───────────────────────────────────────────────
  # Each agent0 container has a corresponding *-init service that runs once on
  # startup, pulls the agent's persona from the gnommoweb Content API, and
  # writes it to the shared volume. The main agent container depends on its
  # init service completing successfully before starting.
  #
  # To re-pull identity after an edit in gnommoweb admin:
  #   docker compose up --force-recreate dobby-init dobby   (etc.)

  dobby-init:
    image: python:3.12-alpine
    volumes:
      - ./agents/dobby:/a0/usr
      - ./scripts:/scripts:ro
    environment:
      AGENT_ID: ${DOBBY_AGENT_ID:-}
      AGENT_TYPE: agent0
      CONTENT_API_URL: ${API_URL}
      CONTENT_API_KEY: ${CONTENT_API_KEY}
    command: ["python3", "/scripts/pull-agent-identity.py"]
    restart: "no"

  gemma-init:
    image: python:3.12-alpine
    volumes:
      - ./agents/gemma:/a0/usr
      - ./scripts:/scripts:ro
    environment:
      AGENT_ID: ${GEMMA_AGENT_ID:-}
      AGENT_TYPE: agent0
      CONTENT_API_URL: ${API_URL}
      CONTENT_API_KEY: ${CONTENT_API_KEY}
    command: ["python3", "/scripts/pull-agent-identity.py"]
    restart: "no"

  gunnar-init:
    image: python:3.12-alpine
    volumes:
      - ./agents/gunnar:/a0/usr
      - ./scripts:/scripts:ro
    environment:
      AGENT_ID: ${GUNNAR_AGENT_ID:-}
      AGENT_TYPE: agent0
      CONTENT_API_URL: ${API_URL}
      CONTENT_API_KEY: ${CONTENT_API_KEY}
    command: ["python3", "/scripts/pull-agent-identity.py"]
    restart: "no"

  hermes-init:
    image: python:3.12-alpine
    volumes:
      - ./agents/hermes:/a0/usr
      - ./scripts:/scripts:ro
    environment:
      AGENT_ID: ${HERMES_AGENT_ID:-}
      AGENT_TYPE: agent0
      CONTENT_API_URL: ${API_URL}
      CONTENT_API_KEY: ${CONTENT_API_KEY}
    command: ["python3", "/scripts/pull-agent-identity.py"]
    restart: "no"

  rind-init:
    image: python:3.12-alpine
    volumes:
      - ./agents/rind:/a0/usr
      - ./scripts:/scripts:ro
    environment:
      AGENT_ID: ${RIND_AGENT_ID:-}
      AGENT_TYPE: agent0
      CONTENT_API_URL: ${API_URL}
      CONTENT_API_KEY: ${CONTENT_API_KEY}
    command: ["python3", "/scripts/pull-agent-identity.py"]
    restart: "no"

  abyssinthia-init:
    image: python:3.12-alpine
    volumes:
      - ./agents/abyssinthia:/a0/usr
      - ./scripts:/scripts:ro
    environment:
      AGENT_ID: ${ABYSSINTHIA_AGENT_ID:-}
      AGENT_TYPE: agent0
      CONTENT_API_URL: ${API_URL}
      CONTENT_API_KEY: ${CONTENT_API_KEY}
    command: ["python3", "/scripts/pull-agent-identity.py"]
    restart: "no"

  # ── Agent Zero instances ───────────────────────────────────────────────────

  dobby:
    image: agent0ai/agent-zero:latest
    container_name: dobby
    ports:
      - "50001:80"    # direct local access for debugging
    volumes:
      - ./agents/dobby:/a0/usr
      - ./shared/skills:/a0/usr/skills
      - ${HOME}/.ssh:/root/.ssh
      - ../gutasktool:/opt/gutasktool
      - ./shared/gutask:/usr/local/bin/gutask
    restart: unless-stopped
    depends_on:
      dobby-init:
        condition: service_completed_successfully
    environment:
      AUTH_LOGIN: ${AUTH_LOGIN}
      AUTH_PASSWORD: ${AUTH_PASSWORD}
      AGENT_ID: ${DOBBY_AGENT_ID}
      AGENT_NAME: ${DOBBY_AGENT_NAME}
      API_URL: ${API_URL}
      CONTENT_API_KEY: ${CONTENT_API_KEY}
    extra_hosts:
      - "host.docker.internal:host-gateway"

  gemma:
    image: agent0ai/agent-zero:latest
    container_name: gemma
    ports:
      - "50002:80"
    volumes:
      - ./agents/gemma:/a0/usr
      - ./shared/skills:/a0/usr/skills
      - ${HOME}/.ssh:/root/.ssh
      - ../gutasktool:/opt/gutasktool
      - ./shared/gutask:/usr/local/bin/gutask
    restart: unless-stopped
    depends_on:
      gemma-init:
        condition: service_completed_successfully
    environment:
      AUTH_LOGIN: ${AUTH_LOGIN}
      AUTH_PASSWORD: ${AUTH_PASSWORD}
      AGENT_ID: ${GEMMA_AGENT_ID}
      AGENT_NAME: ${GEMMA_AGENT_NAME}
      API_URL: ${API_URL}
      CONTENT_API_KEY: ${CONTENT_API_KEY}
    extra_hosts:
      - "host.docker.internal:host-gateway"

  gunnar:
    image: agent0ai/agent-zero:latest
    container_name: gunnar
    ports:
      - "50003:80"
    volumes:
      - ./agents/gunnar:/a0/usr
      - ./shared/skills:/a0/usr/skills
      - ${HOME}/.ssh:/root/.ssh
      - ../gutasktool:/opt/gutasktool
      - ./shared/gutask:/usr/local/bin/gutask
    restart: unless-stopped
    depends_on:
      gunnar-init:
        condition: service_completed_successfully
    environment:
      AUTH_LOGIN: ${AUTH_LOGIN}
      AUTH_PASSWORD: ${AUTH_PASSWORD}
      AGENT_ID: ${GUNNAR_AGENT_ID}
      AGENT_NAME: ${GUNNAR_AGENT_NAME}
      API_URL: ${API_URL}
      CONTENT_API_KEY: ${CONTENT_API_KEY}
    extra_hosts:
      - "host.docker.internal:host-gateway"

  rind:
    image: agent0ai/agent-zero:latest
    container_name: rind
    ports:
      - "50005:80"
    volumes:
      - ./agents/rind:/a0/usr
      - ./shared/skills:/a0/usr/skills
      - ${HOME}/.ssh:/root/.ssh
      - ../gutasktool:/opt/gutasktool
      - ./shared/gutask:/usr/local/bin/gutask
    restart: unless-stopped
    depends_on:
      rind-init:
        condition: service_completed_successfully
    environment:
      AUTH_LOGIN: ${AUTH_LOGIN}
      AUTH_PASSWORD: ${AUTH_PASSWORD}
      AGENT_ID: ${RIND_AGENT_ID}
      AGENT_NAME: ${RIND_AGENT_NAME}
      API_URL: ${API_URL}
      CONTENT_API_KEY: ${CONTENT_API_KEY}
    extra_hosts:
      - "host.docker.internal:host-gateway"

  abyssinthia:
    image: agent0ai/agent-zero:latest
    container_name: abyssinthia
    ports:
      - "50006:80"
    volumes:
      - ./agents/abyssinthia:/a0/usr
      - ./shared/skills:/a0/usr/skills
      - ${HOME}/.ssh:/root/.ssh
      - ../gutasktool:/opt/gutasktool
      - ./shared/gutask:/usr/local/bin/gutask
    restart: unless-stopped
    depends_on:
      abyssinthia-init:
        condition: service_completed_successfully
    environment:
      AUTH_LOGIN: ${AUTH_LOGIN}
      AUTH_PASSWORD: ${AUTH_PASSWORD}
      AGENT_ID: ${ABYSSINTHIA_AGENT_ID}
      AGENT_NAME: ${ABYSSINTHIA_AGENT_NAME}
      API_URL: ${API_URL}
      CONTENT_API_KEY: ${CONTENT_API_KEY}
    extra_hosts:
      - "host.docker.internal:host-gateway"
  hermes:
    image: agent0ai/agent-zero:latest
    container_name: hermes
    ports:
      - "50008:80"
    volumes:
      - ./agents/hermes:/a0/usr
      - ./shared/skills:/a0/usr/skills
      - ${HOME}/.ssh:/root/.ssh
      - ../gutasktool:/opt/gutasktool
      - ./shared/gutask:/usr/local/bin/gutask
    restart: unless-stopped
    depends_on:
      hermes-init:
        condition: service_completed_successfully
    environment:
      AUTH_LOGIN: ${AUTH_LOGIN}
      AUTH_PASSWORD: ${AUTH_PASSWORD}
      AGENT_ID: ${HERMES_AGENT_ID}
      AGENT_NAME: ${HERMES_AGENT_NAME}
      API_URL: ${API_URL}
      CONTENT_API_KEY: ${CONTENT_API_KEY}
    extra_hosts:
      - "host.docker.internal:host-gateway"
  
  # ── Hermes agent ───────────────────────────────────────────────────────────

  gerhard:
    image: nousresearch/hermes-agent:latest
    container_name: gerhard
    volumes:
      - ./agents/gerhard-hermes:/opt/data
      - ./agents/gerhard-workspace:/workspace
      - ./shared/knowledge:/knowledge
      - ./shared/skills:/opt/data/skills
      - ../gutasktool:/opt/gutasktool
      - ${HOME}/.ssh:/root/.ssh
    restart: unless-stopped
    env_file: .env
    environment:
      HERMES_UID: ${HERMES_UID:-1000}
      HERMES_GID: ${HERMES_GID:-1000}
      HERMES_HOME: /opt/data
    extra_hosts:
      - "host.docker.internal:host-gateway"
    command: ["gateway", "run"]

  gerhard-dashboard:
    image: nousresearch/hermes-agent:latest
    container_name: gerhard-dashboard
    ports:
      - "50007:9119"    # web dashboard at localhost:50007
    volumes:
      - ./agents/gerhard-hermes:/opt/data
    restart: unless-stopped
    depends_on:
      - gerhard
    environment:
      HERMES_UID: ${HERMES_UID:-1000}
      HERMES_GID: ${HERMES_GID:-1000}
    extra_hosts:
      - "host.docker.internal:host-gateway"
    command: ["dashboard", "--host", "0.0.0.0", "--no-open", "--insecure", "--tui"]

  # ── Plugins ────────────────────────────────────────────────────────────────

  postgres:
    image: postgres:16-alpine
    container_name: festinger-postgres
    restart: unless-stopped
    environment:
      POSTGRES_USER: festinger
      POSTGRES_PASSWORD: festinger
      POSTGRES_DB: festinger
    volumes:
      - festinger-pgdata:/var/lib/postgresql/data
    healthcheck:
      test: ["CMD-SHELL", "pg_isready -U festinger"]
      interval: 5s
      timeout: 5s
      retries: 10

  festinger:
    build:
      context: ./plugins/festinger
    container_name: festinger
    ports:
      - "11435:11434"    # exposed on host as 11435 to avoid conflict with real Ollama
    restart: unless-stopped
    depends_on:
      postgres:
        condition: service_healthy
    environment:
      POSTGRES_DSN: "postgresql://festinger:festinger@postgres:5432/festinger"
    extra_hosts:
      - "host.docker.internal:host-gateway"

  # ── Tunnel ─────────────────────────────────────────────────────────────────

  glitch-tunnel:
    build:
      context: .
      dockerfile: Dockerfile.tunnel
    container_name: glitch-tunnel
    restart: always
    volumes:
      - ./tunnel:/run/tunnel:ro
    depends_on:
      - dobby
      - gemma
      - gunnar
      - rind
      - abyssinthia
      - gerhard-dashboard

volumes:
  festinger-pgdata:
