services: portfolio: build: . container_name: pythagoras-portfolio restart: unless-stopped command: ["uv", "run", "python", "-m", "src.portfolio.runner"] volumes: - ./data:/app/data - ./portfolios.yml:/app/portfolios.yml:ro env_file: - .env - .env.mainnet # token MAINNET (soldi veri); prevale su .env (vedi micro-test plan) environment: - PYTHONUNBUFFERED=1 healthcheck: test: ["CMD", "python", "-c", "import os; assert any(f.endswith('status.json') for r,d,fs in os.walk('/app/data/portfolios') for f in fs)"] interval: 120s timeout: 10s retries: 3 labels: - com.centurylinklabs.watchtower.enable=false # Dashboard web read-only (stato live, PnL totale/per-strategia, grafico equity, # trade attivi+chiusi). Stessa immagine del runner, monta gli stessi data/ in sola # lettura logica (legge equity.jsonl + status/trades dei worker). Porta 8787. # NB: nessuna auth -> non esporre su internet pubblico, solo rete interna/VPN. dashboard: build: . container_name: pythagoras-dashboard restart: unless-stopped command: ["uv", "run", "python", "-m", "src.live.dashboard", "--port", "8787"] ports: - "8787:8787" volumes: - ./data:/app/data - ./portfolios.yml:/app/portfolios.yml:ro - ./docs/report:/app/docs/report:ro # scheda strategie_attive.html (modal "scheda dettagliata") env_file: - .env - .env.mainnet # token MAINNET (soldi veri); prevale su .env (vedi micro-test plan) environment: - PYTHONUNBUFFERED=1 healthcheck: test: ["CMD", "python", "-c", "import urllib.request; urllib.request.urlopen('http://localhost:8787/api/state', timeout=5)"] interval: 120s timeout: 10s retries: 3 labels: - com.centurylinklabs.watchtower.enable=false