{"content":"# Quick Start - Sindri REST API\n\n## 1. Autenticacao\n\n### Conta do bootstrap\n\nNo login local o username e o email da conta. O default de fabrica e\n`admin@sindri.local` (`BOOTSTRAP_ADMIN__ADMIN_EMAIL`). O user_id `admin` nao\nentra no JSON: sem `@` o resolver nao acha a conta. A senha e o valor de\n`BOOTSTRAP_ADMIN__ADMIN_PASSWORD`. A conta nasce com troca obrigatoria, e a\nrole admin exige fator: a primeira resposta nao traz `access_token`.\n\n```bash\ncurl -X POST https://sindri.tdv-bi.com.br/api/v1/auth/login \\\n  -H \"Content-Type: application/json\" \\\n  -d '{\"username\": \"admin@sindri.local\", \"password\": \"<BOOTSTRAP_ADMIN__ADMIN_PASSWORD>\"}'\n```\n\nResposta: `status` `password_change_required`, `interim_token` presente,\n`user_id` `admin`, `access_token` ausente.\n\n```bash\ncurl -X POST https://sindri.tdv-bi.com.br/api/v1/auth/password/first-access \\\n  -H \"Content-Type: application/json\" \\\n  -d '{\"interim_token\": \"<interim_token>\", \"new_password\": \"<nova-senha>\"}'\n```\n\nResposta da conta admin: `status` `mfa_enrollment_required` e outro\n`interim_token`. Senha fraca ou repetida e recusada.\n\n```bash\ncurl -X POST https://sindri.tdv-bi.com.br/api/v1/auth/mfa/bootstrap/totp \\\n  -H \"Content-Type: application/json\" \\\n  -d '{\"interim_token\": \"<interim_token>\"}'\n```\n\nResposta: `factor_id` e `provisioning_uri` (`otpauth://`), exibida uma vez.\n\n```bash\ncurl -X POST https://sindri.tdv-bi.com.br/api/v1/auth/mfa/bootstrap/totp/activate \\\n  -H \"Content-Type: application/json\" \\\n  -d '{\"interim_token\": \"<interim_token>\", \"factor_id\": \"<factor_id>\", \"code\": \"<codigo>\"}'\n```\n\nResposta: `status` `success`, `access_token` e `refresh_token`.\n\n```bash\ncurl -H \"Authorization: Bearer $TOKEN\" https://sindri.tdv-bi.com.br/api/v1/system/health\n```\n\nCom `AUTH__LOGIN_MODE=gateway` o username e a conta do diretorio\n(`sAMAccountName` ou `DOMINIO\\usuario`). O email do bootstrap nao substitui\nessa conta.\n\n### API Key (automacao M2M)\n```bash\n# Criar API key (requer JWT admin)\ncurl -X POST https://sindri.tdv-bi.com.br/api/v1/auth/api-keys \\\n  -H \"Authorization: Bearer $ADMIN_TOKEN\" \\\n  -d '{\"name\": \"ci-pipeline-runner\", \"permissions\": [\"pipelines:run\", \"storage:list\"]}'\n\n# Response: {\"key\": \"tdv_sk_abc123...\", \"key_id\": \"uuid-here\"}\n\n# Usar API key\ncurl -H \"X-API-Key: tdv_sk_abc123...\" https://sindri.tdv-bi.com.br/api/v1/pipelines\n```\n\n## 2. Primeiro Pipeline\n\n```bash\n# Validar enviando o CONTEUDO do YAML (funciona com o servidor em outra maquina)\ncurl -X POST https://sindri.tdv-bi.com.br/api/v1/pipelines/validate \\\n  -H \"Authorization: Bearer $TOKEN\" \\\n  -H \"Content-Type: application/json\" \\\n  -d \"{\"pipeline_yaml\": $(jq -Rs . < pipeline.yaml)}\"\n\n# Upload do YAML\ncurl -X POST https://sindri.tdv-bi.com.br/api/v1/storage/upload \\\n  -H \"Authorization: Bearer $TOKEN\" \\\n  -F \"file=@pipeline.yaml\" \\\n  -F \"artifact_type=pipeline\"\n\n# Executar (async): a execucao usa REFERENCIA relativa ao root governado pelo\n# servidor (TDV_API_PIPELINE_ROOT), em qualquer topologia. Path absoluto ou com\n# \"..\" e recusado; sem root declarado, nenhuma referencia por path e aceita.\ncurl -X POST https://sindri.tdv-bi.com.br/api/v1/jobs/pipelines/run \\\n  -H \"Authorization: Bearer $TOKEN\" \\\n  -d '{\"config_path\": \"pipelines/pipeline.yaml\"}'\n\n# Response: {\"job_id\": \"job-uuid\", \"status\": \"queued\"}\n\n# Monitorar progresso (SSE stream)\ncurl -N https://sindri.tdv-bi.com.br/api/v1/jobs/job-uuid/events \\\n  -H \"Authorization: Bearer $TOKEN\"\n\n# Verificar resultado\ncurl https://sindri.tdv-bi.com.br/api/v1/jobs/job-uuid \\\n  -H \"Authorization: Bearer $TOKEN\"\n```\n\n## 3. Validacao de Dados (dbt-style)\n\n```bash\n# POST https://sindri.tdv-bi.com.br/api/v1/validation/dbt-test — executa data tests no estilo dbt\ncurl -X POST https://sindri.tdv-bi.com.br/api/v1/validation/dbt-test \\\n  -H \"Authorization: Bearer $TOKEN\" \\\n  -H \"Content-Type: application/json\" \\\n  -d '{\"config_path\": \"validation/dbt_project\"}'\n```\n\n## 4. Analytics (Data Intelligence)\n\n```bash\n# POST https://sindri.tdv-bi.com.br/api/v1/data/classify — classifica colunas como dimensao ou medida BI\ncurl -X POST https://sindri.tdv-bi.com.br/api/v1/data/classify \\\n  -H \"Authorization: Bearer $TOKEN\" \\\n  -H \"Content-Type: application/json\" \\\n  -d '{\"dataset\": \"gold.vendas\"}'\n```\n\n## 5. Agendamento\n\n```bash\n# Criar schedule\ncurl -X POST https://sindri.tdv-bi.com.br/api/v1/schedules \\\n  -H \"Authorization: Bearer $TOKEN\" \\\n  -d '{\"pipeline\": \"etl.yaml\", \"cron\": \"0 8 * * MON-FRI\", \"name\": \"daily-etl\"}'\n\n# Listar\ncurl https://sindri.tdv-bi.com.br/api/v1/schedules \\\n  -H \"Authorization: Bearer $TOKEN\"\n```\n\n## Headers Importantes\n\n| Header | Uso |\n|--------|-----|\n| `Authorization: Bearer <token>` | JWT auth |\n| `X-API-Key: tdv_sk_...` | API key auth (alternativo) |\n| claim JWT `tenant_id` no Bearer token | Multi-tenant (derivado do token, verificado) |\n| `X-Request-Id: uuid` | Rastreamento (opcional, auto-gerado se ausente) |\n| `Idempotency-Key: uuid` | Previne execucao duplicada em POST |\n\n## Error Handling\n\nErros seguem RFC 7807 Problem Details:\n\n```json\n{\n  \"type\": \"https://docs.tdv.io/errors/TDV-6001\",\n  \"title\": \"Step Execution Failed\",\n  \"status\": 422,\n  \"detail\": \"Step 'extract_oracle' falhou: connection timeout\",\n  \"error_code\": \"TDV-6001\",\n  \"retryable\": true,\n  \"context\": {\"step\": \"extract_oracle\", \"attempt\": 3}\n}\n```\n\nConsulte `GET https://sindri.tdv-bi.com.br/api/v1/system/errors` para catalogo completo de error codes.\n\n## MCP\n\nQuando o boundary MCP esta montado neste processo, a documentacao do transporte\ne das tools esta em `GET https://sindri.tdv-bi.com.br/api/v1/docs/mcp`. O cliente MCP conecta no\nendpoint do transporte streamable-http, `https://sindri.tdv-bi.com.br/mcp/mcp` — que nao e\npagina de browser. Probe publico: `GET https://sindri.tdv-bi.com.br/mcp/health/live`."}