# πŸš€ Ambiente de Desenvolvimento Full-Stack β€” Docker Swarm ## Arquitetura ``` β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚ DEV ORCHESTRATOR β”‚ β”‚ (gerencia agentes, tasks, logs, hot reload) β”‚ β”œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€ β”‚ β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚ β”‚ β”‚ FRONTEND β”‚ β”‚ BACKEND β”‚ β”‚ WORKERS β”‚ β”‚ β”‚ β”‚ (Vite+React)β”‚ β”‚ Node+TS) β”‚ β”‚ (Agentes paralelos) β”‚ β”‚ β”‚ β”‚ HMR: 5173 β”‚ β”‚ HMR: 3001 β”‚ β”‚ Python/Node/Go β”‚ β”‚ β”‚ β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β”‚ β”‚ β†˜ β†˜ β†˜ β”‚ β”‚ └───────────────┴────────── Redis Queue β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜β”‚ β”‚ TaskBoard (live) β”‚ β”‚ LogStream (live) β”‚ β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ ``` ## Stacks | Stack | PropΓ³sito | |-------|-----------| | `dev` | Ambiente completo (frontend + backend + workers + Redis + taskboard + logs) | | `dev-frontend` | Apenas Vite HMR (para desenvolvimento isolado) | | `dev-backend` | Apenas API + workers | ## Hot Reload ### Frontend (React + Vite) ```yaml services: frontend: image: node:24-alpine working_dir: /app volumes: - ./frontend:/app:cached # cΓ³digo montado - /app/node_modules # cache node_modules command: sh -c "npm install && npm run dev -- --host 0.0.0.0" networks: [public] deploy: replicas: 1 endpoint_mode: dnsrr ``` ### Backend (Node + ts-node) ```yaml services: backend: image: node:24-alpine working_dir: /app volumes: - ./backend:/app:cached - /app/node_modules command: sh -c "npm install && npx tsx watch src/server.ts" networks: [public] ``` ### Python Worker (uvicorn + watcher) ```yaml services: worker-py: image: python:3.12-slim volumes: - ./workers/python:/app:cached - /app/.venv command: sh -c "pip install -r requirements.txt && watchmedo shell-command --patterns='*.py' --recursive --command='echo CHANGED'" networks: [public] ``` ## Logs em Tempo Real ### OpΓ§Γ£o 1 β€” Loki + Promtail (filebeat alternativa) ```yaml services: promtail: image: grafana/promtail:latest volumes: - /var/log:/var/log:ro - ./promtail-config.yml:/etc/promtail/config.yml command: -config.file=/etc/promtail/config.yml ``` ### OpΓ§Γ£o 2 β€” Direto no Dev Orchestrator (stdout aggregator) ```yaml services: logstream: image: node:24-alpine command: node -e " const {Redis} = require('ioredis'); const r = new Redis(process.env.REDIS_URL); r.subscribe('dev-logs', (err) => { if(err) return; r.on('message', (ch, msg) => process.stdout.write(msg)); }); " depends_on: [{service: redis, condition: service_healthy}] ``` ## Task Queue + Dev Board ```yaml # Redis Queue redis: image: redis:8-alpine command: redis-server --appendonly yes --save 5 1 volumes: - redis-data:/data healthcheck: test: ['CMD', 'redis-cli', 'ping'] interval: 5s timeout: 3s retries: 3 # Task Board Web taskboard: image: node:24-alpine working_dir: /app volumes: - ./taskboard:/app command: sh -c "npm install && npm run dev -- --host 0.0.0.0" ports: - target: 5174 published: 3082 protocol: tcp mode: host environment: - REDIS_URL=redis://redis:6379 networks: [public] labels: - caddy=board.octal.tec.br - caddy.reverse_proxy={{upstreams 5174}} # Worker Agents (paralelos) worker-a: # Frontend specialist image: node:24-alpine command: node /app/workers/agent-a.js environment: - REDIS_URL=redis://redis:6379 - AGENT_ROLE=frontend - TASK_QUEUE=dev-tasks depends_on: [{redis, condition: service_healthy}] worker-b: # Backend specialist image: node:24-alpine command: node /app/workers/agent-b.js environment: - REDIS_URL=redis://redis:6379 - AGENT_ROLE=backend - TASK_QUEUE=dev-tasks worker-c: # DevOps / infra specialist image: python:3.12-slim command: python /app/workers/agent-c.py environment: - REDIS_URL=redis://redis:6379 - AGENT_ROLE=devops - TASK_QUEUE=dev-tasks ``` ## Task Protocol (Redis) ```json // Tarefa enfileirada { "id": "uuid", "type": "feature|bug|refactor|test", "priority": "low|medium|high|critical", "domain": "frontend|backend|devops|fullstack", "title": "...", "description": "...", "files_affected": ["src/..."], "acceptance_criteria": ["..."], "created_at": "2026-05-20T19:00:00Z", "status": "pending|in_progress|done|blocked" } ``` ## Volumes ```yaml volumes: redis-data: ``` ## Deploy ```bash docker stack deploy -c runbooks/dev-stack.yml dev ``` ## Acesso | ServiΓ§o | URL | DescriΓ§Γ£o | |---------|-----|-----------| | Task Board | `board.octal.tec.br` | Kanban + task queue em tempo real | | Frontend HMR | `frontend.octal.tec.br` | Vite React com hot reload | | Backend API | `api.octal.tec.br` | API Node com hot reload (tsx watch) | | Log Stream | `logs.octal.tec.br` | Logs agregados de todos os workers | ## πŸ”— Links Úteis - `board.octal.tec.br` β†’ TaskBoard (kanban + logs) - `api.octal.tec.br` β†’ API REST (health, tasks, agents) - `frontend.octal.tec.br` β†’ Frontend HMR - Vault Obsidian: `/root/Obsidian-Pulse/` β€” `Projetos/pulse-dev.md`