{"openapi":"3.1.0","info":{"title":"Trilha Invoice API","version":"1.0.0","description":"API fiscal multitenant para emitir e receber NFS-e (Sistema Nacional NFS-e) e receber NF-e e CT-e. Você envia e recebe JSON; a conversão para DPS/XML, a assinatura com o certificado da empresa e a conversa com os webservices oficiais ficam por conta da API.\n\n## Primeiros passos\n\n**Usa o Claude?** O caminho mais curto é o conector oficial do Trilha Invoice no diretório do Claude: [https://claude.ai/directory/invoice](https://claude.ai/directory/invoice). Clique em **Conectar**, entre com a sua conta do Trilha Invoice e autorize; numa conversa nova, diga \"Quero emitir minha primeira nota fiscal\" — o assistente conduz a configuração, o envio do certificado por link seguro e a primeira nota em homologação. Sem chave de API. Os passos abaixo são para integrar pela API.\n\n1. Crie a conta e gere uma chave em [https://invoice-app.trilhahub.cloud](https://invoice-app.trilhahub.cloud) → Chaves de API. A chave começa com `tinv_` e é mostrada uma única vez. Sem passar pelo console: `POST /v1/organizations` é público e faz o mesmo em uma chamada — cria a organização, a empresa padrão a partir do endereço enviado e a chave, que já nasce restrita a homologação (produção é o passo 7).\n2. Cadastre o certificado A1 da empresa. Se quem tem o arquivo é uma pessoa — e sempre que você for um assistente de IA —, peça um link com `POST /v1/certificate-upload-sessions` e entregue `uploadUrl` a ela (no MCP, a ferramenta `certificates.request_upload`): o .pfx e a senha vão direto pela página, sem passar pela conversa — nunca peça nem aceite o arquivo ou a senha no chat, e o certificado já sai vinculado à empresa e ao ambiente. Com o arquivo no seu servidor, envie (`POST /v1/certificates`) e vincule (`PUT /v1/companies/{id}/certificate/{environment}`). Depois complete a configuração fiscal. Homologação também exige um A1 ICP-Brasil válido, emitido para o CNPJ da empresa: não existe certificado de teste nem emissão sem certificado, e um autoassinado é recusado com `CERTIFICATE_NOT_TRUSTED`. Enquanto não houver vínculo, configurar numeração e emitente também falha (`CERTIFICATE_LINK_NOT_FOUND`). `GET /v1/organization/pending` lista o que ainda falta para emitir em cada ambiente.\n3. Defina a série e o próximo número da DPS com `PUT /v1/organization/dps-numbering` (no MCP, `numbering.configure`) — pergunte antes à pessoa: quem já emite por outro sistema integrado informa a série e o último número usado (`nextNumber` = último + 1); quem começa agora, ou não sabe a série do outro sistema, usa uma série nova com `nextNumber: 1` — `GET /v1/organization/dps-numbering` sugere uma em `suggestedNewSeries` (a partir de 900, longe da série 1 que os outros sistemas mais usam). Emissão por API só aceita série de 1 a 49999 (`DPS_SERIES_OUT_OF_RANGE`; de 50000 em diante são séries dos emissores públicos). Sem isso, quem já emitia colide na primeira nota (rejeição E0014).\n4. Valide sem custo com `POST /v1/nfse/validate` e emita com `POST /v1/nfse/issue`, sempre com `environment: \"HOMOLOGATION\"` enquanto testa — emissão em homologação não consome saldo da carteira, então saldo zero não impede o teste.\n5. A emissão é assíncrona: a resposta `202` traz `operationId`. Acompanhe por `GET /v1/nfse/{id}` ou, melhor, pelos webhooks `nfse.issued` e `nfse.rejected`.\n6. Autorizada a nota, baixe o PDF (DANFSe) e o XML por `GET /v1/fiscal-documents/{id}/pdf` e `/xml`. O `documentId` vem no webhook `nfse.issued` ou em `GET /v1/fiscal-documents?operationId=`.\n7. Produção é conduzida pelo dono, no console (https://invoice-app.trilhahub.cloud): (a) um plano que emite em produção e saldo, se o plano pedir; (b) levar a configuração testada para produção — Empresas → copiar de homologação (API: `POST /v1/companies/{id}/production-setup`), que reaproveita o mesmo certificado e pede série e próximo número de produção; (c) liberar produção digitando a senha pessoal, com o e-mail da conta confirmado (mais o código de MFA, se houver), para a chave (Chaves de API) ou o assistente (Integrações). `GET /v1/organization/pending?environment=PRODUCTION` lista o que falta, inclusive plano, saldo e a liberação da credencial que pergunta. Nenhuma chave nem assistente libera produção para si (`PRODUCTION_AUTHORIZATION_REQUIRED`), e emitir antes disso volta `CREDENTIAL_POLICY_VIOLATION` com `ruleCode: ENVIRONMENT_NOT_ALLOWED`. A chave usada num onboarding por chat fica no histórico da conversa: não a libere para produção — para o dia a dia, use o console ou o conector MCP (autorização OAuth, com limite mensal).\n\n## Assistentes de IA\n\nSe você é um assistente conversando com o dono da empresa, siga este roteiro:\n\n1. Se você está falando pelo conector (MCP) do Trilha Invoice, a conta da empresa já existe e a própria pessoa autorizou esta conexão: não peça chave de API nem refaça o cadastro. Comece por `organization.pending` e resolva item a item com as ferramentas — `fiscal_settings.configure` (configuração fiscal), `certificates.request_upload` (certificado por link), `numbering.configure` (série e próximo número), `nfse.validate` e `nfse.issue_homologation` para a nota de teste (`nfse.issue` só quando for emitir em produção). Se faltar uma ferramenta para um passo, peça para a pessoa fazê-lo no console.\n2. Logo no início da conversa, antes de qualquer configuração, avise que a emissão vai precisar do certificado digital A1 da empresa (arquivo .pfx ou .p12) e da senha dele — é comum estar com o contador, então peça para a pessoa já ir providenciando. Diga também que o arquivo e a senha não serão pedidos na conversa: quando chegar a hora, você gera um link seguro (`certificates.request_upload` / `POST /v1/certificate-upload-sessions`) e ela envia direto pela página. Nunca peça nem aceite o arquivo ou a senha no chat.\n3. Antes da primeira emissão, pergunte sobre a numeração: a empresa já emite NFS-e por outro sistema integrado (ERP, outro emissor por API)? Se sim, peça a série e o último número usado nela e configure com `numbering.configure` / `PUT /v1/organization/dps-numbering` (`nextNumber` = último + 1). Se não souber, ou se for começar agora, recomende uma série nova, nunca usada por este CNPJ, e configure com `nextNumber: 1` — `numbering.get` / `GET /v1/organization/dps-numbering` devolve `suggestedNewSeries`. Série nova não colide com notas anteriores, porque a numeração do Sistema Nacional é por série.\n4. Emissão por API só aceita série de 1 a 49999: as séries de 50000 em diante são do portal e do aplicativo do governo (E0010 fora da faixa). Por isso notas que a empresa já emitiu pelo portal nacional não entram em conflito com a série usada aqui.\n5. A emissão é assíncrona: depois de `nfse.issue`, `nfse.issue_homologation` ou `nfse.retry`, consulte `nfse.get_status` em alguns segundos até a nota sair (siga o `nextStep` de cada resultado). Se você não conseguir consultar sozinho, avise o usuário que a nota foi enviada e que em alguns segundos ele pode pedir para você verificar se ela foi autorizada. Passe também o link da nota no portal (`portalUrl` do resultado): \"Você pode acompanhar a nota emitida no portal pelo link: <portalUrl>\". Autorizada a nota, entregue o DANFSe na conversa com `fiscal_documents.download_pdf`: ofereça o PDF anexado quando o seu aplicativo permitir e mostre sempre o link, exatamente como veio.\n6. Se pedirem para cancelar uma nota e a ferramenta `nfse.cancel` não estiver entre as suas, você não consegue cancelar por aqui — e o usuário não tem como habilitá-la: assistentes de IA não recebem cancelamento. Diga isso e passe o link da nota (`portalUrl`, que vem em `fiscal_documents.search` e `nfse.get_status`): \"Você pode acompanhar a nota emitida no portal pelo link: <portalUrl>\", onde ele cancela em \"Cancelar nota\". Depois siga com o resto do pedido (por exemplo, emitir a nota nova), perguntando antes a ordem: emitir antes de cancelar deixa as duas notas válidas até o cancelamento.\n7. Tudo o que você configura e emite nasce valendo só em `HOMOLOGATION`. Assim que a primeira nota de homologação for autorizada, pergunte ao cliente se ele quer começar a emitir em produção — só conduza a passagem se ele disser que sim; se não, diga que está tudo pronto para quando quiser. Produção é do dono, no console: plano que emite em produção, copiar a configuração de homologação (Empresas) e liberar digitando a senha pessoal, com e-mail confirmado — você não consegue fazer isso por ele. Guie o passo a passo conferindo `GET /v1/organization/pending?environment=PRODUCTION`. Se você está usando uma chave de API recebida no chat, não peça para liberá-la para produção: ela fica no histórico da conversa; recomende o console ou o conector MCP para o dia a dia.\n8. Antes de emitir, procure o serviço em `service_catalog.list` e use `serviceCode`. Quando uma nota emitida sem `serviceCode` for autorizada, `nfse.get_status` traz `catalogSuggestion`: ofereça salvar o serviço com `service_catalog.create`, para as próximas notas saírem com menos perguntas. Só ofereça depois que a nota for AUTORIZADA (nfse.get_status em COMPLETED) — nota rejeitada ensinaria ao catálogo justamente o que a Sefin recusou. Copie da nota autorizada os códigos e a tributação, sem mudar nada. Na descrição, separe o fixo do variável: fica o que o serviço É (\"Consultoria em sistemas de informação\"); sai o que é só daquela nota — mês, datas, número de contrato ou pedido, nome do cliente, valores —, que nas próximas emissões vai em service.additionalInformation. Se não sobrar uma descrição útil (\"serviços prestados\"), pergunte à pessoa o que o serviço é, ou ofereça a descrição oficial do código nacional. Mostre código e descrição propostos e só grave depois que a pessoa confirmar. O código é um apelido curto em minúsculas com hífen (ex.: consultoria-sistemas).\n9. Quando a empresa estiver em produção, ofereça o aviso por WhatsApp de cada documento recebido (`notifications.configure` / `PUT /v1/notifications/whatsapp/number`): é o que avisa quando o certificado emite nota fora do Trilha Invoice. Recomende manter todos os tipos marcados. Reduzir o aviso depois exige um código enviado ao WhatsApp cadastrado — peça-o à pessoa, nunca tente contornar.\n10. Use `organization.pending` / `GET /v1/organization/pending` para ver o que ainda falta e resolva item a item. Emita primeiro em `HOMOLOGATION`. Se uma ferramenta de configuração não estiver disponível (a conexão não tem o escopo), peça para a pessoa fazer o passo no console — Empresas, Certificados ou Emissor → Numeração.\n\n## Autenticação\n\nToda rota `/v1/*` exige `Authorization: Bearer <chave>`, exceto as consultas públicas de municípios e cadastros, o auto-cadastro (`POST /v1/organizations`), o fluxo OAuth (`/v1/oauth/*`) e as duas rotas da página de envio de certificado (`POST /v1/certificate-upload-sessions/lookup` e `/complete`, autenticadas pelo token do link). Na dúvida, `security: []` na operação marca a rota pública. Cada chave carrega escopos, e cada rota declara o seu em `x-required-scope`; faltando, a resposta é `403 INSUFFICIENT_SCOPE`. Escopos existentes: `approvals:manage`, `billing:adjust`, `billing:read`, `billing:recharge`, `certificates:read`, `certificates:request-upload`, `certificates:write`, `dps-numbering:manage`, `fiscal-document:download`, `fiscal-document:manifest`, `fiscal-document:read`, `fiscal-settings:manage`, `nfse:cancel`, `nfse:issue`, `nfse:read`, `nfse:validate`, `notifications:manage`, `notifications:read`, `organization:manage`, `service-catalog:read`, `service-catalog:write`, `webhook:manage`.\n\nA chave dá acesso fiscal à empresa: guarde-a só no servidor e nunca em aplicativo móvel, front-end ou repositório. Uma chave pode ser restrita a ambientes, CNPJs e tetos de consumo (`PATCH /v1/api-credentials/{id}/policy`).\n\nAplicações de terceiros e assistentes de IA agindo em nome de um usuário não devem pedir a chave dele: usam o fluxo OAuth descrito na seção **Authorization** (Authorization Code + PKCE ou Device Code), e recebem tokens `tinvat_`.\n\n## Conectando um assistente de IA (RFC-022)\n\n**Claude** tem conector oficial, aprovado pela Anthropic, no diretório de conectores: [https://claude.ai/directory/invoice](https://claude.ai/directory/invoice). Instalar por ali dispensa colar endereço ou registrar cliente: é só Conectar e autorizar. Nos planos Team e Enterprise, o dono da organização habilita o conector antes de cada pessoa conectar.\n\nPara as demais plataformas não há conector próprio: qualquer cliente que fale OAuth 2.1 + PKCE e (MCP ou OpenAPI) se conecta sozinho. Dois passos valem para todos:\n\n1. **Registro do cliente** — se sua plataforma já tem um `client_id` nosso (curado à mão), use-o; senão, `POST /v1/oauth/register` (RFC 7591, `/.well-known/oauth-authorization-server` traz `registration_endpoint`) cria um sozinho, `PUBLIC` e com teto de escopo fixo em `nfse:read`, `nfse:validate`, `fiscal-document:read`, `fiscal-document:download`, `service-catalog:read`, `billing:read` e `nfse:issue` — sem `INSERT` nosso, sem chamado de suporte. Um cliente assim nasce **não verificado**: a tela de consentimento avisa disso e mostra o domínio do `redirect_uri`, mas emite normalmente em homologação.\n2. **Autorização** — `GET /v1/oauth/authorize` com `response_type=code`, `client_id`, `redirect_uri`, `scope` (separado por espaço), `code_challenge`/`code_challenge_method=S256` abre a tela de consentimento do Trilha Invoice no navegador do usuário. Sem navegador de retorno (chat puro), use `POST /v1/oauth/device-authorizations` e mostre só o `user_code`.\n\nA partir daí, o que muda é só o transporte de ferramentas:\n\n- **Claude (web e desktop)** — pelo diretório, acima. **Claude Code, VS Code, Cursor, Zed, Gemini CLI, n8n, LibreChat, Open WebUI** (e o Claude, se preferir conector personalizado) — falam MCP. Aponte para `POST /mcp` (Streamable HTTP); o cliente descobre a autorização sozinho pelo `WWW-Authenticate`/`resource_metadata` de um 401. `tools/list` já vem filtrado pelos escopos do token — nenhuma ferramenta que o token não pode usar aparece.\n- **ChatGPT — conectores/apps** — também MCP (`POST /mcp`), mesmo caminho acima.\n- **ChatGPT — GPT Actions**, **Microsoft Copilot (agente declarativo)**, **Google Gemini (function calling/extensão)** — falam OpenAPI, não MCP, e têm um teto baixo de operações por ação/conector. Cole [`/openapi-tools.json`](/openapi-tools.json) (o recorte de ~13 operações do catálogo de ferramentas) onde a plataforma pedir uma especificação — o `/openapi.json` completo (86+ operações) não cabe.\n\nUma emissão (`nfse.issue`/`POST /v1/nfse/issue`) ou cancelamento (`nfse.cancel`/`POST /v1/nfse/{id}/cancel`) pedido por um assistente pode voltar `202` com `status: \"PENDING_APPROVAL\"`: a integração exige confirmação humana, e a resposta traz `approvalId`/`expiresAt` (e, no MCP, um `approvalUrl` pronto para mostrar ao usuário). Não é erro definitivo — acompanhe com `GET /v1/approvals/{id}` (`approvals.get_status` no MCP) até o humano decidir no console.\n\n## Ambientes\n\nHá um único servidor, `https://invoice-api.trilhahub.cloud`. O ambiente fiscal é escolhido por requisição, no campo `environment`: `HOMOLOGATION` (sem validade fiscal, para testes) ou `PRODUCTION`. Certificado, configuração fiscal, numeração e webhooks são independentes por ambiente.\n\n### Cuidado com o host: documentação e API não moram no mesmo lugar\n\nEsta especificação é servida também fora da API — a página pública do produto (`https://invoice.trilhahub.cloud`) publica `/openapi.json` e `/reference` por proxy, e o console (`https://invoice-app.trilhahub.cloud`) redireciona esses caminhos para cá. Ler a documentação em qualquer um deles é esperado; **chamar a API** só funciona em `https://invoice-api.trilhahub.cloud`.\n\nUse sempre o host de `servers[0]` (`https://invoice-api.trilhahub.cloud`) como base das chamadas, e não o host de onde você baixou o arquivo. Nos outros hosts não existe `/v1`: a requisição cai no site e volta como HTML — `200` com a página, ou `405` —, nunca no envelope JSON. Resposta com `content-type: text/html` ou sem `requestId` é sinal de host errado, não de falha da API.\n\n## Formato das respostas\n\nToda resposta JSON vem no mesmo envelope:\n\n```json\n{ \"requestId\": \"9b2f…\", \"status\": \"success\", \"data\": { … }, \"errors\": [] }\n{ \"requestId\": \"9b2f…\", \"status\": \"error\", \"data\": null, \"errors\": [{ \"code\": \"INSUFFICIENT_BALANCE\", \"details\": { \"availableCents\": 120, \"requiredCents\": 150 } }] }\n```\n\nTrate o erro pelo `code`, que é estável, e não pelo texto. `details` (objeto) e `detail` (texto) são opcionais e variam por código. Para correlacionar com o suporte, envie um `X-Request-Id` próprio (até 128 caracteres): ele passa a ser o `requestId` da resposta. As exceções ao envelope são `/health`, `/ready`, `/metrics` e `POST /v1/oauth/token`, que responde no formato do RFC 6749.\n\nValores de documentos fiscais são strings decimais com duas casas (`\"1500.00\"`); saldos e consumo de créditos são inteiros em centavos.\n\n## Validação\n\nToda query string e todo corpo JSON são validados estritamente: um parâmetro que a rota não declara — nome errado, ou de um modo diferente da mesma rota (`/v1/nfse/municipalities?name=` e `?q=` não se combinam, por exemplo) — devolve `422 VALIDATION_ERROR` com `details[].code: \"unrecognized_keys\"` e a lista das chaves rejeitadas em `details[].keys`. Um campo obrigatório ausente, fora do formato ou do intervalo aceito aparece no mesmo `422`, um item por campo em `details`, com `path` até o campo e `message` explicando o que era esperado. Releia a lista de `parameters` (para query/path) ou o schema do `requestBody` (para o corpo) da operação para saber exatamente o que ela aceita antes de tentar de novo — não adivinhe um nome de parâmetro pelo de outra rota.\n\n## Idempotência\n\n`POST /v1/nfse/issue` exige o cabeçalho `Idempotency-Key` (1 a 255 caracteres). Repetir a mesma chave com o mesmo corpo devolve a operação original, com `replayed: true`, sem emitir nem cobrar de novo; com um corpo diferente, `409 IDEMPOTENCY_CONFLICT`. A chave vale por organização durante 24 horas a partir do primeiro uso: depois disso, a mesma chave cria uma emissão nova. Derive-a de algo único do seu lado, como o id do pedido, e guarde o `operationId` devolvido: é ele que diz se um pedido antigo já foi emitido. `POST /v1/nfse/{id}/retry` não usa a chave: só uma operação rejeitada pode ser retomada, o que já impede o reenvio duplo.\n\n## Limites de requisição\n\nAs rotas abaixo têm limite por cliente; acima dele a resposta é `429`, com o cabeçalho `Retry-After` (segundos até a próxima tentativa valer a pena) — espere por ele em vez de tentar de novo imediatamente. As demais não têm limite de taxa, mas podem ter teto de consumo configurado na chave.\n\nO limite conta por credencial nas rotas autenticadas (cada chave de API e cada assistente conectado tem o seu, e uma sessão do console conta pelo usuário) e por IP de origem nas rotas públicas.\n\n| Rota | Limite |\n| --- | --- |\n| `POST /v1/organizations` | 20 por hora |\n| `POST /v1/oauth/authorization-requests`, `POST /v1/oauth/device-authorizations` | 30 por hora |\n| `GET /v1/oauth/authorize` | 60 por hora |\n| `POST /v1/oauth/register` | 10 por hora por IP, 100 por dia no total |\n| `POST /v1/oauth/token`, `POST /v1/oauth/revoke` | 60 por minuto |\n| `POST /v1/certificates`, `POST /v1/certificates/{id}/replace` | 10 por hora |\n| `POST /v1/certificate-upload-sessions` | 20 por hora |\n| `POST /v1/certificate-upload-sessions/lookup` | 30 a cada 15 minutos |\n| `POST /v1/certificate-upload-sessions/complete` | 10 a cada 15 minutos por IP, e 5 envios errados por link |\n| `GET /v1/nfse/municipalities`, `/availability`, `/national-tax-codes`, `/nbs-codes` | 60 por minuto |\n| `GET /v1/registry/cnpj/{taxId}` | 10 por minuto |\n| `GET /v1/registry/cep/{postalCode}` | 30 por minuto |\n| `PUT /v1/notifications/whatsapp/number`, `/number/resend-code` | 3 códigos de verificação por hora por organização |\n| Pedidos de token de segurança (resposta 428) | 5 por hora por organização |\n| `POST /v1/notifications/whatsapp/test` | 3 por hora por organização |\n| `POST /mcp` | 120 por minuto |\n\n## Webhooks\n\nCadastre um endpoint por ambiente com `POST /v1/webhooks`; o `secret` da resposta aparece uma única vez. Os eventos e seus payloads estão na seção **Webhooks** desta referência. Cada entrega é um `POST` JSON com três cabeçalhos:\n\n- `x-trilha-invoice-event-id`: id do evento, igual a `eventId` no corpo. Use-o para descartar entregas repetidas: a mesma entrega pode chegar mais de uma vez.\n- `x-trilha-invoice-timestamp`: segundos desde a época Unix, no momento do envio.\n- `x-trilha-invoice-signature`: `sha256=` seguido do HMAC-SHA256 em hexadecimal, com o `secret` do endpoint, de `<timestamp>.<corpo bruto>`.\n\n```js\nimport { createHmac, timingSafeEqual } from 'node:crypto';\n\n// rawBody: o corpo exatamente como chegou, antes de qualquer JSON.parse.\nfunction assinaturaValida(segredo, headers, rawBody) {\n  const timestamp = headers['x-trilha-invoice-timestamp'];\n  const recebida = headers['x-trilha-invoice-signature'] ?? '';\n  if (Math.abs(Date.now() / 1000 - Number(timestamp)) > 300) return false; // replay\n  const esperada = 'sha256=' + createHmac('sha256', segredo).update(`${timestamp}.${rawBody}`).digest('hex');\n  return recebida.length === esperada.length && timingSafeEqual(Buffer.from(recebida), Buffer.from(esperada));\n}\n```\n\nResponda `2xx` em até `timeoutMs` (padrão 10 s) para confirmar. `429`, `5xx`, timeout ou erro de rede geram nova tentativa, com espera de 5 s × 2ⁿ (no máximo 1 hora entre tentativas), até `maxAttempts` (padrão 8). Qualquer outra resposta, inclusive `3xx` e `4xx`, encerra a entrega como falha definitiva. Entregas e tentativas ficam em `GET /v1/webhook-deliveries`, e `POST /v1/webhook-deliveries/{id}/resend` reenvia manualmente.\n\n## Códigos de erro\n\n| Código | HTTP | Significado |\n| --- | --- | --- |\n| `AUTHENTICATION_REQUIRED` | 401 | Nenhuma credencial enviada. Use `Authorization: Bearer <chave>`. |\n| `INVALID_CREDENTIAL` | 401 | Chave ou token inexistente, revogado ou expirado. |\n| `INSUFFICIENT_SCOPE` | 403 | A credencial não tem o escopo exigido pela rota (`x-required-scope`). |\n| `API_KEY_REQUIRED` | 403 | A rota exige uma API key ou token de integração; sessão de console não serve. |\n| `CREDENTIAL_POLICY_VIOLATION` | 403 | A operação ultrapassa um limite configurado na credencial (ambiente, CNPJ, valor ou teto de consumo). |\n| `SCOPE_ESCALATION_REJECTED` | 403 | Tentativa de criar credencial com escopo que a credencial atual não tem. |\n| `MFA_REQUIRED_FOR_SENSITIVE_SCOPE` | 403 | Conceder este escopo exige MFA ativo no usuário que autoriza. |\n| `CONSOLE_SESSION_REQUIRED` | 403 | A rota só aceita sessão de usuário no console, não API key nem token. |\n| `LAST_ACTIVE_CREDENTIAL` | 409 | Não é possível revogar a última credencial ativa da organização. |\n| `API_CREDENTIAL_NOT_FOUND` | 404 | Credencial não encontrada nesta organização. |\n| `REDIRECT_URI_MISMATCH` | 400 | A `redirectUri` não consta exatamente na lista registrada do cliente. |\n| `SCOPE_NOT_ALLOWED_FOR_CLIENT` | 400 | Escopo pedido fora do que o cliente OAuth pode solicitar. |\n| `SENSITIVE_SCOPE_REQUIRES_CONFIDENTIAL_CLIENT` | 400 | Escopo sensível só pode ser pedido por cliente confidencial. |\n| `UNSUPPORTED_GRANT_TYPE` | 400 | Tipo de grant não suportado pelo cliente. |\n| `AUTHORIZATION_REQUEST_NOT_FOUND` | 404 | Solicitação de autorização inexistente ou expirada. |\n| `AUTHORIZATION_REQUEST_ALREADY_DECIDED` | 409 | A solicitação já foi aprovada ou negada. |\n| `AI_GRANT_REQUIRES_MONTHLY_CEILING` | 422 | Integração de IA que pode emitir precisa de teto mensal de consumo. |\n| `INTEGRATION_NOT_FOUND` | 404 | Integração conectada não encontrada. |\n| `OAUTH_CLIENT_UNKNOWN` | 400 | GET /v1/oauth/authorize com client_id desconhecido ou suspenso — resposta direta, sem redirect (RFC-022 §7.1). |\n| `INVALID_TARGET` | 400 | RFC 8707 (RFC-022 F6): `resource` presente e diferente desta própria API — o único recurso que existe (D51). |\n| `APPROVAL_REQUIRED` | 202 | Só no transporte MCP (RFC-022 §7.6): a operação ficou como `PENDING_APPROVAL` (o mesmo 202 de sempre em POST /v1/nfse/issue e /cancel) e a ferramenta MCP devolve isso com um `approvalUrl` navegável. |\n| `VALIDATION_ERROR` | 422 | Corpo, parâmetro ou query fora do schema. `details` traz a lista de problemas campo a campo. |\n| `INVALID_REQUEST` | 400 | GET /v1/oauth/authorize sem client_id ou redirect_uri — únicos dois parâmetros exigidos antes de qualquer redirect. |\n| `IDEMPOTENCY_KEY_REQUIRED` | 400 | Cabeçalho `Idempotency-Key` ausente ou com mais de 255 caracteres. |\n| `IDEMPOTENCY_CONFLICT` | 409 | A `Idempotency-Key` já foi usada nas últimas 24 horas com um corpo diferente. |\n| `NOTHING_TO_UPDATE` | 422 | Nenhum campo alterável foi enviado. |\n| `RESOURCE_CONFLICT` | 409 | Já existe um registro com o mesmo identificador único. |\n| `NOT_FOUND` | 404 | Caminho sem rota — hoje só em /.well-known/openid-configuration, que não existe porque a API não é um provedor OpenID Connect. |\n| `INSUFFICIENT_BALANCE` | 402 | Saldo da carteira insuficiente. `details` traz `availableCents` e `requiredCents`. |\n| `SUBSCRIPTION_SUSPENDED` | 403 | Assinatura suspensa por inadimplência; `details.reason` explica. |\n| `ACTIVE_SUBSCRIPTION_REQUIRED` | 403 | A operação exige uma assinatura ativa. |\n| `PLAN_FEATURE_NOT_AVAILABLE` | 403 | O recurso não faz parte do plano contratado. |\n| `PLAN_NOT_SELF_ASSIGNABLE` | 403 | Plano concedido por parceiro; a organização não pode se auto-atribuí-lo (POST /v1/subscription). |\n| `UNKNOWN_PLAN_CODE` | 404 | Código de plano inexistente. |\n| `NO_CURRENT_SUBSCRIPTION` | 409 | A organização não tem assinatura corrente. |\n| `CANCELLATION_ALREADY_SCHEDULED` | 409 | O encerramento da assinatura já está agendado. |\n| `NO_SCHEDULED_CANCELLATION` | 409 | Não há encerramento agendado para desfazer. |\n| `SUBSCRIPTION_CHARGE_NOT_FOUND` | 404 | Mensalidade não encontrada. |\n| `AUTO_RECHARGE_CARD_REQUIRED` | 409 | Ligar a recarga automática exige um cartão cadastrado. |\n| `PAYMENT_PROVIDER_UNAVAILABLE` | 502 | O gateway de pagamento falhou. Tente de novo mais tarde. |\n| `UNKNOWN_BILLABLE_EVENT_TYPE` | 404 | Tipo de evento cobrável inexistente. |\n| `MISSING_EVENT_PRICES` | 422 | O plano não tem preço para todos os eventos cobráveis. |\n| `USAGE_STATE_CONFLICT` | 409 | O uso não está num estado que permita a operação (por exemplo, estorno de uso já estornado). |\n| `ORGANIZATION_NOT_FOUND` | 404 | Organização não encontrada. |\n| `EMAIL_ALREADY_REGISTERED` | 409 | O e-mail informado já tem cadastro. |\n| `ORGANIZATION_TAX_ID_ALREADY_REGISTERED` | 409 | O CNPJ/CPF informado já está cadastrado nesta plataforma, como organização ou como empresa de outra organização (RFC-021: gere uma chave de API pelo console da organização existente em vez de tentar cadastrar de novo). |\n| `TAX_ID_IMMUTABLE` | 422 | O CNPJ/CPF de uma organização ou empresa não pode ser alterado. |\n| `COMPANY_NOT_FOUND` | 404 | Empresa não encontrada nesta organização. |\n| `COMPANY_INACTIVE` | 409 | A empresa está inativa. |\n| `COMPANY_TAX_ID_ALREADY_IN_USE` | 409 | Já existe empresa com este CNPJ. |\n| `DEFAULT_COMPANY_MUST_STAY_ACTIVE` | 409 | A empresa padrão não pode ser desativada. |\n| `DEFAULT_COMPANY_NOT_CONFIGURED` | 409 | A organização não tem empresa padrão, exigida para ligar a recepção. |\n| `COMPANY_MUNICIPALITY_REQUIRED` | 422 | A empresa precisa de município cadastrado antes desta configuração. |\n| `FISCAL_CONFIGURATION_REQUIRED` | 422 | Falta configuração fiscal para o ambiente. Veja `GET /v1/organization/pending`. |\n| `ORGANIZATION_MUNICIPALITY_MISSING` | 409 | A organização não tem município cadastrado. |\n| `MUNICIPALITY_NOT_CONFIGURED` | 409 | Não há numeração de DPS configurada para este município. |\n| `SERVICE_CATALOG_ENTRY_NOT_FOUND` | 404 | Entrada do catálogo de serviços não encontrada (na emissão, `serviceCode` inexistente ou arquivado responde 422). |\n| `SERVICE_CATALOG_CODE_CONFLICT` | 409 | Já existe entrada ativa com este código. |\n| `CERTIFICATE_NOT_FOUND` | 404 | Certificado não encontrado no cofre. |\n| `CERTIFICATE_INVALID` | 422 | O arquivo não é um PKCS#12 (.pfx/.p12) válido. |\n| `CERTIFICATE_PASSWORD_INVALID` | 422 | Senha do certificado incorreta. |\n| `NFSE_CANCELLATION_NOT_FOUND` | 404 | Cancelamento não encontrado para esta NFS-e — confira os dois ids: o da emissão e o `operationId` devolvido por POST /v1/nfse/{id}/cancel. |\n| `HOMOLOGATION_CONFIGURATION_MISSING` | 422 | Copiar para produção exige a configuração fiscal de homologação completa (tributação e retenção do ISSQN). |\n| `PRODUCTION_AUTHORIZATION_REQUIRED` | 403 | Liberar produção para uma chave ou um assistente é ação de pessoa no console, com e-mail confirmado e senha pessoal. Uma chave não libera produção para si nem cria chave com mais ambientes que os dela. |\n| `EMAIL_NOT_VERIFIED` | 403 | Confirme o e-mail da conta no console antes de liberar produção. |\n| `PASSWORD_CONFIRMATION_REQUIRED` | 422 | Esta operação libera produção: envie a senha pessoal em `password`. |\n| `PASSWORD_CONFIRMATION_INVALID` | 403 | Senha incorreta, ou a conta ainda está com senha temporária — troque-a antes. |\n| `CERTIFICATE_UPLOAD_LINK_INVALID` | 410 | Link de envio de certificado inexistente, já usado, vencido ou travado por tentativas erradas. Peça outro com POST /v1/certificate-upload-sessions. |\n| `CERTIFICATE_UPLOAD_SESSION_NOT_FOUND` | 404 | Pedido de envio de certificado não encontrado nesta organização. |\n| `CERTIFICATE_EXPIRED` | 422 | O certificado está vencido. |\n| `CERTIFICATE_NOT_TRUSTED` | 422 | O certificado não foi emitido por uma cadeia ICP-Brasil reconhecida. |\n| `CERTIFICATE_IDENTITY_UNDETERMINED` | 422 | Não foi possível extrair CNPJ/CPF do certificado. |\n| `CERTIFICATE_DOCUMENT_MISMATCH` | 422 | O CNPJ/CPF do certificado não corresponde ao da empresa. |\n| `CERTIFICATE_HAS_ACTIVE_LINKS` | 409 | O certificado ainda está vinculado a empresas; desvincule antes de revogar. |\n| `CERTIFICATE_LINK_NOT_FOUND` | 404 | Não há certificado vinculado a esta empresa neste ambiente. |\n| `CERTIFICATE_VAULT_NOT_CONFIGURED` | 503 | O cofre de certificados está indisponível no servidor. |\n| `FISCAL_CREDENTIAL_MISSING` | 409 | A recepção de documentos exige um certificado vinculado. |\n| `MUNICIPALITY_NOT_SUPPORTED` | 422 | O município da prestação está confirmadamente indisponível para emissão. |\n| `SERVICE_DETAILS_REQUIRED` | 422 | Informe `serviceCode` ou `service.nationalTaxCode` e `service.description`. |\n| `ISSQN_RATE_REQUIRED` | 422 | O município não parametriza a alíquota e nenhuma foi informada ou configurada. |\n| `COMPETENCE_DATE_IN_FUTURE` | 422 | A `competenceDate` é posterior a hoje no horário de Brasília — a Sefin recusaria com E0015 (competência posterior à emissão). Informe hoje ou uma data passada, ou omita para usar hoje. |\n| `ISSQN_RATE_ABOVE_LEGAL_LIMIT` | 422 | Alíquota do ISSQN acima de 5% (LC 116/2003, art. 8º, II). |\n| `DPS_SERIES_UNKNOWN` | 422 | A série informada não existe. |\n| `DPS_SERIES_INACTIVE` | 422 | A série informada está inativa. |\n| `DPS_NUMBER_NOT_ALLOWED_IN_AUTO` | 422 | `number` foi enviado para uma série em numeração automática. |\n| `DPS_NUMBER_REQUIRED_IN_MANUAL` | 422 | A série é de numeração manual e `number` não foi enviado. |\n| `DPS_NUMBER_ALREADY_USED` | 409 | O número de DPS já foi usado nesta série. |\n| `DPS_SEQUENCE_CANNOT_REWIND` | 409 | O próximo número não pode ficar abaixo de um já emitido. |\n| `DPS_SERIES_OUT_OF_RANGE` | 422 | Série fora de 1–49999. Emissão por API só aceita essa faixa; de 50000 em diante são séries dos emissores públicos e o Sistema Nacional recusa com E0010. |\n| `DPS_SERIES_MODE_LOCKED` | 409 | O modo da série não pode mudar depois de haver números alocados. |\n| `DPS_SERIES_HAS_ALLOCATIONS` | 409 | A série já tem números alocados; cadastre outra série. |\n| `DPS_SERIES_DEFAULT_MUST_BE_AUTO` | 409 | A série padrão precisa ser de numeração automática. |\n| `DPS_SERIES_DEFAULT_MUST_STAY_ACTIVE` | 409 | A série padrão não pode ser desativada. |\n| `NFSE_OPERATION_NOT_FOUND` | 404 | Operação de NFS-e não encontrada. |\n| `NFSE_NOT_RETRYABLE` | 409 | Só uma emissão rejeitada pode ser retomada. |\n| `NFSE_RETRY_ENVIRONMENT_MISMATCH` | 422 | A retomada precisa usar o mesmo ambiente da emissão original. |\n| `DPS_RETRY_CANNOT_CHANGE_SERIES` | 422 | A retomada não pode trocar a série já alocada. |\n| `DPS_RETRY_CANNOT_CHANGE_NUMBER` | 422 | A retomada não pode trocar o número já alocado. |\n| `DPS_NOT_PREPARED` | 409 | A DPS ainda não foi gerada para esta operação. |\n| `NFSE_CANNOT_CANCEL` | 409 | A NFS-e não está num estado que permita cancelamento. |\n| `CANCELLATION_CONFLICT` | 409 | Já existe um cancelamento em andamento para esta NFS-e. |\n| `APPROVAL_NOT_FOUND` | 404 | Pedido de aprovação não encontrado — ou, em GET /v1/approvals/{id}, existe mas pertence a outra credencial (só a própria é visível ali). |\n| `APPROVAL_ALREADY_DECIDED` | 409 | O pedido de aprovação já foi decidido. |\n| `APPROVAL_EXPIRED` | 409 | O pedido de aprovação expirou. |\n| `MUNICIPALITY_NOT_FOUND` | 404 | Código IBGE ou nome de município não encontrado. |\n| `MUNICIPALITY_AMBIGUOUS` | 409 | Mais de um município corresponde à busca; informe a UF. |\n| `REGISTRY_UNAVAILABLE` | 503 | A consulta pública de CNPJ/CEP está indisponível ou no teto de chamadas. |\n| `FISCAL_DOCUMENT_NOT_FOUND` | 404 | Documento fiscal não encontrado. |\n| `FISCAL_DOCUMENT_PDF_NOT_FOUND` | 404 | O documento não tem PDF; o XML continua disponível. |\n| `FISCAL_DOCUMENT_XML_NOT_FOUND` | 404 | O documento não tem XML armazenado. |\n| `FISCAL_FILE_NOT_FOUND` | 404 | Arquivo não encontrado. |\n| `DOCUMENT_CONTENT_SUMMARY_ONLY` | 409 | O documento chegou só como cabeçalho; o conteúdo completo existe depois da manifestação. |\n| `BATCH_NO_FILES_AVAILABLE` | 409 | Nenhum dos documentos pedidos tem arquivo disponível. |\n| `BATCH_TOO_LARGE` | 413 | O ZIP ultrapassaria o tamanho máximo; peça menos documentos ou use `delivery: LINKS`. |\n| `BATCH_TOO_LARGE_FOR_LINKS` | 422 | Documentos demais para entrega por links. |\n| `MANIFESTATION_NOT_APPLICABLE` | 409 | A manifestação não se aplica a este documento no estado atual. |\n| `MANIFESTATION_REJECTED` | 422 | A SEFAZ rejeitou a manifestação; `detail` traz o código e o motivo. |\n| `DISPUTE_NOT_APPLICABLE` | 409 | O desacordo não cabe neste documento: não é CT-e, a organização não é a tomadora, o CT-e não está autorizado, chegou só como cabeçalho ou já foi contestado. `detail` diz qual. |\n| `DISPUTE_REJECTED` | 422 | A SEFAZ rejeitou o desacordo; `detail` traz o código e o motivo, e `details` os dois separados. |\n| `SEFAZ_DISTRIBUTION_DISABLED` | 503 | A integração com a distribuição da SEFAZ está desligada no servidor. |\n| `INBOUND_MONITOR_NOT_FOUND` | 404 | Recepção de documentos não configurada para este ambiente. |\n| `INBOUND_MONITOR_NOT_PAUSED` | 409 | Pause o monitoramento antes de alterar o NSU. |\n| `INBOUND_MONITOR_NSU_SKIP_NOT_ACKNOWLEDGED` | 409 | Avançar o NSU pula documentos; confirme com `acknowledgeSkippedDocuments: true`. |\n| `RECEPTION_STARTING_POINT_REQUIRED` | 422 | Falta `receptionStartingPoint` (fiscal-settings, na primeira vez que o ambiente ganha um cursor de NFS-e). |\n| `INVALID_PHONE_NUMBER` | 422 | Telefone inválido. Informe com DDD; sem código de país assume Brasil. |\n| `NUMBER_ALREADY_REGISTERED` | 409 | Este já é o número cadastrado. |\n| `NO_ACTIVE_NUMBER` | 404 | Nenhum WhatsApp cadastrado para receber os documentos. |\n| `NO_PENDING_NUMBER` | 404 | Não há número aguardando verificação. Cadastre com PUT /v1/notifications/whatsapp/number. |\n| `VERIFICATION_CODE_INVALID` | 401 | Código de verificação errado; `details.attemptsRemaining` diz quantas tentativas restam. |\n| `VERIFICATION_CODE_EXPIRED` | 401 | Código de verificação vencido (10 minutos). Peça outro em /number/resend-code. |\n| `VERIFICATION_CODE_LOCKED` | 401 | Tentativas esgotadas. Peça outro código em /number/resend-code. |\n| `VERIFICATION_RATE_LIMITED` | 429 | Limite de 3 códigos de verificação por hora atingido. |\n| `SECURITY_TOKEN_REQUIRED` | 428 | A mudança reduz o aviso. O código foi enviado ao WhatsApp cadastrado (`details.sentTo`); reenvie a MESMA mudança com `securityToken: { challengeId, code }`. Assistente: peça o código à pessoa. |\n| `SECURITY_TOKEN_INVALID` | 401 | Token de segurança errado, já usado ou de outro número. |\n| `SECURITY_TOKEN_EXPIRED` | 401 | Token de segurança vencido (10 minutos). Refaça o pedido sem `securityToken` para receber outro. |\n| `SECURITY_TOKEN_LOCKED` | 401 | Tentativas esgotadas para este token. Refaça o pedido sem `securityToken`. |\n| `SECURITY_TOKEN_CHANGE_MISMATCH` | 409 | O token foi emitido para outra mudança. Reenvie exatamente a mudança que gerou o token. |\n| `SECURITY_TOKEN_RATE_LIMITED` | 429 | Limite de 5 tokens de segurança por hora atingido. |\n| `RECIPIENT_OPTED_OUT` | 409 | O número respondeu PARAR NOTAS. Só o próprio número religa, respondendo VOLTAR NOTAS. |\n| `TEST_MESSAGE_RATE_LIMITED` | 429 | Limite de 3 mensagens de teste por hora atingido. |\n| `WHATSAPP_NUMBER_UNREACHABLE` | 422 | A Meta informou que o número não recebe mensagens de WhatsApp. |\n| `WHATSAPP_SEND_FAILED` | 503 | A Meta não aceitou o envio agora. Tente de novo em instantes. |\n| `WHATSAPP_CHANNEL_UNAVAILABLE` | 503 | O envio de WhatsApp não está configurado neste servidor. |\n| `WEBHOOK_ENDPOINT_NOT_FOUND` | 404 | Endpoint de webhook não encontrado. |\n| `WEBHOOK_DELIVERY_NOT_RESENDABLE` | 409 | A entrega ainda está em andamento e não pode ser reenviada agora. |\n| `INTERNAL_ERROR` | 500 | Erro inesperado. Informe o `requestId` ao suporte. |\n\nRejeições do webservice oficial não viram código próprio: aparecem em `data.rejections` de `GET /v1/nfse/{id}`, com o código e a descrição exatamente como a Sefin devolveu.\n\n## Versionamento\n\nA versão faz parte do caminho (`/v1`). Campos e rotas novos entram na mesma versão, então ignore campos desconhecidos nas respostas. Remover ou mudar o sentido de algo exige uma nova versão."},"servers":[{"url":"https://invoice-api.trilhahub.cloud","description":"Trilha Invoice — único host que atende /v1"}],"tags":[{"name":"NFS-e","description":"Validação, emissão, consulta, retomada e cancelamento de NFS-e no Sistema Nacional."},{"name":"Billing","description":"Carteira, consumo, planos, assinatura, mensalidades e recarga."},{"name":"Webhooks","description":"Endpoints que recebem os eventos da organização, e o histórico de entregas."},{"name":"Approvals","description":"Operações retidas por regra de confirmação humana, aguardando aprovação."},{"name":"Files","description":"Documentos fiscais emitidos e recebidos, seus eventos, arquivos e a recepção de NF-e/CT-e."},{"name":"Operations","description":"Saúde do serviço, métricas e contexto da credencial."},{"name":"Organizations","description":"Cadastro, perfil, configuração fiscal, numeração de DPS e chaves de API."},{"name":"Companies","description":"Empresas (CNPJs) da organização e o vínculo de cada uma com um certificado por ambiente."},{"name":"Municipalities","description":"Consulta pública de disponibilidade de emissão de NFS-e por município (código IBGE). Não requer autenticação; sujeita a rate limit."},{"name":"Registry","description":"Consulta de cadastros públicos (CNPJ na base da Receita Federal e endereço por CEP) para pré-preencher formulários. Não requer autenticação; sujeita a rate limit e a um teto de chamadas ao provedor externo, que responde 503 quando atingido."},{"name":"Certificates","description":"Certificados digitais A1 usados para assinar os documentos fiscais emitidos pela organização. Cadastro rápido pelo portal: https://invoice-app.trilhahub.cloud/certificados"},{"name":"Service Catalog","description":"Serviços recorrentes salvos sob um código curto (ex.: \"consultoria\") — código de tributação nacional, descrição, NBS e tributação/retenção do ISSQN preenchidos uma vez e reaproveitados via serviceCode em POST /v1/nfse/issue e /validate."},{"name":"Authorization","description":"Fluxo de autorização para assistentes de IA e aplicações de terceiros agindo em nome de um usuário. Regra central: nenhum segredo — API key, access token, refresh token ou client secret — deve aparecer no conteúdo de uma conversa, ser pedido ao usuário por chat ou ser registrado em log. O usuário autoriza em uma página do próprio Trilha Invoice e a troca do código por token acontece entre servidores, no backend do conector, que é quem detém o client_secret. Use o Authorization Code + PKCE (S256, obrigatório) quando houver navegador com redirect; use o Device Code (RFC 8628) quando não houver — nesse caso mostre ao usuário apenas o user_code e a verification_uri. Um grant de IA nasce restrito a HOMOLOGATION e com teto mensal; promover para produção é uma ação separada do usuário no console."},{"name":"Notifications","description":"Aviso por WhatsApp de cada documento fiscal baixado em **produção** (nunca em homologação), com o PDF anexado quando existe. Serve para monitorar o uso do certificado digital: uma NFS-e com o CNPJ da organização como prestador que chega pela recepção foi emitida fora do Trilha Invoice. Um número por organização, verificado por código antes de receber. **Ampliar o aviso é livre; reduzir exige token de segurança** — a resposta 428 `SECURITY_TOKEN_REQUIRED` traz `challengeId`, e o código de 6 dígitos chega ao WhatsApp cadastrado. Reenvie a MESMA mudança com `securityToken: { challengeId, code }`. Um assistente não tem como obter o código sozinho: peça-o à pessoa."}],"paths":{"/health":{"get":{"summary":"Liveness do processo","tags":["Operations"],"security":[],"responses":{"200":{"description":"Processo vivo","content":{"application/json":{"schema":{"type":"object","properties":{"status":{"const":"ok"}}}}}}},"operationId":"getHealth"}},"/ready":{"get":{"summary":"Prontidão das dependências","tags":["Operations"],"security":[],"responses":{"200":{"description":"Todas as dependências no ar","content":{"application/json":{"schema":{"type":"object","properties":{"status":{"type":"string","enum":["ready","not_ready"]},"components":{"type":"object","properties":{"database":{"type":"string","enum":["up","down"]},"redis":{"type":"string","enum":["up","down"]},"storage":{"type":"string","enum":["up","down"]}}}}}}}},"503":{"description":"Uma ou mais dependências indisponíveis; o corpo tem o mesmo formato e aponta qual","content":{"application/json":{"schema":{"type":"object","properties":{"status":{"type":"string","enum":["ready","not_ready"]},"components":{"type":"object","properties":{"database":{"type":"string","enum":["up","down"]},"redis":{"type":"string","enum":["up","down"]},"storage":{"type":"string","enum":["up","down"]}}}}}}}}},"operationId":"getReadiness"}},"/metrics":{"get":{"summary":"Métricas Prometheus","tags":["Operations"],"security":[{"metricsToken":[]}],"responses":{"200":{"description":"Métricas no formato Prometheus","content":{"text/plain":{"schema":{"type":"string"}}}},"401":{"description":"Token de métricas inválido"}},"operationId":"getMetrics"}},"/.well-known/oauth-authorization-server":{"get":{"summary":"Metadata de descoberta OAuth 2.0 (RFC 8414)","description":"Sem authorization_endpoint clássico: a autorização começa em POST /v1/oauth/authorization-requests (fluxo com navegador) ou POST /v1/oauth/device-authorizations (device code), ambos na seção Authorization.","tags":["Authorization"],"security":[],"responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","properties":{"issuer":{"type":"string","format":"uri"},"token_endpoint":{"type":"string","format":"uri"},"revocation_endpoint":{"type":"string","format":"uri"},"device_authorization_endpoint":{"type":"string","format":"uri"},"grant_types_supported":{"type":"array","items":{"type":"string"}},"token_endpoint_auth_methods_supported":{"type":"array","items":{"type":"string"}},"code_challenge_methods_supported":{"type":"array","items":{"type":"string"}},"scopes_supported":{"type":"array","items":{"type":"string"}},"service_documentation":{"type":"string","format":"uri"}}}}}}},"operationId":"getOAuthAuthorizationServerMetadata"}},"/.well-known/oauth-protected-resource":{"get":{"summary":"Metadata de descoberta do recurso protegido (RFC 9728)","description":"É para aqui que o header WWW-Authenticate de um 401 aponta (resource_metadata) — permite a um cliente OAuth/MCP achar sozinho o authorization server sem ter lido a prosa da seção Authorization antes.","tags":["Authorization"],"security":[],"responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","properties":{"resource":{"type":"string","format":"uri"},"authorization_servers":{"type":"array","items":{"type":"string","format":"uri"}},"bearer_methods_supported":{"type":"array","items":{"type":"string"}},"scopes_supported":{"type":"array","items":{"type":"string"}},"resource_documentation":{"type":"string","format":"uri"}}}}}}},"operationId":"getOAuthProtectedResourceMetadata"}},"/v1/context":{"get":{"summary":"Contexto da credencial autenticada","security":[{"bearerAuth":[]}],"x-required-scope":"nfse:read","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/ContextResponse"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"description":"Quem sou eu e o que posso fazer: organização, credencial e escopos efetivos. É a primeira chamada útil de um integrador — evita descobrir por 403 que a credencial não tem o escopo.","tags":["Operations"],"operationId":"getContext"}},"/v1/organizations":{"post":{"summary":"Auto-cadastro de empresa","description":"Cria a organização, o usuário titular e a **empresa padrão** — o endereço enviado aqui vira essa empresa (RFC-018 §5.5), e é ela que resolve toda rota com `companyId` ausente. Não chame `POST /v1/companies` depois para o mesmo CNPJ: ele já pertence à empresa padrão e a chamada volta `COMPANY_TAX_ID_ALREADY_IN_USE`. A resposta traz em `apiKey.secret` uma chave `tinv_` mostrada uma única vez, com todos os escopos menos `billing:adjust` e `approvals:manage` e restrita a `HOMOLOGATION` — produção é liberada por uma pessoa no console, com e-mail confirmado e senha pessoal; a própria chave não consegue se promover (`PRODUCTION_AUTHORIZATION_REQUIRED`). Com ela, o próximo passo é `GET /v1/organization/pending`, que lista o que falta para emitir. Dois avisos antes de chamar: o CNPJ **não** é conferido contra a Receita Federal e fica reservado para esta organização em toda a plataforma (`ORGANIZATION_TAX_ID_ALREADY_REGISTERED` em qualquer tentativa posterior, inclusive sua), então cadastre só CNPJ que você controla; e um assistente de IA que se identifica com `X-Client-Id` recebe `apiKey: null` e segue pela confirmação de e-mail mais a tela de consentimento (RFC-015 §8).","tags":["Organizations"],"security":[],"responses":{"201":{"description":"Organização, empresa padrão e titular criados. `apiKey.secret` vem preenchido no caminho servidor-a-servidor e nulo quando a chamada declara `X-Client-Id`","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/OrganizationCreated"},"errors":{"type":"array","maxItems":0}}}}}},"409":{"description":"CNPJ ou e-mail já cadastrado","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"422":{"description":"Dados inválidos","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"429":{"description":"Limite de cadastros excedido","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}},"headers":{"Retry-After":{"description":"Segundos até a próxima tentativa.","schema":{"type":"integer"}}}}},"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateOrganizationRequest"}}}},"operationId":"registerOrganization"}},"/v1/oauth/register":{"post":{"summary":"Registro dinâmico de cliente (RFC 7591)","description":"Público, sem intervenção manual (RFC-022 §7.2). Nasce sempre `PUBLIC`, `UNVERIFIED` e com teto de escopo fixo no perfil `ai-issuer` (`nfse:read`, `nfse:validate`, `fiscal-document:read`, `fiscal-document:download`, `service-catalog:read`, `billing:read`, `nfse:issue`) — o que vier em `scope` só pode restringir esse teto, nunca ampliá-lo. `client_name` que se pareça com marca conhecida (\"ChatGPT\", \"Claude\", \"Gemini\", \"Copilot\", \"TrilhaHUB\", \"Trilha Invoice\"...) é recusado. Erro no formato do próprio RFC 7591 (`error`/`error_description`), não no envelope da API. Sem `client_secret` (cliente público) nem `registration_access_token` — o registro é imutável, sem gestão própria pelo cliente.","tags":["Authorization"],"security":[],"responses":{"201":{"description":"Cliente registrado","content":{"application/json":{"schema":{"type":"object","required":["client_id","client_id_issued_at","redirect_uris","token_endpoint_auth_method"],"properties":{"client_id":{"type":"string"},"client_id_issued_at":{"type":"integer","description":"Época Unix, em segundos."},"client_name":{"type":"string"},"redirect_uris":{"type":"array","items":{"type":"string","format":"uri"}},"grant_types":{"type":"array","items":{"type":"string"}},"response_types":{"type":"array","items":{"type":"string"}},"token_endpoint_auth_method":{"const":"none"},"scope":{"type":"string","description":"Teto efetivo concedido ao cliente, espaço-separado."}}}}}},"400":{"description":"invalid_redirect_uri ou invalid_client_metadata (inclui nome reservado)","content":{"application/json":{"schema":{"type":"object","required":["error"],"properties":{"error":{"type":"string","enum":["invalid_redirect_uri","invalid_client_metadata"]},"error_description":{"type":"string"}}}}}},"429":{"description":"Teto diário global de registros atingido","content":{"application/json":{"schema":{"type":"object","required":["error"],"properties":{"error":{"type":"string","enum":["invalid_redirect_uri","invalid_client_metadata"]},"error_description":{"type":"string"}}}}}}},"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["redirect_uris"],"properties":{"redirect_uris":{"type":"array","minItems":1,"maxItems":10,"items":{"type":"string","format":"uri"},"description":"https, ou http://localhost e http://127.0.0.1 em desenvolvimento. Sem fragmento."},"client_name":{"type":"string","maxLength":200,"description":"Recusado se lembrar uma marca conhecida."},"scope":{"type":"string","description":"Espaço-separado. Só restringe o teto fixo `ai-issuer`, nunca amplia — o que não for parte dele é ignorado, não rejeitado."},"token_endpoint_auth_method":{"type":"string","description":"Aceito e ignorado: o cliente nasce sempre público (`none`)."},"grant_types":{"type":"array","items":{"type":"string"},"description":"Aceito e ignorado: o conjunto é fixo."},"response_types":{"type":"array","items":{"type":"string"},"description":"Aceito e ignorado: sempre `[\"code\"]`."}}}}}},"operationId":"registerOAuthClient"}},"/v1/oauth/authorize":{"get":{"summary":"Iniciar autorização por redirect (RFC-022 §7.1)","description":"authorization_endpoint padrão do OAuth 2.1 — o cliente abre esta URL no navegador do usuário, em vez de chamar POST /v1/oauth/authorization-requests pelo backend. `scope` é separado por espaço, não array JSON. client_id e redirect_uri são validados antes de qualquer redirecionamento (erro aqui é `400` com envelope da API, nunca 302 para uma URI não confirmada); depois disso, todo erro volta como `error`/`error_description`/`state` na própria redirect_uri (RFC 6749 §4.1.2.1).","tags":["Authorization"],"security":[],"parameters":[{"name":"response_type","in":"query","required":true,"schema":{"const":"code"}},{"name":"client_id","in":"query","required":true,"schema":{"type":"string"}},{"name":"redirect_uri","in":"query","required":true,"schema":{"type":"string","format":"uri"}},{"name":"scope","in":"query","required":true,"schema":{"type":"string"},"description":"Escopos separados por espaço, ex.: \"nfse:read nfse:validate\"."},{"name":"state","in":"query","required":false,"schema":{"type":"string"}},{"name":"code_challenge","in":"query","required":true,"schema":{"type":"string"}},{"name":"code_challenge_method","in":"query","required":true,"schema":{"const":"S256"}},{"name":"resource","in":"query","required":false,"schema":{"type":"string","format":"uri"},"description":"RFC 8707. Só há um recurso — esta própria API — então um valor diferente volta pelo redirect como `error=invalid_target`, em vez de ser ignorado."}],"responses":{"302":{"description":"Redireciona para a tela de consentimento do console, ou de volta para redirect_uri com error=... quando algo na solicitação já validada falhou"},"400":{"description":"client_id desconhecido/suspenso ou redirect_uri fora da lista do cliente — não redireciona","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"operationId":"startAuthorizationByRedirect"}},"/v1/oauth/authorization-requests":{"post":{"summary":"Criar solicitação de autorização (fluxo com navegador)","description":"Chamado pelo backend do conector, não pelo modelo. Devolve a authorizationUrl para o usuário abrir; nada aqui é segredo, então o link pode ser apresentado no chat.","tags":["Authorization"],"security":[],"responses":{"201":{"description":"Solicitação criada","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"requestId":{"type":"string","format":"uuid"},"authorizationUrl":{"type":"string","format":"uri","description":"Para onde mandar o usuário aprovar. Nunca peça a chave dele no chat."},"expiresAt":{"type":"string","format":"date-time"}}},"errors":{"type":"array","maxItems":0}}}}}},"400":{"description":"redirect_uri, escopo ou grant type não permitido para o cliente","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"401":{"description":"Cliente desconhecido, suspenso ou client_secret inválido"},"422":{"description":"Dados inválidos","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"429":{"description":"Limite de solicitações excedido","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}},"headers":{"Retry-After":{"description":"Segundos até a próxima tentativa.","schema":{"type":"integer"}}}}},"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AuthorizationRequestBody"}}}},"operationId":"createAuthorizationRequest"}},"/v1/oauth/device-authorizations":{"post":{"summary":"Criar autorização por device code (chat sem navegador)","description":"RFC 8628. Mostre ao usuário apenas user_code e verification_uri — o device_code fica no backend do conector e nunca aparece na conversa. Faça polling em /v1/oauth/token respeitando o interval devolvido.","tags":["Authorization"],"security":[],"responses":{"201":{"description":"device_code e user_code emitidos","content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeviceAuthorizationResponse"}}}},"400":{"description":"Escopo ou grant type não permitido para o cliente","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"401":{"description":"Cliente desconhecido, suspenso ou client_secret inválido"},"429":{"description":"Limite de solicitações excedido","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}},"headers":{"Retry-After":{"description":"Segundos até a próxima tentativa.","schema":{"type":"integer"}}}}},"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeviceAuthorizationRequestBody"}}}},"operationId":"createDeviceAuthorization"}},"/v1/oauth/token":{"post":{"summary":"Trocar código por token, ou renovar","description":"Único endpoint que responde no formato do RFC 6749 em vez do envelope da API, para funcionar com bibliotecas OAuth prontas. Aceita JSON e form-urlencoded. No fluxo de device, `authorization_pending` significa continuar o polling. Refresh tokens são rotacionados a cada uso: reapresentar um token já usado é tratado como vazamento e revoga a integração inteira.","tags":["Authorization"],"security":[],"responses":{"200":{"description":"Tokens emitidos","content":{"application/json":{"schema":{"$ref":"#/components/schemas/TokenResponse"}}}},"400":{"description":"invalid_grant, authorization_pending, slow_down, access_denied ou expired_token","content":{"application/json":{"schema":{"$ref":"#/components/schemas/OAuthErrorResponse"}}}},"401":{"description":"invalid_client","content":{"application/json":{"schema":{"$ref":"#/components/schemas/OAuthErrorResponse"}}}},"422":{"description":"Dados inválidos","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"429":{"description":"Limite de trocas excedido","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}},"headers":{"Retry-After":{"description":"Segundos até a próxima tentativa.","schema":{"type":"integer"}}}}},"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TokenRequestBody"}}}},"operationId":"exchangeOAuthToken"}},"/v1/oauth/revoke":{"post":{"summary":"Revogar a integração a partir de um token","description":"RFC 7009. Aceita access ou refresh token e encerra o grant inteiro. Responde 200 inclusive para token desconhecido, para não virar oráculo de tokens válidos.","tags":["Authorization"],"security":[],"responses":{"200":{"description":"Revogado (ou token desconhecido)"},"401":{"description":"invalid_client","content":{"application/json":{"schema":{"$ref":"#/components/schemas/OAuthErrorResponse"}}}}},"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RevokeTokenRequest"}}}},"operationId":"revokeOAuthToken"}},"/v1/integrations":{"get":{"summary":"Listar aplicações conectadas","description":"Exige sessão de console: um assistente autorizado não lista nem revoga integrações, mesmo carregando organization:manage.","tags":["Authorization"],"security":[{"consoleSession":[]}],"responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"items":{"type":"array","items":{"$ref":"#/components/schemas/ConnectedIntegration"}}}},"errors":{"type":"array","maxItems":0}}}}}},"403":{"description":"Requer sessão de console","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"operationId":"listIntegrations"}},"/v1/integrations/{id}/policy":{"patch":{"summary":"Ajustar limites de uma aplicação conectada","description":"Faz merge com a política atual, ao contrário de /v1/api-credentials/{id}/policy, que substitui tudo. Liberar produção mandando apenas allowedEnvironments apagaria o teto mensal — por isso o merge, e por isso a exigência de teto é revalidada aqui.","tags":["Authorization"],"security":[{"consoleSession":[]}],"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CredentialPolicyRequest"}}}},"responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"policy":{"$ref":"#/components/schemas/CredentialPolicyRequest"}}},"errors":{"type":"array","maxItems":0}}}}}},"403":{"description":"Requer sessão de console","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Integração não encontrada","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"422":{"description":"Grant de IA que pode emitir precisa de teto mensal","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"operationId":"updateIntegrationPolicy"}},"/v1/integrations/{id}":{"delete":{"summary":"Revogar uma aplicação conectada","description":"Invalida access tokens, refresh tokens e a credencial derivada na mesma transação.","tags":["Authorization"],"security":[{"consoleSession":[]}],"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"status":{"const":"REVOKED"}}},"errors":{"type":"array","maxItems":0}}}}}},"403":{"description":"Requer sessão de console","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Integração não encontrada","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"operationId":"revokeIntegration"}},"/v1/organizations/me":{"patch":{"summary":"Atualizar perfil da empresa","security":[{"bearerAuth":[]}],"x-required-scope":"organization:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"id":{"type":"string","format":"uuid"}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"422":{"description":"Dados inválidos","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateOrganizationRequest"}}}},"tags":["Organizations"],"operationId":"updateOrganizationProfile"}},"/v1/organization/fiscal-settings":{"get":{"summary":"Consultar configuração fiscal atual por ambiente","security":[{"bearerAuth":[]}],"x-required-scope":"fiscal-settings:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/FiscalSettingsSnapshot"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"x-ai-tool":true,"description":"Aceita `fiscal-settings:manage` (o escopo estreito, concedível a assistente de IA) ou `organization:manage`.","parameters":[{"name":"environment","in":"query","required":false,"schema":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"],"default":"HOMOLOGATION"}},{"name":"companyId","in":"query","required":false,"schema":{"type":"string","format":"uuid"},"description":"Ausente resolve para a empresa padrão (RFC-018)."}],"tags":["Organizations"],"operationId":"getFiscalSettings"},"patch":{"summary":"Configurar padrão fiscal de ISSQN e regime tributário por ambiente","security":[{"bearerAuth":[]}],"x-required-scope":"fiscal-settings:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"422":{"description":"Dados inválidos, município da empresa ausente (COMPANY_MUNICIPALITY_REQUIRED)","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"x-ai-tool":true,"description":"Aceita `fiscal-settings:manage` (escopo estreito, concedível a assistente de IA) ou `organization:manage`. A trava de ambiente da credencial vale: um assistente liberado só em homologação só configura homologação. Os rótulos de cada código estão nos campos de `issuerTaxSettings`.","requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/FiscalSettingsRequest"}}}},"tags":["Organizations"],"operationId":"updateFiscalSettings"}},"/v1/organization/fiscal-settings/emitter":{"patch":{"summary":"Alterar série de DPS e inscrição municipal sem reenviar o certificado","security":[{"bearerAuth":[]}],"x-required-scope":"organization:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"dpsSeries":{"type":"string","pattern":"^\\d{1,5}$"},"municipalRegistration":{"type":["string","null"],"pattern":"^\\d{1,15}$"}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"CERTIFICATE_LINK_NOT_FOUND — a empresa não tem certificado vinculado neste ambiente. Numeração e emitente moram no vínculo empresa+ambiente, então vincule um certificado com PUT /v1/companies/{id}/certificate/{environment} antes de configurar a série.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"409":{"description":"A nova série já tem números alocados (DPS_SERIES_HAS_ALLOCATIONS) — semeie o próximo número em PATCH /v1/organization/dps-sequences ou cadastre uma série sem uso anterior","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"422":{"description":"Dados inválidos ou nada a atualizar","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"description":"dpsSeries vive em dps_series_config (a série is_default) e municipalRegistration em companies. Até aqui só entravam por POST /v1/certificates, o que transformava um ajuste de cadastro em pré-requisito de reenviar o PKCS#12. Informe pelo menos um de dpsSeries/municipalRegistration. Para definir série padrão e próximo número juntos, prefira PUT /v1/organization/dps-numbering; série de 1 a 49999. municipalRegistration: null desassocia a inscrição municipal da credencial ativa daquele ambiente — para o emitente cujo município não tem cadastro complementar no CNC NFS-e e cuja DPS não pode carregar prestador/IM. É o único jeito de manter a IM fora da DPS: issuerTaxSettings.includeMunicipalRegistration não existe mais, e a IM entra na DPS sempre que a empresa tem uma cadastrada.","requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":false,"required":["environment"],"properties":{"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"dpsSeries":{"type":"string","pattern":"^\\d{1,5}$"},"municipalRegistration":{"type":["string","null"],"pattern":"^\\d{1,15}$"},"companyId":{"type":"string","format":"uuid","description":"Ausente resolve para a empresa padrão (RFC-018)."}}}}}},"tags":["Organizations"],"operationId":"updateEmitterSettings"}},"/v1/organization/dps-numbering":{"get":{"summary":"Consultar a numeração da DPS e uma série sugerida","security":[{"bearerAuth":[]}],"x-required-scope":"nfse:read","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","required":["environment","allowedSeriesRange","defaultSeries","series","suggestedNewSeries"],"properties":{"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"allowedSeriesRange":{"type":"object","properties":{"min":{"const":1},"max":{"const":49999}}},"defaultSeries":{"type":["object","null"],"properties":{"series":{"type":"string"},"nextNumber":{"type":"string"},"used":{"type":"boolean"}}},"series":{"type":"array","items":{"type":"object","properties":{"series":{"type":"string"},"mode":{"type":"string","enum":["AUTO","MANUAL"]},"active":{"type":"boolean"},"isDefault":{"type":"boolean"},"nextNumber":{"type":"string"},"used":{"type":"boolean","description":"Já emitiu por aqui nesta série"}}}},"suggestedNewSeries":{"type":["string","null"],"description":"Menor série de 1 a 49999 sem uso nesta empresa/ambiente"}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"x-ai-tool":true,"description":"Série padrão, próximo número e séries já cadastradas da empresa no ambiente, a faixa aceita para emissão por API (1 a 49999 — de 50000 em diante são séries dos emissores públicos, recusadas com E0010) e `suggestedNewSeries`, a menor série ainda não usada aqui, que começa limpa no número 1 (a numeração do Sistema Nacional é por CNPJ + município + série). A sugestão só conhece o que passou pelo Trilha Invoice: se a empresa emite por outro sistema integrado, pergunte a série e o último número.","parameters":[{"name":"environment","in":"query","required":false,"schema":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"],"default":"HOMOLOGATION"}},{"name":"companyId","in":"query","required":false,"schema":{"type":"string","format":"uuid"},"description":"Ausente resolve para a empresa padrão."}],"tags":["Organizations"],"operationId":"getDpsNumbering"},"put":{"summary":"Definir a série padrão e o próximo número num passo só","security":[{"bearerAuth":[]}],"x-required-scope":"dps-numbering:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","required":["environment","allowedSeriesRange","defaultSeries","series","suggestedNewSeries"],"properties":{"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"allowedSeriesRange":{"type":"object","properties":{"min":{"const":1},"max":{"const":49999}}},"defaultSeries":{"type":["object","null"],"properties":{"series":{"type":"string"},"nextNumber":{"type":"string"},"used":{"type":"boolean"}}},"series":{"type":"array","items":{"type":"object","properties":{"series":{"type":"string"},"mode":{"type":"string","enum":["AUTO","MANUAL"]},"active":{"type":"boolean"},"isDefault":{"type":"boolean"},"nextNumber":{"type":"string"},"used":{"type":"boolean","description":"Já emitiu por aqui nesta série"}}}},"suggestedNewSeries":{"type":["string","null"],"description":"Menor série de 1 a 49999 sem uso nesta empresa/ambiente"}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Sem certificado vinculado para emissão neste ambiente (`CERTIFICATE_LINK_NOT_FOUND`)","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"409":{"description":"Sequência não pode retroceder, ou série com números já alocados","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"422":{"description":"`DPS_SERIES_OUT_OF_RANGE` (fora de 1–49999) ou dados inválidos","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"x-ai-tool":true,"description":"Cadastra a série (modo AUTO) se ainda não existir, elege como padrão do ambiente e, com `nextNumber`, semeia o próximo número — o mesmo que PUT /v1/organization/dps-series/{series} + PATCH /v1/organization/fiscal-settings/emitter + PATCH /v1/organization/dps-sequences, na ordem certa. Quem já emite por outro sistema informa a série dele e `nextNumber` = último + 1; quem começa agora usa `suggestedNewSeries` de GET /v1/organization/dps-numbering com `nextNumber: 1`, que confirma a série nova.","requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":false,"required":["environment","series"],"properties":{"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"series":{"type":"string","pattern":"^\\d{1,5}$","description":"De 1 a 49999"},"nextNumber":{"type":"integer","minimum":1,"description":"Próximo número a emitir. Só avança, nunca retrocede"},"companyId":{"type":"string","format":"uuid"}}}}}},"tags":["Organizations"],"operationId":"configureDpsNumbering"}},"/v1/organization/dps-sequences":{"get":{"summary":"Listar sequências de numeração de DPS","security":[{"bearerAuth":[]}],"x-required-scope":"organization:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"items":{"type":"array","items":{"$ref":"#/components/schemas/DpsSequence"}}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"parameters":[{"name":"environment","in":"query","required":false,"schema":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]}},{"name":"companyId","in":"query","required":false,"schema":{"type":"string","format":"uuid"},"description":"Ausente resolve para a empresa padrão (RFC-018)."}],"tags":["Organizations"],"operationId":"listDpsSequences"},"patch":{"summary":"Semear o próximo número de uma sequência","security":[{"bearerAuth":[]}],"x-required-scope":"organization:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"municipalityCode":{"type":"string","pattern":"^\\d{7}$"},"series":{"type":"string","pattern":"^\\d{1,5}$"},"nextNumber":{"type":"integer"}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"409":{"description":"A sequência já passou desse número (DPS_SEQUENCE_CANNOT_REWIND) — só é possível avançar, nunca retroceder","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"422":{"description":"Dados inválidos","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"description":"Para quem migra de outro emissor e precisa continuar a numeração vigente (próximo número 4821, não 1). Só avança: nextNumber precisa ser >= ao valor atual. Para definir série padrão e próximo número juntos, use PUT /v1/organization/dps-numbering.","requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":false,"required":["environment","municipalityCode","series","nextNumber"],"properties":{"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"municipalityCode":{"type":"string","pattern":"^\\d{7}$"},"series":{"type":"string","pattern":"^\\d{1,5}$"},"nextNumber":{"type":"integer","minimum":1,"maximum":999999999999999},"companyId":{"type":"string","format":"uuid","description":"Ausente resolve para a empresa padrão (RFC-018)."}}}}}},"tags":["Organizations"],"operationId":"seedDpsSequence"}},"/v1/organization/dps-series":{"get":{"summary":"Listar séries de DPS e seu modo","security":[{"bearerAuth":[]}],"x-required-scope":"organization:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"items":{"type":"array","items":{"$ref":"#/components/schemas/DpsSeriesConfig"}}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"description":"Uma série é AUTO (o Trilha Invoice aloca o número) ou MANUAL (o cliente informa series e number em toda emissão). isDefault marca a série usada quando POST /v1/nfse/issue não informa uma.","parameters":[{"name":"environment","in":"query","required":false,"schema":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]}},{"name":"companyId","in":"query","required":false,"schema":{"type":"string","format":"uuid"},"description":"Ausente resolve para a empresa padrão (RFC-018)."}],"tags":["Organizations"],"operationId":"listDpsSeries"}},"/v1/organization/dps-series/{series}":{"put":{"summary":"Cadastrar ou atualizar uma série de DPS","security":[{"bearerAuth":[]}],"x-required-scope":"organization:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/DpsSeriesConfig"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"CERTIFICATE_LINK_NOT_FOUND — a empresa não tem certificado vinculado neste ambiente. Numeração e emitente moram no vínculo empresa+ambiente, então vincule um certificado com PUT /v1/companies/{id}/certificate/{environment} antes de configurar a série.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"409":{"description":"Troca de modo de uma série com números já alocados (DPS_SERIES_MODE_LOCKED — reenvie com ?confirm=true), ou a série default não pode ficar inativa/MANUAL","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"422":{"description":"Dados inválidos","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"description":"Cadastro fino de série (modo AUTO/MANUAL, ativa/inativa). Para o caso comum — definir a série padrão e o próximo número — use PUT /v1/organization/dps-numbering, que faz tudo num passo. Série de 1 a 49999 (`DPS_SERIES_OUT_OF_RANGE`): de 50000 em diante são séries dos emissores públicos.","parameters":[{"name":"series","in":"path","required":true,"schema":{"type":"string","pattern":"^\\d{1,5}$"}},{"name":"confirm","in":"query","required":false,"schema":{"type":"string","enum":["true","false"]},"description":"true para trocar o modo mesmo com números já alocados na série."}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":false,"required":["environment","mode"],"properties":{"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"mode":{"type":"string","enum":["AUTO","MANUAL"]},"active":{"type":"boolean","default":true},"companyId":{"type":"string","format":"uuid","description":"Ausente resolve para a empresa padrão (RFC-018)."}}}}}},"tags":["Organizations"],"operationId":"upsertDpsSeries"}},"/v1/organization/pending":{"get":{"summary":"Checklist de pendências para emissão","security":[{"bearerAuth":[]}],"x-required-scope":"nfse:read","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/Readiness"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"description":"Consulte antes de emitir: `ready: false` significa que existe pendência CRITICAL e a emissão vai falhar — melhor dizer ao usuário o que falta do que gastar uma tentativa para descobrir. O checklist é avaliado pela finalidade do vínculo de certificado da empresa (campo `purpose`): uma empresa que vinculou o certificado como \"somente recepção\" não é cobrada pelos parâmetros de emissão e pode aparecer `ready: true` sem nunca poder emitir.","parameters":[{"name":"environment","in":"query","required":false,"schema":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"],"default":"HOMOLOGATION"}},{"name":"companyId","in":"query","required":false,"schema":{"type":"string","format":"uuid"},"description":"Ausente resolve para a empresa padrão (RFC-018)."}],"tags":["Organizations"],"operationId":"getIssuancePendingItems"}},"/v1/service-catalog":{"get":{"summary":"Listar entradas do catálogo de serviços","security":[{"bearerAuth":[]}],"x-required-scope":"service-catalog:read","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"items":{"type":"array","items":{"$ref":"#/components/schemas/ServiceCatalogEntry"}}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"parameters":[{"name":"status","in":"query","required":false,"schema":{"type":"string","enum":["ACTIVE","ARCHIVED"]}}],"tags":["Service Catalog"],"operationId":"listServiceCatalogEntries"},"post":{"summary":"Cadastrar uma entrada no catálogo de serviços","security":[{"bearerAuth":[]}],"x-required-scope":"service-catalog:write","responses":{"201":{"description":"Entrada criada","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/ServiceCatalogEntry"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"409":{"description":"Já existe uma entrada com esse code","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"422":{"description":"Dados inválidos","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateServiceCatalogEntryRequest"},"examples":{"exemplo":{"summary":"Consultoria","value":{"code":"consultoria","nationalTaxCode":"010101","description":"Consultoria em tecnologia da informação","municipalTax":{"taxation":"1","withholding":"1","rate":"5.00"}}}}}}},"tags":["Service Catalog"],"operationId":"createServiceCatalogEntry"}},"/v1/service-catalog/{id}":{"patch":{"summary":"Atualizar uma entrada do catálogo de serviços","security":[{"bearerAuth":[]}],"x-required-scope":"service-catalog:write","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/ServiceCatalogEntry"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Entrada não encontrada","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"422":{"description":"Dados inválidos","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateServiceCatalogEntryRequest"}}}},"tags":["Service Catalog"],"operationId":"updateServiceCatalogEntry"}},"/v1/service-catalog/{id}/archive":{"post":{"summary":"Arquivar uma entrada do catálogo de serviços","security":[{"bearerAuth":[]}],"x-required-scope":"service-catalog:write","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"id":{"type":"string","format":"uuid"}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Entrada não encontrada ou já arquivada","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"description":"Uma entrada arquivada não resolve mais via serviceCode em novas emissões; operações já emitidas não são afetadas (os valores foram copiados no momento da emissão).","parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"tags":["Service Catalog"],"operationId":"archiveServiceCatalogEntry"}},"/v1/api-credentials":{"get":{"summary":"Listar credenciais de API da empresa","security":[{"bearerAuth":[]}],"x-required-scope":"organization:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"items":{"type":"array","items":{"$ref":"#/components/schemas/ApiCredentialMetadata"}}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"tags":["Organizations"],"operationId":"listApiCredentials"},"post":{"summary":"Emitir uma nova credencial de API","security":[{"bearerAuth":[]}],"x-required-scope":"organization:manage","responses":{"201":{"description":"Credencial criada; segredo retornado uma única vez","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"name":{"type":"string"},"prefix":{"type":"string"},"secret":{"type":"string","description":"Mostrado uma única vez — não há endpoint que devolva este valor de novo."},"scopes":{"type":"array","items":{"type":"string"}},"warning":{"type":"string"}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"409":{"description":"Já existe uma credencial com esse nome","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"422":{"description":"Dados inválidos","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"description":"A chave nova nasce restrita a HOMOLOGATION. Produção é ação de pessoa: no console, com `allowProduction`, e-mail confirmado e a senha pessoal em `password`; criada por outra chave, só herda produção se a criadora já tiver.","requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateApiCredentialRequest"}}}},"tags":["Organizations"],"operationId":"createApiCredential"}},"/v1/api-credentials/{id}/revoke":{"post":{"summary":"Revogar uma credencial de API","security":[{"bearerAuth":[]}],"x-required-scope":"organization:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"status":{"const":"REVOKED"}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Credencial não encontrada","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"409":{"description":"Não é possível revogar a única credencial ativa","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"tags":["Organizations"],"operationId":"revokeApiCredential"}},"/v1/api-credentials/{id}/policy":{"patch":{"summary":"Definir guardrails de consumo da credencial","security":[{"bearerAuth":[]}],"x-required-scope":"organization:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"policy":{"$ref":"#/components/schemas/CredentialPolicyRequest"}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Credencial não encontrada","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"422":{"description":"Dados inválidos","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"description":"Substitui a política inteira. Uma política que passa a liberar PRODUCTION (sem `allowedEnvironments`, ou com PRODUCTION nele) só é aceita de uma pessoa no console, com e-mail confirmado e `password` — chamada por chave de API responde `PRODUCTION_AUTHORIZATION_REQUIRED`.","parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":false,"properties":{"allowedEnvironments":{"type":"array","minItems":1,"items":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]}},"allowedIssuerDocuments":{"type":"array","minItems":1,"items":{"type":"string","pattern":"^(\\d{11}|\\d{14})$"}},"maxDocumentValueCents":{"type":"integer","minimum":0},"approvalRequiredAboveCents":{"type":"integer","minimum":0},"allowedRecipientDocuments":{"type":"array","minItems":1,"items":{"type":"string","pattern":"^(\\d{11}|\\d{14})$"}},"maxMonthlyIssuances":{"type":"integer","minimum":1},"maxMonthlyAmountCents":{"type":"integer","minimum":0},"dailyEventLimit":{"type":"integer","minimum":1},"monthlyEventLimit":{"type":"integer","minimum":1},"dailyBudgetCents":{"type":"integer","minimum":0},"monthlyBudgetCents":{"type":"integer","minimum":0},"password":{"type":"string","description":"Senha pessoal de quem está no console — só quando libera produção. Nunca é gravada."},"mfaCode":{"type":"string","description":"Código do autenticador, quando a conta tem MFA e a operação libera produção."}}}}}},"tags":["Organizations"],"operationId":"updateApiCredentialPolicy"}},"/v1/certificates":{"get":{"summary":"Listar o cofre de certificados","security":[{"bearerAuth":[]}],"x-required-scope":"certificates:read","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"items":{"type":"array","items":{"$ref":"#/components/schemas/CertificateMetadata"}}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"x-ai-tool":true,"description":"Cada certificado com a lista de empresas/ambientes que o usam — ver `links`. Sem CNPJ nem ambiente no nível do certificado (RFC-018): quem usa é o vínculo, não o arquivo.","tags":["Certificates"],"operationId":"listCertificates"},"post":{"summary":"Subir um certificado A1 no cofre","security":[{"bearerAuth":[]}],"x-required-scope":"certificates:write","responses":{"201":{"description":"Certificado cadastrado (ou reaproveitado por fingerprint); apenas metadados são retornados","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/CertificateMetadata"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"422":{"description":"Certificado ou senha inválidos","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"503":{"description":"Certificate Vault não configurado","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"description":"O certificado A1 (e-CNPJ/e-CPF) deve ser enviado como um arquivo PKCS#12 (.pfx/.p12), codificado em base64 no campo `pfxBase64` (até 1 MiB decodificado), junto com a senha em `passphrase`. Precisa ter sido emitido por uma AC da ICP-Brasil — inclusive para homologação, que não tem certificado de teste nem caminho sem certificado: um autoassinado é recusado com `CERTIFICATE_NOT_TRUSTED`. Prefere não lidar com base64? Cadastre pelo portal, sem chamar a API diretamente: https://invoice-app.trilhahub.cloud/certificados Sobe só o arquivo — sem empresa, sem ambiente. Vincule a uma empresa com PUT /v1/companies/{id}/certificate/{environment}. **Assistente de IA não usa esta rota**: pedir o .pfx e a senha na conversa deixa a chave privada da empresa no histórico do chat. Peça um link com POST /v1/certificate-upload-sessions (no MCP, `certificates.request_upload`) e a pessoa envia pela página.","requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateCertificateRequest"},"examples":{"exemplo":{"summary":"Upload de certificado A1","value":{"pfxBase64":"1G7VnI2LwFcbL8kaJov7RAnjUVYTbpViYD1vqrGidkY7gCTkEzLl768iWwmMSxWg","passphrase":"senha-do-certificado"}}}}}},"tags":["Certificates"],"operationId":"uploadCertificate"}},"/v1/certificates/{id}":{"get":{"summary":"Consultar um certificado do cofre","security":[{"bearerAuth":[]}],"x-required-scope":"certificates:read","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/CertificateMetadata"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Certificado não encontrado","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"tags":["Certificates"],"operationId":"getCertificate"}},"/v1/certificates/{id}/replace":{"post":{"summary":"Substituir o arquivo de um certificado","security":[{"bearerAuth":[]}],"x-required-scope":"certificates:write","responses":{"201":{"description":"Arquivo substituído; o anterior passa a REPLACED e todo vínculo ativo passa a apontar para o novo","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/CertificateMetadata"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Certificado ativo não encontrado","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"422":{"description":"Certificado ou senha inválidos","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"503":{"description":"Certificate Vault não configurado","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"description":"O certificado A1 (e-CNPJ/e-CPF) deve ser enviado como um arquivo PKCS#12 (.pfx/.p12), codificado em base64 no campo `pfxBase64` (até 1 MiB decodificado), junto com a senha em `passphrase`. Precisa ter sido emitido por uma AC da ICP-Brasil — inclusive para homologação, que não tem certificado de teste nem caminho sem certificado: um autoassinado é recusado com `CERTIFICATE_NOT_TRUSTED`. Prefere não lidar com base64? Cadastre pelo portal, sem chamar a API diretamente: https://invoice-app.trilhahub.cloud/certificados Troca o arquivo mantendo todos os vínculos ativos (RFC-018 §5.3).","parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateCertificateRequest"}}}},"tags":["Certificates"],"operationId":"replaceCertificate"}},"/v1/certificates/{id}/revoke":{"post":{"summary":"Revogar um certificado ativo","security":[{"bearerAuth":[]}],"x-required-scope":"certificates:write","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"status":{"const":"REVOKED"}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Certificado ativo não encontrado","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"409":{"description":"Certificado tem vínculo ativo — desvincule de cada empresa (DELETE .../certificate/{environment}) antes de revogar","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"tags":["Certificates"],"operationId":"revokeCertificate"}},"/v1/certificate-upload-sessions":{"post":{"summary":"Pedir um link para a pessoa enviar o certificado","security":[{"bearerAuth":[]}],"x-required-scope":"certificates:request-upload","responses":{"201":{"description":"Link criado. Entregue `uploadUrl` à pessoa que tem o certificado","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","required":["id","companyId","environment","intendedUse","status","attemptsRemaining","expiresAt","completedAt","certificateId","createdAt","uploadUrl","company","warning"],"properties":{"id":{"type":"string","format":"uuid"},"companyId":{"type":"string","format":"uuid"},"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"intendedUse":{"type":"string","enum":["ISSUANCE_AND_RECEPTION","RECEPTION_ONLY"]},"status":{"type":"string","enum":["PENDING","COMPLETED","EXPIRED","LOCKED"],"description":"PENDING: aguardando o envio. COMPLETED: certificado guardado e vinculado. EXPIRED: passou de expiresAt sem envio. LOCKED: tentativas erradas demais — peça um link novo"},"attemptsRemaining":{"type":"integer","minimum":0},"expiresAt":{"type":"string","format":"date-time"},"completedAt":{"type":["string","null"],"format":"date-time"},"certificateId":{"type":["string","null"],"format":"uuid"},"createdAt":{"type":"string","format":"date-time"},"uploadUrl":{"type":"string","format":"uri","description":"Link de uso único para a pessoa abrir no navegador. Entregue sem alterar"},"company":{"type":"object","required":["id","legalName","taxId"],"properties":{"id":{"type":"string","format":"uuid"},"legalName":{"type":"string"},"taxId":{"type":"string"}}},"warning":{"type":"string"}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Empresa não encontrada","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"409":{"description":"Sem `companyId` e a organização não tem empresa padrão","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"422":{"description":"`FISCAL_CONFIGURATION_REQUIRED`: para uso em emissão, configure antes o ambiente (`PATCH /v1/organization/fiscal-settings`) — o vínculo exige configuração fiscal ativa","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"503":{"description":"Certificate Vault ou console não configurados","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"x-ai-tool":true,"description":"**Caminho recomendado para assistentes de IA e para quem não tem o arquivo em mãos.** Em vez de receber o .pfx e a senha e repassá-los a `POST /v1/certificates` — o que deixa a chave privada da empresa no histórico da conversa —, peça um link e entregue `uploadUrl` à pessoa. Ela abre no navegador, confere a empresa e o ambiente, escolhe o arquivo e digita a senha; a plataforma guarda no cofre e vincula à empresa/ambiente pedidos aqui, com as mesmas validações de `POST /v1/certificates` e `PUT /v1/companies/{id}/certificate/{environment}`. O link vale uma única vez, expira em 30 minutos e trava depois de 5 envios errados. Acompanhe por `GET /v1/certificate-upload-sessions/{id}` ou `GET /v1/organization/pending`. O escopo `certificates:request-upload` só permite pedir o link — por isso um assistente de IA conectado por OAuth pode recebê-lo, e `certificates:write` não.","requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":false,"required":["environment"],"properties":{"companyId":{"type":"string","format":"uuid","description":"Empresa que vai usar o certificado. Ausente = empresa padrão"},"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"intendedUse":{"type":"string","enum":["ISSUANCE_AND_RECEPTION","RECEPTION_ONLY"],"default":"ISSUANCE_AND_RECEPTION"}}}}}},"tags":["Certificates"],"operationId":"createCertificateUploadSession"}},"/v1/certificate-upload-sessions/{id}":{"get":{"summary":"Consultar um pedido de envio de certificado","security":[{"bearerAuth":[]}],"x-required-scope":"certificates:request-upload","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","required":["id","companyId","environment","intendedUse","status","attemptsRemaining","expiresAt","completedAt","certificateId","createdAt"],"properties":{"id":{"type":"string","format":"uuid"},"companyId":{"type":"string","format":"uuid"},"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"intendedUse":{"type":"string","enum":["ISSUANCE_AND_RECEPTION","RECEPTION_ONLY"]},"status":{"type":"string","enum":["PENDING","COMPLETED","EXPIRED","LOCKED"],"description":"PENDING: aguardando o envio. COMPLETED: certificado guardado e vinculado. EXPIRED: passou de expiresAt sem envio. LOCKED: tentativas erradas demais — peça um link novo"},"attemptsRemaining":{"type":"integer","minimum":0},"expiresAt":{"type":"string","format":"date-time"},"completedAt":{"type":["string","null"],"format":"date-time"},"certificateId":{"type":["string","null"],"format":"uuid"},"createdAt":{"type":"string","format":"date-time"}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Pedido não encontrado","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"x-ai-tool":true,"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"tags":["Certificates"],"operationId":"getCertificateUploadSession"}},"/v1/certificate-upload-sessions/lookup":{"post":{"summary":"Ler um link de envio de certificado","description":"Pública, autenticada só pelo token do link. É o que a página do console chama para mostrar à pessoa de qual empresa e ambiente é o pedido antes do envio. POST, e não GET, para o token não parar em log de acesso.","tags":["Certificates"],"security":[],"responses":{"200":{"description":"Link válido","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","required":["companyLegalName","companyTaxId","environment","intendedUse","expiresAt","attemptsRemaining"],"properties":{"companyLegalName":{"type":"string"},"companyTaxId":{"type":"string"},"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"intendedUse":{"type":"string","enum":["ISSUANCE_AND_RECEPTION","RECEPTION_ONLY"]},"expiresAt":{"type":"string","format":"date-time"},"attemptsRemaining":{"type":"integer","minimum":0}}},"errors":{"type":"array","maxItems":0}}}}}},"410":{"description":"Link inexistente, usado, vencido ou travado","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"429":{"description":"Muitas tentativas","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}},"headers":{"Retry-After":{"description":"Segundos até a próxima tentativa.","schema":{"type":"integer"}}}}},"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":false,"required":["token"],"properties":{"token":{"type":"string","pattern":"^tinvcu_[A-Za-z0-9_-]{43}$","description":"O que vem depois de `#t=` no uploadUrl"}}}}}},"operationId":"lookupCertificateUploadSession"}},"/v1/certificate-upload-sessions/complete":{"post":{"summary":"Enviar o certificado por um link","description":"Pública, autenticada só pelo token do link. Guarda o certificado no cofre e o vincula à empresa e ao ambiente do pedido. Erro de senha, arquivo, validade ou CNPJ responde o mesmo código de `POST /v1/certificates` / `PUT /v1/companies/{id}/certificate/{environment}` e consome uma tentativa.","tags":["Certificates"],"security":[],"responses":{"200":{"description":"Certificado guardado e vinculado","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","required":["status","environment"],"properties":{"status":{"const":"COMPLETED"},"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]}}},"errors":{"type":"array","maxItems":0}}}}}},"410":{"description":"Link inexistente, usado, vencido ou travado","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"422":{"description":"Certificado, senha ou CNPJ inválidos, ou o ambiente deixou de ter configuração fiscal","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"429":{"description":"Muitas tentativas","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}},"headers":{"Retry-After":{"description":"Segundos até a próxima tentativa.","schema":{"type":"integer"}}}},"503":{"description":"Certificate Vault não configurado","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":false,"required":["token","pfxBase64","passphrase"],"properties":{"token":{"type":"string","pattern":"^tinvcu_[A-Za-z0-9_-]{43}$","description":"O que vem depois de `#t=` no uploadUrl"},"pfxBase64":{"type":"string","format":"byte","description":"PKCS#12 (.pfx/.p12) file, base64-encoded, up to 1 MiB decoded"},"passphrase":{"type":"string","minLength":1,"maxLength":1024}}}}}},"operationId":"completeCertificateUploadSession"}},"/v1/companies":{"get":{"summary":"Listar empresas da organização","security":[{"bearerAuth":[]}],"x-required-scope":"organization:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"items":{"type":"array","items":{"$ref":"#/components/schemas/CompanyMetadata"}}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"tags":["Companies"],"operationId":"listCompanies"},"post":{"summary":"Cadastrar uma empresa","security":[{"bearerAuth":[]}],"x-required-scope":"organization:manage","responses":{"201":{"description":"Empresa criada","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/CompanyMetadata"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"409":{"description":"CNPJ já pertence a uma empresa na plataforma","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"422":{"description":"Dados inválidos","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateCompanyRequest"},"examples":{"exemplo":{"summary":"Matriz","value":{"label":"Matriz","taxId":"12345678000195","legalName":"Trilha Exemplo Serviços de Tecnologia Ltda","tradeName":"Trilha Exemplo","stateRegistrationExempt":true,"municipalityCode":"3550308","postalCode":"01310100","street":"Avenida Paulista","addressNumber":"1000","neighborhood":"Bela Vista"}}}}}},"tags":["Companies"],"operationId":"createCompany"}},"/v1/companies/{id}":{"get":{"summary":"Consultar uma empresa","security":[{"bearerAuth":[]}],"x-required-scope":"organization:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/CompanyMetadata"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Empresa não encontrada","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"tags":["Companies"],"operationId":"getCompany"},"patch":{"summary":"Atualizar uma empresa","security":[{"bearerAuth":[]}],"x-required-scope":"organization:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/CompanyMetadata"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Empresa não encontrada","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"409":{"description":"CNPJ já em uso, ou tentativa de desativar a empresa padrão","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"422":{"description":"Dados inválidos, ou tax_id imutável (empresa já emitiu documento fiscal)","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateCompanyRequest"}}}},"tags":["Companies"],"operationId":"updateCompany"}},"/v1/companies/{id}/default":{"patch":{"summary":"Eleger a empresa padrão","security":[{"bearerAuth":[]}],"x-required-scope":"organization:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/CompanyMetadata"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Empresa não encontrada","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"409":{"description":"Empresa inativa não pode ser eleita padrão","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"description":"companyId ausente em qualquer endpoint fiscal resolve para a empresa padrão — transacional: zera as outras.","parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"tags":["Companies"],"operationId":"setDefaultCompany"}},"/v1/companies/{id}/production-setup":{"post":{"summary":"Levar para produção a configuração já testada em homologação","security":[{"bearerAuth":[]}],"x-required-scope":"organization:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"companyId":{"type":"string","format":"uuid"},"fiscalConfiguration":{"type":"string","enum":["COPIED","ALREADY_CONFIGURED"]},"certificate":{"type":"string","enum":["LINKED","ALREADY_LINKED","NOT_AVAILABLE"]},"numbering":{"type":"string","enum":["CONFIGURED","PENDING"]},"readiness":{"type":"object","description":"O mesmo de GET /v1/organization/pending?environment=PRODUCTION, já depois da cópia"}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"422":{"description":"`HOMOLOGATION_CONFIGURATION_MISSING` ou dados inválidos","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"description":"Copia para PRODUCTION a configuração fiscal de HOMOLOGATION e vincula o mesmo certificado (já está no cofre: não se reenvia arquivo nem senha). Não sobrescreve o que já existe em produção. A numeração não é copiada — a sequência de produção no Sistema Nacional é outra: informe `series` (1 a 49999) e `nextNumber`, ou configure depois em PUT /v1/organization/dps-numbering. A resposta traz o checklist de produção (plano, saldo, liberação). Uma chave restrita a homologação — como a do onboarding por chat — é recusada.","parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"requestBody":{"required":false,"content":{"application/json":{"schema":{"type":"object","additionalProperties":false,"properties":{"series":{"type":"string","pattern":"^\\d{1,5}$","description":"Série de produção (1 a 49999)"},"nextNumber":{"type":"integer","minimum":1,"description":"Próximo número da série em produção; série nova = 1"}}}}}},"tags":["Companies"],"operationId":"setupCompanyProduction"}},"/v1/companies/{id}/certificate/{environment}":{"put":{"summary":"Vincular um certificado a uma empresa/ambiente","security":[{"bearerAuth":[]}],"x-required-scope":"organization:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/CompanyMetadata"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Empresa ou certificado não encontrado","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"422":{"description":"Documento do certificado não bate com o CNPJ da empresa, ou falta configuração fiscal do ambiente","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}},{"name":"environment","in":"path","required":true,"schema":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LinkCertificateRequest"}}}},"tags":["Companies"],"operationId":"linkCompanyCertificate"},"delete":{"summary":"Desvincular o certificado de uma empresa/ambiente","security":[{"bearerAuth":[]}],"x-required-scope":"organization:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/CompanyMetadata"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Nenhum vínculo ativo para esta empresa/ambiente","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}},{"name":"environment","in":"path","required":true,"schema":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]}}],"tags":["Companies"],"operationId":"unlinkCompanyCertificate"}},"/v1/nfse/municipalities/{ibgeCode}":{"get":{"operationId":"getMunicipalityNfseAvailability","summary":"Consultar disponibilidade de emissão de NFS-e por código IBGE","tags":["Municipalities"],"security":[],"parameters":[{"name":"ibgeCode","in":"path","required":true,"schema":{"type":"string","pattern":"^\\d{7}$"}}],"responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"ibgeCode":{"type":"string","pattern":"^\\d{7}$"},"municipality":{"type":"string"},"state":{"type":"string","minLength":2,"maxLength":2},"nationalIntegrated":{"type":["boolean","null"],"description":"Se o município está integrado à infraestrutura nacional NFS-e."},"emissionAvailable":{"type":"boolean","description":"Se a disponibilidade foi CONFIRMADA. `false` com `status` `UNKNOWN` ou `CHECK_ERROR` quer dizer \"não verificado\" (a consulta ao Sistema Nacional ainda não rodou ou falhou), não \"indisponível\" — para saber se a emissão é recusada, use `emissionBlocked`."},"emissionBlocked":{"type":"boolean","description":"Se POST /v1/nfse/issue recusa a emissão para este município (`MUNICIPALITY_NOT_SUPPORTED`). Só é `true` diante de uma negativa confirmada; falha da consulta não bloqueia, e o próprio Sistema Nacional valida o resto."},"status":{"type":"string","enum":["UNKNOWN","AVAILABLE","UNAVAILABLE","TEMPORARILY_UNAVAILABLE","CHECK_ERROR"],"description":"`AVAILABLE`/`UNAVAILABLE`: confirmado. `TEMPORARILY_UNAVAILABLE`: bloqueia. `UNKNOWN`/`CHECK_ERROR`: não verificado, não bloqueia."},"lastCheckedAt":{"type":["string","null"],"format":"date-time"}}},"errors":{"type":"array","maxItems":0}}}}}},"404":{"description":"Município fora do catálogo IBGE","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"429":{"description":"Limite de requisições excedido","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}},"headers":{"Retry-After":{"description":"Segundos até a próxima tentativa.","schema":{"type":"integer"}}}}}}},"/v1/nfse/availability":{"get":{"operationId":"getMunicipalityNfseAvailabilitySimplified","summary":"Consultar apenas se a emissão está disponível para um código IBGE","tags":["Municipalities"],"security":[],"parameters":[{"name":"ibgeCode","in":"query","required":true,"description":"Código IBGE de 7 dígitos do município de prestação do serviço (locationCode em POST /v1/nfse/issue). Achar o código a partir do nome do município é GET /v1/nfse/municipalities?q=.","schema":{"type":"string","pattern":"^\\d{7}$"},"example":"3550308"}],"responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"available":{"type":"boolean","description":"Disponibilidade CONFIRMADA. `false` com `status` `UNKNOWN`/`CHECK_ERROR` é \"não verificado\", não \"indisponível\"."},"emissionBlocked":{"type":"boolean","description":"Se a emissão é recusada para este município. É o campo para decidir se dá para emitir."},"status":{"type":"string","enum":["UNKNOWN","AVAILABLE","UNAVAILABLE","TEMPORARILY_UNAVAILABLE","CHECK_ERROR"]}}},"errors":{"type":"array","maxItems":0}}}}}},"404":{"description":"Município fora do catálogo IBGE","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"429":{"description":"Limite de requisições excedido","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}},"headers":{"Retry-After":{"description":"Segundos até a próxima tentativa.","schema":{"type":"integer"}}}}}}},"/v1/nfse/municipalities":{"get":{"operationId":"searchOrListMunicipalities","summary":"Buscar município por nome/UF, ou listar o catálogo paginado quando `name` não é informado","description":"Dois modos mutuamente exclusivos na mesma rota GET, escolhidos pela presença de `name` — combina os operationIds `searchMunicipalities` (com `name`) e `listMunicipalities` (sem `name`) da RFC, já que ambos leem a mesma tabela e o Fastify não separa por presença de query param. **Modo busca exata** (`name`, com `state` opcional para desambiguar): devolve um objeto único, ou 404 `MUNICIPALITY_NOT_FOUND` sem casamento, ou 409 com mais de um. **Modo listagem** (sem `name`; `q`, `state`, `available`, `limit`, `offset`): sempre devolve uma página, com casamento parcial e case-insensitive em `q`. Os dois grupos de parâmetro não se combinam — `name` junto de `q`/`limit`/`offset` devolve 422 `VALIDATION_ERROR` (`unrecognized_keys`), porque cada modo valida contra um schema `.strict()` próprio que não conhece os parâmetros do outro.","tags":["Municipalities"],"x-ai-tool":true,"security":[],"parameters":[{"name":"name","in":"query","required":false,"description":"Nome exato (ou prefixo suficiente para casar um único município) para o modo busca — sozinho ou com `state`. Incompatível com `q`/`limit`/`offset`. Para autocompletar por texto parcial, use `q` no modo listagem, não este parâmetro.","schema":{"type":"string","minLength":1,"maxLength":200}},{"name":"q","in":"query","required":false,"description":"Casamento parcial e case-insensitive no nome do município, só no modo listagem (sem `name`). É o que alimenta um autocompletar: comece com 2-3 letras e refine por `state` se a lista vier grande.","schema":{"type":"string","minLength":1,"maxLength":200},"example":"curi"},{"name":"state","in":"query","required":false,"description":"Sigla da UF (2 letras). Nos dois modos: desambigua `name` e filtra a listagem de `q`.","schema":{"type":"string","minLength":2,"maxLength":2},"example":"PR"},{"name":"available","in":"query","required":false,"description":"Só no modo listagem: filtra por emissionAvailable. Omitido, lista os dois valores.","schema":{"type":"string","enum":["true","false"]}},{"name":"limit","in":"query","required":false,"description":"Só no modo listagem — tamanho da página.","schema":{"type":"integer","minimum":1,"maximum":100,"default":50}},{"name":"offset","in":"query","required":false,"description":"Só no modo listagem — deslocamento da página.","schema":{"type":"integer","minimum":0,"default":0}}],"responses":{"200":{"description":"Sucesso — objeto único quando `name` é informado, lista paginada caso contrário","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"oneOf":[{"type":"object","properties":{"ibgeCode":{"type":"string","pattern":"^\\d{7}$"},"municipality":{"type":"string"},"state":{"type":"string","minLength":2,"maxLength":2},"nationalIntegrated":{"type":["boolean","null"],"description":"Se o município está integrado à infraestrutura nacional NFS-e."},"emissionAvailable":{"type":"boolean","description":"Se a disponibilidade foi CONFIRMADA. `false` com `status` `UNKNOWN` ou `CHECK_ERROR` quer dizer \"não verificado\" (a consulta ao Sistema Nacional ainda não rodou ou falhou), não \"indisponível\" — para saber se a emissão é recusada, use `emissionBlocked`."},"emissionBlocked":{"type":"boolean","description":"Se POST /v1/nfse/issue recusa a emissão para este município (`MUNICIPALITY_NOT_SUPPORTED`). Só é `true` diante de uma negativa confirmada; falha da consulta não bloqueia, e o próprio Sistema Nacional valida o resto."},"status":{"type":"string","enum":["UNKNOWN","AVAILABLE","UNAVAILABLE","TEMPORARILY_UNAVAILABLE","CHECK_ERROR"],"description":"`AVAILABLE`/`UNAVAILABLE`: confirmado. `TEMPORARILY_UNAVAILABLE`: bloqueia. `UNKNOWN`/`CHECK_ERROR`: não verificado, não bloqueia."},"lastCheckedAt":{"type":["string","null"],"format":"date-time"}},"title":"Município único (modo busca, name)","required":["ibgeCode","municipality","state"]},{"type":"object","title":"Página de municípios (modo listagem, sem name)","required":["items","limit","offset","hasMore","total"],"properties":{"items":{"type":"array","items":{"type":"object","properties":{"ibgeCode":{"type":"string","pattern":"^\\d{7}$"},"municipality":{"type":"string"},"state":{"type":"string","minLength":2,"maxLength":2},"nationalIntegrated":{"type":["boolean","null"],"description":"Se o município está integrado à infraestrutura nacional NFS-e."},"emissionAvailable":{"type":"boolean","description":"Se a disponibilidade foi CONFIRMADA. `false` com `status` `UNKNOWN` ou `CHECK_ERROR` quer dizer \"não verificado\" (a consulta ao Sistema Nacional ainda não rodou ou falhou), não \"indisponível\" — para saber se a emissão é recusada, use `emissionBlocked`."},"emissionBlocked":{"type":"boolean","description":"Se POST /v1/nfse/issue recusa a emissão para este município (`MUNICIPALITY_NOT_SUPPORTED`). Só é `true` diante de uma negativa confirmada; falha da consulta não bloqueia, e o próprio Sistema Nacional valida o resto."},"status":{"type":"string","enum":["UNKNOWN","AVAILABLE","UNAVAILABLE","TEMPORARILY_UNAVAILABLE","CHECK_ERROR"],"description":"`AVAILABLE`/`UNAVAILABLE`: confirmado. `TEMPORARILY_UNAVAILABLE`: bloqueia. `UNKNOWN`/`CHECK_ERROR`: não verificado, não bloqueia."},"lastCheckedAt":{"type":["string","null"],"format":"date-time"}}}},"limit":{"type":"integer"},"offset":{"type":"integer"},"hasMore":{"type":"boolean"},"total":{"type":"integer","description":"Total de municípios que casam com o filtro aplicado (antes de limit/offset)."}}}]},"errors":{"type":"array","maxItems":0}}}}}},"404":{"description":"Modo busca (`name`): nenhum município casou","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"409":{"description":"Modo busca (`name`): nome ambíguo entre mais de um município — refine com `state`","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"422":{"description":"Parâmetros do modo errado combinados (ex. `name` com `q`), ou fora dos limites de cada campo","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"429":{"description":"Limite de requisições excedido","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}},"headers":{"Retry-After":{"description":"Segundos até a próxima tentativa.","schema":{"type":"integer"}}}}}}},"/v1/registry/cnpj/{taxId}":{"get":{"operationId":"lookupCompanyByTaxId","summary":"Consultar dados cadastrais de um CNPJ na base pública da Receita Federal","description":"Pré-preenchimento de formulário, não fonte fiscal: o dado vem de um espelho público e gratuito do cadastro da Receita Federal, pode estar desatualizado e todo campo devolvido continua editável por quem preenche. Respostas são cacheadas e o provedor externo tem teto de chamadas — daí o 503, que significa \"tente mais tarde ou preencha à mão\".","tags":["Registry"],"security":[],"parameters":[{"name":"taxId","in":"path","required":true,"schema":{"type":"string","pattern":"^\\d{14}$"}}],"responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"taxId":{"type":"string","pattern":"^\\d{14}$"},"legalName":{"type":["string","null"]},"tradeName":{"type":["string","null"]},"postalCode":{"type":["string","null"],"pattern":"^\\d{8}$"},"street":{"type":["string","null"]},"number":{"type":["string","null"]},"complement":{"type":["string","null"]},"neighborhood":{"type":["string","null"]},"ibgeCode":{"type":["string","null"],"pattern":"^\\d{7}$"},"phone":{"type":["string","null"]}}},"errors":{"type":"array","maxItems":0}}}}}},"404":{"description":"CNPJ ausente da base pública consultada","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"422":{"description":"CNPJ malformado ou com dígitos verificadores inválidos","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"429":{"description":"Limite de requisições excedido","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}},"headers":{"Retry-After":{"description":"Segundos até a próxima tentativa.","schema":{"type":"integer"}}}},"503":{"description":"Provedor externo indisponível ou teto de chamadas atingido","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}}}},"/v1/registry/cep/{postalCode}":{"get":{"operationId":"lookupAddressByPostalCode","summary":"Consultar logradouro, bairro e código IBGE de um CEP","description":"Mesmas regras de cache, rate limit e indisponibilidade de /v1/registry/cnpj/{taxId}.","tags":["Registry"],"security":[],"parameters":[{"name":"postalCode","in":"path","required":true,"schema":{"type":"string","pattern":"^\\d{8}$"}}],"responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"postalCode":{"type":"string","pattern":"^\\d{8}$"},"street":{"type":["string","null"]},"neighborhood":{"type":["string","null"]},"ibgeCode":{"type":["string","null"],"pattern":"^\\d{7}$"}}},"errors":{"type":"array","maxItems":0}}}}}},"404":{"description":"CEP inexistente","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"422":{"description":"CEP fora do formato de 8 dígitos","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"429":{"description":"Limite de requisições excedido","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}},"headers":{"Retry-After":{"description":"Segundos até a próxima tentativa.","schema":{"type":"integer"}}}},"503":{"description":"Provedor externo indisponível ou teto de chamadas atingido","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}}}},"/v1/nfse/national-tax-codes":{"get":{"summary":"Buscar código de tributação nacional por código ou descrição","description":"Catálogo oficial do Anexo B do Comitê Gestor da NFS-e (335 códigos) — usado pela busca no cadastro do catálogo de serviços (POST /v1/service-catalog). Consulta pública, sem autenticação, sujeita a rate limit.","tags":["Service Catalog"],"security":[],"parameters":[{"name":"q","in":"query","required":true,"description":"Casamento parcial no código de 6 dígitos ou na descrição oficial — mínimo 2 caracteres.","schema":{"type":"string","minLength":2,"maxLength":200},"example":"consultoria"}],"responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"items":{"type":"array","items":{"type":"object","properties":{"code":{"type":"string"},"description":{"type":"string"}}}}}},"errors":{"type":"array","maxItems":0}}}}}},"429":{"description":"Limite de requisições excedido","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}},"headers":{"Retry-After":{"description":"Segundos até a próxima tentativa.","schema":{"type":"integer"}}}}},"operationId":"searchNationalTaxCodes"}},"/v1/nfse/nbs-codes":{"get":{"summary":"Buscar código NBS por código ou descrição","description":"Catálogo oficial NBS 2.0 do Anexo B do Comitê Gestor da NFS-e (917 códigos-folha) — mesmo uso e formato de /v1/nfse/national-tax-codes.","tags":["Service Catalog"],"security":[],"parameters":[{"name":"q","in":"query","required":true,"description":"Casamento parcial no código de 9 dígitos ou na descrição oficial — mínimo 2 caracteres.","schema":{"type":"string","minLength":2,"maxLength":200},"example":"consultoria"}],"responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"items":{"type":"array","items":{"type":"object","properties":{"code":{"type":"string"},"description":{"type":"string"}}}}}},"errors":{"type":"array","maxItems":0}}}}}},"429":{"description":"Limite de requisições excedido","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}},"headers":{"Retry-After":{"description":"Segundos até a próxima tentativa.","schema":{"type":"integer"}}}}},"operationId":"searchNbsCodes"}},"/v1/nfse":{"get":{"summary":"Listar emissões de NFS-e","security":[{"bearerAuth":[]}],"x-required-scope":"nfse:read","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"items":{"type":"array","items":{"$ref":"#/components/schemas/NfseOperationSummary"}},"limit":{"type":"integer"},"offset":{"type":"integer"},"hasMore":{"type":"boolean"}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"parameters":[{"name":"status","in":"query","required":false,"schema":{"type":"string","enum":["RECEIVED","VALIDATING","READY","QUEUED","RUNNING","WAITING_PROVIDER","COMPLETED","FAILED","MANUAL_REVIEW"]}},{"name":"environment","in":"query","required":false,"schema":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","minimum":1,"maximum":100,"default":50}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0}}],"tags":["NFS-e"],"operationId":"listNfse"}},"/v1/nfse/validate":{"post":{"summary":"Validar dados para emissão","security":[{"bearerAuth":[]}],"x-required-scope":"nfse:validate","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"valid":{"const":true},"normalized":{"type":"object","description":"O payload já com os padrões da configuração fiscal aplicados — é este que POST /v1/nfse/issue vai usar."}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"422":{"description":"Organização não está pronta para emitir neste ambiente (ver GET /v1/organization/pending), ou o município informado está confirmadamente indisponível para emissão","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"x-ai-tool":true,"description":"Se a tributação/retenção do ISSQN, a alíquota ou os demais parâmetros fiscais não estiverem claros, não é obrigatório, mas ajuda: peça ao usuário uma NFS-e emitida anteriormente para o mesmo serviço (XML ou PDF). Esses valores costumam se repetir entre emissões, então extraí-los de um documento anterior simplifica o preenchimento e reduz erro de configuração. Este endpoint roda as mesmas checagens de prontidão e disponibilidade de município que POST /v1/nfse/issue e devolve o payload já normalizado com os padrões da configuração fiscal aplicados — sem custo e sem criar operação.","requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/NfseIssueRequest"},"examples":{"completo":{"summary":"Emissão com todos os dados do serviço","value":{"externalReference":"pedido-10482","environment":"HOMOLOGATION","customer":{"document":"11222333000181","name":"Cliente Exemplo Ltda","address":{"municipalityCode":"5208707","postalCode":"74000000","street":"Avenida Goiás","number":"100","neighborhood":"Setor Central"}},"service":{"locationCode":"5208707","nationalTaxCode":"010101","description":"Desenvolvimento de sistema sob encomenda — agosto/2026","amount":"1500.00"},"municipalTax":{"taxation":"1","withholding":"1","rate":"5.00"},"competenceDate":"2026-08-31"}},"catalogo":{"summary":"Emissão usando uma entrada do catálogo de serviços","value":{"environment":"HOMOLOGATION","serviceCode":"consultoria","customer":{"document":"52998224725","name":"Maria Exemplo"},"service":{"amount":"800.00"}}}}}}},"tags":["NFS-e"],"operationId":"validateNfse"}},"/v1/nfse/issue":{"post":{"summary":"Solicitar emissão de NFS-e","security":[{"bearerAuth":[]}],"x-required-scope":"nfse:issue","responses":{"202":{"description":"Aceito para processamento assíncrono","headers":{"Location":{"description":"Rota de status para acompanhar o desfecho (GET) — presente só no ramo aceito, ausente quando a resposta é o ramo \"retida para aprovação\" (não há operação para consultar ainda).","schema":{"type":"string","format":"uri-reference"}}},"content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/NfseIssueAccepted"},"errors":{"type":"array","maxItems":0}}}}}},"400":{"description":"Idempotency-Key ausente","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"402":{"description":"Saldo insuficiente","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"409":{"description":"Conflito de idempotência","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"422":{"description":"Dados inválidos","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"x-ai-tool":true,"description":"Se a tributação/retenção do ISSQN, a alíquota ou os demais parâmetros fiscais não estiverem claros, não é obrigatório, mas ajuda: peça ao usuário uma NFS-e emitida anteriormente para o mesmo serviço (XML ou PDF). Esses valores costumam se repetir entre emissões, então extraí-los de um documento anterior simplifica o preenchimento e reduz erro de configuração. Acompanhe o desfecho por GET /v1/nfse/{id} (o id vem em data.operationId, e a própria resposta já traz o location dessa rota). A maioria das emissões conclui em poucos segundos: comece consultando a cada 2-3 segundos e alongue o intervalo se demorar. COMPLETED e FAILED são finais. WAITING_PROVIDER não é: o resultado do envio ficou incerto e uma rotina em segundo plano confirma sozinha com o provedor nacional, em geral em 1 a 2 minutos — continue acompanhando a cada 15-30 segundos (data.reconciliation diz se ainda está em andamento) e não reenvie a nota. Ver a descrição de operationalStatus em NfseOperationDetail para o que cada um significa. Em PRODUCTION, a chave ou o assistente precisa ter produção liberada por uma pessoa no console (e-mail confirmado + senha); antes disso a resposta é 403 `CREDENTIAL_POLICY_VIOLATION` com `ruleCode: ENVIRONMENT_NOT_ALLOWED`. Numeração: PUT /v1/organization/dps-numbering.","parameters":[{"name":"Idempotency-Key","in":"header","required":true,"description":"Única por emissão, por exemplo o id do pedido. Repetida em até 24 horas com o mesmo corpo devolve a operação original; com outro corpo, 409. Depois de 24 horas, cria uma emissão nova.","schema":{"type":"string","minLength":1,"maxLength":255},"example":"pedido-10482"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/NfseIssueRequest"},"examples":{"completo":{"summary":"Emissão com todos os dados do serviço","value":{"externalReference":"pedido-10482","environment":"HOMOLOGATION","customer":{"document":"11222333000181","name":"Cliente Exemplo Ltda","address":{"municipalityCode":"5208707","postalCode":"74000000","street":"Avenida Goiás","number":"100","neighborhood":"Setor Central"}},"service":{"locationCode":"5208707","nationalTaxCode":"010101","description":"Desenvolvimento de sistema sob encomenda — agosto/2026","amount":"1500.00"},"municipalTax":{"taxation":"1","withholding":"1","rate":"5.00"},"competenceDate":"2026-08-31"}},"catalogo":{"summary":"Emissão usando uma entrada do catálogo de serviços","value":{"environment":"HOMOLOGATION","serviceCode":"consultoria","customer":{"document":"52998224725","name":"Maria Exemplo"},"service":{"amount":"800.00"}}}}}}},"tags":["NFS-e"],"operationId":"issueNfse"}},"/v1/nfse/{id}":{"get":{"summary":"Consultar operação de emissão","security":[{"bearerAuth":[]}],"x-required-scope":"nfse:read","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/NfseOperationDetail"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Operação não encontrada","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"x-ai-tool":true,"description":"Para agentes de IA: assim que esta operação mostrar operationalStatus COMPLETED e fiscalStatus AUTHORIZED, não basta informar que a emissão teve sucesso — busque o documento fiscal correspondente (GET /v1/fiscal-documents, filtrando por este operationId) e, imediatamente, disponibilize ao usuário tanto o PDF (DANFSe) quanto o XML autorizado, via GET /v1/fiscal-documents/{id}/pdf e GET /v1/fiscal-documents/{id}/xml. Faça isso de forma proativa, sem esperar o usuário pedir. As URLs de download expiram em 5 minutos — gere-as na hora de entregar os arquivos, não com antecedência — e apontam para o armazenamento de arquivos, não para o host da API: entregue o link para a pessoa abrir no navegador dela. Se o seu ambiente bloquear o download, é esse endereço que precisa ser liberado; se o link vencer, peça outro. Quando fiscalStatus é REJECTED, data.rejections traz o(s) motivo(s) exatamente como devolvidos pelo webservice oficial (code/description/complement), acrescido de um `hint` opcional com orientação de correção para os códigos que a API já conhece — nunca uma tradução inventada para um código desconhecido. Quando operationalStatus é WAITING_PROVIDER, data.reconciliation explica que não é uma rejeição confirmada — o resultado do envio oficial ficou ambíguo e uma rotina em background já tenta confirmar de novo automaticamente; normalmente resolve sozinho em um a dois minutos, sem precisar reenviar. Para conferir o que foi de fato enviado ao provedor nacional — inclusive numa rejeição — use GET /v1/nfse/{id}/dps-xml.","parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"tags":["NFS-e"],"operationId":"getNfse"}},"/v1/nfse/{id}/dps-xml":{"get":{"summary":"Gerar URL temporária do XML da DPS enviada","security":[{"bearerAuth":[]}],"x-required-scope":"fiscal-document:download","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/FiscalFileDownload"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Operação não encontrada","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"409":{"description":"A DPS ainda não foi preparada para esta tentativa (DPS_NOT_PREPARED)","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"description":"URL de download de curta duração para o XML da DPS assinada exatamente como foi enviado ao provedor nacional. Disponível assim que a operação chega a READY e independe do desfecho — numa rejeição (fiscalStatus REJECTED) é o artefato para conferir campo a campo o que a administração recusou. Sem o parâmetro attempt devolve a tentativa corrente (issuanceAttempt); um inteiro >= 1 seleciona a DPS de um retry anterior. Distinto de GET /v1/fiscal-documents/{id}/xml, que só existe após a autorização e traz a NFS-e resultante.","parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}},{"name":"attempt","in":"query","required":false,"schema":{"type":"integer","minimum":1}}],"tags":["NFS-e"],"operationId":"getNfseDpsXmlUrl"}},"/v1/nfse/{id}/cancel":{"post":{"summary":"Solicitar cancelamento de NFS-e","security":[{"bearerAuth":[]}],"x-required-scope":"nfse:cancel","responses":{"202":{"description":"Aceito para processamento assíncrono","headers":{"Location":{"description":"Rota de status para acompanhar o desfecho (GET) — presente só no ramo aceito, ausente quando a resposta é o ramo \"retida para aprovação\" (não há operação para consultar ainda).","schema":{"type":"string","format":"uri-reference"}}},"content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/NfseCancelAccepted"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"409":{"description":"NFS-e não pode ser cancelada ou conflito de cancelamento","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"422":{"description":"Dados inválidos","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"x-ai-tool":true,"description":"Assíncrono: a resposta 202 traz em data.operationId o id do CANCELAMENTO (não da nota) e, no header `location`, a rota para acompanhá-lo: GET /v1/nfse/{id}/cancel/{cancellationId}. Não use esse id em GET /v1/nfse/{id}, que é só de emissões. Consulte a cada 2-3 segundos até `fiscalStatus` CANCELLED ou REJECTED. Depois de cancelada, a própria nota (GET /v1/nfse/{id} com o id da emissão) passa a mostrar o documento como CANCELLED.","parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/NfseCancelRequest"},"examples":{"erro":{"summary":"Erro na emissão","value":{"reasonCode":"1","reason":"Erro na descrição do serviço prestado"}}}}}},"tags":["NFS-e"],"operationId":"cancelNfse"}},"/v1/nfse/{id}/cancel/{cancellationId}":{"get":{"summary":"Acompanhar um cancelamento de NFS-e","security":[{"bearerAuth":[]}],"x-required-scope":"nfse:read","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"operationId":{"type":"string","format":"uuid","description":"Id do cancelamento"},"issuanceOperationId":{"type":"string","format":"uuid","description":"Id da emissão cancelada"},"operationalStatus":{"type":"string","enum":["RECEIVED","RUNNING","WAITING_PROVIDER","COMPLETED","FAILED","MANUAL_REVIEW"]},"fiscalStatus":{"type":["string","null"],"enum":["CANCEL_PENDING","CANCELLED","REJECTED","UNKNOWN",null]},"reasonCode":{"type":["string","null"],"enum":["1","2","9",null]},"failureCode":{"type":["string","null"]},"rejections":{"type":["array","null"],"items":{"type":"object"}},"createdAt":{"type":"string","format":"date-time"},"updatedAt":{"type":"string","format":"date-time"}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Cancelamento não encontrado para esta NFS-e","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"x-ai-tool":true,"description":"Situação do cancelamento pedido em POST /v1/nfse/{id}/cancel (é o `location` daquela resposta). `fiscalStatus` CANCELLED = cancelamento registrado; REJECTED = recusado (ver `rejections`); CANCEL_PENDING = em andamento — acompanhe a cada 2-3 segundos; em WAITING_PROVIDER a confirmação é automática, não reenvie.","parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}},{"name":"cancellationId","in":"path","required":true,"schema":{"type":"string","format":"uuid"},"description":"`operationId` devolvido por POST /v1/nfse/{id}/cancel"}],"tags":["NFS-e"],"operationId":"getNfseCancellation"}},"/v1/nfse/{id}/retry":{"post":{"summary":"Retomar uma emissão rejeitada com os dados corrigidos","security":[{"bearerAuth":[]}],"x-required-scope":"nfse:issue","responses":{"202":{"description":"Aceito para processamento assíncrono","headers":{"Location":{"description":"Rota de status para acompanhar o desfecho (GET) — presente só no ramo aceito, ausente quando a resposta é o ramo \"retida para aprovação\" (não há operação para consultar ainda).","schema":{"type":"string","format":"uri-reference"}}},"content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"operationId":{"type":"string","format":"uuid"},"operationalStatus":{"const":"RECEIVED"},"fiscalStatus":{"const":"NOT_SUBMITTED"},"issuanceAttempt":{"type":"integer","minimum":2}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"402":{"description":"Saldo insuficiente para re-reservar o consumo","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Operação não encontrada","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"409":{"description":"A operação não está em FAILED (NFSE_NOT_RETRYABLE)","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"422":{"description":"Dados inválidos, ambiente divergente, ou tentativa de trocar série/número já alocados (DPS_RETRY_CANNOT_CHANGE_NUMBER / DPS_RETRY_CANNOT_CHANGE_SERIES)","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"description":"Reprocessa a MESMA operação de emissão com o payload corrigido, preservando a série e o número de DPS já alocados — ao contrário de uma emissão nova, que alocaria outro número e deixaria o anterior vago. Só operações em operationalStatus FAILED (rejeição confirmada ou falha de validação da DPS) são retentáveis; WAITING_PROVIDER se reconcilia sozinho. Não exige Idempotency-Key: a pré-condição FAILED já barra o reenvio duplo.","parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/NfseIssueRequest"}}}},"tags":["NFS-e"],"operationId":"retryNfse"}},"/v1/wallet":{"get":{"summary":"Consultar carteira","security":[{"bearerAuth":[]}],"x-required-scope":"billing:read","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/WalletSnapshot"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"tags":["Billing"],"operationId":"getWallet"}},"/v1/usage":{"get":{"summary":"Consultar histórico de consumo","security":[{"bearerAuth":[]}],"x-required-scope":"billing:read","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"items":{"type":"array","items":{"$ref":"#/components/schemas/UsageRecord"}},"limit":{"type":"integer"},"offset":{"type":"integer"},"hasMore":{"type":"boolean"}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","minimum":1,"maximum":100,"default":50}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0}}],"tags":["Billing"],"operationId":"listUsage"}},"/v1/usage/summary":{"get":{"summary":"Consultar consumo do ciclo, excedente e alertas","security":[{"bearerAuth":[]}],"x-required-scope":"billing:read","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/UsageSummary"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"tags":["Billing"],"operationId":"getUsageSummary"}},"/v1/usage/alerts":{"get":{"summary":"Listar percentuais de alerta de franquia","security":[{"bearerAuth":[]}],"x-required-scope":"billing:read","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"items":{"type":"array","items":{"$ref":"#/components/schemas/UsageAlertSetting"}}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"tags":["Billing"],"operationId":"listUsageAlerts"},"put":{"summary":"Configurar percentuais de alerta de franquia","security":[{"bearerAuth":[]}],"x-required-scope":"organization:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/UsageAlertSetting"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UsageAlertSettingRequest"}}}},"tags":["Billing"],"operationId":"updateUsageAlerts"}},"/v1/usage/{id}/refund":{"post":{"summary":"Estornar um uso já capturado","security":[{"bearerAuth":[]}],"x-required-scope":"billing:adjust","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"status":{"type":"string"}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"409":{"description":"Uso não está no estado CAPTURED","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UsageRefundRequest"}}}},"tags":["Billing"],"operationId":"refundUsage"}},"/v1/plans":{"get":{"summary":"Listar planos comerciais disponíveis","security":[{"bearerAuth":[]}],"x-required-scope":"billing:read","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"items":{"type":"array","items":{"$ref":"#/components/schemas/CommercialPlan"}}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"tags":["Billing"],"operationId":"listPlans"}},"/v1/subscription":{"get":{"summary":"Consultar a assinatura atual","security":[{"bearerAuth":[]}],"x-required-scope":"billing:read","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/SubscriptionSummary"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"tags":["Billing"],"operationId":"getSubscription"},"post":{"summary":"Trocar de plano","security":[{"bearerAuth":[]}],"x-required-scope":"organization:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/SubscriptionSummary"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ChangePlanRequest"}}}},"tags":["Billing"],"operationId":"changePlan"},"delete":{"summary":"Agendar o encerramento da assinatura para o fim do ciclo pago corrente","security":[{"bearerAuth":[]}],"x-required-scope":"organization:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/SubscriptionCancellation"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"tags":["Billing"],"operationId":"scheduleSubscriptionCancellation"}},"/v1/subscription/resume":{"post":{"summary":"Desfazer o encerramento agendado, enquanto o ciclo ainda corre","security":[{"bearerAuth":[]}],"x-required-scope":"organization:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/SubscriptionSummary"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"tags":["Billing"],"operationId":"resumeSubscription"}},"/v1/subscription/charges":{"get":{"summary":"Listar mensalidades cobradas","security":[{"bearerAuth":[]}],"x-required-scope":"billing:read","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"items":{"type":"array","items":{"$ref":"#/components/schemas/SubscriptionCharge"}},"limit":{"type":"integer"},"offset":{"type":"integer"},"hasMore":{"type":"boolean"}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","minimum":1,"maximum":100,"default":50}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0}}],"tags":["Billing"],"operationId":"listSubscriptionCharges"}},"/v1/subscription/charges/{id}/payment-link":{"post":{"summary":"Reemitir o link de pagamento de uma mensalidade — idempotente, e um no-op sem o gateway de pagamento configurado (404)","security":[{"bearerAuth":[]}],"x-required-scope":"billing:recharge","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/SubscriptionCharge"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"tags":["Billing"],"operationId":"reissueChargePaymentLink"}},"/v1/subscription/checkout":{"post":{"summary":"Garantir a cobrança do mês corrente e devolver o link de pagamento Asaas — para assinar um plano pago e já ir direto para o checkout, sem esperar a virada do ciclo. Idempotente (reaproveita a cobrança do mês se já existir); `data` vem null sem mensalidade a cobrar neste mês (plano FREE); 404 sem o gateway de pagamento configurado","security":[{"bearerAuth":[]}],"x-required-scope":"organization:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"oneOf":[{"$ref":"#/components/schemas/SubscriptionCharge"},{"type":"null"}],"description":"null quando o plano atual não tem mensalidade (FREE) — nada a cobrar neste mês."},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"tags":["Billing"],"operationId":"checkoutSubscription"}},"/v1/wallet/auto-recharge":{"get":{"summary":"Consultar a política de recarga automática","security":[{"bearerAuth":[]}],"x-required-scope":"billing:read","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/AutoRechargePolicy"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"tags":["Billing"],"operationId":"getAutoRechargePolicy"}},"/v1/wallet/auto-recharge/card":{"put":{"summary":"Cadastrar/substituir o cartão de recarga automática — 404 sem o gateway de pagamento configurado","security":[{"bearerAuth":[]}],"x-required-scope":"billing:recharge","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/AutoRechargePolicy"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SaveAutoRechargeCardRequest"}}}},"tags":["Billing"],"operationId":"saveAutoRechargeCard"},"delete":{"summary":"Remover o cartão de recarga automática","security":[{"bearerAuth":[]}],"x-required-scope":"billing:recharge","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/AutoRechargePolicy"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"tags":["Billing"],"operationId":"removeAutoRechargeCard"}},"/v1/wallet/auto-recharge/policy":{"patch":{"summary":"Configurar limiar, valor e teto mensal da recarga automática","security":[{"bearerAuth":[]}],"x-required-scope":"billing:recharge","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/AutoRechargePolicy"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateAutoRechargePolicyRequest"}}}},"tags":["Billing"],"operationId":"updateAutoRechargePolicy"}},"/v1/wallet/topup-requests":{"get":{"summary":"Listar pedidos de recarga","security":[{"bearerAuth":[]}],"x-required-scope":"billing:read","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"items":{"type":"array","items":{"$ref":"#/components/schemas/WalletTopUpRequest"}},"limit":{"type":"integer"},"offset":{"type":"integer"},"hasMore":{"type":"boolean"}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","minimum":1,"maximum":100,"default":50}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0}}],"tags":["Billing"],"operationId":"listTopUpRequests"},"post":{"summary":"Solicitar recarga de carteira — devolve um Pix real quando o gateway de pagamento está configurado, senão instruções estáticas","security":[{"bearerAuth":[]}],"x-required-scope":"billing:recharge","responses":{"201":{"description":"Pedido criado como PENDING","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/WalletTopUpRequest"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateTopUpRequestBody"}}}},"tags":["Billing"],"operationId":"createTopUpRequest"}},"/v1/wallet/topup-requests/{id}/cancel":{"post":{"summary":"Cancelar pedido de recarga não concluído","security":[{"bearerAuth":[]}],"x-required-scope":"billing:recharge","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"status":{"const":"CANCELED"},"outcome":{"type":"string","enum":["CANCELED","ALREADY_CANCELED"]}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"409":{"description":"Pedido não encontrado ou já confirmado — recarga já concluída não pode ser cancelada","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"description":"Fecha um pedido ainda PENDING, com ou sem cobrança Pix já gerada na Asaas — o cliente desistindo de pagar. Idempotente: chamar de novo sobre um pedido já CANCELED devolve `outcome: \"ALREADY_CANCELED\"` em vez de erro. Pedidos PENDING também são cancelados automaticamente depois de 48h sem confirmação.","parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"tags":["Billing"],"operationId":"cancelTopUpRequest"}},"/v1/approvals/{id}":{"get":{"summary":"Consultar uma prévia de aprovação própria","security":[{"bearerAuth":[]}],"x-required-scope":"nfse:read","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/ApprovalRequest"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Não encontrada, ou pertence a outra credencial","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"description":"RFC-022 §7.6 — sem `approvals:manage`: devolve a prévia só quando a credencial que chama é a mesma que a criou (a de um grant que abriu `PENDING_APPROVAL` em POST /v1/nfse/issue ou /cancel). É o que um assistente usa para saber se a aprovação humana já andou.","tags":["Approvals"],"operationId":"getApproval"}},"/v1/approvals":{"get":{"summary":"Listar pedidos de aprovação","security":[{"bearerAuth":[]}],"x-required-scope":"approvals:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"items":{"type":"array","items":{"$ref":"#/components/schemas/ApprovalRequest"}},"limit":{"type":"integer"},"offset":{"type":"integer"},"hasMore":{"type":"boolean"}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"parameters":[{"name":"status","in":"query","required":false,"schema":{"type":"string","enum":["PENDING","APPROVED","REJECTED","EXPIRED"]}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","minimum":1,"maximum":100,"default":50}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0}}],"tags":["Approvals"],"operationId":"listApprovals"}},"/v1/approvals/{id}/decision":{"post":{"summary":"Aprovar ou rejeitar uma operação pendente","security":[{"bearerAuth":[]}],"x-required-scope":"approvals:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/ApprovalRequest"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Pedido de aprovação não encontrado","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"409":{"description":"Pedido já decidido ou expirado","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"422":{"description":"Dados inválidos","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApprovalDecisionRequest"}}}},"tags":["Approvals"],"operationId":"decideApproval"}},"/v1/fiscal-files/{id}/download":{"get":{"summary":"Gerar URL temporária de download","security":[{"bearerAuth":[]}],"x-required-scope":"fiscal-document:download","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/FiscalFileDownload"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Arquivo não encontrado","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"tags":["Files"],"operationId":"getFiscalFileDownloadUrl"}},"/v1/fiscal-documents":{"get":{"summary":"Listar documentos fiscais","security":[{"bearerAuth":[]}],"x-required-scope":"fiscal-document:read","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/FiscalDocumentPage"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"description":"Cada item traz, além da identidade do documento, um resumo copiado do XML autorizado (issuerName/issuerDocument, customerName/customerDocument, serviceDescription, serviceAmount, netAmount, documentNumber, competenceDate) — use-o para responder de quem é a nota e por quanto sem baixar e parsear o XML. Os campos do resumo são nulos quando o layout do documento não foi reconhecido; nesse caso o XML em GET /v1/fiscal-documents/{id}/xml continua sendo a fonte completa. A resposta traz `total` e `totalServiceAmount` do recorte inteiro, não da página — para responder \"quantas e quanto\" sem percorrer a paginação.","parameters":[{"name":"environment","in":"query","required":false,"schema":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]}},{"name":"origin","in":"query","required":false,"schema":{"type":"string","enum":["ISSUED","RECEIVED"]}},{"name":"operationId","in":"query","required":false,"schema":{"type":"string","format":"uuid"},"description":"Filtra pelo id da operação de emissão (GET /v1/nfse/{id}) — o caminho direto do id da operação até o documento correspondente."},{"name":"organizationRole","in":"query","required":false,"schema":{"type":"string","enum":["PROVIDER","CUSTOMER","OTHER"]},"description":"Papel da organização dentro do documento. CUSTOMER lista as notas emitidas contra o CNPJ dela — é este o filtro para isso, e não origin=RECEIVED, que diz apenas que o documento chegou pelo monitoramento do ADN (o mesmo feed traz notas em que o CNPJ figura como emitente, tomador ou intermediário)."},{"name":"issuedFrom","in":"query","required":false,"schema":{"type":"string","format":"date-time"},"description":"Instante ISO 8601, inclusivo. O recorte por dia depende do fuso de quem pergunta, então envie o instante já resolvido em vez de uma data civil."},{"name":"issuedTo","in":"query","required":false,"schema":{"type":"string","format":"date-time"},"description":"Instante ISO 8601, inclusivo."},{"name":"q","in":"query","required":false,"schema":{"type":"string","minLength":2,"maxLength":200},"description":"Busca por nome do emitente ou do tomador, CNPJ/CPF (com ou sem máscara), número da nota ou chave de acesso."},{"name":"partyDocument","in":"query","required":false,"schema":{"type":"string"},"description":"CNPJ/CPF da contraparte, com ou sem máscara. Casa com emitente ou tomador — de que lado a organização está já é dito por organizationRole."},{"name":"state","in":"query","required":false,"schema":{"type":"string","minLength":2,"maxLength":2},"description":"UF do emitente. Nas notas recebidas, o estado da contraparte."},{"name":"municipalityCode","in":"query","required":false,"schema":{"type":"string","pattern":"^\\d{7}$"},"description":"Código IBGE do município do emitente."},{"name":"amountMin","in":"query","required":false,"schema":{"type":"string","example":"100.00"},"description":"Valor mínimo do serviço (vServ), string decimal como no resto da API."},{"name":"amountMax","in":"query","required":false,"schema":{"type":"string","example":"5000.00"},"description":"Valor máximo do serviço."},{"name":"competenceFrom","in":"query","required":false,"schema":{"type":"string","format":"date"},"description":"Competência inicial (dCompet), data civil YYYY-MM-DD — aqui não há instante nem fuso, ao contrário de issuedFrom."},{"name":"competenceTo","in":"query","required":false,"schema":{"type":"string","format":"date"},"description":"Competência final, YYYY-MM-DD."},{"name":"fiscalStatus","in":"query","required":false,"schema":{"type":"string","example":"AUTHORIZED"},"description":"Situação fiscal do documento, como AUTHORIZED, CANCELLED ou CANCEL_PENDING."},{"name":"documentType","in":"query","required":false,"schema":{"type":"string","enum":["NFSE","NFE","CTE"]},"description":"NFS-e (serviço), NF-e (mercadoria) ou CT-e (transporte). Sem filtro, os três."},{"name":"contentLevel","in":"query","required":false,"schema":{"type":"string","enum":["SUMMARY","FULL"]},"description":"SUMMARY lista o que chegou apenas como cabeçalho — é assim que se acha o que ainda espera manifestação do destinatário."},{"name":"manifestationState","in":"query","required":false,"schema":{"type":"string","enum":["NOT_APPLICABLE","PENDING","ACKNOWLEDGED","CONFIRMED","DENIED","NOT_PERFORMED","DISPUTED"]},"description":"PENDING lista as NF-e que ainda não foram manifestadas e estão dentro do prazo."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","minimum":1,"maximum":100,"default":50}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0}}],"tags":["Files"],"operationId":"listFiscalDocuments"}},"/v1/fiscal-documents/{id}":{"get":{"summary":"Obter documento fiscal","security":[{"bearerAuth":[]}],"x-required-scope":"fiscal-document:read","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/FiscalDocument"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Documento não encontrado","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"description":"Mesmo resumo devolvido pelos itens de GET /v1/fiscal-documents, para um documento só — existir como rota própria é o que permite um link recarregável para a tela de detalhe, em vez de reencontrar o item numa página da listagem.","parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"tags":["Files"],"operationId":"getFiscalDocument"}},"/v1/fiscal-documents/{id}/events":{"get":{"summary":"Listar eventos fiscais do documento","security":[{"bearerAuth":[]}],"x-required-scope":"fiscal-document:read","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/FiscalDocumentEventList"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Documento não encontrado","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"description":"Eventos oficiais sobre este documento. NF-e/CT-e, da SEFAZ: cancelamento (110111), carta de correção (110110), manifestação do destinatário (2102xx), desacordo do tomador de CT-e (610110). NFS-e, do ADN: cancelamento (101101), substituição (105102), confirmação e rejeição. São eventos fiscais com protocolo e sequência oficiais, distintos do log interno da plataforma.","parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"tags":["Files"],"operationId":"listFiscalDocumentEvents"}},"/v1/fiscal-documents/{id}/manifestation":{"post":{"summary":"Manifestar-se sobre uma NF-e recebida","security":[{"bearerAuth":[]}],"x-required-scope":"fiscal-document:manifest","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/ManifestationResult"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Documento não encontrado","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"409":{"description":"Manifestação não se aplica a este documento (não é NF-e, a organização não é a destinatária, ou já houve manifestação definitiva)","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"422":{"description":"A SEFAZ rejeitou o evento; o motivo vem em errors[].detail","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"503":{"description":"Recepção de NF-e/CT-e desabilitada nesta instalação","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"description":"Registra a manifestação do destinatário na SEFAZ, em nome da organização. É ato fiscal de escrita, com efeito legal — daí o escopo próprio. CIENCIA declara conhecimento e é o que libera o XML completo de uma NF-e recebida só como cabeçalho; ela não impede uma manifestação definitiva depois. CONFIRMACAO, DESCONHECIMENTO e OPERACAO_NAO_REALIZADA são terminais e nunca são registradas automaticamente pela plataforma, em nenhum modo de configuração. OPERACAO_NAO_REALIZADA exige justification de 15 a 255 caracteres. Depois de uma CIENCIA aceita, o XML completo chega pela distribuição normal, sob um NSU novo — acompanhe pelo webhook fiscal_document.content_upgraded.","parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["type"],"properties":{"type":{"type":"string","enum":["CIENCIA","CONFIRMACAO","DESCONHECIMENTO","OPERACAO_NAO_REALIZADA"]},"justification":{"type":"string","minLength":15,"maxLength":255,"description":"Obrigatória e exclusiva de OPERACAO_NAO_REALIZADA."}}}}}},"tags":["Files"],"operationId":"manifestFiscalDocument"}},"/v1/fiscal-documents/{id}/dispute":{"post":{"summary":"Registrar desacordo em um CT-e recebido","security":[{"bearerAuth":[]}],"x-required-scope":"fiscal-document:manifest","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/CteDisputeResult"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Documento não encontrado","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"409":{"description":"Desacordo não se aplica (não é CT-e, a organização não é a tomadora, o CT-e não está autorizado, chegou só como cabeçalho ou já foi contestado)","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"422":{"description":"A SEFAZ rejeitou o evento; cStat e motivo vêm em errors[].detail","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"503":{"description":"Recepção de NF-e/CT-e desabilitada nesta instalação","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"description":"Registra a prestação do serviço em desacordo (evento 610110) na SEFAZ autorizadora do CT-e, assinada com o certificado da empresa que recebeu o documento. Só o tomador do serviço pode registrar, e a plataforma confere isso no XML antes de enviar. É declaração de fato e nunca é feita automaticamente. Aceito o evento, o documento passa a manifestation.state = DISPUTED e sai o webhook fiscal_document.manifestation_registered com type PRESTACAO_EM_DESACORDO e source PLATFORM.","parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["observation"],"properties":{"observation":{"type":"string","minLength":15,"maxLength":255,"description":"O que não foi prestado como contratado. Vai à SEFAZ como xObs."}}}}}},"tags":["Files"],"operationId":"disputeFiscalDocument"}},"/v1/inbound-manifestation-settings":{"get":{"summary":"Consultar o modo de manifestação","security":[{"bearerAuth":[]}],"x-required-scope":"fiscal-document:read","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/ManifestationSettingsList"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"description":"Devolve sempre os dois ambientes: ausência de configuração é o padrão MANUAL, não ausência de resposta.","tags":["Files"],"operationId":"getManifestationSettings"},"put":{"summary":"Definir o modo de manifestação","security":[{"bearerAuth":[]}],"x-required-scope":"organization:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/ManifestationSettings"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"description":"AUTO_CIENCIA faz a plataforma registrar a ciência da operação sozinha, em nome da organização, para toda NF-e recebida contra o CNPJ dela. Só a ciência: as manifestações definitivas continuam exigindo chamada explícita. autoDelaySeconds é a janela antes disso acontecer — serve para o comprador olhar o cabeçalho e decidir por desconhecimento antes de a plataforma dar ciência por ele.","requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["environment","mode"],"properties":{"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"mode":{"type":"string","enum":["MANUAL","AUTO_CIENCIA"]},"autoDelaySeconds":{"type":"integer","minimum":0,"maximum":604800,"default":0}}}}}},"tags":["Files"],"operationId":"updateManifestationSettings"}},"/v1/fiscal-documents/{id}/pdf":{"get":{"summary":"Gerar URL temporária do PDF (DANFSe)","security":[{"bearerAuth":[]}],"x-required-scope":"fiscal-document:download","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/FiscalFileDownload"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Documento ou PDF não encontrado","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"description":"Devolve uma URL assinada que expira em 5 minutos — peça-a na hora de baixar ou entregar o arquivo, não com antecedência. O id é o do documento fiscal (`documentId` do webhook nfse.issued, ou GET /v1/fiscal-documents?operationId=), não o da operação de emissão. A DANFSe existe também para os documentos recebidos do ADN (origin RECEIVED), gerada na recepção a partir do XML. O 404 aqui significa que este documento não tem PDF — o XML em /xml continua disponível.","parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"tags":["Files"],"operationId":"getFiscalDocumentPdfUrl"}},"/v1/fiscal-documents/{id}/xml":{"get":{"summary":"Gerar URL temporária do XML autorizado","security":[{"bearerAuth":[]}],"x-required-scope":"fiscal-document:download","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/FiscalFileDownload"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Documento ou XML não encontrado","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"description":"Devolve uma URL assinada que expira em 5 minutos — peça-a na hora de baixar ou entregar o arquivo, não com antecedência. O id é o do documento fiscal (`documentId` do webhook nfse.issued, ou GET /v1/fiscal-documents?operationId=), não o da operação de emissão.","parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"tags":["Files"],"operationId":"getFiscalDocumentXmlUrl"}},"/v1/fiscal-documents/batch-download":{"post":{"summary":"Baixar PDF e XML de vários documentos de uma vez","security":[{"bearerAuth":[]}],"x-required-scope":"fiscal-document:download","responses":{"200":{"description":"Em delivery LINKS, o envelope com uma URL assinada por arquivo. Em delivery ZIP, o arquivo compactado: o corpo é o próprio ZIP.","headers":{"x-batch-skipped":{"description":"Só em delivery ZIP. JSON com a contagem, por motivo, dos documentos que ficaram de fora — contagem e não lista de ids, para caber num cabeçalho. Ex.: {\"total\":2,\"byReason\":{\"CONTENT_SUMMARY_ONLY\":2}}","schema":{"$ref":"#/components/schemas/FiscalBatchDownloadSkipSummary"}},"x-batch-file-count":{"description":"Só em delivery ZIP. Quantos arquivos o ZIP carrega.","schema":{"type":"integer"}}},"content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/FiscalBatchDownloadLinks"},"errors":{"type":"array","maxItems":0}}}},"application/zip":{"schema":{"type":"string","format":"binary"}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"409":{"description":"Nenhum arquivo disponível no lote inteiro; errors[0].details.skipped diz o porquê de cada documento","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"413":{"description":"O ZIP passaria de 100 MiB; divida a seleção","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"422":{"description":"delivery LINKS com mais de 10 documentos","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"description":"Um pedido para muitos documentos, em vez de uma chamada por arquivo a GET /v1/fiscal-documents/{id}/pdf|xml. Documentos que ainda são só cabeçalho (contentLevel SUMMARY), ou cujo arquivo não existe, não derrubam o lote: saem em `skipped`, com o motivo, e o restante é entregue. Os nomes dos arquivos trazem tipo, número e chave de acesso — é por eles que a nota é reencontrada fora da plataforma.","requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/FiscalBatchDownloadRequest"}}}},"tags":["Files"],"operationId":"batchDownloadFiscalDocuments"}},"/v1/fiscal-documents/download-log":{"get":{"summary":"Listar o log de baixas de documento","security":[{"bearerAuth":[]}],"x-required-scope":"fiscal-document:read","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/FiscalFileDownloadLogPage"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"description":"Quem baixou PDF ou XML de qual documento e quando — uma linha por arquivo entregue por GET /v1/fiscal-documents/{id}/pdf|xml ou por POST /v1/fiscal-documents/batch-download (batch: true). O ator vem como USER (console, com nome e e-mail), API_CREDENTIAL (nome da credencial) ou OAUTH_CLIENT (nome do app conectado); nulo só se a credencial, o usuário ou o app tiverem sido removidos depois da baixa. Ordenado do mais recente para o mais antigo.","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","minimum":1,"maximum":100,"default":20}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0}}],"tags":["Files"],"operationId":"listFiscalDocumentDownloadLog"}},"/v1/inbound-monitor":{"put":{"summary":"Ligar ou desligar a recepção de NF-e/CT-e","security":[{"bearerAuth":[]}],"x-required-scope":"organization:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/InboundReceptionSettings"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"409":{"description":"Falta certificado ativo no ambiente, ou a organização não tem município cadastrado (o serviço de distribuição exige cUFAutor)","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"description":"Só NF-e e CT-e: o cursor de NFS-e é criado ao salvar as configurações fiscais. startingPoint só tem efeito na criação do cursor, mas é obrigatório sempre que enabled é true — não há valor padrão silencioso, porque o padrão errado aqui é dinheiro: FROM_ZERO sozinho já significou faturar de uma vez todo o histórico que a SEFAZ ainda mantinha do CNPJ. Opções: FROM_NOW (sem histórico), LAST_7_DAYS/LAST_30_DAYS/LAST_90_DAYS (corte exato por data de emissão, aplicado pelo poller sem custo) e FROM_ZERO (todo o histórico ainda disponível, cada documento faturável — confirme o volume e o custo antes). Religar também zera o contador de falhas e reabre o circuit breaker.","requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["environment","documentType","enabled"],"properties":{"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"documentType":{"type":"string","enum":["NFE","CTE"]},"enabled":{"type":"boolean"},"companyId":{"type":"string","format":"uuid","description":"Ausente resolve para a empresa padrão. NSU é sequência por CNPJ consultante no SEFAZ — cada empresa cadastrada tem o próprio cursor."},"startingPoint":{"type":"string","enum":["FROM_NOW","LAST_7_DAYS","LAST_30_DAYS","LAST_90_DAYS","FROM_ZERO"],"description":"Obrigatório quando enabled é true. Ignorado ao desligar, e ignorado religando um cursor que já existe."}}}}}},"tags":["Files"],"operationId":"updateInboundMonitor"},"get":{"summary":"Consultar o monitoramento de documentos recebidos","security":[{"bearerAuth":[]}],"x-required-scope":"fiscal-document:read","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"items":{"type":"array","items":{"$ref":"#/components/schemas/InboundMonitorStatus"}}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"description":"Estado do cursor de NSU por empresa e ambiente. Falhas consecutivas do ADN afastam a próxima consulta exponencialmente e, sustentadas, pausam o cursor (status PAUSED, pausedByFailures true) — enquanto isso nenhum documento novo chega, então verifique isto antes de concluir que a organização não recebeu notas no período. Sem companyId, lista os cursores de TODAS as empresas da organização (companyLabel preenchido); com companyId, só os dela.","parameters":[{"name":"companyId","in":"query","required":false,"schema":{"type":"string","format":"uuid"}}],"tags":["Files"],"operationId":"getInboundMonitor"}},"/v1/inbound-monitor/{environment}/resume":{"post":{"summary":"Retomar o monitoramento pausado","security":[{"bearerAuth":[]}],"x-required-scope":"organization:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/InboundMonitorStatus"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Não há cursor de monitoramento para o ambiente/empresa, ou companyId não existe","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"parameters":[{"name":"environment","in":"path","required":true,"schema":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]}},{"name":"companyId","in":"query","required":false,"schema":{"type":"string","format":"uuid"},"description":"Ausente resolve para a empresa padrão."},{"name":"documentType","in":"query","required":false,"schema":{"type":"string","enum":["NFSE","NFE","CTE"],"default":"NFSE"}}],"tags":["Files"],"operationId":"resumeInboundMonitor"}},"/v1/inbound-monitor/{environment}/pause":{"post":{"summary":"Pausar o monitoramento","security":[{"bearerAuth":[]}],"x-required-scope":"organization:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/InboundMonitorStatus"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Não há cursor de monitoramento para o ambiente/empresa, ou companyId não existe","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"description":"Para as consultas mantendo a posição (lastNsu). É o passo antes de alterar o NSU de partida.","parameters":[{"name":"environment","in":"path","required":true,"schema":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]}},{"name":"companyId","in":"query","required":false,"schema":{"type":"string","format":"uuid"},"description":"Ausente resolve para a empresa padrão."},{"name":"documentType","in":"query","required":false,"schema":{"type":"string","enum":["NFSE","NFE","CTE"],"default":"NFSE"}}],"tags":["Files"],"operationId":"pauseInboundMonitor"}},"/v1/inbound-monitor/{environment}/nsu":{"put":{"summary":"Definir o NSU de partida (migração de outro sistema)","security":[{"bearerAuth":[]}],"x-required-scope":"organization:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"$ref":"#/components/schemas/InboundMonitorStatus"},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Não há cursor de monitoramento para o ambiente/empresa, ou companyId não existe","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"409":{"description":"INBOUND_MONITOR_NOT_PAUSED: pause antes (e espere a consulta em andamento terminar). INBOUND_MONITOR_NSU_SKIP_NOT_ACKNOWLEDGED: o NSU avança e pularia documentos; reenvie com acknowledgeSkippedDocuments true.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"description":"lastNsu é o último NSU que o sistema anterior já leu; a próxima consulta traz os documentos depois dele. Voltar o NSU é seguro (documento já recebido não é gravado nem cobrado de novo). Avançar pula documentos sem aviso posterior e exige acknowledgeSkippedDocuments. Só com o monitoramento pausado; retome depois.","parameters":[{"name":"environment","in":"path","required":true,"schema":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]}},{"name":"companyId","in":"query","required":false,"schema":{"type":"string","format":"uuid"},"description":"Ausente resolve para a empresa padrão."},{"name":"documentType","in":"query","required":false,"schema":{"type":"string","enum":["NFSE","NFE","CTE"],"default":"NFSE"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":false,"required":["lastNsu"],"properties":{"lastNsu":{"type":"string","pattern":"^\\d{1,20}$"},"acknowledgeSkippedDocuments":{"type":"boolean"}}}}}},"tags":["Files"],"operationId":"setInboundMonitorNsu"}},"/v1/webhooks":{"get":{"summary":"Listar endpoints de webhook","security":[{"bearerAuth":[]}],"x-required-scope":"webhook:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"items":{"type":"array","items":{"$ref":"#/components/schemas/WebhookEndpoint"}}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"tags":["Webhooks"],"operationId":"listWebhooks"},"post":{"summary":"Cadastrar endpoint de webhook","security":[{"bearerAuth":[]}],"x-required-scope":"webhook:manage","responses":{"201":{"description":"Endpoint criado; segredo retornado uma única vez","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"secret":{"type":"string","description":"Mostrado uma única vez — não há endpoint que devolva este valor de novo."},"warning":{"type":"string"}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"422":{"description":"Dados inválidos","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateWebhookRequest"},"examples":{"erp":{"summary":"Eventos de emissão em homologação","value":{"name":"ERP — homologação","url":"https://erp.example.com/webhooks/trilha-invoice","events":["nfse.issued","nfse.rejected","nfse.cancelled"],"environment":"HOMOLOGATION"}}}}}},"tags":["Webhooks"],"operationId":"createWebhook"}},"/v1/webhooks/{id}/rotate-secret":{"post":{"summary":"Rotacionar segredo do webhook","security":[{"bearerAuth":[]}],"x-required-scope":"webhook:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"secret":{"type":"string","description":"Mostrado uma única vez — não há endpoint que devolva este valor de novo."},"warning":{"type":"string"}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Endpoint não encontrado","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"tags":["Webhooks"],"operationId":"rotateWebhookSecret"}},"/v1/webhooks/{id}/status":{"patch":{"summary":"Alterar status do webhook","security":[{"bearerAuth":[]}],"x-required-scope":"webhook:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"status":{"type":"string","enum":["ACTIVE","INACTIVE","REVOKED"]}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"Endpoint não encontrado","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":false,"required":["status"],"properties":{"status":{"type":"string","enum":["ACTIVE","INACTIVE","REVOKED"]}}}}}},"tags":["Webhooks"],"operationId":"updateWebhookStatus"}},"/v1/webhook-deliveries":{"get":{"summary":"Listar entregas recentes","security":[{"bearerAuth":[]}],"x-required-scope":"webhook:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"items":{"type":"array","items":{"$ref":"#/components/schemas/WebhookDelivery"}}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"tags":["Webhooks"],"operationId":"listWebhookDeliveries"}},"/v1/webhook-deliveries/{id}/attempts":{"get":{"summary":"Listar tentativas de uma entrega","security":[{"bearerAuth":[]}],"x-required-scope":"webhook:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"items":{"type":"array","items":{"$ref":"#/components/schemas/WebhookDeliveryAttempt"}}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"tags":["Webhooks"],"operationId":"listWebhookDeliveryAttempts"}},"/v1/notifications/whatsapp":{"get":{"summary":"Consultar o aviso de documentos por WhatsApp","security":[{"bearerAuth":[]}],"x-required-scope":"notifications:read","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"channelAvailable":{"type":"boolean","description":"false = envio de WhatsApp não configurado no servidor"},"recipient":{"oneOf":[{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"label":{"type":"string"},"phone":{"type":"string","description":"Sempre mascarado"},"status":{"type":"string","enum":["PENDING_VERIFICATION","ACTIVE","OPTED_OUT","DISABLED"]},"disabledReason":{"type":["string","null"]},"roles":{"type":"array","minItems":1,"items":{"type":"string","enum":["PROVIDER","CUSTOMER","OTHER"]},"description":"PROVIDER = emitido com o CNPJ da organização fora do Trilha Invoice (uso do certificado); CUSTOMER = recebido de fornecedor; OTHER = demais"},"documentTypes":{"type":"array","minItems":1,"items":{"type":"string","enum":["NFSE","NFE","CTE"]}},"companyIds":{"type":["array","null"],"minItems":1,"items":{"type":"string","format":"uuid"},"description":"null = todas as empresas"},"attachPdf":{"type":"boolean"},"verifiedAt":{"type":["string","null"],"format":"date-time"},"activatedAt":{"type":["string","null"],"format":"date-time"},"optedOutAt":{"type":["string","null"],"format":"date-time"}}},{"type":"null"}]},"pendingRecipient":{"type":["object","null"],"properties":{"id":{"type":"string","format":"uuid"},"label":{"type":"string"},"phone":{"type":"string"},"verificationExpiresAt":{"type":["string","null"],"format":"date-time"},"replacesCurrent":{"type":"boolean"}}},"lastDelivery":{"type":["object","null"],"properties":{"status":{"type":"string"},"trigger":{"type":"string"},"createdAt":{"type":"string","format":"date-time"},"failureCode":{"type":["string","null"]}}}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"x-ai-tool":true,"tags":["Notifications"],"operationId":"getWhatsappNotifications"},"patch":{"summary":"Ajustar filtros ou ativar/desativar o aviso","security":[{"bearerAuth":[]}],"x-required-scope":"notifications:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"label":{"type":"string"},"phone":{"type":"string","description":"Sempre mascarado"},"status":{"type":"string","enum":["PENDING_VERIFICATION","ACTIVE","OPTED_OUT","DISABLED"]},"disabledReason":{"type":["string","null"]},"roles":{"type":"array","minItems":1,"items":{"type":"string","enum":["PROVIDER","CUSTOMER","OTHER"]},"description":"PROVIDER = emitido com o CNPJ da organização fora do Trilha Invoice (uso do certificado); CUSTOMER = recebido de fornecedor; OTHER = demais"},"documentTypes":{"type":"array","minItems":1,"items":{"type":"string","enum":["NFSE","NFE","CTE"]}},"companyIds":{"type":["array","null"],"minItems":1,"items":{"type":"string","format":"uuid"},"description":"null = todas as empresas"},"attachPdf":{"type":"boolean"},"verifiedAt":{"type":["string","null"],"format":"date-time"},"activatedAt":{"type":["string","null"],"format":"date-time"},"optedOutAt":{"type":["string","null"],"format":"date-time"}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"`NO_ACTIVE_NUMBER`: nenhum número cadastrado","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"409":{"description":"`RECIPIENT_OPTED_OUT` (só o próprio número religa, respondendo VOLTAR NOTAS) ou `SECURITY_TOKEN_CHANGE_MISMATCH`","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"428":{"description":"`SECURITY_TOKEN_REQUIRED`: a mudança reduz o aviso; o código foi enviado ao número cadastrado","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"x-ai-tool":true,"description":"Desmarcar papel, tipo de documento ou empresa, ou desativar (`status: DISABLED`), reduz o monitoramento e exige `securityToken`. Ampliar, renomear e ligar/desligar o PDF passam direto.","requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":false,"properties":{"label":{"type":"string","maxLength":60},"roles":{"type":"array","minItems":1,"items":{"type":"string","enum":["PROVIDER","CUSTOMER","OTHER"]},"description":"PROVIDER = emitido com o CNPJ da organização fora do Trilha Invoice (uso do certificado); CUSTOMER = recebido de fornecedor; OTHER = demais"},"documentTypes":{"type":"array","minItems":1,"items":{"type":"string","enum":["NFSE","NFE","CTE"]}},"companyIds":{"type":["array","null"],"minItems":1,"items":{"type":"string","format":"uuid"},"description":"null = todas as empresas"},"attachPdf":{"type":"boolean"},"status":{"type":"string","enum":["ACTIVE","DISABLED"]},"securityToken":{"type":"object","additionalProperties":false,"required":["challengeId","code"],"properties":{"challengeId":{"type":"string","format":"uuid"},"code":{"type":"string","pattern":"^\\d{6}$"}},"description":"Token de segurança: `challengeId` da resposta 428 e o código que chegou ao WhatsApp cadastrado"}}}}}},"tags":["Notifications"],"operationId":"updateWhatsappNotifications"}},"/v1/notifications/whatsapp/number":{"put":{"summary":"Cadastrar ou trocar o WhatsApp que recebe os documentos","security":[{"bearerAuth":[]}],"x-required-scope":"notifications:manage","responses":{"202":{"description":"Código de verificação enviado ao número novo","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"recipientId":{"type":"string","format":"uuid"},"phone":{"type":"string","description":"Mascarado"},"verificationExpiresAt":{"type":"string","format":"date-time"},"next":{"type":"string"}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"`COMPANY_NOT_FOUND`: um dos `companyIds` não é desta organização","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"409":{"description":"`NUMBER_ALREADY_REGISTERED`","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"422":{"description":"`INVALID_PHONE_NUMBER` ou `WHATSAPP_NUMBER_UNREACHABLE`","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"428":{"description":"`SECURITY_TOKEN_REQUIRED`: trocar o número atual exige o código enviado a ele","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"429":{"description":"`VERIFICATION_RATE_LIMITED` ou `SECURITY_TOKEN_RATE_LIMITED`","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"503":{"description":"`WHATSAPP_CHANNEL_UNAVAILABLE` ou `WHATSAPP_SEND_FAILED`","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"x-ai-tool":true,"description":"O número só passa a receber depois de `POST /v1/notifications/whatsapp/number/verify` com o código que chegou nele. Na troca, o número atual continua recebendo até o novo ser verificado.","requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":false,"required":["phone"],"properties":{"phone":{"type":"string","example":"+55 62 99999-1234","description":"Sem código de país e com 10 ou 11 dígitos, assume Brasil"},"label":{"type":"string","maxLength":60,"default":"WhatsApp"},"roles":{"type":"array","minItems":1,"items":{"type":"string","enum":["PROVIDER","CUSTOMER","OTHER"]},"description":"PROVIDER = emitido com o CNPJ da organização fora do Trilha Invoice (uso do certificado); CUSTOMER = recebido de fornecedor; OTHER = demais"},"documentTypes":{"type":"array","minItems":1,"items":{"type":"string","enum":["NFSE","NFE","CTE"]}},"companyIds":{"type":["array","null"],"minItems":1,"items":{"type":"string","format":"uuid"},"description":"null = todas as empresas"},"attachPdf":{"type":"boolean"},"securityToken":{"type":"object","additionalProperties":false,"required":["challengeId","code"],"properties":{"challengeId":{"type":"string","format":"uuid"},"code":{"type":"string","pattern":"^\\d{6}$"}},"description":"Token de segurança: `challengeId` da resposta 428 e o código que chegou ao WhatsApp cadastrado"}}}}}},"tags":["Notifications"],"operationId":"registerWhatsappNumber"},"delete":{"summary":"Remover o WhatsApp que recebe os documentos","security":[{"bearerAuth":[]}],"x-required-scope":"notifications:manage","responses":{"204":{"description":"Removido"},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"`NO_ACTIVE_NUMBER`","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"428":{"description":"`SECURITY_TOKEN_REQUIRED`","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"description":"Sempre exige o token de segurança enquanto o número estiver recebendo.","requestBody":{"required":false,"content":{"application/json":{"schema":{"type":"object","additionalProperties":false,"properties":{"securityToken":{"type":"object","additionalProperties":false,"required":["challengeId","code"],"properties":{"challengeId":{"type":"string","format":"uuid"},"code":{"type":"string","pattern":"^\\d{6}$"}},"description":"Token de segurança: `challengeId` da resposta 428 e o código que chegou ao WhatsApp cadastrado"}}}}}},"tags":["Notifications"],"operationId":"removeWhatsappNumber"}},"/v1/notifications/whatsapp/number/verify":{"post":{"summary":"Confirmar o número com o código recebido","security":[{"bearerAuth":[]}],"x-required-scope":"notifications:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"label":{"type":"string"},"phone":{"type":"string","description":"Sempre mascarado"},"status":{"type":"string","enum":["PENDING_VERIFICATION","ACTIVE","OPTED_OUT","DISABLED"]},"disabledReason":{"type":["string","null"]},"roles":{"type":"array","minItems":1,"items":{"type":"string","enum":["PROVIDER","CUSTOMER","OTHER"]},"description":"PROVIDER = emitido com o CNPJ da organização fora do Trilha Invoice (uso do certificado); CUSTOMER = recebido de fornecedor; OTHER = demais"},"documentTypes":{"type":"array","minItems":1,"items":{"type":"string","enum":["NFSE","NFE","CTE"]}},"companyIds":{"type":["array","null"],"minItems":1,"items":{"type":"string","format":"uuid"},"description":"null = todas as empresas"},"attachPdf":{"type":"boolean"},"verifiedAt":{"type":["string","null"],"format":"date-time"},"activatedAt":{"type":["string","null"],"format":"date-time"},"optedOutAt":{"type":["string","null"],"format":"date-time"}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"`NO_PENDING_NUMBER`","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"x-ai-tool":true,"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":false,"required":["code"],"properties":{"code":{"type":"string","pattern":"^\\d{6}$"}}}}}},"tags":["Notifications"],"operationId":"verifyWhatsappNumber"}},"/v1/notifications/whatsapp/number/resend-code":{"post":{"summary":"Reenviar o código de verificação","security":[{"bearerAuth":[]}],"x-required-scope":"notifications:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"verificationExpiresAt":{"type":"string","format":"date-time"}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"`NO_PENDING_NUMBER`","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"429":{"description":"`VERIFICATION_RATE_LIMITED`","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"tags":["Notifications"],"operationId":"resendWhatsappVerificationCode"}},"/v1/notifications/whatsapp/test":{"post":{"summary":"Enviar uma mensagem de teste","security":[{"bearerAuth":[]}],"x-required-scope":"notifications:manage","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"deliveryId":{"type":"string","format":"uuid"}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"404":{"description":"`NO_ACTIVE_NUMBER`","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"429":{"description":"`TEST_MESSAGE_RATE_LIMITED`","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"x-ai-tool":true,"tags":["Notifications"],"operationId":"sendWhatsappTestMessage"}},"/v1/notifications/whatsapp/deliveries":{"get":{"summary":"Listar as últimas 50 entregas","security":[{"bearerAuth":[]}],"x-required-scope":"notifications:read","responses":{"200":{"description":"Sucesso","content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"items":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"trigger":{"type":"string","enum":["DOCUMENT_RECEIVED","TEST","DIGEST","VERIFICATION","SECURITY_TOKEN"]},"status":{"type":"string","enum":["QUEUED","SENT","DELIVERED","READ","FAILED","AGGREGATED","SKIPPED"]},"documentId":{"type":["string","null"],"format":"uuid"},"withPdf":{"type":["boolean","null"]},"failureCode":{"type":["string","null"]},"sentAt":{"type":["string","null"],"format":"date-time"},"createdAt":{"type":"string","format":"date-time"}}}}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"tags":["Notifications"],"operationId":"listWhatsappDeliveries"}},"/v1/webhook-deliveries/{id}/resend":{"post":{"summary":"Reenviar uma entrega manualmente","security":[{"bearerAuth":[]}],"x-required-scope":"webhook:manage","responses":{"202":{"description":"Aceito para processamento assíncrono","headers":{"Location":{"description":"Rota de status para acompanhar o desfecho (GET) — presente só no ramo aceito, ausente quando a resposta é o ramo \"retida para aprovação\" (não há operação para consultar ainda).","schema":{"type":"string","format":"uri-reference"}}},"content":{"application/json":{"schema":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"success"},"data":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"deliveryStatus":{"const":"PENDING"}}},"errors":{"type":"array","maxItems":0}}}}}},"401":{"description":"Credencial ausente ou inválida","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"403":{"description":"Escopo insuficiente ou recurso indisponível no plano","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}},"409":{"description":"Entrega não pode ser reenviada","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorEnvelope"}}}}},"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string","format":"uuid"}}],"tags":["Webhooks"],"operationId":"resendWebhookDelivery"}}},"components":{"securitySchemes":{"bearerAuth":{"type":"http","scheme":"bearer","bearerFormat":"API key","description":"API key gerada no console (Chaves de API) ou por POST /v1/api-credentials, começando com `tinv_`; ou access token de integração OAuth, começando com `tinvat_`. Envie como `Authorization: Bearer <valor>`."},"metricsToken":{"type":"http","scheme":"bearer","description":"Valor de METRICS_TOKEN"},"consoleSession":{"type":"apiKey","in":"cookie","name":"tinv_console_session","description":"Sessão de console de um usuário humano. Um access token de grant é recusado nestas rotas mesmo carregando o escopo — consentir e gerir integrações é ação de pessoa."}},"schemas":{"ErrorEnvelope":{"type":"object","required":["requestId","status","data","errors"],"properties":{"requestId":{"type":"string"},"status":{"const":"error"},"data":{"type":"null"},"errors":{"type":"array","minItems":1,"items":{"type":"object","required":["code"],"properties":{"code":{"type":"string","description":"Código estável do erro. Catálogo completo na introdução desta referência."},"detail":{"type":"string","description":"Explicação em texto, quando o código a tem."},"details":{"description":"Dados estruturados do erro; o formato varia por código."}}}}}},"NfseIssueRequest":{"type":"object","additionalProperties":false,"required":["environment","customer","service"],"description":"service.locationCode, municipalTax e competenceDate são opcionais: quando ausentes, são preenchidos a partir da configuração fiscal da organização para este ambiente (município do emitente, tributação/retenção padrão do ISSQN, data de hoje) — exigida por GET /v1/organization/pending antes de qualquer emissão. serviceCode referencia uma entrada de GET /v1/service-catalog e, quando presente, dispensa service.nationalTaxCode e service.description (preenchidos a partir do catálogo) e também serve de padrão para municipalTax, com prioridade sobre o padrão da organização mas menor que valores explícitos nesta requisição. Sem serviceCode, nationalTaxCode e description são obrigatórios. Valores explícitos sempre prevalecem sobre catálogo e configuração fiscal.","properties":{"externalReference":{"type":"string","minLength":1,"maxLength":128},"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"companyId":{"type":"string","format":"uuid","description":"Ausente resolve para a empresa padrão (RFC-018)."},"serviceCode":{"type":"string","pattern":"^[a-z0-9][a-z0-9-]{0,59}$","description":"Código de uma entrada ativa do catálogo de serviços (ver GET /v1/service-catalog)."},"series":{"type":"string","pattern":"^\\d{1,5}$","description":"Série de DPS. Opcional. Se omitida, usa a série default (GET /v1/organization/dps-series, isDefault). Só faz sentido informar para emitir contra uma série MANUAL específica."},"number":{"type":"string","pattern":"^\\d{1,15}$","description":"Número do DPS (nDPS). Obrigatório quando a série-alvo é MANUAL; enviar num série AUTO é erro 422 (DPS_NUMBER_NOT_ALLOWED_IN_AUTO). Número já usado na série devolve 409 (DPS_NUMBER_ALREADY_USED)."},"customer":{"type":"object","additionalProperties":false,"required":["document","name"],"properties":{"document":{"type":"string","pattern":"^(\\d{11}|\\d{14})$"},"name":{"type":"string","minLength":2,"maxLength":200},"address":{"type":"object","additionalProperties":false,"required":["municipalityCode","postalCode","street","number","neighborhood"],"properties":{"municipalityCode":{"type":"string","pattern":"^\\d{7}$"},"postalCode":{"type":"string","pattern":"^\\d{8}$"},"street":{"type":"string","minLength":1,"maxLength":255},"number":{"type":"string","minLength":1,"maxLength":60},"complement":{"type":"string","minLength":1,"maxLength":156},"neighborhood":{"type":"string","minLength":1,"maxLength":60}}}}},"service":{"type":"object","additionalProperties":false,"required":["amount"],"description":"nationalTaxCode e description são obrigatórios quando serviceCode não é informado.","properties":{"locationCode":{"type":"string","pattern":"^\\d{7}$","description":"Código IBGE do município da prestação"},"nationalTaxCode":{"type":"string","pattern":"^\\d{6}$","description":"Código de tributação nacional"},"municipalTaxCode":{"type":"string","minLength":1,"maxLength":20},"nbsCode":{"type":"string","pattern":"^\\d{9}$"},"description":{"type":"string","minLength":3,"maxLength":2000},"additionalInformation":{"type":"string","minLength":1,"maxLength":2000,"pattern":"^[!-ÿ](?:[ -ÿ]*[!-ÿ])?$","description":"Informações complementares desta nota (xInfComp da DPS; o DANFSe mostra em \"Informações complementares\"): mês de referência, contrato, pedido. Separado de description, que pode vir fixa do catálogo (serviceCode) — não substitui a descrição, soma-se a ela na nota. Nunca vem do catálogo. Uma linha só e apenas caracteres Latin-1: sem quebra de linha, travessão (–), aspas curvas ou emoji."},"amount":{"type":"string","pattern":"^\\d{1,13}\\.\\d{2}$","example":"1500.00"}}},"municipalTax":{"type":"object","additionalProperties":false,"required":["taxation","withholding"],"properties":{"taxation":{"type":"string","enum":["1","2","3","4"],"description":"Tributação do ISSQN: 1 = Operação Tributável, 2 = Imune, 3 = Exportação, 4 = Não Incidência."},"withholding":{"type":"string","enum":["1","2","3"],"description":"Retenção do ISSQN: 1 = Não Retido, 2 = Retido pelo Tomador, 3 = Retido pelo Intermediário."},"rate":{"type":"string","pattern":"^(?:[0-4]\\.\\d{2}|5\\.00)$","example":"5.00","description":"Alíquota do ISS no município de incidência, de 0.00 a 5.00 — o máximo legal é 5% (LC 116/2003, art. 8º, II). Não confundir com a alíquota efetiva do Simples Nacional (fiscal-settings.issuerTaxSettings.simpleNationalAliquotPercent), que costuma ser maior. Uma alíquota acima do teto — inclusive a herdada de um serviceCode gravado antes desta regra — devolve 422 (ISSQN_RATE_ABOVE_LEGAL_LIMIT) antes de qualquer cobrança. Para prestador ME/EPP do Simples Nacional apurando o ISSQN pelo Simples, SEM retenção (withholding = \"1\"), em município ativo no Sistema Nacional NFS-e, o campo é REMOVIDO da DPS automaticamente: informá-lo é rejeitado pela Sefin com E0625, porque o município parametriza a alíquota e o ISS é recolhido no DAS. Havendo retenção, a alíquota é enviada e é ela que determina o valor retido. Município não integrado sem alíquota configurada devolve 422 (ISSQN_RATE_REQUIRED)."}}},"federalTax":{"type":"object","additionalProperties":false,"required":["cst","pisAmount","cofinsAmount","withholding"],"properties":{"cst":{"type":"string","pattern":"^\\d{2}$"},"pisAmount":{"type":"string","pattern":"^\\d{1,13}(?:\\.\\d{1,2})?$"},"cofinsAmount":{"type":"string","pattern":"^\\d{1,13}(?:\\.\\d{1,2})?$"},"withholding":{"type":"string","enum":["0","1","2","3","4","5","6","7","8","9"]}}},"approximateTax":{"type":"object","additionalProperties":false,"required":["federalAmount","stateAmount","municipalAmount"],"properties":{"federalAmount":{"type":"string"},"stateAmount":{"type":"string"},"municipalAmount":{"type":"string"}}},"ibsCbs":{"type":"object","additionalProperties":false,"required":["purpose","finalConsumption","operationIndicator","recipientIndicator","taxSituation","taxClassification"],"properties":{"purpose":{"const":"0"},"finalConsumption":{"type":"string","enum":["0","1"]},"operationIndicator":{"type":"string","pattern":"^\\d{6}$"},"recipientIndicator":{"type":"string","enum":["0","1"]},"taxSituation":{"type":"string","pattern":"^\\d{3}$"},"taxClassification":{"type":"string","pattern":"^\\d{6}$"}}},"competenceDate":{"type":"string","format":"date"}}},"NfseCancelRequest":{"type":"object","additionalProperties":false,"required":["reasonCode","reason"],"properties":{"reasonCode":{"type":"string","enum":["1","2","9"],"description":"Motivo oficial do cancelamento (cMotivo): 1 = Erro na emissão; 2 = Serviço não prestado; 9 = Outros."},"reason":{"type":"string","minLength":15,"maxLength":255,"description":"Justificativa em texto (15 a 255 caracteres), enviada no evento oficial."}}},"CreateWebhookRequest":{"type":"object","additionalProperties":false,"required":["name","url","events","environment"],"properties":{"name":{"type":"string","minLength":1,"maxLength":100},"url":{"type":"string","format":"uri","maxLength":2048},"events":{"type":"array","minItems":1,"uniqueItems":true,"items":{"type":"string","enum":["nfse.received","nfse.processing","nfse.issued","nfse.rejected","nfse.cancelled","nfse.cancel_rejected","fiscal_document.available","fiscal_document.externally_cancelled","fiscal_document.content_upgraded","fiscal_document.event_received","fiscal_document.manifestation_registered","billing.charge_created","billing.low_balance"]}},"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"timeoutMs":{"type":"integer","minimum":1000,"maximum":30000,"default":10000},"maxAttempts":{"type":"integer","minimum":1,"maximum":20,"default":8}}},"CreateOrganizationRequest":{"type":"object","additionalProperties":false,"required":["legalName","taxId","email","address","owner"],"properties":{"legalName":{"type":"string","minLength":2,"maxLength":200},"taxId":{"type":"string","pattern":"^\\d{14}$","description":"CNPJ"},"email":{"type":"string","format":"email","maxLength":254},"phone":{"type":"string","pattern":"^\\d{10,11}$"},"address":{"type":"object","additionalProperties":false,"required":["municipalityCode","postalCode","street","number","neighborhood"],"properties":{"municipalityCode":{"type":"string","pattern":"^\\d{7}$"},"postalCode":{"type":"string","pattern":"^\\d{8}$"},"street":{"type":"string","minLength":1,"maxLength":255},"number":{"type":"string","minLength":1,"maxLength":60},"complement":{"type":"string","minLength":1,"maxLength":156},"neighborhood":{"type":"string","minLength":1,"maxLength":60}},"description":"Endereço da primeira empresa (CNPJ emitente), criada junto com a organização. A organização em si não guarda endereço: depois do cadastro, cada empresa tem o seu, editável em PATCH /v1/companies/{id}."},"owner":{"type":"object","additionalProperties":false,"required":["name","email"],"description":"No password here: the owner account is created awaiting activation and receives an e-mail with a link (valid 48h) to set their own password — see POST /v1/console/activation/confirm.","properties":{"name":{"type":"string","minLength":2,"maxLength":200},"email":{"type":"string","format":"email","maxLength":254}}}}},"UpdateOrganizationRequest":{"type":"object","additionalProperties":false,"description":"Só contato. Endereço é de cada empresa: use PATCH /v1/companies/{id}.","properties":{"email":{"type":"string","format":"email","maxLength":254},"phone":{"type":"string","pattern":"^\\d{10,11}$"}}},"FiscalSettingsRequest":{"type":"object","additionalProperties":false,"required":["environment","defaultIssqnTaxation","defaultIssqnWithholding","issuerTaxSettings"],"properties":{"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"municipalityCode":{"type":["string","null"],"pattern":"^\\d{7}$","description":"Município da PRESTAÇÃO padrão (o service.locationCode usado quando a emissão não informa um). Ausente ou null herda o município da empresa — informe um código só para prestar serviço num município diferente do endereço dela. Não é o município emissor: esse vem sempre da empresa."},"defaultIssqnTaxation":{"type":"string","enum":["1","2","3","4"],"description":"Tributação do ISSQN: 1 = Operação Tributável, 2 = Imune, 3 = Exportação, 4 = Não Incidência."},"defaultIssqnWithholding":{"type":"string","enum":["1","2","3"],"description":"Retenção do ISSQN: 1 = Não Retido, 2 = Retido pelo Tomador, 3 = Retido pelo Intermediário."},"issuerTaxSettings":{"type":"object","additionalProperties":false,"required":["simpleNationalOption","specialTaxRegime"],"description":"Regime tributário do emitente, usado para montar a DPS oficial (prestador/regTrib). Sem isso configurado, POST /v1/nfse/issue é bloqueado por GET /v1/organization/pending.","properties":{"simpleNationalOption":{"type":"string","enum":["1","2","3"],"description":"Opção pelo Simples Nacional: 1 = Não optante, 2 = Optante MEI, 3 = Optante ME/EPP (os mesmos rótulos impressos na DANFSe)."},"simpleNationalAssessmentRegime":{"type":"string","enum":["1","2","3"],"description":"Só para optante ME/EPP (simpleNationalOption = \"3\"), e obrigatório nesse caso. Em qual regime os tributos são apurados: 1 = federais e ISS pelo Simples (o caso comum — use este se a empresa não ultrapassou sublimite); 2 = federais pelo Simples e ISS por fora, pela legislação municipal; 3 = federais e ISS por fora do Simples. Rótulos do leiaute oficial (regApTribSN)."},"specialTaxRegime":{"type":"string","enum":["0","1","2","3","4","5","6","9"],"description":"Regime especial de tributação municipal (regEspTrib): 0 = Nenhum (o caso comum); 1 = Ato cooperado (cooperativa); 2 = Estimativa; 3 = Microempresa municipal; 4 = Notário ou registrador; 5 = Profissional autônomo; 6 = Sociedade de profissionais; 9 = Outros. Na dúvida, 0 — o contador confirma."},"simpleNationalAliquotPercent":{"type":"string","pattern":"^\\d{1,2}(\\.\\d{2})?$","description":"Alíquota efetiva do Simples Nacional, em percentual (ex.: \"6.00\"); obrigatória quando simpleNationalOption = \"3\". Vai na DPS para o cálculo dos tributos aproximados. Não é a alíquota nominal da tabela: é a efetiva do mês, que o contador calcula (ou que aparece no PGDAS-D). Na dúvida, peça ao contador."}}},"companyId":{"type":"string","format":"uuid","description":"Empresa a configurar. Ausente resolve para a empresa padrão da organização."},"receptionStartingPoint":{"type":"string","enum":["FROM_NOW","LAST_7_DAYS","LAST_30_DAYS","LAST_90_DAYS","FROM_ZERO"],"description":"Só interessa a quem vai RECEBER notas: a partir de quando buscar as NFS-e emitidas contra a empresa. Para quem só emite, omita — o padrão é `FROM_NOW`, que não busca nem cobra histórico nenhum. Vale só na primeira vez que o ambiente é configurado; salvamentos seguintes o ignoram."}}},"CreateCertificateRequest":{"type":"object","additionalProperties":false,"required":["pfxBase64","passphrase"],"properties":{"pfxBase64":{"type":"string","format":"byte","description":"PKCS#12 (.pfx/.p12) file, base64-encoded, up to 1 MiB decoded"},"passphrase":{"type":"string","minLength":1,"maxLength":1024}}},"CertificateMetadata":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"status":{"type":"string","enum":["ACTIVE","REPLACED","REVOKED"]},"documentNumber":{"type":["string","null"],"description":"CNPJ/CPF extraído do subject, mascarado exceto os últimos 4 dígitos; nulo se não reconhecido"},"issuer":{"type":"string"},"subject":{"type":"string"},"serialNumber":{"type":"string"},"fingerprint":{"type":"string"},"validFrom":{"type":"string","format":"date-time"},"validUntil":{"type":"string","format":"date-time"},"links":{"type":"array","items":{"$ref":"#/components/schemas/CertificateLink"},"description":"Quem usa este certificado, em qual empresa e ambiente."}}},"CertificateLink":{"type":"object","properties":{"companyId":{"type":"string","format":"uuid"},"companyLabel":{"type":"string"},"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"intendedUse":{"type":"string","enum":["ISSUANCE_AND_RECEPTION","RECEPTION_ONLY"]},"status":{"type":"string","enum":["ACTIVE","REVOKED"]}}},"CompanyMetadata":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"label":{"type":"string"},"taxId":{"type":"string"},"legalName":{"type":"string"},"tradeName":{"type":["string","null"]},"municipalRegistration":{"type":["string","null"]},"stateRegistration":{"type":["string","null"]},"stateRegistrationExempt":{"type":"boolean"},"municipalityCode":{"type":["string","null"]},"postalCode":{"type":["string","null"]},"street":{"type":["string","null"]},"addressNumber":{"type":["string","null"]},"neighborhood":{"type":["string","null"]},"addressComplement":{"type":["string","null"]},"status":{"type":"string","enum":["ACTIVE","INACTIVE"]},"isDefault":{"type":"boolean"},"certificates":{"type":"object","properties":{"HOMOLOGATION":{"type":["object","null"],"properties":{"certificateId":{"type":"string","format":"uuid"},"validTo":{"type":"string","format":"date-time"}}},"PRODUCTION":{"type":["object","null"],"properties":{"certificateId":{"type":"string","format":"uuid"},"validTo":{"type":"string","format":"date-time"}}}}}}},"CreateCompanyRequest":{"type":"object","additionalProperties":false,"required":["label","taxId","legalName"],"properties":{"label":{"type":"string","minLength":1,"maxLength":255},"taxId":{"type":"string","pattern":"^\\d{11}$|^\\d{14}$"},"legalName":{"type":"string","minLength":1,"maxLength":255},"tradeName":{"type":"string","minLength":1,"maxLength":255},"municipalRegistration":{"type":"string","pattern":"^\\d{1,15}$"},"stateRegistration":{"type":"string","minLength":1,"maxLength":32},"stateRegistrationExempt":{"type":"boolean"},"municipalityCode":{"type":"string","pattern":"^\\d{7}$"},"postalCode":{"type":"string","pattern":"^\\d{8}$"},"street":{"type":"string","minLength":1,"maxLength":255},"addressNumber":{"type":"string","minLength":1,"maxLength":32},"neighborhood":{"type":"string","minLength":1,"maxLength":255},"addressComplement":{"type":"string","minLength":1,"maxLength":255}}},"UpdateCompanyRequest":{"type":"object","additionalProperties":false,"properties":{"label":{"type":"string","minLength":1,"maxLength":255},"taxId":{"type":"string","pattern":"^\\d{11}$|^\\d{14}$"},"legalName":{"type":"string","minLength":1,"maxLength":255},"tradeName":{"type":["string","null"],"minLength":1,"maxLength":255},"municipalRegistration":{"type":["string","null"],"pattern":"^\\d{1,15}$"},"stateRegistration":{"type":["string","null"],"minLength":1,"maxLength":32},"stateRegistrationExempt":{"type":"boolean"},"municipalityCode":{"type":["string","null"],"pattern":"^\\d{7}$"},"postalCode":{"type":["string","null"],"pattern":"^\\d{8}$"},"street":{"type":["string","null"],"minLength":1,"maxLength":255},"addressNumber":{"type":["string","null"],"minLength":1,"maxLength":32},"neighborhood":{"type":["string","null"],"minLength":1,"maxLength":255},"addressComplement":{"type":["string","null"],"minLength":1,"maxLength":255},"status":{"type":"string","enum":["ACTIVE","INACTIVE"]}}},"LinkCertificateRequest":{"type":"object","additionalProperties":false,"required":["certificateId"],"properties":{"certificateId":{"type":"string","format":"uuid"},"intendedUse":{"type":"string","enum":["ISSUANCE_AND_RECEPTION","RECEPTION_ONLY"],"default":"ISSUANCE_AND_RECEPTION"}}},"ContextResponse":{"type":"object","properties":{"organization":{"type":["object","null"],"properties":{"id":{"type":"string","format":"uuid"},"legalName":{"type":"string"},"taxId":{"type":"string","description":"CNPJ/CPF da organização, só dígitos."},"status":{"type":"string"},"email":{"type":["string","null"]},"phone":{"type":["string","null"]},"ownerActivated":{"type":"boolean","description":"Se o dono já abriu o e-mail de ativação e criou a senha pessoal — necessária para liberar produção. Se ainda não chegou, o e-mail pode ser reenviado em POST /v1/console/activation/resend, com { \"email\" } (pública; responde igual exista ou não a conta)."}}},"credentialId":{"type":["string","null"],"format":"uuid"},"user":{"type":["object","null"],"description":"Preenchido só em sessão de console; nulo quando a chamada usa API key ou token de grant.","properties":{"id":{"type":"string","format":"uuid"},"fullName":{"type":"string"},"email":{"type":"string","format":"email"},"role":{"type":"string","enum":["OWNER","VIEWER"]},"mfaEnabled":{"type":"boolean"}}},"scopes":{"type":"array","items":{"type":"string"},"description":"Escopos efetivos desta credencial — o que ela pode fazer, já resolvido."}}},"Readiness":{"type":"object","properties":{"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"purpose":{"type":"string","enum":["ISSUANCE","RECEPTION_ONLY"],"description":"A lente aplicada nesta avaliação, derivada do `intendedUse` do vínculo ativo. `RECEPTION_ONLY` quando o certificado vinculado só serve para receber: nesse caso as pendências de emissão (configuração fiscal, ISSQN, regime do emitente, município) não são cobradas, porque a empresa não vai emitir. Sem certificado vinculado a lente é `ISSUANCE`, que é o caminho de quem acabou de se cadastrar."},"intendedUse":{"type":["string","null"],"enum":["ISSUANCE_AND_RECEPTION","RECEPTION_ONLY",null],"description":"Uso declarado no vínculo ativo do ambiente; nulo quando não há certificado vinculado."},"ready":{"type":"boolean","description":"Falso quando há pendência CRITICAL para o `purpose` avaliado. Atenção: `ready: true` com `purpose: \"RECEPTION_ONLY\"` significa pronta para **receber**, não para emitir — a emissão é sempre avaliada pela lente `ISSUANCE` em POST /v1/nfse/validate|issue, que recusa um vínculo somente-recepção com `CERTIFICATE_RECEPTION_ONLY`."},"pending":{"type":"array","items":{"type":"object","properties":{"code":{"type":"string","example":"CERTIFICATE_EXPIRED","description":"Vocabulário próprio do checklist, distinto do catálogo de erros HTTP: `FISCAL_CREDENTIAL_MISSING`, `CERTIFICATE_EXPIRED`, `CERTIFICATE_EXPIRING_SOON`, `CERTIFICATE_RECEPTION_ONLY` (o vínculo é somente-recepção e não assina DPS), `FISCAL_CONFIGURATION_MISSING`, `ISSQN_TAXATION_MISSING`, `ISSQN_WITHHOLDING_MISSING`, `ISSUER_TAX_SETTINGS_MISSING`, `MUNICIPALITY_MISSING`, `INBOUND_MONITOR_PAUSED` e `DOCUMENT_DELIVERY_FAILED`. Os CRITICAL são devolvidos como `errors[].code` no 422 de POST /v1/nfse/validate|issue."},"severity":{"type":"string","enum":["WARNING","CRITICAL"]},"message":{"type":"string"}}}}}},"NfseRejection":{"type":"object","properties":{"code":{"type":"string"},"description":{"type":"string","description":"Texto do webservice oficial, verbatim."},"complement":{"type":"string"},"hint":{"type":["object","null"],"description":"Explicação nossa, só para os códigos efetivamente mapeados (ou mensagens de rejeição reconhecidas) — nunca uma tradução inventada.","properties":{"title":{"type":"string"},"hint":{"type":"string"}}}}},"NfseAttempt":{"type":"object","description":"Um envio real ao provedor oficial: a tentativa inicial e cada reenvio, manual (retry) ou automático (reconciliação de WAITING_PROVIDER). Distinto de issuanceAttempt, que só conta reenvios pedidos pelo usuário.","properties":{"attempt":{"type":"integer","minimum":1},"result":{"type":"string","enum":["SUCCESS","RETRYABLE_ERROR","FINAL_ERROR","UNKNOWN"]},"errorCode":{"type":["string","null"]},"httpStatus":{"type":["integer","null"]},"startedAt":{"type":"string","format":"date-time"},"finishedAt":{"type":["string","null"],"format":"date-time"},"hasDpsXml":{"type":"boolean","description":"Quando true, o XML desta tentativa pode ser baixado via GET /v1/nfse/{id}/dps-xml?attempt={attempt}."},"rejections":{"type":["array","null"],"items":{"$ref":"#/components/schemas/NfseRejection"},"description":"O que o provedor oficial respondeu NESTA tentativa. O campo rejections no nível da operação é sobrescrito a cada falha e só descreve a última. Preenchido em tentativas FINAL_ERROR."}}},"NfseOperationSummary":{"type":"object","required":["id","environment","operationalStatus","createdAt"],"properties":{"id":{"type":"string","format":"uuid"},"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"externalReference":{"type":["string","null"]},"operationalStatus":{"type":"string","enum":["RECEIVED","VALIDATING","READY","QUEUED","RUNNING","WAITING_PROVIDER","COMPLETED","FAILED","MANUAL_REVIEW"],"description":"Estado do processamento interno da operação. Terminais na emissão: COMPLETED (autorizada), FAILED (rejeitada ou falha de validação), WAITING_PROVIDER (resultado oficial ambíguo, reconciliação automática em curso — ver data.reconciliation). MANUAL_REVIEW só ocorre hoje no fluxo de cancelamento."},"fiscalStatus":{"type":["string","null"],"enum":["NOT_SUBMITTED","SUBMITTED","PROCESSING","AUTHORIZED","REJECTED","CANCEL_PENDING","CANCELLED","UNKNOWN",null],"description":"Estado fiscal reportado pelo provedor oficial, independente do operationalStatus. Pares esperados: RECEIVED/VALIDATING/READY/QUEUED/RUNNING → NOT_SUBMITTED; WAITING_PROVIDER → UNKNOWN; COMPLETED → AUTHORIZED; FAILED → REJECTED; CANCEL_PENDING/CANCELLED aparecem após um pedido de cancelamento, feito pela tela Documentos ou por POST /v1/nfse/{id}/cancel — mesmo depois da autorização, este campo continua acompanhando o desfecho. Trate UNKNOWN como transitório (não reenvie) e REJECTED como definitivo (ver data.rejections)."},"failureCode":{"type":["string","null"]},"createdAt":{"type":"string","format":"date-time"},"fiscalDocumentId":{"type":["string","null"],"format":"uuid","description":"Presente assim que a operação autoriza a NFS-e — aponta para GET /v1/fiscal-documents/{id}, de onde vêm PDF/XML."},"documentNumber":{"type":["string","null"],"description":"Número da NFS-e (nNFSe), só depois de autorizada — atribuído pela administração e pode divergir do nDPS (dpsNumber/dpsSeries) que a organização controlou ao emitir."},"dpsSeries":{"type":["string","null"],"description":"Série do nDPS, presente desde a alocação — antes mesmo da autorização. Ver documentNumber."},"dpsNumber":{"type":["string","null"],"description":"Número do nDPS. Ver documentNumber."},"customerDocument":{"type":["string","null"],"description":"CNPJ/CPF do tomador, só dígitos. Vem do documento fiscal depois da autorização, do payload de emissão antes disso."},"customerName":{"type":["string","null"]},"amount":{"type":["string","null"],"example":"1450.00","description":"Valor do serviço (vServ). Vem do documento fiscal depois da autorização, do payload de emissão antes disso."},"netAmount":{"type":["string","null"],"example":"1420.00","description":"Valor líquido (vLiq), só depois da autorização."}}},"NfseOperationDetail":{"type":"object","required":["id","environment","operationalStatus","createdAt","issuanceAttempt","updatedAt","attempts"],"properties":{"id":{"type":"string","format":"uuid"},"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"externalReference":{"type":["string","null"]},"operationalStatus":{"type":"string","enum":["RECEIVED","VALIDATING","READY","QUEUED","RUNNING","WAITING_PROVIDER","COMPLETED","FAILED","MANUAL_REVIEW"],"description":"Estado do processamento interno da operação. Terminais na emissão: COMPLETED (autorizada), FAILED (rejeitada ou falha de validação), WAITING_PROVIDER (resultado oficial ambíguo, reconciliação automática em curso — ver data.reconciliation). MANUAL_REVIEW só ocorre hoje no fluxo de cancelamento."},"fiscalStatus":{"type":["string","null"],"enum":["NOT_SUBMITTED","SUBMITTED","PROCESSING","AUTHORIZED","REJECTED","CANCEL_PENDING","CANCELLED","UNKNOWN",null],"description":"Estado fiscal reportado pelo provedor oficial, independente do operationalStatus. Pares esperados: RECEIVED/VALIDATING/READY/QUEUED/RUNNING → NOT_SUBMITTED; WAITING_PROVIDER → UNKNOWN; COMPLETED → AUTHORIZED; FAILED → REJECTED; CANCEL_PENDING/CANCELLED aparecem após um pedido de cancelamento, feito pela tela Documentos ou por POST /v1/nfse/{id}/cancel — mesmo depois da autorização, este campo continua acompanhando o desfecho. Trate UNKNOWN como transitório (não reenvie) e REJECTED como definitivo (ver data.rejections)."},"failureCode":{"type":["string","null"]},"createdAt":{"type":"string","format":"date-time"},"fiscalDocumentId":{"type":["string","null"],"format":"uuid","description":"Presente assim que a operação autoriza a NFS-e — aponta para GET /v1/fiscal-documents/{id}, de onde vêm PDF/XML."},"documentNumber":{"type":["string","null"],"description":"Número da NFS-e (nNFSe), só depois de autorizada — atribuído pela administração e pode divergir do nDPS (dpsNumber/dpsSeries) que a organização controlou ao emitir."},"dpsSeries":{"type":["string","null"],"description":"Série do nDPS, presente desde a alocação — antes mesmo da autorização. Ver documentNumber."},"dpsNumber":{"type":["string","null"],"description":"Número do nDPS. Ver documentNumber."},"customerDocument":{"type":["string","null"],"description":"CNPJ/CPF do tomador, só dígitos. Vem do documento fiscal depois da autorização, do payload de emissão antes disso."},"customerName":{"type":["string","null"]},"amount":{"type":["string","null"],"example":"1450.00","description":"Valor do serviço (vServ). Vem do documento fiscal depois da autorização, do payload de emissão antes disso."},"netAmount":{"type":["string","null"],"example":"1420.00","description":"Valor líquido (vLiq), só depois da autorização."},"providerReference":{"type":["string","null"],"description":"Chave de acesso da NFS-e autorizada. Mesmo valor de nfse.accessKey."},"issuanceAttempt":{"type":"integer","minimum":1,"description":"1 no envio normal; incrementa a cada POST /v1/nfse/{id}/retry."},"dps":{"type":["object","null"],"description":"Série e número do DPS. Presentes assim que a operação sai de RECEIVED — alocados pelo Trilha Invoice (série AUTO) ou informados pelo cliente (série MANUAL). number aqui é o nDPS, que pode divergir do número da NFS-e (ver nfse.number).","properties":{"series":{"type":"string","pattern":"^[0-9]{1,5}$"},"number":{"type":"string","description":"nDPS, sem zeros à esquerda."},"municipalityCode":{"type":"string","pattern":"^[0-9]{7}$"}}},"nfse":{"type":["object","null"],"description":"Dados da NFS-e autorizada. Nulo até fiscalStatus AUTHORIZED.","properties":{"number":{"type":["string","null"],"description":"Número da NFS-e atribuído pela administração."},"accessKey":{"type":"string","pattern":"^[0-9]{44}$|^[0-9]{50}$","description":"Chave de acesso (44 ou 50 dígitos)."},"issuedAt":{"type":["string","null"],"format":"date-time"}}},"rejections":{"type":["array","null"],"items":{"$ref":"#/components/schemas/NfseRejection"}},"reconciliation":{"type":["object","null"],"description":"Presente só em WAITING_PROVIDER: o envio oficial ficou ambíguo e uma rotina em background já tenta confirmar de novo. Não é rejeição — não reenvie a nota.","properties":{"inProgress":{"type":"boolean"},"message":{"type":"string"}}},"requestSnapshot":{"type":"object","description":"Payload de emissão já resolvido, exatamente como foi enviado ao provedor. Base para pré-preencher a correção de uma emissão FAILED antes de reenviar via POST /v1/nfse/{id}/retry — federalTax/approximateTax/ibsCbs, quando presentes, devem ser reenviados sem alteração.","properties":{"customer":{"type":"object","properties":{"document":{"type":"string"},"name":{"type":"string"},"address":{"type":["object","null"]}}},"service":{"type":"object","properties":{"locationCode":{"type":"string"},"nationalTaxCode":{"type":"string"},"municipalTaxCode":{"type":["string","null"]},"nbsCode":{"type":["string","null"]},"description":{"type":"string"},"additionalInformation":{"type":["string","null"]},"amount":{"type":"string"}}},"municipalTax":{"type":"object","properties":{"taxation":{"type":"string"},"withholding":{"type":"string"},"rate":{"type":["string","null"]}}},"competenceDate":{"type":"string","format":"date"},"series":{"type":"string"},"number":{"type":"string"},"externalReference":{"type":"string"},"federalTax":{"type":"object"},"approximateTax":{"type":"object"},"ibsCbs":{"type":"object"}}},"updatedAt":{"type":"string","format":"date-time"},"attempts":{"type":"array","description":"Log de retransmissões: uma linha por envio real ao provedor, incluindo a tentativa que autorizou a nota.","items":{"$ref":"#/components/schemas/NfseAttempt"}}}},"DpsSequence":{"type":"object","properties":{"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"municipalityCode":{"type":"string","pattern":"^\\d{7}$"},"series":{"type":"string","pattern":"^\\d{1,5}$"},"nextNumber":{"type":"string","description":"Próximo nDPS que o modo AUTO vai alocar nesta série. String (bigint)."},"mode":{"type":"string","enum":["AUTO","MANUAL"]},"active":{"type":"boolean"},"updatedAt":{"type":"string","format":"date-time"}}},"DpsSeriesConfig":{"type":"object","properties":{"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"municipalityCode":{"type":"string","pattern":"^\\d{7}$"},"series":{"type":"string","pattern":"^\\d{1,5}$"},"mode":{"type":"string","enum":["AUTO","MANUAL"]},"active":{"type":"boolean"},"isDefault":{"type":"boolean","description":"true quando é a série usada por POST /v1/nfse/issue sem series explícita."},"nextNumber":{"type":["string","null"],"description":"Próximo nDPS no modo AUTO; nulo se nada foi emitido ainda."},"updatedAt":{"type":"string","format":"date-time"}}},"NfseIssueAccepted":{"oneOf":[{"type":"object","title":"Emissão aceita","required":["status","operationId","operationalStatus"],"properties":{"status":{"type":"string","const":"ACCEPTED"},"operationId":{"type":"string","format":"uuid"},"operationalStatus":{"type":"string","enum":["RECEIVED","VALIDATING","READY","QUEUED","RUNNING","WAITING_PROVIDER","COMPLETED","FAILED","MANUAL_REVIEW"]},"fiscalStatus":{"type":["string","null"],"enum":["NOT_SUBMITTED","SUBMITTED","PROCESSING","AUTHORIZED","REJECTED","CANCEL_PENDING","CANCELLED","UNKNOWN",null]},"replayed":{"type":"boolean","description":"true quando a Idempotency-Key já havia sido usada: nada novo foi criado."},"billing":{"type":"object","properties":{"planCode":{"type":"string"},"amountCents":{"type":"integer"},"status":{"type":"string","enum":["RESERVED"]}}}}},{"type":"object","title":"Retida para aprovação","required":["status","approvalId"],"properties":{"status":{"type":"string","const":"PENDING_APPROVAL"},"approvalId":{"type":"string","format":"uuid"},"reasonCodes":{"type":"array","items":{"type":"string"}},"expiresAt":{"type":"string","format":"date-time"}}}],"discriminator":{"propertyName":"status"}},"NfseCancelAccepted":{"oneOf":[{"type":"object","title":"Cancelamento aceito","required":["status","operationId","operationalStatus"],"properties":{"status":{"type":"string","const":"ACCEPTED"},"operationId":{"type":"string","format":"uuid"},"operationalStatus":{"type":"string","enum":["RECEIVED","VALIDATING","READY","QUEUED","RUNNING","WAITING_PROVIDER","COMPLETED","FAILED","MANUAL_REVIEW"]},"fiscalStatus":{"type":["string","null"],"enum":["NOT_SUBMITTED","SUBMITTED","PROCESSING","AUTHORIZED","REJECTED","CANCEL_PENDING","CANCELLED","UNKNOWN",null]},"replayed":{"type":"boolean"}}},{"type":"object","title":"Retido para aprovação","required":["status","approvalId"],"properties":{"status":{"type":"string","const":"PENDING_APPROVAL"},"approvalId":{"type":"string","format":"uuid"},"reasonCodes":{"type":"array","items":{"type":"string"}},"expiresAt":{"type":"string","format":"date-time"}}}],"discriminator":{"propertyName":"status"}},"WalletSnapshot":{"type":"object","description":"Saldos em centavos inteiros — diferente dos valores de documento fiscal, que são strings decimais.","properties":{"balanceCents":{"type":"integer"},"reservedCents":{"type":"integer","description":"Reservado por operações em andamento; ainda não capturado."},"availableCents":{"type":"integer"},"currency":{"type":"string","example":"BRL"},"lowBalance":{"type":"boolean"},"recommendedTopUpCents":{"type":"integer"}}},"UsageRecord":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"operationId":{"type":"string","format":"uuid"},"eventType":{"type":"string","example":"NFSE_ISSUANCE"},"status":{"type":"string","example":"CAPTURED"},"amountCents":{"type":"integer"},"currency":{"type":"string"},"billedVia":{"type":"string"},"credentialId":{"type":["string","null"],"format":"uuid"},"balanceBeforeCents":{"type":["integer","null"]},"balanceAfterCents":{"type":["integer","null"]},"unitPriceCents":{"type":["integer","null"],"description":"Nulo em registros anteriores à tarifação progressiva."},"pricingTierId":{"type":["string","null"],"format":"uuid"},"quantityInCycle":{"type":["integer","null"],"description":"Posição da operação no ciclo — é ela que determina a faixa aplicada."},"billingCycleStart":{"type":["string","null"],"format":"date-time"},"createdAt":{"type":"string","format":"date-time"}}},"UsageSummary":{"type":"object","properties":{"billingCycleStart":{"type":"string","format":"date-time"},"billingCycleEnd":{"type":"string","format":"date-time"},"planCode":{"type":"string"},"planName":{"type":"string"},"currency":{"type":"string"},"subscriptionFeeCents":{"type":"integer"},"events":{"type":"array","items":{"type":"object","properties":{"eventType":{"type":"string"},"eventName":{"type":"string"},"included":{"type":"integer","description":"Franquia do plano para este evento."},"used":{"type":"integer"},"remaining":{"type":"integer"},"percentage":{"type":"number"},"excessQuantity":{"type":"integer"},"excessAmountCents":{"type":"integer"},"nextUnitPriceCents":{"type":"integer","description":"Quanto custará a próxima unidade, já na faixa vigente."},"alertThresholds":{"type":"array","items":{"type":"integer"}},"alertsReached":{"type":"array","items":{"type":"integer"}}}}},"excessAmountCents":{"type":"integer"},"estimatedNextInvoiceCents":{"type":"integer"}}},"FiscalDocument":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"operationId":{"type":["string","null"],"format":"uuid","description":"Operação de emissão que originou o documento; nulo nos recebidos do ADN."},"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"origin":{"type":"string","enum":["ISSUED","RECEIVED"],"description":"Por onde o documento chegou: ISSUED pela nossa API, RECEIVED pelo monitoramento do ADN. Não diz de quem é a nota — para isso, organizationRole."},"accessKey":{"type":["string","null"],"pattern":"^\\d{44}$|^\\d{50}$","description":"50 dígitos na NFS-e, 44 na NF-e e no CT-e."},"protocol":{"type":["string","null"],"description":"Registro oficial da autorização. NFS-e: nDFSe, o número que o ambiente gerador atribui à nota (o Sistema Nacional não emite um protocolo à parte). NF-e/CT-e: nProt da SEFAZ. Nulo quando o XML autorizado não o traz."},"fiscalStatus":{"type":"string","example":"AUTHORIZED"},"issuedAt":{"type":["string","null"],"format":"date-time"},"createdAt":{"type":"string","format":"date-time"},"documentNumber":{"type":["string","null"],"description":"Número da NFS-e (nNFSe)."},"dpsSeries":{"type":["string","null"],"description":"Série do nDPS — número que a organização controlou ao emitir, distinto de documentNumber (nNFSe), que a administração atribui e pode divergir dele. Só para NFS-e emitida por nós."},"dpsNumber":{"type":["string","null"],"description":"Número do nDPS. Ver dpsSeries."},"competenceDate":{"type":["string","null"],"format":"date","description":"Competência (dCompet), data civil YYYY-MM-DD — sem hora nem fuso."},"issuerDocument":{"type":["string","null"],"description":"CNPJ/CPF do prestador, só dígitos."},"issuerName":{"type":["string","null"]},"issuerMunicipalityCode":{"type":["string","null"],"pattern":"^\\d{7}$"},"issuerMunicipalityName":{"type":["string","null"],"description":"Resolvido pelo código IBGE no catálogo de municípios; o XML traz só o código."},"issuerState":{"type":["string","null"],"minLength":2,"maxLength":2},"customerDocument":{"type":["string","null"],"description":"CNPJ/CPF do tomador, só dígitos."},"customerName":{"type":["string","null"]},"serviceDescription":{"type":["string","null"]},"serviceAmount":{"type":["string","null"],"example":"1500.00","description":"Valor do serviço (vServ), string decimal."},"netAmount":{"type":["string","null"],"example":"1470.00","description":"Valor líquido (vLiq), string decimal."},"organizationRole":{"type":["string","null"],"enum":["PROVIDER","CUSTOMER","OTHER",null],"description":"Papel da sua organização no documento, comparando o CNPJ dela com prestador e tomador no XML. CUSTOMER = nota emitida contra o seu CNPJ; PROVIDER = emitida pelo seu CNPJ; OTHER = ele aparece só como intermediário. Nulo quando o layout não foi reconhecido."},"documentType":{"type":"string","enum":["NFSE","NFE","CTE"],"description":"NFS-e (serviço), NF-e (mercadoria) ou CT-e (transporte)."},"contentLevel":{"type":"string","enum":["SUMMARY","FULL"],"description":"SUMMARY é o documento entregue apenas como cabeçalho: a SEFAZ distribui o resumo da NF-e antes de qualquer manifestação, e o XML completo só passa a existir depois dela. A promoção SUMMARY -> FULL mantém o mesmo id e não é cobrada de novo — é a mesma nota em dois momentos."},"amount":{"type":["string","null"],"example":"1450.00","description":"Valor total do documento, comparável entre os três tipos: vServ na NFS-e, vNF na NF-e, vTPrest no CT-e. serviceAmount continua existindo com a semântica estrita de valor do serviço."},"manifestation":{"$ref":"#/components/schemas/FiscalDocumentManifestation"},"xmlAvailable":{"type":"boolean","description":"false enquanto contentLevel for SUMMARY."},"pdfAvailable":{"type":"boolean","description":"false enquanto contentLevel for SUMMARY."},"issuerNameLookalike":{"type":"boolean","description":"true quando o nome do emitente se parece com o da sua organização mas o CNPJ é outro — a forma de uma nota emitida indevidamente em seu nome. É um aviso: organizationRole continua vindo da comparação de CNPJ, e o documento não é reclassificado. Heurística conservadora, que erra para o lado de não avisar."}}},"FiscalDocumentManifestation":{"type":"object","description":"Manifestação do destinatário (NF-e modelo 55) e, no CT-e, o desacordo do tomador (evento 610110), que deixa o estado DISPUTED. Em NFS-e o estado é sempre NOT_APPLICABLE.","properties":{"state":{"type":["string","null"],"enum":["NOT_APPLICABLE","PENDING","ACKNOWLEDGED","CONFIRMED","DENIED","NOT_PERFORMED","DISPUTED",null]},"deadlineAt":{"type":["string","null"],"format":"date-time","description":"Prazo legal para manifestar."},"availableActions":{"type":"array","items":{"type":"string","enum":["CIENCIA","CONFIRMACAO","DESCONHECIMENTO","OPERACAO_NAO_REALIZADA"]},"description":"O que a SEFAZ ainda aceitaria para este documento. Vazia quando não se aplica ou quando já houve manifestação definitiva. Ciência sai da lista depois de registrada; as definitivas permanecem. Sempre vazia fora da NF-e."},"disputeAvailable":{"type":"boolean","description":"CT-e: a organização ainda pode registrar a prestação do serviço em desacordo (POST /v1/fiscal-documents/{id}/dispute). Falso para quem emitiu, para CT-e cancelado, só com cabeçalho ou já contestado. Ser a tomadora é conferido no momento do pedido, pelo XML."}}},"FiscalDocumentEvent":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"eventCode":{"type":"string","example":"210210","description":"tpEvento oficial: da SEFAZ (NF-e, CT-e) ou do Sistema Nacional (NFS-e)."},"eventKind":{"type":"string","enum":["CANCELLATION","MANIFESTATION","CORRECTION","OTHER"]},"eventName":{"type":"string","example":"CIENCIA","description":"Nome estável do evento; OUTRO quando o código não está no catálogo."},"sequence":{"type":"integer","description":"nSeqEvento."},"direction":{"type":"string","enum":["RECEIVED","SENT"],"description":"RECEIVED: distribuído pela SEFAZ ou pelo ADN. SENT: registrado por nós em nome da organização."},"protocol":{"type":["string","null"]},"authorDocument":{"type":["string","null"]},"occurredAt":{"type":"string","format":"date-time"},"payload":{"type":"object","additionalProperties":true}}},"FiscalDocumentEventList":{"type":"object","properties":{"items":{"type":"array","items":{"$ref":"#/components/schemas/FiscalDocumentEvent"}}}},"ManifestationResult":{"type":"object","properties":{"documentId":{"type":"string","format":"uuid"},"type":{"type":"string","enum":["CIENCIA","CONFIRMACAO","DESCONHECIMENTO","OPERACAO_NAO_REALIZADA"]},"state":{"type":"string","enum":["NOT_APPLICABLE","PENDING","ACKNOWLEDGED","CONFIRMED","DENIED","NOT_PERFORMED","DISPUTED"]},"protocol":{"type":["string","null"]},"alreadyRegistered":{"type":"boolean","description":"A SEFAZ já tinha este evento registrado; o resultado prático é o mesmo de sucesso."}}},"CteDisputeResult":{"type":"object","properties":{"documentId":{"type":"string","format":"uuid"},"state":{"type":"string","enum":["DISPUTED"]},"protocol":{"type":["string","null"],"description":"nProt do evento na SEFAZ autorizadora."}}},"ManifestationSettings":{"type":"object","properties":{"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"documentType":{"type":"string","enum":["NFE"]},"mode":{"type":"string","enum":["MANUAL","AUTO_CIENCIA"],"description":"MANUAL (padrão de fábrica): nada é manifestado sem chamada explícita. AUTO_CIENCIA: a plataforma registra a ciência da operação sozinha — e só ela. Confirmação, desconhecimento e operação não realizada nunca são automáticos, em nenhum modo."},"autoDelaySeconds":{"type":"integer","description":"Espera antes da ciência automática, para dar tempo de decidir por desconhecimento."},"updatedAt":{"type":["string","null"],"format":"date-time"}}},"ManifestationSettingsList":{"type":"object","properties":{"items":{"type":"array","items":{"$ref":"#/components/schemas/ManifestationSettings"}}}},"FiscalDocumentPage":{"type":"object","properties":{"items":{"type":"array","items":{"$ref":"#/components/schemas/FiscalDocument"}},"limit":{"type":"integer"},"offset":{"type":"integer"},"hasMore":{"type":"boolean"},"total":{"type":"integer","description":"Documentos no recorte inteiro, não só na página."},"totalServiceAmount":{"type":["string","null"],"example":"12500.00","description":"Soma de serviceAmount no recorte inteiro. Nulo — e não \"0.00\" — quando nenhum documento do recorte tem valor resumido."},"totalAmount":{"type":["string","null"],"example":"12500.00","description":"Soma equivalente sobre amount, o valor comparável entre os três tipos de documento."}}},"FiscalFileDownload":{"type":"object","properties":{"url":{"type":"string","format":"uri","description":"URL temporária. Gere na hora de entregar o arquivo, não com antecedência."},"expiresAt":{"type":"string","format":"date-time"},"mimeType":{"type":"string","example":"application/pdf"},"sha256":{"type":"string","description":"Hash do conteúdo armazenado, para conferir o download."}}},"FiscalFileDownloadLogEntry":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"occurredAt":{"type":"string","format":"date-time"},"documentId":{"type":"string","format":"uuid"},"documentType":{"type":"string","enum":["NFSE","NFE","CTE"]},"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"documentNumber":{"type":["string","null"]},"accessKey":{"type":["string","null"]},"issuerName":{"type":["string","null"]},"customerName":{"type":["string","null"]},"format":{"type":"string","enum":["PDF","XML"]},"batch":{"type":"boolean","description":"true quando veio de POST /v1/fiscal-documents/batch-download — um evento por arquivo entregue."},"actor":{"type":["object","null"],"description":"Nulo só no caso patológico de a credencial, o usuário ou o app conectado terem sido removidos depois da baixa.","properties":{"kind":{"type":"string","enum":["USER","API_CREDENTIAL","OAUTH_CLIENT"]},"name":{"type":"string"},"email":{"type":"string","description":"Só presente quando kind é USER."}}}}},"FiscalFileDownloadLogPage":{"type":"object","properties":{"items":{"type":"array","items":{"$ref":"#/components/schemas/FiscalFileDownloadLogEntry"}},"limit":{"type":"integer"},"offset":{"type":"integer"},"hasMore":{"type":"boolean"}}},"FiscalBatchDownloadRequest":{"type":"object","additionalProperties":false,"required":["documentIds"],"properties":{"documentIds":{"type":"array","minItems":1,"maxItems":100,"items":{"type":"string","format":"uuid"},"description":"Ids de GET /v1/fiscal-documents. Repetições são ignoradas."},"formats":{"type":"array","minItems":1,"maxItems":2,"items":{"type":"string","enum":["PDF","XML"]},"description":"Padrão: os dois."},"delivery":{"type":"string","enum":["LINKS","ZIP"],"default":"ZIP","description":"LINKS devolve uma URL assinada por arquivo, no envelope JSON, e aceita no máximo 10 documentos. ZIP devolve o arquivo compactado no corpo da resposta (application/zip), com os arquivos em pastas pdf/ e xml/."}}},"FiscalBatchDownloadSkip":{"type":"object","properties":{"documentId":{"type":"string","format":"uuid"},"format":{"type":["string","null"],"enum":["PDF","XML",null]},"reason":{"type":"string","enum":["DOCUMENT_NOT_FOUND","CONTENT_SUMMARY_ONLY","FILE_NOT_FOUND","FILE_TOO_LARGE","FILE_UNREADABLE"],"description":"DOCUMENT_NOT_FOUND e CONTENT_SUMMARY_ONLY excluem o documento inteiro (format nulo); os demais dizem respeito a um formato só, então o outro pode ter sido entregue. FILE_TOO_LARGE só ocorre em delivery ZIP."}}},"FiscalBatchDownloadSkipSummary":{"type":"object","properties":{"total":{"type":"integer","description":"Documentos distintos que ficaram de fora."},"byReason":{"type":"object","additionalProperties":{"type":"integer"},"example":{"CONTENT_SUMMARY_ONLY":2,"FILE_NOT_FOUND":1}}}},"FiscalBatchDownloadLinks":{"type":"object","properties":{"delivery":{"const":"LINKS"},"files":{"type":"array","items":{"type":"object","properties":{"documentId":{"type":"string","format":"uuid"},"format":{"type":"string","enum":["PDF","XML"]},"filename":{"type":"string","example":"NFSE-000123-35240712345678000199550010000001231000001234.xml"},"url":{"type":"string","format":"uri"},"mimeType":{"type":"string","example":"application/xml"},"sha256":{"type":"string"},"sizeBytes":{"type":"integer"}}}},"skipped":{"type":"array","items":{"$ref":"#/components/schemas/FiscalBatchDownloadSkip"}},"expiresAt":{"type":"string","format":"date-time"}}},"InboundMonitorStatus":{"type":"object","properties":{"companyId":{"type":"string","format":"uuid","description":"Empresa dona deste cursor — NSU é sequência por CNPJ consultante no SEFAZ/ADN, não da organização."},"companyLabel":{"type":["string","null"],"description":"Só preenchido por GET /v1/inbound-monitor sem companyId (a listagem de todas as empresas); nulo nas respostas de escrita."},"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"documentType":{"type":"string","enum":["NFSE","NFE","CTE"]},"status":{"type":"string","enum":["ACTIVE","PAUSED"]},"lastNsu":{"type":"string","description":"Último NSU consultado no provedor; é de onde a próxima varredura continua."},"maxNsu":{"type":["string","null"],"description":"Último NSU que existe no provedor. lastNsu < maxNsu significa que ainda há backlog. Nulo em NFS-e: o ADN não informa o total."},"pollIntervalSeconds":{"type":"integer"},"consecutiveFailures":{"type":"integer"},"nextPollAt":{"type":"string","format":"date-time"},"lastPolledAt":{"type":["string","null"],"format":"date-time"},"pausedByFailures":{"type":"boolean","description":"PAUSED por falhas consecutivas do provedor (circuit breaker), não por outra razão."},"waitingForBalanceSince":{"type":["string","null"],"format":"date-time","description":"Desde quando a recepção está parada num documento que precisa ser pago, com a carteira sem saldo. Não conta como falha nem pausa: volta sozinha quando entra crédito na carteira."},"unsupportedDocumentCount":{"type":"integer","description":"DF-e pulados por não estarem no formato de NFS-e autorizada reconhecido (ex.: evento de cancelamento). Não conta como falha do ADN."},"lastUnsupportedNsu":{"type":["string","null"]},"lastUnsupportedAt":{"type":["string","null"],"format":"date-time"},"startingPoint":{"type":["string","null"],"enum":["FROM_NOW","LAST_7_DAYS","LAST_30_DAYS","LAST_90_DAYS","FROM_ZERO",null],"description":"A escolha feita ao ligar a recepção (NF-e/CT-e) ou salvar a Configuração fiscal (NFS-e)."},"receiveFromAt":{"type":["string","null"],"format":"date-time","description":"Documento com data de emissão anterior a este instante é descartado, sem gravar e sem cobrar."},"skippedBeforeCutoffCount":{"type":"integer","description":"Quantos documentos foram descartados por receiveFromAt — histórico fora do corte escolhido."},"lastSkippedBeforeCutoffNsu":{"type":["string","null"]},"lastSkippedBeforeCutoffAt":{"type":["string","null"],"format":"date-time"},"lastFailure":{"type":["object","null"],"description":"Última falha da consulta ao provedor. Continua preenchida depois de retomar e só some na próxima consulta bem-sucedida.","properties":{"message":{"type":"string","description":"Mensagem técnica da falha, com a causa encadeada quando houver."},"at":{"type":"string","format":"date-time"}}}}},"InboundReceptionSettings":{"type":"object","properties":{"companyId":{"type":"string","format":"uuid","description":"Empresa dona deste cursor — NSU é sequência por CNPJ consultante no SEFAZ, não da organização."},"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"documentType":{"type":"string","enum":["NFE","CTE"]},"status":{"type":"string","enum":["ACTIVE","PAUSED"]},"startingPoint":{"type":["string","null"],"enum":["FROM_NOW","LAST_7_DAYS","LAST_30_DAYS","LAST_90_DAYS","FROM_ZERO",null],"description":"A escolha feita ao ligar a recepção. Só tem efeito na criação do cursor."},"initialSyncMode":{"type":"string","enum":["FROM_NOW","FROM_ZERO"]},"initialSyncCompletedAt":{"type":["string","null"],"format":"date-time"},"receiveFromAt":{"type":["string","null"],"format":"date-time","description":"Documento com data de emissão anterior a este instante é descartado, sem gravar e sem cobrar. Nulo em FROM_ZERO."},"lastNsu":{"type":"string"},"maxNsu":{"type":["string","null"]}}},"CreateApiCredentialRequest":{"type":"object","additionalProperties":false,"required":["name","scopes"],"properties":{"name":{"type":"string","minLength":1,"maxLength":100},"scopes":{"type":"array","minItems":1,"uniqueItems":true,"items":{"type":"string","enum":["approvals:manage","billing:adjust","billing:read","billing:recharge","certificates:read","certificates:request-upload","certificates:write","dps-numbering:manage","fiscal-document:download","fiscal-document:manifest","fiscal-document:read","fiscal-settings:manage","nfse:cancel","nfse:issue","nfse:read","nfse:validate","notifications:manage","notifications:read","organization:manage","service-catalog:read","service-catalog:write","webhook:manage"]}},"expiresAt":{"type":"string","format":"date-time"},"allowProduction":{"type":"boolean","description":"Sem isto a chave nasce restrita a HOMOLOGATION. Criada por outra chave, só vale se a criadora já tem produção (e herda os ambientes dela). Criada no console, exige `password` (e `mfaCode`, com MFA)."},"password":{"type":"string","description":"Senha pessoal de quem está no console — só quando libera produção. Nunca é gravada."},"mfaCode":{"type":"string","description":"Código do autenticador, quando a conta tem MFA e a operação libera produção."}}},"ApiCredentialMetadata":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"name":{"type":"string"},"prefix":{"type":"string"},"scopes":{"type":"array","items":{"type":"string","enum":["approvals:manage","billing:adjust","billing:read","billing:recharge","certificates:read","certificates:request-upload","certificates:write","dps-numbering:manage","fiscal-document:download","fiscal-document:manifest","fiscal-document:read","fiscal-settings:manage","nfse:cancel","nfse:issue","nfse:read","nfse:validate","notifications:manage","notifications:read","organization:manage","service-catalog:read","service-catalog:write","webhook:manage"]}},"status":{"type":"string","enum":["ACTIVE","REVOKED"]},"policy":{"$ref":"#/components/schemas/CredentialPolicyRequest"},"expiresAt":{"type":["string","null"],"format":"date-time"},"lastUsedAt":{"type":["string","null"],"format":"date-time"},"createdAt":{"type":"string","format":"date-time"},"revokedAt":{"type":["string","null"],"format":"date-time"}}},"CredentialPolicyRequest":{"type":"object","additionalProperties":false,"properties":{"allowedEnvironments":{"type":"array","minItems":1,"items":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]}},"allowedIssuerDocuments":{"type":"array","minItems":1,"items":{"type":"string","pattern":"^(\\d{11}|\\d{14})$"}},"maxDocumentValueCents":{"type":"integer","minimum":0},"approvalRequiredAboveCents":{"type":"integer","minimum":0},"allowedRecipientDocuments":{"type":"array","minItems":1,"items":{"type":"string","pattern":"^(\\d{11}|\\d{14})$"}},"maxMonthlyIssuances":{"type":"integer","minimum":1},"maxMonthlyAmountCents":{"type":"integer","minimum":0},"dailyEventLimit":{"type":"integer","minimum":1},"monthlyEventLimit":{"type":"integer","minimum":1},"dailyBudgetCents":{"type":"integer","minimum":0},"monthlyBudgetCents":{"type":"integer","minimum":0}}},"AuthorizationRequestBody":{"type":"object","additionalProperties":false,"required":["clientId","scopes","redirectUri","codeChallenge","codeChallengeMethod"],"properties":{"clientId":{"type":"string","example":"chatgpt-production"},"clientSecret":{"type":"string","description":"Obrigatório para cliente confidencial."},"scopes":{"type":"array","minItems":1,"uniqueItems":true,"items":{"type":"string","enum":["approvals:manage","billing:adjust","billing:read","billing:recharge","certificates:read","certificates:request-upload","certificates:write","dps-numbering:manage","fiscal-document:download","fiscal-document:manifest","fiscal-document:read","fiscal-settings:manage","nfse:cancel","nfse:issue","nfse:read","nfse:validate","notifications:manage","notifications:read","organization:manage","service-catalog:read","service-catalog:write","webhook:manage"]}},"redirectUri":{"type":"string","format":"uri","description":"Precisa constar exatamente na lista registrada do cliente — sem wildcard nem prefixo."},"codeChallenge":{"type":"string","minLength":43,"maxLength":128,"description":"base64url(sha256(code_verifier))."},"codeChallengeMethod":{"const":"S256"},"state":{"type":"string","maxLength":512,"description":"Devolvido intacto no redirect; valide no retorno."},"resource":{"type":"string","format":"uri","description":"RFC 8707. Só há um recurso — esta própria API; outro valor é recusado (400 INVALID_TARGET)."}}},"DeviceAuthorizationRequestBody":{"type":"object","additionalProperties":false,"required":["clientId","scopes"],"properties":{"clientId":{"type":"string"},"clientSecret":{"type":"string"},"scopes":{"type":"array","minItems":1,"uniqueItems":true,"items":{"type":"string","enum":["approvals:manage","billing:adjust","billing:read","billing:recharge","certificates:read","certificates:request-upload","certificates:write","dps-numbering:manage","fiscal-document:download","fiscal-document:manifest","fiscal-document:read","fiscal-settings:manage","nfse:cancel","nfse:issue","nfse:read","nfse:validate","notifications:manage","notifications:read","organization:manage","service-catalog:read","service-catalog:write","webhook:manage"]}},"resource":{"type":"string","format":"uri","description":"RFC 8707. Só há um recurso — esta própria API; outro valor é recusado (400 INVALID_TARGET)."}}},"DeviceAuthorizationResponse":{"type":"object","required":["device_code","user_code","verification_uri","expires_in","interval"],"properties":{"device_code":{"type":"string","description":"Fica no backend do conector; nunca mostre ao usuário."},"user_code":{"type":"string","example":"K7QM-3XW9","description":"O único valor a exibir no chat."},"verification_uri":{"type":"string","format":"uri"},"verification_uri_complete":{"type":"string","format":"uri"},"expires_in":{"type":"integer"},"interval":{"type":"integer","description":"Segundos mínimos entre chamadas de polling."}}},"TokenRequestBody":{"type":"object","required":["grant_type","client_id"],"properties":{"grant_type":{"type":"string","enum":["authorization_code","urn:ietf:params:oauth:grant-type:device_code","refresh_token"]},"client_id":{"type":"string"},"client_secret":{"type":"string"},"code":{"type":"string","description":"grant_type=authorization_code."},"code_verifier":{"type":"string","minLength":43,"maxLength":128,"description":"grant_type=authorization_code."},"redirect_uri":{"type":"string","description":"grant_type=authorization_code; precisa bater com o da solicitação."},"device_code":{"type":"string","description":"grant_type=device_code."},"refresh_token":{"type":"string","description":"grant_type=refresh_token."},"resource":{"type":"string","format":"uri","description":"RFC 8707. Só há um recurso — esta própria API; outro valor é recusado (invalid_target)."}}},"TokenResponse":{"type":"object","required":["access_token","token_type","expires_in"],"properties":{"access_token":{"type":"string","description":"Use em Authorization: Bearer. Nunca exiba ao usuário."},"refresh_token":{"type":"string","description":"Rotacionado a cada uso; guarde apenas no backend."},"token_type":{"const":"Bearer"},"expires_in":{"type":"integer"},"scope":{"type":"string","description":"Escopos concedidos, separados por espaço."}}},"OAuthErrorResponse":{"type":"object","required":["error"],"properties":{"error":{"type":"string","enum":["invalid_request","invalid_client","invalid_grant","unsupported_grant_type","authorization_pending","slow_down","access_denied","expired_token","invalid_target"]},"error_description":{"type":"string"}}},"RevokeTokenRequest":{"type":"object","additionalProperties":false,"required":["client_id","token"],"properties":{"client_id":{"type":"string"},"client_secret":{"type":"string"},"token":{"type":"string","description":"Access token ou refresh token."}}},"UsageAlertSettingRequest":{"type":"object","additionalProperties":false,"required":["eventType","thresholdsPercent"],"properties":{"eventType":{"type":"string","example":"NFSE_EMISSION_REQUEST"},"thresholdsPercent":{"type":"array","minItems":1,"maxItems":10,"items":{"type":"integer","minimum":1,"maximum":100},"example":[80,90,100]}}},"ApprovalDecisionRequest":{"type":"object","additionalProperties":false,"required":["decision"],"properties":{"decision":{"type":"string","enum":["APPROVED","REJECTED"]},"reason":{"type":"string","minLength":1,"maxLength":500}}},"UsageRefundRequest":{"type":"object","additionalProperties":false,"required":["reason"],"properties":{"reason":{"type":"string","minLength":1,"maxLength":500}}},"CreateServiceCatalogEntryRequest":{"type":"object","additionalProperties":false,"required":["code","nationalTaxCode","description","municipalTax"],"properties":{"code":{"type":"string","pattern":"^[a-z0-9][a-z0-9-]{0,59}$","description":"Apelido curto e único usado como serviceCode em POST /v1/nfse/issue e /validate.","example":"consultoria"},"nationalTaxCode":{"type":"string","pattern":"^\\d{6}$","description":"Código de tributação nacional"},"municipalTaxCode":{"type":"string","minLength":1,"maxLength":20},"nbsCode":{"type":"string","pattern":"^\\d{9}$"},"description":{"type":"string","minLength":3,"maxLength":2000},"municipalTax":{"type":"object","additionalProperties":false,"required":["taxation","withholding"],"properties":{"taxation":{"type":"string","enum":["1","2","3","4"],"description":"Tributação do ISSQN: 1 = Operação Tributável, 2 = Imune, 3 = Exportação, 4 = Não Incidência."},"withholding":{"type":"string","enum":["1","2","3"],"description":"Retenção do ISSQN: 1 = Não Retido, 2 = Retido pelo Tomador, 3 = Retido pelo Intermediário."},"rate":{"type":"string","pattern":"^(?:[0-4]\\.\\d{2}|5\\.00)$","example":"5.00","description":"Alíquota do ISS no município de incidência, de 0.00 a 5.00 — o máximo legal é 5% (LC 116/2003, art. 8º, II). Não confundir com a alíquota efetiva do Simples Nacional (fiscal-settings.issuerTaxSettings.simpleNationalAliquotPercent), que costuma ser maior. Uma alíquota acima do teto — inclusive a herdada de um serviceCode gravado antes desta regra — devolve 422 (ISSQN_RATE_ABOVE_LEGAL_LIMIT) antes de qualquer cobrança. Para prestador ME/EPP do Simples Nacional apurando o ISSQN pelo Simples, SEM retenção (withholding = \"1\"), em município ativo no Sistema Nacional NFS-e, o campo é REMOVIDO da DPS automaticamente: informá-lo é rejeitado pela Sefin com E0625, porque o município parametriza a alíquota e o ISS é recolhido no DAS. Havendo retenção, a alíquota é enviada e é ela que determina o valor retido. Município não integrado sem alíquota configurada devolve 422 (ISSQN_RATE_REQUIRED)."}}}}},"UpdateServiceCatalogEntryRequest":{"type":"object","additionalProperties":false,"description":"Ao menos um campo deve ser informado. code não é editável.","properties":{"nationalTaxCode":{"type":"string","pattern":"^\\d{6}$","description":"Código de tributação nacional"},"municipalTaxCode":{"type":"string","minLength":1,"maxLength":20},"nbsCode":{"type":"string","pattern":"^\\d{9}$"},"description":{"type":"string","minLength":3,"maxLength":2000},"municipalTax":{"type":"object","additionalProperties":false,"required":["taxation","withholding"],"properties":{"taxation":{"type":"string","enum":["1","2","3","4"],"description":"Tributação do ISSQN: 1 = Operação Tributável, 2 = Imune, 3 = Exportação, 4 = Não Incidência."},"withholding":{"type":"string","enum":["1","2","3"],"description":"Retenção do ISSQN: 1 = Não Retido, 2 = Retido pelo Tomador, 3 = Retido pelo Intermediário."},"rate":{"type":"string","pattern":"^(?:[0-4]\\.\\d{2}|5\\.00)$","example":"5.00","description":"Alíquota do ISS no município de incidência, de 0.00 a 5.00 — o máximo legal é 5% (LC 116/2003, art. 8º, II). Não confundir com a alíquota efetiva do Simples Nacional (fiscal-settings.issuerTaxSettings.simpleNationalAliquotPercent), que costuma ser maior. Uma alíquota acima do teto — inclusive a herdada de um serviceCode gravado antes desta regra — devolve 422 (ISSQN_RATE_ABOVE_LEGAL_LIMIT) antes de qualquer cobrança. Para prestador ME/EPP do Simples Nacional apurando o ISSQN pelo Simples, SEM retenção (withholding = \"1\"), em município ativo no Sistema Nacional NFS-e, o campo é REMOVIDO da DPS automaticamente: informá-lo é rejeitado pela Sefin com E0625, porque o município parametriza a alíquota e o ISS é recolhido no DAS. Havendo retenção, a alíquota é enviada e é ela que determina o valor retido. Município não integrado sem alíquota configurada devolve 422 (ISSQN_RATE_REQUIRED)."}}}}},"WebhookEndpoint":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"name":{"type":"string"},"url":{"type":"string","format":"uri"},"events":{"type":"array","items":{"type":"string"}},"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"status":{"type":"string","enum":["ACTIVE","INACTIVE","REVOKED"]},"timeoutMs":{"type":"integer"},"maxAttempts":{"type":"integer"},"createdAt":{"type":"string","format":"date-time"}}},"WebhookDelivery":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"event":{"type":"string","example":"fiscal_document.available"},"endpointName":{"type":"string"},"status":{"type":"string","example":"DELIVERED"},"attemptCount":{"type":"integer"},"manualResendCount":{"type":"integer"},"lastHttpStatus":{"type":["integer","null"]},"lastLatencyMs":{"type":["integer","null"]},"createdAt":{"type":"string","format":"date-time"}}},"WebhookDeliveryAttempt":{"type":"object","properties":{"attemptNumber":{"type":"integer"},"outcome":{"type":"string"},"httpStatus":{"type":["integer","null"]},"latencyMs":{"type":["integer","null"]},"responseSummary":{"type":["string","null"],"description":"Trecho da resposta do endpoint, truncado."},"errorMessage":{"type":["string","null"]},"attemptedAt":{"type":"string","format":"date-time"}}},"ApprovalRequest":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"organizationId":{"type":"string","format":"uuid"},"credentialId":{"type":["string","null"],"format":"uuid"},"kind":{"type":"string","enum":["NFSE_ISSUE","NFSE_CANCEL"]},"status":{"type":"string","enum":["PENDING","APPROVED","REJECTED","EXPIRED"]},"reasonCodes":{"type":"array","items":{"type":"string"},"description":"Regras de guardrail que retiveram a operação."},"environment":{"type":["string","null"],"enum":["HOMOLOGATION","PRODUCTION",null],"description":"Nulo em NFSE_CANCEL: o ambiente vem da NFS-e alvo, resolvido só na aprovação."},"requestPayload":{"type":"object"},"targetOperationId":{"type":["string","null"],"format":"uuid"},"resultingOperationId":{"type":["string","null"],"format":"uuid","description":"A operação criada pela aprovação — é por ela que se acompanha a emissão daí em diante."},"decidedByCredentialId":{"type":["string","null"],"format":"uuid"},"decidedAt":{"type":["string","null"],"format":"date-time"},"decisionReason":{"type":["string","null"]},"expiresAt":{"type":"string","format":"date-time"},"createdAt":{"type":"string","format":"date-time"}}},"UsageAlertSetting":{"type":"object","properties":{"eventType":{"type":"string"},"thresholdsPercent":{"type":"array","items":{"type":"integer"}},"isDefault":{"type":"boolean","description":"true quando a organização não configurou e vale o padrão 80/90/100."}}},"FiscalSettingsSnapshot":{"type":["object","null"],"description":"Nulo quando o ambiente ainda não foi configurado — o que aparece como pendência CRITICAL em GET /v1/organization/pending.","properties":{"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"municipalityCode":{"type":["string","null"],"pattern":"^\\d{7}$","description":"Já resolvido: o próprio da configuração fiscal quando há um, senão o da empresa. Nulo só quando nem a empresa tem endereço."},"municipalityInheritedFromCompany":{"type":"boolean","description":"true quando o município acima veio da empresa, por não haver um próprio na configuração fiscal."},"defaultIssqnTaxation":{"type":["string","null"],"enum":["1","2","3","4",null]},"defaultIssqnWithholding":{"type":["string","null"],"enum":["1","2","3",null]},"issuerTaxSettings":{"type":"object","description":"Regime tributário do emitente, como gravado — pode vir vazio se a configuração estiver pela metade."},"dpsSeries":{"type":["string","null"],"pattern":"^\\d{1,5}$","description":"Série default de DPS (a série marcada is_default para a empresa/ambiente). Nula sem certificado de emissão vinculado ao ambiente."},"municipalRegistration":{"type":["string","null"],"pattern":"^\\d{1,15}$","description":"Inscrição municipal do emitente (da empresa). Nula quando o emitente não tem IM — município sem cadastro complementar no CNC NFS-e; limpe-a em PATCH /v1/organization/fiscal-settings/emitter."}}},"ConnectedIntegration":{"type":"object","description":"Um assistente ou aplicação de terceiro que a organização autorizou (RFC-015).","properties":{"id":{"type":"string","format":"uuid"},"clientId":{"type":"string"},"clientDisplayName":{"type":"string"},"scopes":{"type":"array","items":{"type":"string"}},"credentialId":{"type":"string","format":"uuid"},"authorizedBy":{"type":["object","null"],"description":"A pessoa que consentiu. Nulo quando o usuário de console foi removido depois.","properties":{"id":{"type":"string","format":"uuid"},"fullName":{"type":"string"},"email":{"type":"string","format":"email"}}},"environments":{"type":"array","items":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]}},"requireApprovalForAllIssuances":{"type":"boolean","description":"Toda emissão vira pedido de aprovação no console. Desligado por padrão; o dono liga em Aplicações conectadas."},"approvalRequiredAboveCents":{"type":["integer","null"],"description":"Emissões acima deste valor viram pedido de aprovação mesmo com o modo acima desligado."},"monthlyEventLimit":{"type":["integer","null"]},"monthlyBudgetCents":{"type":["integer","null"]},"createdAt":{"type":"string","format":"date-time"},"lastUsedAt":{"type":["string","null"],"format":"date-time"}}},"OrganizationCreated":{"type":"object","properties":{"organization":{"type":"object"},"apiKey":{"type":["object","null"],"properties":{"id":{"type":"string","format":"uuid"},"prefix":{"type":"string"},"secret":{"type":"string","description":"Mostrado uma única vez."},"scopes":{"type":"array","items":{"type":"string"}},"warning":{"type":"string"}}},"owner":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"fullName":{"type":"string"},"email":{"type":"string","format":"email"},"role":{"const":"OWNER"},"activationEmailSent":{"type":"boolean"},"activationToken":{"type":["string","null"],"description":"Preenchido só quando não há servidor de e-mail configurado."},"activationTokenExpiresAt":{"type":["string","null"],"format":"date-time"},"warning":{"type":"string"}}}}},"ServiceCatalogEntry":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"code":{"type":"string","pattern":"^[a-z0-9][a-z0-9-]{0,59}$","description":"Apelido curto e único usado como serviceCode em POST /v1/nfse/issue e /validate.","example":"consultoria"},"nationalTaxCode":{"type":"string"},"municipalTaxCode":{"type":["string","null"]},"nbsCode":{"type":["string","null"]},"description":{"type":"string"},"municipalTax":{"type":"object","additionalProperties":false,"required":["taxation","withholding"],"properties":{"taxation":{"type":"string","enum":["1","2","3","4"],"description":"Tributação do ISSQN: 1 = Operação Tributável, 2 = Imune, 3 = Exportação, 4 = Não Incidência."},"withholding":{"type":"string","enum":["1","2","3"],"description":"Retenção do ISSQN: 1 = Não Retido, 2 = Retido pelo Tomador, 3 = Retido pelo Intermediário."},"rate":{"type":"string","pattern":"^(?:[0-4]\\.\\d{2}|5\\.00)$","example":"5.00","description":"Alíquota do ISS no município de incidência, de 0.00 a 5.00 — o máximo legal é 5% (LC 116/2003, art. 8º, II). Não confundir com a alíquota efetiva do Simples Nacional (fiscal-settings.issuerTaxSettings.simpleNationalAliquotPercent), que costuma ser maior. Uma alíquota acima do teto — inclusive a herdada de um serviceCode gravado antes desta regra — devolve 422 (ISSQN_RATE_ABOVE_LEGAL_LIMIT) antes de qualquer cobrança. Para prestador ME/EPP do Simples Nacional apurando o ISSQN pelo Simples, SEM retenção (withholding = \"1\"), em município ativo no Sistema Nacional NFS-e, o campo é REMOVIDO da DPS automaticamente: informá-lo é rejeitado pela Sefin com E0625, porque o município parametriza a alíquota e o ISS é recolhido no DAS. Havendo retenção, a alíquota é enviada e é ela que determina o valor retido. Município não integrado sem alíquota configurada devolve 422 (ISSQN_RATE_REQUIRED)."}}},"status":{"type":"string","enum":["ACTIVE","ARCHIVED"]},"createdAt":{"type":"string","format":"date-time"},"updatedAt":{"type":"string","format":"date-time"}}},"CommercialPlan":{"type":"object","properties":{"code":{"type":"string"},"name":{"type":"string"},"currency":{"type":"string","example":"BRL"},"subscriptionFeeCents":{"type":"integer"},"prices":{"type":"object","additionalProperties":{"type":"integer"}},"includedQuota":{"type":"object","additionalProperties":{"type":"integer"}},"features":{"type":"object","additionalProperties":true},"tiers":{"type":"array","items":{"type":"object","properties":{"eventType":{"type":"string"},"startQuantity":{"type":"integer","description":"Primeira unidade do volume mensal coberta pela faixa (a franquia conta na numeração)."},"endQuantity":{"type":["integer","null"],"description":"Última unidade coberta; nulo quando a faixa é aberta."},"unitPriceCents":{"type":"integer"}}}}}},"SubscriptionSummary":{"type":"object","properties":{"planCode":{"type":"string"},"planName":{"type":"string"},"status":{"type":"string","enum":["ACTIVE","SUSPENDED","CANCELLED"]},"subscriptionFeeCents":{"type":"integer"},"includedQuota":{"type":"object","additionalProperties":{"type":"integer"}},"startsAt":{"type":"string","format":"date-time"},"endsAt":{"type":["string","null"],"format":"date-time","description":"Numa assinatura ACTIVE/SUSPENDED, não-nulo significa encerramento agendado para esta data (fim do ciclo pago) — até lá o serviço não muda em nada."},"suspendedAt":{"type":["string","null"],"format":"date-time","description":"Preenchido só enquanto a assinatura está suspensa."},"suspensionReason":{"type":["string","null"],"enum":["UNPAID_SUBSCRIPTION_CHARGE",null]}}},"SubscriptionCancellation":{"type":"object","properties":{"subscription":{"type":"object","properties":{"planCode":{"type":"string"},"planName":{"type":"string"},"status":{"type":"string","enum":["ACTIVE","SUSPENDED","CANCELLED"]},"subscriptionFeeCents":{"type":"integer"},"includedQuota":{"type":"object","additionalProperties":{"type":"integer"}},"startsAt":{"type":"string","format":"date-time"},"endsAt":{"type":["string","null"],"format":"date-time","description":"Numa assinatura ACTIVE/SUSPENDED, não-nulo significa encerramento agendado para esta data (fim do ciclo pago) — até lá o serviço não muda em nada."},"suspendedAt":{"type":["string","null"],"format":"date-time","description":"Preenchido só enquanto a assinatura está suspensa."},"suspensionReason":{"type":["string","null"],"enum":["UNPAID_SUBSCRIPTION_CHARGE",null]}},"description":"A assinatura, ainda corrente: endsAt é quando o serviço para (fim do ciclo pago)."},"outstandingChargeCount":{"type":"integer","description":"Mensalidades que continuam devidas depois do encerramento."},"outstandingChargeCents":{"type":"integer"}}},"SubscriptionCharge":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"periodStart":{"type":"string","format":"date-time"},"dueDate":{"type":"string","format":"date-time","description":"Vencimento da mensalidade; passado dele, a assinatura entra na carência da régua."},"amountCents":{"type":"integer"},"status":{"type":"string","enum":["PENDING","CONFIRMED","CANCELED"]},"paymentInstructions":{"type":"object","description":"invoiceUrl só existe depois que a cobrança foi criada no provedor de pagamento.","properties":{"provider":{"type":"string"},"billingType":{"type":"string"},"invoiceUrl":{"type":"string","format":"uri"}}},"createdAt":{"type":"string","format":"date-time"},"confirmedAt":{"type":["string","null"],"format":"date-time"}}},"ChangePlanRequest":{"type":"object","additionalProperties":false,"required":["planCode"],"properties":{"planCode":{"type":"string","minLength":1,"maxLength":50}}},"AutoRechargePolicy":{"type":"object","properties":{"enabled":{"type":"boolean"},"thresholdCents":{"type":["integer","null"],"description":"Saldo disponível abaixo do qual a recarga dispara."},"rechargeAmountCents":{"type":["integer","null"]},"monthlyLimitCents":{"type":["integer","null"],"description":"Teto de quanto a recarga automática pode gastar no mês calendário."},"cardLastFour":{"type":["string","null"]},"cardBrand":{"type":["string","null"]},"updatedAt":{"type":["string","null"],"format":"date-time"}}},"SaveAutoRechargeCardRequest":{"type":"object","additionalProperties":false,"description":"Dado de cartão vai direto ao gateway de pagamento para tokenização e nunca é persistido pelo Trilha Invoice (só o token, a bandeira e os últimos 4 dígitos retornados).","required":["holderName","number","expiryMonth","expiryYear","ccv","holderEmail","holderCpfCnpj","holderPostalCode","holderAddressNumber","holderPhone"],"properties":{"holderName":{"type":"string","minLength":2,"maxLength":200},"number":{"type":"string","pattern":"^\\d{13,19}$"},"expiryMonth":{"type":"string","pattern":"^(0[1-9]|1[0-2])$"},"expiryYear":{"type":"string","pattern":"^\\d{4}$"},"ccv":{"type":"string","pattern":"^\\d{3,4}$"},"holderEmail":{"type":"string","format":"email","maxLength":254},"holderCpfCnpj":{"type":"string","pattern":"^(\\d{11}|\\d{14})$"},"holderPostalCode":{"type":"string","pattern":"^\\d{8}$"},"holderAddressNumber":{"type":"string","minLength":1,"maxLength":20},"holderPhone":{"type":"string","pattern":"^\\d{10,11}$"}}},"UpdateAutoRechargePolicyRequest":{"type":"object","additionalProperties":false,"required":["enabled","thresholdCents","rechargeAmountCents","monthlyLimitCents"],"description":"monthlyLimitCents deve ser maior ou igual a rechargeAmountCents.","properties":{"enabled":{"type":"boolean"},"thresholdCents":{"type":"integer","minimum":0,"maximum":10000000},"rechargeAmountCents":{"type":"integer","minimum":2000,"maximum":10000000},"monthlyLimitCents":{"type":"integer","minimum":1,"maximum":10000000}}},"WalletTopUpRequest":{"type":"object","properties":{"id":{"type":"string","format":"uuid"},"amountCents":{"type":"integer"},"status":{"type":"string","enum":["PENDING","CONFIRMED","CANCELED"]},"paymentInstructions":{"type":"object","description":"Com gateway de pagamento configurado vem a cobrança Pix (pixCopyPaste/pixQrCodeBase64); sem ele, a instrução estática (pixKey/instructions).","properties":{"provider":{"type":"string"},"billingType":{"type":"string"},"pixCopyPaste":{"type":"string","description":"Payload copia-e-cola do Pix."},"pixQrCodeBase64":{"type":"string","description":"PNG do QR code em base64, sem o prefixo data:."},"expiresAt":{"type":"string","format":"date-time","description":"Quando a cobrança Pix expira."},"pixKey":{"type":["string","null"]},"instructions":{"type":"string"}}},"createdAt":{"type":"string","format":"date-time"},"confirmedAt":{"type":["string","null"],"format":"date-time"}}},"CreateTopUpRequestBody":{"type":"object","additionalProperties":false,"required":["amountCents"],"properties":{"amountCents":{"type":"integer","minimum":2000,"maximum":10000000,"description":"Mínimo R$ 20,00 — abaixo disso, o overhead de confirmação Pix/manual não compensa para nenhum dos lados."}}}}},"webhooks":{"nfse.received":{"post":{"summary":"Pedido de emissão ou cancelamento recebido","description":"A operação foi aceita e entrou na fila. Sai tanto para emissão quanto para cancelamento.","operationId":"webhook_nfse_received","security":[],"parameters":[{"name":"x-trilha-invoice-event-id","in":"header","required":true,"schema":{"type":"string","format":"uuid"}},{"name":"x-trilha-invoice-timestamp","in":"header","required":true,"schema":{"type":"string","pattern":"^\\d+$"},"description":"Segundos desde a época Unix."},{"name":"x-trilha-invoice-signature","in":"header","required":true,"schema":{"type":"string","pattern":"^sha256=[0-9a-f]{64}$"},"description":"HMAC-SHA256 de `<timestamp>.<corpo bruto>` com o segredo do endpoint."}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["eventId","event","environment","organizationId","resourceId","occurredAt","data"],"properties":{"eventId":{"type":"string","format":"uuid"},"event":{"const":"nfse.received"},"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"organizationId":{"type":"string","format":"uuid"},"resourceId":{"type":"string","description":"Id do recurso afetado: a operação (nfse.*), o documento (fiscal_document.*), a mensalidade (billing.charge_created) ou a carteira (billing.low_balance)."},"occurredAt":{"type":"string","format":"date-time"},"data":{"type":"object","required":["operationId","status"],"properties":{"operationId":{"type":"string","format":"uuid"},"status":{"const":"RECEIVED"}}}}}}}},"responses":{"429":{"description":"Nova tentativa mais tarde."},"2XX":{"description":"Entrega confirmada."},"5XX":{"description":"Nova tentativa mais tarde."},"default":{"description":"Qualquer outra resposta encerra a entrega como falha definitiva."}}}},"nfse.processing":{"post":{"summary":"Resultado do envio ainda incerto","description":"O webservice oficial não confirmou o resultado. Não é rejeição: a API reconsulta sozinha, normalmente em um a dois minutos. Não reenvie a emissão.","operationId":"webhook_nfse_processing","security":[],"parameters":[{"name":"x-trilha-invoice-event-id","in":"header","required":true,"schema":{"type":"string","format":"uuid"}},{"name":"x-trilha-invoice-timestamp","in":"header","required":true,"schema":{"type":"string","pattern":"^\\d+$"},"description":"Segundos desde a época Unix."},{"name":"x-trilha-invoice-signature","in":"header","required":true,"schema":{"type":"string","pattern":"^sha256=[0-9a-f]{64}$"},"description":"HMAC-SHA256 de `<timestamp>.<corpo bruto>` com o segredo do endpoint."}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["eventId","event","environment","organizationId","resourceId","occurredAt","data"],"properties":{"eventId":{"type":"string","format":"uuid"},"event":{"const":"nfse.processing"},"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"organizationId":{"type":"string","format":"uuid"},"resourceId":{"type":"string","description":"Id do recurso afetado: a operação (nfse.*), o documento (fiscal_document.*), a mensalidade (billing.charge_created) ou a carteira (billing.low_balance)."},"occurredAt":{"type":"string","format":"date-time"},"data":{"type":"object","required":["operationId","reconciliationRequired"],"properties":{"operationId":{"type":"string","format":"uuid"},"reconciliationRequired":{"const":true}}}}}}}},"responses":{"429":{"description":"Nova tentativa mais tarde."},"2XX":{"description":"Entrega confirmada."},"5XX":{"description":"Nova tentativa mais tarde."},"default":{"description":"Qualquer outra resposta encerra a entrega como falha definitiva."}}}},"nfse.issued":{"post":{"summary":"NFS-e autorizada","description":"A nota foi autorizada. Use `documentId` para baixar PDF e XML em `/v1/fiscal-documents/{id}`.","operationId":"webhook_nfse_issued","security":[],"parameters":[{"name":"x-trilha-invoice-event-id","in":"header","required":true,"schema":{"type":"string","format":"uuid"}},{"name":"x-trilha-invoice-timestamp","in":"header","required":true,"schema":{"type":"string","pattern":"^\\d+$"},"description":"Segundos desde a época Unix."},{"name":"x-trilha-invoice-signature","in":"header","required":true,"schema":{"type":"string","pattern":"^sha256=[0-9a-f]{64}$"},"description":"HMAC-SHA256 de `<timestamp>.<corpo bruto>` com o segredo do endpoint."}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["eventId","event","environment","organizationId","resourceId","occurredAt","data"],"properties":{"eventId":{"type":"string","format":"uuid"},"event":{"const":"nfse.issued"},"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"organizationId":{"type":"string","format":"uuid"},"resourceId":{"type":"string","description":"Id do recurso afetado: a operação (nfse.*), o documento (fiscal_document.*), a mensalidade (billing.charge_created) ou a carteira (billing.low_balance)."},"occurredAt":{"type":"string","format":"date-time"},"data":{"type":"object","required":["operationId","documentId","accessKey"],"properties":{"operationId":{"type":"string","format":"uuid"},"documentId":{"type":"string","format":"uuid"},"accessKey":{"type":"string","description":"Chave de acesso da NFS-e."},"series":{"type":["string","null"],"description":"Série da DPS."},"dpsNumber":{"type":["string","null"],"description":"Número da DPS."},"nfseNumber":{"type":["string","null"],"description":"Número da NFS-e atribuído pelo sistema nacional."}}}}},"example":{"eventId":"0f1c2d3e-4b5a-4c6d-9e8f-7a6b5c4d3e2f","event":"nfse.issued","environment":"HOMOLOGATION","organizationId":"3a9e1f40-2b7c-4d8e-9f10-a1b2c3d4e5f6","resourceId":"7d4c3b2a-1f0e-4d9c-8b7a-6f5e4d3c2b1a","occurredAt":"2026-08-31T14:05:09.000Z","data":{"operationId":"7d4c3b2a-1f0e-4d9c-8b7a-6f5e4d3c2b1a","documentId":"c1d2e3f4-a5b6-4c7d-8e9f-0a1b2c3d4e5f","accessKey":"52087072211222333000181000000000000126080000000017","series":"1","dpsNumber":"17","nfseNumber":"17"}}}}},"responses":{"429":{"description":"Nova tentativa mais tarde."},"2XX":{"description":"Entrega confirmada."},"5XX":{"description":"Nova tentativa mais tarde."},"default":{"description":"Qualquer outra resposta encerra a entrega como falha definitiva."}}}},"nfse.rejected":{"post":{"summary":"NFS-e rejeitada","description":"O webservice oficial rejeitou a emissão. `code` é o primeiro código de rejeição; a lista completa, com descrição, está em `GET /v1/nfse/{id}`. Corrija e use `POST /v1/nfse/{id}/retry`.","operationId":"webhook_nfse_rejected","security":[],"parameters":[{"name":"x-trilha-invoice-event-id","in":"header","required":true,"schema":{"type":"string","format":"uuid"}},{"name":"x-trilha-invoice-timestamp","in":"header","required":true,"schema":{"type":"string","pattern":"^\\d+$"},"description":"Segundos desde a época Unix."},{"name":"x-trilha-invoice-signature","in":"header","required":true,"schema":{"type":"string","pattern":"^sha256=[0-9a-f]{64}$"},"description":"HMAC-SHA256 de `<timestamp>.<corpo bruto>` com o segredo do endpoint."}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["eventId","event","environment","organizationId","resourceId","occurredAt","data"],"properties":{"eventId":{"type":"string","format":"uuid"},"event":{"const":"nfse.rejected"},"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"organizationId":{"type":"string","format":"uuid"},"resourceId":{"type":"string","description":"Id do recurso afetado: a operação (nfse.*), o documento (fiscal_document.*), a mensalidade (billing.charge_created) ou a carteira (billing.low_balance)."},"occurredAt":{"type":"string","format":"date-time"},"data":{"type":"object","required":["operationId","code"],"properties":{"operationId":{"type":"string","format":"uuid"},"code":{"type":"string"}}}}}}}},"responses":{"429":{"description":"Nova tentativa mais tarde."},"2XX":{"description":"Entrega confirmada."},"5XX":{"description":"Nova tentativa mais tarde."},"default":{"description":"Qualquer outra resposta encerra a entrega como falha definitiva."}}}},"nfse.cancelled":{"post":{"summary":"NFS-e cancelada","description":"O cancelamento foi homologado pelo sistema nacional. `source` diz por onde: `API` quando pedido por `POST /v1/nfse/{id}/cancel`; `EXTERNAL` quando feito fora da plataforma (portal nacional, outro emissor) e descoberto pelo monitoramento — nesse caso `operationId` é o da emissão, e sai também `fiscal_document.externally_cancelled`.","operationId":"webhook_nfse_cancelled","security":[],"parameters":[{"name":"x-trilha-invoice-event-id","in":"header","required":true,"schema":{"type":"string","format":"uuid"}},{"name":"x-trilha-invoice-timestamp","in":"header","required":true,"schema":{"type":"string","pattern":"^\\d+$"},"description":"Segundos desde a época Unix."},{"name":"x-trilha-invoice-signature","in":"header","required":true,"schema":{"type":"string","pattern":"^sha256=[0-9a-f]{64}$"},"description":"HMAC-SHA256 de `<timestamp>.<corpo bruto>` com o segredo do endpoint."}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["eventId","event","environment","organizationId","resourceId","occurredAt","data"],"properties":{"eventId":{"type":"string","format":"uuid"},"event":{"const":"nfse.cancelled"},"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"organizationId":{"type":"string","format":"uuid"},"resourceId":{"type":"string","description":"Id do recurso afetado: a operação (nfse.*), o documento (fiscal_document.*), a mensalidade (billing.charge_created) ou a carteira (billing.low_balance)."},"occurredAt":{"type":"string","format":"date-time"},"data":{"type":"object","required":["operationId","documentId","accessKey"],"properties":{"operationId":{"type":"string","format":"uuid"},"documentId":{"type":"string","format":"uuid"},"accessKey":{"type":"string"},"source":{"type":"string","enum":["API","EXTERNAL"]}}}}}}}},"responses":{"429":{"description":"Nova tentativa mais tarde."},"2XX":{"description":"Entrega confirmada."},"5XX":{"description":"Nova tentativa mais tarde."},"default":{"description":"Qualquer outra resposta encerra a entrega como falha definitiva."}}}},"nfse.cancel_rejected":{"post":{"summary":"Cancelamento rejeitado","description":"O sistema nacional recusou o cancelamento. A nota continua válida.","operationId":"webhook_nfse_cancel_rejected","security":[],"parameters":[{"name":"x-trilha-invoice-event-id","in":"header","required":true,"schema":{"type":"string","format":"uuid"}},{"name":"x-trilha-invoice-timestamp","in":"header","required":true,"schema":{"type":"string","pattern":"^\\d+$"},"description":"Segundos desde a época Unix."},{"name":"x-trilha-invoice-signature","in":"header","required":true,"schema":{"type":"string","pattern":"^sha256=[0-9a-f]{64}$"},"description":"HMAC-SHA256 de `<timestamp>.<corpo bruto>` com o segredo do endpoint."}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["eventId","event","environment","organizationId","resourceId","occurredAt","data"],"properties":{"eventId":{"type":"string","format":"uuid"},"event":{"const":"nfse.cancel_rejected"},"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"organizationId":{"type":"string","format":"uuid"},"resourceId":{"type":"string","description":"Id do recurso afetado: a operação (nfse.*), o documento (fiscal_document.*), a mensalidade (billing.charge_created) ou a carteira (billing.low_balance)."},"occurredAt":{"type":"string","format":"date-time"},"data":{"type":"object","required":["operationId","code"],"properties":{"operationId":{"type":"string","format":"uuid"},"code":{"type":"string"}}}}}}}},"responses":{"429":{"description":"Nova tentativa mais tarde."},"2XX":{"description":"Entrega confirmada."},"5XX":{"description":"Nova tentativa mais tarde."},"default":{"description":"Qualquer outra resposta encerra a entrega como falha definitiva."}}}},"fiscal_document.available":{"post":{"summary":"Documento recebido disponível","description":"Chegou um documento em que a organização é tomadora ou destinatária. Não sai para notas emitidas pela própria organização — para essas, use `nfse.issued`. Com `contentLevel` `SUMMARY`, só o cabeçalho está disponível até a manifestação.","operationId":"webhook_fiscal_document_available","security":[],"parameters":[{"name":"x-trilha-invoice-event-id","in":"header","required":true,"schema":{"type":"string","format":"uuid"}},{"name":"x-trilha-invoice-timestamp","in":"header","required":true,"schema":{"type":"string","pattern":"^\\d+$"},"description":"Segundos desde a época Unix."},{"name":"x-trilha-invoice-signature","in":"header","required":true,"schema":{"type":"string","pattern":"^sha256=[0-9a-f]{64}$"},"description":"HMAC-SHA256 de `<timestamp>.<corpo bruto>` com o segredo do endpoint."}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["eventId","event","environment","organizationId","resourceId","occurredAt","data"],"properties":{"eventId":{"type":"string","format":"uuid"},"event":{"const":"fiscal_document.available"},"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"organizationId":{"type":"string","format":"uuid"},"resourceId":{"type":"string","description":"Id do recurso afetado: a operação (nfse.*), o documento (fiscal_document.*), a mensalidade (billing.charge_created) ou a carteira (billing.low_balance)."},"occurredAt":{"type":"string","format":"date-time"},"data":{"type":"object","required":["documentId","origin","accessKey"],"properties":{"documentId":{"type":"string","format":"uuid"},"accessKey":{"type":"string","description":"Chave de acesso do documento."},"documentType":{"type":"string","enum":["NFSE","NFE","CTE"]},"origin":{"const":"RECEIVED"},"contentLevel":{"type":"string","enum":["SUMMARY","FULL"]}}}}}}}},"responses":{"429":{"description":"Nova tentativa mais tarde."},"2XX":{"description":"Entrega confirmada."},"5XX":{"description":"Nova tentativa mais tarde."},"default":{"description":"Qualquer outra resposta encerra a entrega como falha definitiva."}}}},"fiscal_document.content_upgraded":{"post":{"summary":"Documento recebido ganhou conteúdo completo","description":"Um documento que tinha só o cabeçalho passou a ter o XML completo. É o mesmo documento, com o mesmo id.","operationId":"webhook_fiscal_document_content_upgraded","security":[],"parameters":[{"name":"x-trilha-invoice-event-id","in":"header","required":true,"schema":{"type":"string","format":"uuid"}},{"name":"x-trilha-invoice-timestamp","in":"header","required":true,"schema":{"type":"string","pattern":"^\\d+$"},"description":"Segundos desde a época Unix."},{"name":"x-trilha-invoice-signature","in":"header","required":true,"schema":{"type":"string","pattern":"^sha256=[0-9a-f]{64}$"},"description":"HMAC-SHA256 de `<timestamp>.<corpo bruto>` com o segredo do endpoint."}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["eventId","event","environment","organizationId","resourceId","occurredAt","data"],"properties":{"eventId":{"type":"string","format":"uuid"},"event":{"const":"fiscal_document.content_upgraded"},"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"organizationId":{"type":"string","format":"uuid"},"resourceId":{"type":"string","description":"Id do recurso afetado: a operação (nfse.*), o documento (fiscal_document.*), a mensalidade (billing.charge_created) ou a carteira (billing.low_balance)."},"occurredAt":{"type":"string","format":"date-time"},"data":{"type":"object","required":["documentId","contentLevel","accessKey","documentType"],"properties":{"documentId":{"type":"string","format":"uuid"},"accessKey":{"type":"string","description":"Chave de acesso do documento."},"documentType":{"type":"string","enum":["NFSE","NFE","CTE"]},"contentLevel":{"const":"FULL"}}}}}}}},"responses":{"429":{"description":"Nova tentativa mais tarde."},"2XX":{"description":"Entrega confirmada."},"5XX":{"description":"Nova tentativa mais tarde."},"default":{"description":"Qualquer outra resposta encerra a entrega como falha definitiva."}}}},"fiscal_document.externally_cancelled":{"post":{"summary":"Documento cancelado fora da plataforma","description":"Um documento foi cancelado sem passar pela API: com `origin` `RECEIVED`, pelo emitente de uma nota que a organização recebeu; com `ISSUED`, no portal nacional ou em outro emissor, numa NFS-e que a organização emitiu por aqui. Descoberto pelo evento distribuído (ADN, SEFAZ) ou pela checagem periódica no Sistema Nacional. `eventCode` é o tipo de evento que cancelou (101101 cancelamento, 105102 substituição…).","operationId":"webhook_fiscal_document_externally_cancelled","security":[],"parameters":[{"name":"x-trilha-invoice-event-id","in":"header","required":true,"schema":{"type":"string","format":"uuid"}},{"name":"x-trilha-invoice-timestamp","in":"header","required":true,"schema":{"type":"string","pattern":"^\\d+$"},"description":"Segundos desde a época Unix."},{"name":"x-trilha-invoice-signature","in":"header","required":true,"schema":{"type":"string","pattern":"^sha256=[0-9a-f]{64}$"},"description":"HMAC-SHA256 de `<timestamp>.<corpo bruto>` com o segredo do endpoint."}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["eventId","event","environment","organizationId","resourceId","occurredAt","data"],"properties":{"eventId":{"type":"string","format":"uuid"},"event":{"const":"fiscal_document.externally_cancelled"},"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"organizationId":{"type":"string","format":"uuid"},"resourceId":{"type":"string","description":"Id do recurso afetado: a operação (nfse.*), o documento (fiscal_document.*), a mensalidade (billing.charge_created) ou a carteira (billing.low_balance)."},"occurredAt":{"type":"string","format":"date-time"},"data":{"type":"object","required":["documentId","accessKey","origin"],"properties":{"documentId":{"type":"string","format":"uuid"},"accessKey":{"type":"string","description":"Chave de acesso do documento."},"documentType":{"type":"string","enum":["NFSE","NFE","CTE"]},"origin":{"type":"string","enum":["ISSUED","RECEIVED"]},"eventCode":{"type":["string","null"]}}}}}}}},"responses":{"429":{"description":"Nova tentativa mais tarde."},"2XX":{"description":"Entrega confirmada."},"5XX":{"description":"Nova tentativa mais tarde."},"default":{"description":"Qualquer outra resposta encerra a entrega como falha definitiva."}}}},"fiscal_document.event_received":{"post":{"summary":"Evento fiscal recebido","description":"Evento oficial sobre um documento, distribuído pela SEFAZ (NF-e, CT-e) ou pelo ADN (NFS-e): cancelamento, substituição, carta de correção, manifestação ou desacordo feitos por outro sistema. `eventKind` e `eventName` dizem o que ele é sem precisar de tabela de códigos. `documentId` é nulo quando o evento chega antes do documento.","operationId":"webhook_fiscal_document_event_received","security":[],"parameters":[{"name":"x-trilha-invoice-event-id","in":"header","required":true,"schema":{"type":"string","format":"uuid"}},{"name":"x-trilha-invoice-timestamp","in":"header","required":true,"schema":{"type":"string","pattern":"^\\d+$"},"description":"Segundos desde a época Unix."},{"name":"x-trilha-invoice-signature","in":"header","required":true,"schema":{"type":"string","pattern":"^sha256=[0-9a-f]{64}$"},"description":"HMAC-SHA256 de `<timestamp>.<corpo bruto>` com o segredo do endpoint."}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["eventId","event","environment","organizationId","resourceId","occurredAt","data"],"properties":{"eventId":{"type":"string","format":"uuid"},"event":{"const":"fiscal_document.event_received"},"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"organizationId":{"type":"string","format":"uuid"},"resourceId":{"type":"string","description":"Id do recurso afetado: a operação (nfse.*), o documento (fiscal_document.*), a mensalidade (billing.charge_created) ou a carteira (billing.low_balance)."},"occurredAt":{"type":"string","format":"date-time"},"data":{"type":"object","required":["eventId","documentId","accessKey","eventCode"],"properties":{"eventId":{"type":"string","format":"uuid"},"documentId":{"type":["string","null"],"format":"uuid"},"documentType":{"type":"string","enum":["NFSE","NFE","CTE"]},"accessKey":{"type":"string"},"eventCode":{"type":"string","description":"tpEvento oficial (SEFAZ ou Sistema Nacional)."},"eventKind":{"type":"string","enum":["CANCELLATION","MANIFESTATION","CORRECTION","OTHER"]},"eventName":{"type":"string","example":"CANCELAMENTO_POR_SUBSTITUICAO","description":"Nome estável do evento, como CANCELAMENTO, CARTA_CORRECAO, CIENCIA, PRESTACAO_EM_DESACORDO; OUTRO quando o código não está no catálogo."},"sequence":{"type":"integer","minimum":1}}}}}}}},"responses":{"429":{"description":"Nova tentativa mais tarde."},"2XX":{"description":"Entrega confirmada."},"5XX":{"description":"Nova tentativa mais tarde."},"default":{"description":"Qualquer outra resposta encerra a entrega como falha definitiva."}}}},"fiscal_document.manifestation_registered":{"post":{"summary":"Manifestação registrada","description":"A SEFAZ registrou uma manifestação sobre o documento. Na NF-e, a do destinatário — feita pela API, automaticamente pela regra configurada (`source` `PLATFORM`) ou em outro sistema e distribuída como evento (`EXTERNAL`). No CT-e, a prestação do serviço em desacordo registrada pelo tomador — pela API (`POST /v1/fiscal-documents/{id}/dispute`, `PLATFORM`) ou em outro sistema (`EXTERNAL`) — e o cancelamento dela (`EXTERNAL`). `state` é o estado em que o documento ficou.","operationId":"webhook_fiscal_document_manifestation_registered","security":[],"parameters":[{"name":"x-trilha-invoice-event-id","in":"header","required":true,"schema":{"type":"string","format":"uuid"}},{"name":"x-trilha-invoice-timestamp","in":"header","required":true,"schema":{"type":"string","pattern":"^\\d+$"},"description":"Segundos desde a época Unix."},{"name":"x-trilha-invoice-signature","in":"header","required":true,"schema":{"type":"string","pattern":"^sha256=[0-9a-f]{64}$"},"description":"HMAC-SHA256 de `<timestamp>.<corpo bruto>` com o segredo do endpoint."}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["eventId","event","environment","organizationId","resourceId","occurredAt","data"],"properties":{"eventId":{"type":"string","format":"uuid"},"event":{"const":"fiscal_document.manifestation_registered"},"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"organizationId":{"type":"string","format":"uuid"},"resourceId":{"type":"string","description":"Id do recurso afetado: a operação (nfse.*), o documento (fiscal_document.*), a mensalidade (billing.charge_created) ou a carteira (billing.low_balance)."},"occurredAt":{"type":"string","format":"date-time"},"data":{"type":"object","required":["documentId","accessKey","type","protocol","automatic"],"properties":{"documentId":{"type":"string","format":"uuid"},"accessKey":{"type":"string","description":"Chave de acesso do documento."},"documentType":{"type":"string","enum":["NFSE","NFE","CTE"]},"type":{"type":"string","enum":["CIENCIA","CONFIRMACAO","DESCONHECIMENTO","OPERACAO_NAO_REALIZADA","PRESTACAO_EM_DESACORDO","CANCELAMENTO_PRESTACAO_EM_DESACORDO"]},"eventCode":{"type":"string"},"protocol":{"type":["string","null"]},"state":{"type":"string","enum":["ACKNOWLEDGED","CONFIRMED","DENIED","NOT_PERFORMED","DISPUTED","NOT_APPLICABLE"]},"automatic":{"type":"boolean"},"source":{"type":"string","enum":["PLATFORM","EXTERNAL"]}}}}}}}},"responses":{"429":{"description":"Nova tentativa mais tarde."},"2XX":{"description":"Entrega confirmada."},"5XX":{"description":"Nova tentativa mais tarde."},"default":{"description":"Qualquer outra resposta encerra a entrega como falha definitiva."}}}},"billing.charge_created":{"post":{"summary":"Mensalidade gerada","description":"A mensalidade do mês foi gerada. O link de pagamento é criado logo em seguida e fica em `GET /v1/subscription/charges`. A assinatura não pertence a um ambiente fiscal: o evento vai para os endpoints cadastrados em `PRODUCTION`.","operationId":"webhook_billing_charge_created","security":[],"parameters":[{"name":"x-trilha-invoice-event-id","in":"header","required":true,"schema":{"type":"string","format":"uuid"}},{"name":"x-trilha-invoice-timestamp","in":"header","required":true,"schema":{"type":"string","pattern":"^\\d+$"},"description":"Segundos desde a época Unix."},{"name":"x-trilha-invoice-signature","in":"header","required":true,"schema":{"type":"string","pattern":"^sha256=[0-9a-f]{64}$"},"description":"HMAC-SHA256 de `<timestamp>.<corpo bruto>` com o segredo do endpoint."}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["eventId","event","environment","organizationId","resourceId","occurredAt","data"],"properties":{"eventId":{"type":"string","format":"uuid"},"event":{"const":"billing.charge_created"},"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"organizationId":{"type":"string","format":"uuid"},"resourceId":{"type":"string","description":"Id do recurso afetado: a operação (nfse.*), o documento (fiscal_document.*), a mensalidade (billing.charge_created) ou a carteira (billing.low_balance)."},"occurredAt":{"type":"string","format":"date-time"},"data":{"type":"object","required":["chargeId","amountCents","periodStart","dueDate"],"properties":{"chargeId":{"type":"string","format":"uuid"},"amountCents":{"type":"integer","description":"Valor da mensalidade em centavos."},"periodStart":{"type":"string","format":"date","description":"Primeiro dia do mês cobrado."},"dueDate":{"type":"string","format":"date"}}}}}}}},"responses":{"429":{"description":"Nova tentativa mais tarde."},"2XX":{"description":"Entrega confirmada."},"5XX":{"description":"Nova tentativa mais tarde."},"default":{"description":"Qualquer outra resposta encerra a entrega como falha definitiva."}}}},"billing.low_balance":{"post":{"summary":"Saldo baixo","description":"O saldo disponível da carteira (saldo menos reservas) ficou abaixo do limite do plano. Sai uma vez, na travessia — novos débitos abaixo do limite não repetem o aviso; uma recarga que devolve o saldo acima dele rearma. Vai para os endpoints cadastrados em `PRODUCTION`, o único ambiente que consome crédito.","operationId":"webhook_billing_low_balance","security":[],"parameters":[{"name":"x-trilha-invoice-event-id","in":"header","required":true,"schema":{"type":"string","format":"uuid"}},{"name":"x-trilha-invoice-timestamp","in":"header","required":true,"schema":{"type":"string","pattern":"^\\d+$"},"description":"Segundos desde a época Unix."},{"name":"x-trilha-invoice-signature","in":"header","required":true,"schema":{"type":"string","pattern":"^sha256=[0-9a-f]{64}$"},"description":"HMAC-SHA256 de `<timestamp>.<corpo bruto>` com o segredo do endpoint."}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["eventId","event","environment","organizationId","resourceId","occurredAt","data"],"properties":{"eventId":{"type":"string","format":"uuid"},"event":{"const":"billing.low_balance"},"environment":{"type":"string","enum":["HOMOLOGATION","PRODUCTION"]},"organizationId":{"type":"string","format":"uuid"},"resourceId":{"type":"string","description":"Id do recurso afetado: a operação (nfse.*), o documento (fiscal_document.*), a mensalidade (billing.charge_created) ou a carteira (billing.low_balance)."},"occurredAt":{"type":"string","format":"date-time"},"data":{"type":"object","required":["walletId","availableCents","balanceCents","reservedCents","thresholdCents","currency"],"properties":{"walletId":{"type":"string","format":"uuid"},"availableCents":{"type":"integer"},"balanceCents":{"type":"integer"},"reservedCents":{"type":"integer"},"thresholdCents":{"type":"integer","description":"Limite de saldo baixo do plano."},"currency":{"const":"BRL"}}}}}}}},"responses":{"429":{"description":"Nova tentativa mais tarde."},"2XX":{"description":"Entrega confirmada."},"5XX":{"description":"Nova tentativa mais tarde."},"default":{"description":"Qualquer outra resposta encerra a entrega como falha definitiva."}}}}}}