{
  "openapi": "3.1.0",
  "info": {
    "title": "API NFsPlus",
    "version": "1.0.0",
    "summary": "Emissão de NFS-e pelo padrão nacional.",
    "description": "API REST para emitir e gerenciar NFS-e pelo padrão nacional. JSON em UTF-8, nomes de campo em `snake_case`, datas em ISO 8601.\n\n- **Autenticação:** `Authorization: Bearer nfsp_test_…` ou `nfsp_live_…`. **A chave define o ambiente**: `test` usa o Sandbox (sem validade jurídica), `live` emite em produção. Não há outro host nem parâmetro de ambiente.\n- **Dinheiro:** sempre em centavos inteiros (`150000` = R$ 1.500,00), sem exceções.\n- **Emissão assíncrona:** `POST /v1/notas` responde `202`; o resultado chega por webhook ou consultando a nota.\n- **Idempotência:** `Idempotency-Key` é obrigatório ao emitir.\n- **Listas:** paginação por cursor, `{ \"dados\": [...], \"proximo_cursor\": \"...\" | null }`.\n- **Erros:** `application/problem+json` (RFC 9457) com o campo estável `code`.",
    "contact": {
      "name": "Suporte NFsPlus",
      "url": "https://nfsplus.com.br"
    }
  },
  "servers": [
    {
      "url": "https://api.nfsplus.com.br",
      "description": "Sandbox e produção (a chave decide)"
    },
    {
      "url": "http://localhost:3000",
      "description": "Desenvolvimento local"
    }
  ],
  "security": [
    {
      "bearerAuth": []
    }
  ],
  "tags": [
    {
      "name": "Notas",
      "description": "Emissão, consulta, cancelamento e arquivos (XML e PDF) das NFS-e."
    },
    {
      "name": "Prestadores",
      "description": "Os CNPJs que emitem notas, com seus padrões fiscais e a situação do certificado."
    },
    {
      "name": "Tomadores",
      "description": "Cadastro de quem contrata o serviço, para reutilizar nas emissões."
    },
    {
      "name": "Certificados",
      "description": "Certificados digitais A1 usados para assinar as notas em produção."
    },
    {
      "name": "Webhooks",
      "description": "Endpoints que recebem eventos assinados, histórico de entregas e reenvio."
    },
    {
      "name": "Exportações",
      "description": "Arquivos com as notas de um período (ZIP, CSV ou JSON) para contabilidade."
    },
    {
      "name": "Consultas",
      "description": "CNPJ na Receita, catálogo nacional de serviços (cTribNac e CNAE) e sugestão de código de tributação."
    },
    {
      "name": "Sandbox",
      "description": "Simulador: programe como o município \"responde\" no ambiente de testes."
    },
    {
      "name": "Uso",
      "description": "Consumo do plano, franquia e limites da conta."
    },
    {
      "name": "Relatórios",
      "description": "Emissão, faturamento, impostos, rejeições e uso do plano, para conciliar com a contabilidade."
    },
    {
      "name": "Documentação",
      "description": "O próprio contrato da API."
    }
  ],
  "paths": {
    "/v1/relatorios/emissao": {
      "get": {
        "operationId": "relatorioEmissao",
        "tags": [
          "Relatórios"
        ],
        "summary": "Relatório de emissão",
        "description": "Notas por período, empresa e status, taxa de sucesso, tempo até autorizar, valor emitido, ISS (total, retido e a recolher) e ticket médio. Com a chave só de `relatorios:ler`, os valores em dinheiro vêm `null` e `valores_ocultos` é `true`. Datas em AAAA-MM-DD no fuso de Brasília; dinheiro em centavos inteiros. Com `formato=csv` ou `formato=pdf` a resposta é o arquivo.\n\n**Escopo necessário:** `relatorios:ler`.",
        "parameters": [
          {
            "name": "periodo",
            "in": "query",
            "required": false,
            "description": "Atalho de período: `hoje`, `ontem`, `7d`, `30d`, `90d`, `mes_atual`, `mes_anterior` ou `ano_atual`. Padrão: 30 dias. Perde para `de` e `ate`.",
            "schema": {
              "type": "string",
              "enum": [
                "hoje",
                "ontem",
                "7d",
                "30d",
                "90d",
                "mes_atual",
                "mes_anterior",
                "ano_atual"
              ]
            }
          },
          {
            "name": "de",
            "in": "query",
            "required": false,
            "description": "Primeiro dia (AAAA-MM-DD, fuso de Brasília), inclusive. Período máximo: 3 anos.",
            "schema": {
              "type": "string",
              "pattern": "^\\d{4}-\\d{2}-\\d{2}$"
            }
          },
          {
            "name": "ate",
            "in": "query",
            "required": false,
            "description": "Último dia (AAAA-MM-DD, fuso de Brasília), inclusive.",
            "schema": {
              "type": "string",
              "pattern": "^\\d{4}-\\d{2}-\\d{2}$"
            }
          },
          {
            "name": "prestador_id",
            "in": "query",
            "required": false,
            "description": "Só estes prestadores (um ou mais ids, separados por vírgula ou repetidos). Omitido: todos da conta.",
            "schema": {
              "type": "string",
              "maxLength": 2000
            }
          },
          {
            "name": "status",
            "in": "query",
            "required": false,
            "description": "Só notas com estes status (separados por vírgula). Impostos e faturamento consideram apenas autorizadas.",
            "schema": {
              "type": "string",
              "maxLength": 2000
            }
          },
          {
            "name": "ambiente",
            "in": "query",
            "required": false,
            "description": "Ignorado na API: o ambiente é o da chave de API (use uma chave de produção para dados reais).",
            "schema": {
              "type": "string",
              "enum": [
                "sandbox",
                "producao"
              ]
            }
          },
          {
            "name": "tomador_id",
            "in": "query",
            "required": false,
            "description": "Só as notas deste tomador cadastrado.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          },
          {
            "name": "codigo_tributacao",
            "in": "query",
            "required": false,
            "description": "Só notas com estes códigos de tributação nacional (até 6 dígitos, separados por vírgula).",
            "schema": {
              "type": "string",
              "maxLength": 2000
            }
          },
          {
            "name": "municipio_ibge",
            "in": "query",
            "required": false,
            "description": "Só notas de prestadores nestes municípios (IBGE, 7 dígitos, separados por vírgula).",
            "schema": {
              "type": "string",
              "maxLength": 2000
            }
          },
          {
            "name": "valor_min",
            "in": "query",
            "required": false,
            "description": "Valor mínimo do serviço, em centavos.",
            "schema": {
              "type": "integer",
              "minimum": 0,
              "maximum": 9999999999999
            }
          },
          {
            "name": "valor_max",
            "in": "query",
            "required": false,
            "description": "Valor máximo do serviço, em centavos.",
            "schema": {
              "type": "integer",
              "minimum": 0,
              "maximum": 9999999999999
            }
          },
          {
            "name": "iss_retido",
            "in": "query",
            "required": false,
            "description": "`true` só notas com ISS retido; `false` só as sem retenção.",
            "schema": {
              "type": "string",
              "enum": [
                "true",
                "false"
              ]
            }
          },
          {
            "name": "q",
            "in": "query",
            "required": false,
            "description": "Busca por parte do nome do tomador, da referência externa, do número da NFS-e ou da descrição do serviço.",
            "schema": {
              "type": "string",
              "minLength": 1,
              "maxLength": 80
            }
          },
          {
            "name": "agrupar",
            "in": "query",
            "required": false,
            "description": "Granularidade da série: `dia` (até 366 dias de período), `semana` ou `mes`. Padrão conforme o tamanho do período.",
            "schema": {
              "type": "string",
              "enum": [
                "dia",
                "semana",
                "mes"
              ]
            }
          },
          {
            "name": "comparar",
            "in": "query",
            "required": false,
            "description": "`true` inclui a comparação com o período anterior de mesma duração.",
            "schema": {
              "type": "string",
              "enum": [
                "true",
                "false"
              ],
              "default": "false"
            }
          },
          {
            "name": "formato",
            "in": "query",
            "required": false,
            "description": "`json` (padrão), `csv` (pt-BR: separador `;`, vírgula decimal, UTF-8 com BOM) ou `pdf`. Com `csv` ou `pdf` a resposta é o arquivo, não JSON.",
            "schema": {
              "type": "string",
              "enum": [
                "json",
                "csv",
                "pdf"
              ],
              "default": "json"
            }
          },
          {
            "name": "tabela",
            "in": "query",
            "required": false,
            "description": "Com `formato=csv`: qual tabela do relatório exportar (o padrão é a primeira).",
            "schema": {
              "type": "string",
              "pattern": "^[a-z_]{1,30}$"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "O relatório.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/RelatorioEmissao"
                },
                "example": {
                  "periodo": {
                    "de": "2026-04-01",
                    "ate": "2026-04-30",
                    "dias": 30,
                    "fuso": "America/Sao_Paulo"
                  },
                  "ambiente": "producao",
                  "agrupar": "semana",
                  "filtros": {
                    "periodo": null,
                    "de": "2026-04-01",
                    "ate": "2026-04-30",
                    "comparar": false
                  },
                  "valores_ocultos": false,
                  "resumo": {
                    "notas": {
                      "total": 120,
                      "autorizadas": 104,
                      "canceladas": 3,
                      "rejeitadas": 9,
                      "erro": 2,
                      "processando": 2,
                      "rascunho": 0
                    },
                    "taxa_sucesso_pct": 90.5,
                    "tempo_medio_autorizacao_s": 6.4,
                    "tempo_p95_autorizacao_s": 14.2,
                    "valor_emitido_centavos": 18450000,
                    "valor_cancelado_centavos": 420000,
                    "desconto_centavos": 0,
                    "iss_total_centavos": 369000,
                    "iss_retido_centavos": 92250,
                    "iss_a_recolher_centavos": 276750,
                    "ticket_medio_centavos": 177403
                  },
                  "comparacao": null,
                  "serie": [
                    {
                      "inicio": "2026-03-30",
                      "total": 30,
                      "autorizadas": 26,
                      "canceladas": 1,
                      "rejeitadas": 2,
                      "erro": 1,
                      "processando": 0,
                      "valor_centavos": 4600000,
                      "iss_centavos": 92000
                    }
                  ],
                  "por_empresa": [
                    {
                      "prestador_id": "5b1c3f0e-7a2d-4e58-9c61-0d4f8a2b6e13",
                      "razao_social": "Estúdio Exemplo Ltda",
                      "cnpj": "12345678000195",
                      "total": 120,
                      "autorizadas": 104,
                      "canceladas": 3,
                      "rejeitadas": 9,
                      "erro": 2,
                      "taxa_sucesso_pct": 90.5,
                      "valor_emitido_centavos": 18450000,
                      "iss_total_centavos": 369000
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "relatorios:ler"
            ]
          }
        ],
        "x-escopo": "relatorios:ler"
      }
    },
    "/v1/relatorios/faturamento": {
      "get": {
        "operationId": "relatorioFaturamento",
        "tags": [
          "Relatórios"
        ],
        "summary": "Relatório de faturamento",
        "description": "Valor das notas autorizadas agrupado por tomador, serviço, município, empresa ou período, com participação, ticket médio e variação contra o período anterior (`comparar=true`). Datas em AAAA-MM-DD no fuso de Brasília; dinheiro em centavos inteiros. Com `formato=csv` ou `formato=pdf` a resposta é o arquivo.\n\n**Escopo necessário:** `relatorios:financeiro`.",
        "parameters": [
          {
            "name": "periodo",
            "in": "query",
            "required": false,
            "description": "Atalho de período: `hoje`, `ontem`, `7d`, `30d`, `90d`, `mes_atual`, `mes_anterior` ou `ano_atual`. Padrão: 30 dias. Perde para `de` e `ate`.",
            "schema": {
              "type": "string",
              "enum": [
                "hoje",
                "ontem",
                "7d",
                "30d",
                "90d",
                "mes_atual",
                "mes_anterior",
                "ano_atual"
              ]
            }
          },
          {
            "name": "de",
            "in": "query",
            "required": false,
            "description": "Primeiro dia (AAAA-MM-DD, fuso de Brasília), inclusive. Período máximo: 3 anos.",
            "schema": {
              "type": "string",
              "pattern": "^\\d{4}-\\d{2}-\\d{2}$"
            }
          },
          {
            "name": "ate",
            "in": "query",
            "required": false,
            "description": "Último dia (AAAA-MM-DD, fuso de Brasília), inclusive.",
            "schema": {
              "type": "string",
              "pattern": "^\\d{4}-\\d{2}-\\d{2}$"
            }
          },
          {
            "name": "prestador_id",
            "in": "query",
            "required": false,
            "description": "Só estes prestadores (um ou mais ids, separados por vírgula ou repetidos). Omitido: todos da conta.",
            "schema": {
              "type": "string",
              "maxLength": 2000
            }
          },
          {
            "name": "status",
            "in": "query",
            "required": false,
            "description": "Só notas com estes status (separados por vírgula). Impostos e faturamento consideram apenas autorizadas.",
            "schema": {
              "type": "string",
              "maxLength": 2000
            }
          },
          {
            "name": "ambiente",
            "in": "query",
            "required": false,
            "description": "Ignorado na API: o ambiente é o da chave de API (use uma chave de produção para dados reais).",
            "schema": {
              "type": "string",
              "enum": [
                "sandbox",
                "producao"
              ]
            }
          },
          {
            "name": "tomador_id",
            "in": "query",
            "required": false,
            "description": "Só as notas deste tomador cadastrado.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          },
          {
            "name": "codigo_tributacao",
            "in": "query",
            "required": false,
            "description": "Só notas com estes códigos de tributação nacional (até 6 dígitos, separados por vírgula).",
            "schema": {
              "type": "string",
              "maxLength": 2000
            }
          },
          {
            "name": "municipio_ibge",
            "in": "query",
            "required": false,
            "description": "Só notas de prestadores nestes municípios (IBGE, 7 dígitos, separados por vírgula).",
            "schema": {
              "type": "string",
              "maxLength": 2000
            }
          },
          {
            "name": "valor_min",
            "in": "query",
            "required": false,
            "description": "Valor mínimo do serviço, em centavos.",
            "schema": {
              "type": "integer",
              "minimum": 0,
              "maximum": 9999999999999
            }
          },
          {
            "name": "valor_max",
            "in": "query",
            "required": false,
            "description": "Valor máximo do serviço, em centavos.",
            "schema": {
              "type": "integer",
              "minimum": 0,
              "maximum": 9999999999999
            }
          },
          {
            "name": "iss_retido",
            "in": "query",
            "required": false,
            "description": "`true` só notas com ISS retido; `false` só as sem retenção.",
            "schema": {
              "type": "string",
              "enum": [
                "true",
                "false"
              ]
            }
          },
          {
            "name": "q",
            "in": "query",
            "required": false,
            "description": "Busca por parte do nome do tomador, da referência externa, do número da NFS-e ou da descrição do serviço.",
            "schema": {
              "type": "string",
              "minLength": 1,
              "maxLength": 80
            }
          },
          {
            "name": "agrupar",
            "in": "query",
            "required": false,
            "description": "Granularidade da série: `dia` (até 366 dias de período), `semana` ou `mes`. Padrão conforme o tamanho do período.",
            "schema": {
              "type": "string",
              "enum": [
                "dia",
                "semana",
                "mes"
              ]
            }
          },
          {
            "name": "comparar",
            "in": "query",
            "required": false,
            "description": "`true` inclui a comparação com o período anterior de mesma duração.",
            "schema": {
              "type": "string",
              "enum": [
                "true",
                "false"
              ],
              "default": "false"
            }
          },
          {
            "name": "formato",
            "in": "query",
            "required": false,
            "description": "`json` (padrão), `csv` (pt-BR: separador `;`, vírgula decimal, UTF-8 com BOM) ou `pdf`. Com `csv` ou `pdf` a resposta é o arquivo, não JSON.",
            "schema": {
              "type": "string",
              "enum": [
                "json",
                "csv",
                "pdf"
              ],
              "default": "json"
            }
          },
          {
            "name": "tabela",
            "in": "query",
            "required": false,
            "description": "Com `formato=csv`: qual tabela do relatório exportar (o padrão é a primeira).",
            "schema": {
              "type": "string",
              "pattern": "^[a-z_]{1,30}$"
            }
          },
          {
            "name": "dimensao",
            "in": "query",
            "required": false,
            "description": "Como agrupar: `tomador`, `servico`, `municipio`, `empresa` ou `periodo`. Padrão `tomador`.",
            "schema": {
              "type": "string",
              "enum": [
                "tomador",
                "servico",
                "municipio",
                "empresa",
                "periodo"
              ],
              "default": "tomador"
            }
          },
          {
            "name": "limite",
            "in": "query",
            "required": false,
            "description": "Quantos itens mostrar (1 a 100). O restante vem somado em `outros`. Padrão 10.",
            "schema": {
              "type": "integer",
              "minimum": 1,
              "maximum": 100,
              "default": 10
            }
          },
          {
            "name": "ordenar",
            "in": "query",
            "required": false,
            "description": "Ordena por `valor` (padrão), `quantidade` ou `nome`.",
            "schema": {
              "type": "string",
              "enum": [
                "valor",
                "quantidade",
                "nome"
              ],
              "default": "valor"
            }
          },
          {
            "name": "ordem",
            "in": "query",
            "required": false,
            "description": "`desc` (padrão) ou `asc`.",
            "schema": {
              "type": "string",
              "enum": [
                "asc",
                "desc"
              ],
              "default": "desc"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "O relatório.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/RelatorioFaturamento"
                },
                "example": {
                  "periodo": {
                    "de": "2026-04-01",
                    "ate": "2026-04-30",
                    "dias": 30,
                    "fuso": "America/Sao_Paulo"
                  },
                  "ambiente": "producao",
                  "dimensao": "tomador",
                  "filtros": {
                    "de": "2026-04-01",
                    "ate": "2026-04-30",
                    "dimensao": "tomador",
                    "limite": 10,
                    "ordenar": "valor",
                    "ordem": "desc"
                  },
                  "total": {
                    "notas": 104,
                    "valor_centavos": 18450000,
                    "iss_centavos": 369000,
                    "ticket_medio_centavos": 177403
                  },
                  "agrupar": null,
                  "itens": [
                    {
                      "chave": "***.456.789-**",
                      "rotulo": "Maria Souza",
                      "detalhe": null,
                      "notas": 12,
                      "valor_centavos": 3600000,
                      "iss_centavos": 72000,
                      "ticket_medio_centavos": 300000,
                      "participacao_pct": 19.5,
                      "variacao_pct": null
                    }
                  ],
                  "outros": {
                    "notas": 92,
                    "valor_centavos": 14850000,
                    "iss_centavos": 297000,
                    "participacao_pct": 80.5
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "relatorios:financeiro"
            ]
          }
        ],
        "x-escopo": "relatorios:financeiro"
      }
    },
    "/v1/relatorios/impostos": {
      "get": {
        "operationId": "relatorioImpostos",
        "tags": [
          "Relatórios"
        ],
        "summary": "Relatório de impostos",
        "description": "ISS devido e retido por mês de competência (padrão: últimos 6 meses), com o detalhe por empresa e município. PIS, COFINS, CSLL, IRRF e INSS retidos não são registrados e vêm indicados em `retencoes_federais`. Datas em AAAA-MM-DD no fuso de Brasília; dinheiro em centavos inteiros. Com `formato=csv` ou `formato=pdf` a resposta é o arquivo.\n\n**Escopo necessário:** `relatorios:financeiro`.",
        "parameters": [
          {
            "name": "periodo",
            "in": "query",
            "required": false,
            "description": "Atalho de período: `hoje`, `ontem`, `7d`, `30d`, `90d`, `mes_atual`, `mes_anterior` ou `ano_atual`. Padrão: 30 dias. Perde para `de` e `ate`.",
            "schema": {
              "type": "string",
              "enum": [
                "hoje",
                "ontem",
                "7d",
                "30d",
                "90d",
                "mes_atual",
                "mes_anterior",
                "ano_atual"
              ]
            }
          },
          {
            "name": "de",
            "in": "query",
            "required": false,
            "description": "Primeiro dia (AAAA-MM-DD, fuso de Brasília), inclusive. Período máximo: 3 anos.",
            "schema": {
              "type": "string",
              "pattern": "^\\d{4}-\\d{2}-\\d{2}$"
            }
          },
          {
            "name": "ate",
            "in": "query",
            "required": false,
            "description": "Último dia (AAAA-MM-DD, fuso de Brasília), inclusive.",
            "schema": {
              "type": "string",
              "pattern": "^\\d{4}-\\d{2}-\\d{2}$"
            }
          },
          {
            "name": "prestador_id",
            "in": "query",
            "required": false,
            "description": "Só estes prestadores (um ou mais ids, separados por vírgula ou repetidos). Omitido: todos da conta.",
            "schema": {
              "type": "string",
              "maxLength": 2000
            }
          },
          {
            "name": "status",
            "in": "query",
            "required": false,
            "description": "Só notas com estes status (separados por vírgula). Impostos e faturamento consideram apenas autorizadas.",
            "schema": {
              "type": "string",
              "maxLength": 2000
            }
          },
          {
            "name": "ambiente",
            "in": "query",
            "required": false,
            "description": "Ignorado na API: o ambiente é o da chave de API (use uma chave de produção para dados reais).",
            "schema": {
              "type": "string",
              "enum": [
                "sandbox",
                "producao"
              ]
            }
          },
          {
            "name": "tomador_id",
            "in": "query",
            "required": false,
            "description": "Só as notas deste tomador cadastrado.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          },
          {
            "name": "codigo_tributacao",
            "in": "query",
            "required": false,
            "description": "Só notas com estes códigos de tributação nacional (até 6 dígitos, separados por vírgula).",
            "schema": {
              "type": "string",
              "maxLength": 2000
            }
          },
          {
            "name": "municipio_ibge",
            "in": "query",
            "required": false,
            "description": "Só notas de prestadores nestes municípios (IBGE, 7 dígitos, separados por vírgula).",
            "schema": {
              "type": "string",
              "maxLength": 2000
            }
          },
          {
            "name": "valor_min",
            "in": "query",
            "required": false,
            "description": "Valor mínimo do serviço, em centavos.",
            "schema": {
              "type": "integer",
              "minimum": 0,
              "maximum": 9999999999999
            }
          },
          {
            "name": "valor_max",
            "in": "query",
            "required": false,
            "description": "Valor máximo do serviço, em centavos.",
            "schema": {
              "type": "integer",
              "minimum": 0,
              "maximum": 9999999999999
            }
          },
          {
            "name": "iss_retido",
            "in": "query",
            "required": false,
            "description": "`true` só notas com ISS retido; `false` só as sem retenção.",
            "schema": {
              "type": "string",
              "enum": [
                "true",
                "false"
              ]
            }
          },
          {
            "name": "q",
            "in": "query",
            "required": false,
            "description": "Busca por parte do nome do tomador, da referência externa, do número da NFS-e ou da descrição do serviço.",
            "schema": {
              "type": "string",
              "minLength": 1,
              "maxLength": 80
            }
          },
          {
            "name": "agrupar",
            "in": "query",
            "required": false,
            "description": "Granularidade da série: `dia` (até 366 dias de período), `semana` ou `mes`. Padrão conforme o tamanho do período.",
            "schema": {
              "type": "string",
              "enum": [
                "dia",
                "semana",
                "mes"
              ]
            }
          },
          {
            "name": "comparar",
            "in": "query",
            "required": false,
            "description": "`true` inclui a comparação com o período anterior de mesma duração.",
            "schema": {
              "type": "string",
              "enum": [
                "true",
                "false"
              ],
              "default": "false"
            }
          },
          {
            "name": "formato",
            "in": "query",
            "required": false,
            "description": "`json` (padrão), `csv` (pt-BR: separador `;`, vírgula decimal, UTF-8 com BOM) ou `pdf`. Com `csv` ou `pdf` a resposta é o arquivo, não JSON.",
            "schema": {
              "type": "string",
              "enum": [
                "json",
                "csv",
                "pdf"
              ],
              "default": "json"
            }
          },
          {
            "name": "tabela",
            "in": "query",
            "required": false,
            "description": "Com `formato=csv`: qual tabela do relatório exportar (o padrão é a primeira).",
            "schema": {
              "type": "string",
              "pattern": "^[a-z_]{1,30}$"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "O relatório.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/RelatorioImpostos"
                },
                "example": {
                  "periodo": {
                    "de": "2026-04-01",
                    "ate": "2026-04-30",
                    "base": "competencia"
                  },
                  "ambiente": "producao",
                  "filtros": {
                    "de": "2026-04-01",
                    "ate": "2026-04-30"
                  },
                  "total": {
                    "notas": 104,
                    "valor_servicos_centavos": 18450000,
                    "desconto_centavos": 0,
                    "base_calculo_centavos": 18450000,
                    "iss_total_centavos": 369000,
                    "iss_retido_centavos": 92250,
                    "iss_a_recolher_centavos": 276750,
                    "aliquota_efetiva_pct": 2,
                    "notas_sem_valor_de_iss": 0
                  },
                  "por_competencia": [
                    {
                      "competencia": "2026-04",
                      "notas": 104,
                      "valor_servicos_centavos": 18450000,
                      "desconto_centavos": 0,
                      "base_calculo_centavos": 18450000,
                      "iss_total_centavos": 369000,
                      "iss_retido_centavos": 92250,
                      "iss_a_recolher_centavos": 276750,
                      "aliquota_efetiva_pct": 2,
                      "notas_sem_valor_de_iss": 0
                    }
                  ],
                  "detalhe": [],
                  "canceladas_no_periodo": {
                    "notas": 3,
                    "valor_servicos_centavos": 420000
                  },
                  "retencoes_federais": {
                    "disponivel": false,
                    "motivo": "O NFsPlus não registra PIS, COFINS, CSLL, IRRF nem INSS retidos."
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "relatorios:financeiro"
            ]
          }
        ],
        "x-escopo": "relatorios:financeiro"
      }
    },
    "/v1/relatorios/ocorrencias": {
      "get": {
        "operationId": "relatorioOcorrencias",
        "tags": [
          "Relatórios"
        ],
        "summary": "Relatório de rejeições, erros e cancelamentos",
        "description": "Motivos de rejeição e erro agrupados por código, com orientação para corrigir, e os cancelamentos por tipo e motivo. Datas em AAAA-MM-DD no fuso de Brasília; dinheiro em centavos inteiros. Com `formato=csv` ou `formato=pdf` a resposta é o arquivo.\n\n**Escopo necessário:** `relatorios:ler`.",
        "parameters": [
          {
            "name": "periodo",
            "in": "query",
            "required": false,
            "description": "Atalho de período: `hoje`, `ontem`, `7d`, `30d`, `90d`, `mes_atual`, `mes_anterior` ou `ano_atual`. Padrão: 30 dias. Perde para `de` e `ate`.",
            "schema": {
              "type": "string",
              "enum": [
                "hoje",
                "ontem",
                "7d",
                "30d",
                "90d",
                "mes_atual",
                "mes_anterior",
                "ano_atual"
              ]
            }
          },
          {
            "name": "de",
            "in": "query",
            "required": false,
            "description": "Primeiro dia (AAAA-MM-DD, fuso de Brasília), inclusive. Período máximo: 3 anos.",
            "schema": {
              "type": "string",
              "pattern": "^\\d{4}-\\d{2}-\\d{2}$"
            }
          },
          {
            "name": "ate",
            "in": "query",
            "required": false,
            "description": "Último dia (AAAA-MM-DD, fuso de Brasília), inclusive.",
            "schema": {
              "type": "string",
              "pattern": "^\\d{4}-\\d{2}-\\d{2}$"
            }
          },
          {
            "name": "prestador_id",
            "in": "query",
            "required": false,
            "description": "Só estes prestadores (um ou mais ids, separados por vírgula ou repetidos). Omitido: todos da conta.",
            "schema": {
              "type": "string",
              "maxLength": 2000
            }
          },
          {
            "name": "status",
            "in": "query",
            "required": false,
            "description": "Só notas com estes status (separados por vírgula). Impostos e faturamento consideram apenas autorizadas.",
            "schema": {
              "type": "string",
              "maxLength": 2000
            }
          },
          {
            "name": "ambiente",
            "in": "query",
            "required": false,
            "description": "Ignorado na API: o ambiente é o da chave de API (use uma chave de produção para dados reais).",
            "schema": {
              "type": "string",
              "enum": [
                "sandbox",
                "producao"
              ]
            }
          },
          {
            "name": "tomador_id",
            "in": "query",
            "required": false,
            "description": "Só as notas deste tomador cadastrado.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          },
          {
            "name": "codigo_tributacao",
            "in": "query",
            "required": false,
            "description": "Só notas com estes códigos de tributação nacional (até 6 dígitos, separados por vírgula).",
            "schema": {
              "type": "string",
              "maxLength": 2000
            }
          },
          {
            "name": "municipio_ibge",
            "in": "query",
            "required": false,
            "description": "Só notas de prestadores nestes municípios (IBGE, 7 dígitos, separados por vírgula).",
            "schema": {
              "type": "string",
              "maxLength": 2000
            }
          },
          {
            "name": "valor_min",
            "in": "query",
            "required": false,
            "description": "Valor mínimo do serviço, em centavos.",
            "schema": {
              "type": "integer",
              "minimum": 0,
              "maximum": 9999999999999
            }
          },
          {
            "name": "valor_max",
            "in": "query",
            "required": false,
            "description": "Valor máximo do serviço, em centavos.",
            "schema": {
              "type": "integer",
              "minimum": 0,
              "maximum": 9999999999999
            }
          },
          {
            "name": "iss_retido",
            "in": "query",
            "required": false,
            "description": "`true` só notas com ISS retido; `false` só as sem retenção.",
            "schema": {
              "type": "string",
              "enum": [
                "true",
                "false"
              ]
            }
          },
          {
            "name": "q",
            "in": "query",
            "required": false,
            "description": "Busca por parte do nome do tomador, da referência externa, do número da NFS-e ou da descrição do serviço.",
            "schema": {
              "type": "string",
              "minLength": 1,
              "maxLength": 80
            }
          },
          {
            "name": "agrupar",
            "in": "query",
            "required": false,
            "description": "Granularidade da série: `dia` (até 366 dias de período), `semana` ou `mes`. Padrão conforme o tamanho do período.",
            "schema": {
              "type": "string",
              "enum": [
                "dia",
                "semana",
                "mes"
              ]
            }
          },
          {
            "name": "comparar",
            "in": "query",
            "required": false,
            "description": "`true` inclui a comparação com o período anterior de mesma duração.",
            "schema": {
              "type": "string",
              "enum": [
                "true",
                "false"
              ],
              "default": "false"
            }
          },
          {
            "name": "formato",
            "in": "query",
            "required": false,
            "description": "`json` (padrão), `csv` (pt-BR: separador `;`, vírgula decimal, UTF-8 com BOM) ou `pdf`. Com `csv` ou `pdf` a resposta é o arquivo, não JSON.",
            "schema": {
              "type": "string",
              "enum": [
                "json",
                "csv",
                "pdf"
              ],
              "default": "json"
            }
          },
          {
            "name": "tabela",
            "in": "query",
            "required": false,
            "description": "Com `formato=csv`: qual tabela do relatório exportar (o padrão é a primeira).",
            "schema": {
              "type": "string",
              "pattern": "^[a-z_]{1,30}$"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "O relatório.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/RelatorioOcorrencias"
                },
                "example": {
                  "periodo": {
                    "de": "2026-04-01",
                    "ate": "2026-04-30"
                  },
                  "ambiente": "producao",
                  "filtros": {
                    "de": "2026-04-01",
                    "ate": "2026-04-30"
                  },
                  "valores_ocultos": false,
                  "resumo": {
                    "rejeitadas": 9,
                    "com_erro": 2,
                    "valor_nao_emitido_centavos": 1980000,
                    "canceladas": 3,
                    "valor_cancelado_centavos": 420000
                  },
                  "rejeicoes": [
                    {
                      "codigo": "E0100",
                      "mensagem": "CNPJ do tomador inválido.",
                      "campo": "tomador.documento",
                      "tipo": "rejeitada",
                      "notas": 6,
                      "ocorrencias": 6,
                      "valor_centavos": 1200000,
                      "ultima_em": "2026-04-27T14:03:10.000Z",
                      "orientacao": "Confira o documento do tomador e reenvie.",
                      "exemplos": []
                    }
                  ],
                  "cancelamentos": {
                    "por_tipo": [
                      {
                        "tipo": "outros",
                        "notas": 3,
                        "valor_centavos": 420000
                      }
                    ],
                    "motivos": [
                      {
                        "motivo": "outros",
                        "notas": 3
                      }
                    ]
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "relatorios:ler"
            ]
          }
        ],
        "x-escopo": "relatorios:ler"
      }
    },
    "/v1/relatorios/uso": {
      "get": {
        "operationId": "relatorioUso",
        "tags": [
          "Relatórios"
        ],
        "summary": "Relatório de uso do plano e custo",
        "description": "Notas incluídas, excedentes, custo do período, projeção do ciclo e alerta de limite. Sem `de`/`ate`, usa o ciclo atual do plano. Datas em AAAA-MM-DD no fuso de Brasília; dinheiro em centavos inteiros. Com `formato=csv` ou `formato=pdf` a resposta é o arquivo.\n\n**Escopo necessário:** `relatorios:financeiro`.",
        "parameters": [
          {
            "name": "periodo",
            "in": "query",
            "required": false,
            "description": "Atalho de período: `hoje`, `ontem`, `7d`, `30d`, `90d`, `mes_atual`, `mes_anterior` ou `ano_atual`. Padrão: 30 dias. Perde para `de` e `ate`.",
            "schema": {
              "type": "string",
              "enum": [
                "hoje",
                "ontem",
                "7d",
                "30d",
                "90d",
                "mes_atual",
                "mes_anterior",
                "ano_atual"
              ]
            }
          },
          {
            "name": "de",
            "in": "query",
            "required": false,
            "description": "Primeiro dia (AAAA-MM-DD, fuso de Brasília), inclusive. Período máximo: 3 anos.",
            "schema": {
              "type": "string",
              "pattern": "^\\d{4}-\\d{2}-\\d{2}$"
            }
          },
          {
            "name": "ate",
            "in": "query",
            "required": false,
            "description": "Último dia (AAAA-MM-DD, fuso de Brasília), inclusive.",
            "schema": {
              "type": "string",
              "pattern": "^\\d{4}-\\d{2}-\\d{2}$"
            }
          },
          {
            "name": "prestador_id",
            "in": "query",
            "required": false,
            "description": "Só estes prestadores (um ou mais ids, separados por vírgula ou repetidos). Omitido: todos da conta.",
            "schema": {
              "type": "string",
              "maxLength": 2000
            }
          },
          {
            "name": "status",
            "in": "query",
            "required": false,
            "description": "Só notas com estes status (separados por vírgula). Impostos e faturamento consideram apenas autorizadas.",
            "schema": {
              "type": "string",
              "maxLength": 2000
            }
          },
          {
            "name": "ambiente",
            "in": "query",
            "required": false,
            "description": "Ignorado na API: o ambiente é o da chave de API (use uma chave de produção para dados reais).",
            "schema": {
              "type": "string",
              "enum": [
                "sandbox",
                "producao"
              ]
            }
          },
          {
            "name": "tomador_id",
            "in": "query",
            "required": false,
            "description": "Só as notas deste tomador cadastrado.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          },
          {
            "name": "codigo_tributacao",
            "in": "query",
            "required": false,
            "description": "Só notas com estes códigos de tributação nacional (até 6 dígitos, separados por vírgula).",
            "schema": {
              "type": "string",
              "maxLength": 2000
            }
          },
          {
            "name": "municipio_ibge",
            "in": "query",
            "required": false,
            "description": "Só notas de prestadores nestes municípios (IBGE, 7 dígitos, separados por vírgula).",
            "schema": {
              "type": "string",
              "maxLength": 2000
            }
          },
          {
            "name": "valor_min",
            "in": "query",
            "required": false,
            "description": "Valor mínimo do serviço, em centavos.",
            "schema": {
              "type": "integer",
              "minimum": 0,
              "maximum": 9999999999999
            }
          },
          {
            "name": "valor_max",
            "in": "query",
            "required": false,
            "description": "Valor máximo do serviço, em centavos.",
            "schema": {
              "type": "integer",
              "minimum": 0,
              "maximum": 9999999999999
            }
          },
          {
            "name": "iss_retido",
            "in": "query",
            "required": false,
            "description": "`true` só notas com ISS retido; `false` só as sem retenção.",
            "schema": {
              "type": "string",
              "enum": [
                "true",
                "false"
              ]
            }
          },
          {
            "name": "q",
            "in": "query",
            "required": false,
            "description": "Busca por parte do nome do tomador, da referência externa, do número da NFS-e ou da descrição do serviço.",
            "schema": {
              "type": "string",
              "minLength": 1,
              "maxLength": 80
            }
          },
          {
            "name": "agrupar",
            "in": "query",
            "required": false,
            "description": "Granularidade da série: `dia` (até 366 dias de período), `semana` ou `mes`. Padrão conforme o tamanho do período.",
            "schema": {
              "type": "string",
              "enum": [
                "dia",
                "semana",
                "mes"
              ]
            }
          },
          {
            "name": "comparar",
            "in": "query",
            "required": false,
            "description": "`true` inclui a comparação com o período anterior de mesma duração.",
            "schema": {
              "type": "string",
              "enum": [
                "true",
                "false"
              ],
              "default": "false"
            }
          },
          {
            "name": "formato",
            "in": "query",
            "required": false,
            "description": "`json` (padrão), `csv` (pt-BR: separador `;`, vírgula decimal, UTF-8 com BOM) ou `pdf`. Com `csv` ou `pdf` a resposta é o arquivo, não JSON.",
            "schema": {
              "type": "string",
              "enum": [
                "json",
                "csv",
                "pdf"
              ],
              "default": "json"
            }
          },
          {
            "name": "tabela",
            "in": "query",
            "required": false,
            "description": "Com `formato=csv`: qual tabela do relatório exportar (o padrão é a primeira).",
            "schema": {
              "type": "string",
              "pattern": "^[a-z_]{1,30}$"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "O relatório.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/RelatorioUso"
                },
                "example": {
                  "periodo": {
                    "de": "2026-04-01",
                    "ate": "2026-04-30",
                    "dias": 30,
                    "em_andamento": false,
                    "fuso": "America/Sao_Paulo"
                  },
                  "plano": {
                    "codigo": "pro",
                    "nome": "Pro",
                    "tipo_cobranca": "assinatura",
                    "notas_incluidas": 300,
                    "preco_excedente_centavos": 150,
                    "preco_nota_prepago_centavos": null,
                    "mensalidade_centavos": 14900
                  },
                  "consumo": {
                    "notas_autorizadas": 104,
                    "na_franquia": 104,
                    "excedentes": 0,
                    "pre_pagas": 0,
                    "rejeitadas": 9,
                    "canceladas": 3,
                    "custo_excedente_centavos": 0,
                    "custo_prepago_centavos": 0,
                    "custo_total_centavos": 14900
                  },
                  "limite": {
                    "percentual_usado": 34.7,
                    "restantes": 196,
                    "nivel": "ok",
                    "alerta": null
                  },
                  "projecao": null,
                  "creditos": null,
                  "comparacao": null,
                  "serie": [],
                  "historico": [
                    {
                      "competencia": "2026-04-01",
                      "notas": 104,
                      "excedentes": 0,
                      "valor_centavos": 0
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "relatorios:financeiro"
            ]
          }
        ],
        "x-escopo": "relatorios:financeiro"
      }
    },
    "/v1/notas": {
      "post": {
        "operationId": "emitirNota",
        "tags": [
          "Notas"
        ],
        "summary": "Emitir uma NFS-e",
        "description": "Cria uma nota e a coloca na fila de emissão. **A emissão é assíncrona**: a resposta é `202` com a nota em `status: \"processando\"`. O resultado chega por webhook (`nota.autorizada`, `nota.rejeitada` ou `nota.erro`) ou consultando `GET /v1/notas/{id}`.\n\nO cabeçalho `Idempotency-Key` é **obrigatório**. O ambiente (Sandbox ou produção) é definido pela chave de API usada.\n\nValores em **centavos**. A alíquota do ISS é uma porcentagem (`2` = 2%). Campos de serviço e alíquota omitidos assumem os `padroes_fiscais` do prestador.\n\n**Escopo necessário:** `notas:emitir`.",
        "parameters": [
          {
            "name": "Idempotency-Key",
            "in": "header",
            "required": true,
            "description": "Identifica a intenção de emitir. Gere um UUID novo por nota e **reutilize-o em qualquer repetição** da mesma chamada: se a primeira tentativa chegou, você recebe a mesma resposta (com `Idempotent-Replayed: true`) e nada é emitido em duplicidade. Até 128 caracteres ASCII visíveis; vale por 7 dias.",
            "schema": {
              "type": "string"
            },
            "example": "3f2b8c1e-9a47-4d6e-b5c0-1e7a9d2f4b68"
          },
          {
            "name": "X-Sandbox-Scenario",
            "in": "header",
            "required": false,
            "description": "Só no Sandbox: força o resultado da operação. Valores: `autorizar`, `rejeitar:<codigo>`, `erro_tecnico`, `lento:<segundos>`, `timeout_incerto`, `cancelamento_negado`, `prazo_expirado` (em `cancelar` e `substituir`: trata a nota como emitida há mais tempo que os prazos, sem precisar esperar anos), `webhook_falha:<n>` (as n primeiras entregas de webhook dos eventos da nota falham de propósito, com intervalo de ~2 s entre as tentativas; a nota é autorizada normalmente). Com chave de produção a API responde `400 cabecalho_sandbox_em_producao`.",
            "schema": {
              "type": "string"
            },
            "example": "rejeitar:E160"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "prestador_id": {
                    "type": "string",
                    "format": "uuid",
                    "description": "Identificador do prestador (o CNPJ que emite). Se omitido e houver um único prestador ativo, ele é usado."
                  },
                  "referencia_externa": {
                    "type": "string",
                    "minLength": 1,
                    "maxLength": 100,
                    "description": "O identificador da venda no **seu** sistema. É único por conta e ambiente (exceto notas rejeitadas): reenviar a mesma referência dá `409 referencia_externa_duplicada`."
                  },
                  "competencia": {
                    "type": "string",
                    "pattern": "^\\d{4}-\\d{2}-\\d{2}$",
                    "description": "Mês de competência do serviço, no formato AAAA-MM-DD. Padrão: hoje (fuso de Brasília). Não pode ser futura."
                  },
                  "tomador": {
                    "type": "object",
                    "properties": {
                      "tomador_id": {
                        "type": "string",
                        "format": "uuid",
                        "description": "Identificador de um tomador cadastrado."
                      },
                      "tipo_documento": {
                        "type": "string",
                        "enum": [
                          "cpf",
                          "cnpj",
                          "estrangeiro",
                          "nenhum"
                        ],
                        "description": "Tipo do documento do tomador. Se omitido com `documento`, é detectado (11 dígitos = CPF, 14 = CNPJ)."
                      },
                      "documento": {
                        "type": "string",
                        "minLength": 3,
                        "maxLength": 30,
                        "description": "CPF ou CNPJ, com ou sem pontuação. Nunca volta em claro nas respostas."
                      },
                      "nome": {
                        "type": "string",
                        "minLength": 2,
                        "maxLength": 150,
                        "description": "Nome ou razão social."
                      },
                      "email": {
                        "type": "string",
                        "format": "email",
                        "maxLength": 200,
                        "description": "E-mail."
                      },
                      "telefone": {
                        "type": "string",
                        "pattern": "^[0-9]{10,11}$",
                        "description": "Telefone com DDD, só dígitos (10 ou 11)."
                      },
                      "endereco": {
                        "type": "object",
                        "properties": {
                          "cep": {
                            "type": "string",
                            "pattern": "^[0-9]{8}$"
                          },
                          "logradouro": {
                            "type": "string",
                            "minLength": 1,
                            "maxLength": 125
                          },
                          "numero": {
                            "type": "string",
                            "minLength": 1,
                            "maxLength": 10
                          },
                          "complemento": {
                            "anyOf": [
                              {
                                "type": "string",
                                "maxLength": 60
                              },
                              {
                                "type": "null"
                              }
                            ]
                          },
                          "bairro": {
                            "type": "string",
                            "minLength": 1,
                            "maxLength": 60
                          },
                          "municipio_ibge": {
                            "type": "string",
                            "pattern": "^[0-9]{7}$",
                            "description": "Município do prestador (IBGE, 7 dígitos). Precisa estar na cobertura."
                          }
                        },
                        "required": [
                          "cep",
                          "logradouro",
                          "numero",
                          "bairro",
                          "municipio_ibge"
                        ],
                        "additionalProperties": false,
                        "description": "Endereço completo."
                      }
                    },
                    "additionalProperties": false,
                    "description": "Quem contrata o serviço. Informe `tomador_id` **ou** os dados completos."
                  },
                  "servico": {
                    "type": "object",
                    "properties": {
                      "codigo_tributacao_nacional": {
                        "type": "string",
                        "pattern": "^[0-9]{6}$",
                        "description": "Código de tributação nacional (6 dígitos: item da LC 116 + subitem + desdobro). Ex.: `010701`. Na emissão ele é conferido com o catálogo nacional e com os CNAEs do prestador (veja `forcar_codigo`)."
                      },
                      "codigo_tributacao_municipal": {
                        "type": "string",
                        "minLength": 1,
                        "maxLength": 20,
                        "description": "Código de tributação municipal, quando o município exige."
                      },
                      "codigo_nbs": {
                        "type": "string",
                        "pattern": "^[0-9]{9}$",
                        "description": "Código NBS (9 dígitos)."
                      },
                      "descricao": {
                        "type": "string",
                        "minLength": 1,
                        "maxLength": 2000,
                        "description": "Descrição do serviço que aparece na nota."
                      },
                      "local_prestacao_ibge": {
                        "type": "string",
                        "pattern": "^[0-9]{7}$",
                        "description": "Município onde o serviço foi prestado (IBGE, 7 dígitos). Padrão: o município do prestador."
                      },
                      "forcar_codigo": {
                        "type": "boolean",
                        "description": "Dispensa a conferência do código com o catálogo e com os CNAEs do prestador. A responsabilidade pelo enquadramento passa a ser de quem emite, e a nota registra que o código foi forçado."
                      }
                    },
                    "additionalProperties": false,
                    "default": {},
                    "description": "O serviço prestado. Qualquer campo omitido cai no padrão fiscal do prestador."
                  },
                  "valores": {
                    "type": "object",
                    "properties": {
                      "valor_servicos_centavos": {
                        "type": "integer",
                        "exclusiveMinimum": 0,
                        "maximum": 9999999999999,
                        "description": "Valor do serviço em centavos: R$ 1.500,00 = `150000`."
                      },
                      "desconto_incondicionado_centavos": {
                        "type": "integer",
                        "minimum": 0,
                        "maximum": 9999999999999,
                        "description": "Desconto incondicionado em centavos. Precisa ser menor que o valor do serviço."
                      },
                      "iss_retido": {
                        "type": "boolean",
                        "description": "O tomador retém o ISS. MEI não pode ter ISS retido."
                      },
                      "aliquota_iss": {
                        "type": "number",
                        "minimum": 0,
                        "maximum": 5,
                        "description": "Alíquota do ISS em porcentagem (2 = 2%), de 0 a 5. Padrão: a do prestador."
                      }
                    },
                    "required": [
                      "valor_servicos_centavos"
                    ],
                    "additionalProperties": false,
                    "description": "Valores da nota. Todo dinheiro é em **centavos inteiros**."
                  },
                  "informacoes_complementares": {
                    "type": "string",
                    "minLength": 1,
                    "maxLength": 2000,
                    "description": "Texto livre impresso na nota (até 2.000 caracteres)."
                  },
                  "metadados": {
                    "type": "object",
                    "additionalProperties": {
                      "type": "string",
                      "maxLength": 500
                    },
                    "description": "Até 20 pares chave/valor (texto até 500 caracteres) para você correlacionar com o seu sistema. Voltam nas respostas e nos webhooks."
                  }
                },
                "required": [
                  "tomador",
                  "valores"
                ],
                "additionalProperties": false
              },
              "examples": {
                "tomador-inline": {
                  "summary": "Tomador pessoa física informado na hora",
                  "value": {
                    "referencia_externa": "pedido-48213",
                    "tomador": {
                      "tipo_documento": "cpf",
                      "documento": "52998224725",
                      "nome": "Maria Souza",
                      "email": "maria@example.com"
                    },
                    "servico": {
                      "codigo_tributacao_nacional": "010701",
                      "descricao": "Desenvolvimento de software sob encomenda"
                    },
                    "valores": {
                      "valor_servicos_centavos": 150000,
                      "aliquota_iss": 2
                    },
                    "metadados": {
                      "pedido": "48213"
                    }
                  }
                },
                "tomador-cadastrado": {
                  "summary": "Tomador cadastrado e padrões do prestador",
                  "value": {
                    "tomador": {
                      "tomador_id": "3b8d0f52-91c4-4a7e-8f26-5e1c7a9d4b02"
                    },
                    "valores": {
                      "valor_servicos_centavos": 99900
                    }
                  }
                }
              }
            }
          }
        },
        "responses": {
          "202": {
            "description": "Nota aceita e na fila. Se a `Idempotency-Key` já foi usada com o mesmo corpo, repete a resposta original e inclui `Idempotent-Replayed: true`.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              },
              "Location": {
                "description": "URL da nota (`/v1/notas/{id}`).",
                "schema": {
                  "type": "string"
                }
              },
              "Idempotent-Replayed": {
                "description": "`true` quando esta resposta é a repetição de uma emissão anterior com a mesma chave.",
                "schema": {
                  "type": "string"
                }
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Nota"
                },
                "example": {
                  "id": "7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25",
                  "fase": "enfileirada",
                  "ambiente": "sandbox",
                  "sem_validade_juridica": true,
                  "prestador_id": "0c1f7e3a-5d2b-4c8e-9a41-7b6d2e9f1a30",
                  "referencia_externa": "pedido-48213",
                  "competencia": "2026-11-13",
                  "tomador": {
                    "id": "3b8d0f52-91c4-4a7e-8f26-5e1c7a9d4b02",
                    "tipo_documento": "cpf",
                    "documento_mascarado": "***.982.247-**",
                    "nome": "Maria Souza"
                  },
                  "servico": {
                    "codigo_tributacao_nacional": "010701",
                    "codigo_tributacao_municipal": null,
                    "codigo_nbs": null,
                    "descricao": "Desenvolvimento de software sob encomenda",
                    "local_prestacao_ibge": "3550308"
                  },
                  "valores": {
                    "valor_servicos_centavos": 150000,
                    "desconto_incondicionado_centavos": 0,
                    "aliquota_iss": 2,
                    "valor_iss_centavos": 3000,
                    "iss_retido": false
                  },
                  "informacoes_complementares": null,
                  "metadados": {
                    "pedido": "48213"
                  },
                  "dps": {
                    "serie": "1",
                    "numero": 37,
                    "id": "DPS355030821122233300018100001000000000000037"
                  },
                  "cancelamento": null,
                  "substituicao": null,
                  "prazos": null,
                  "erros": null,
                  "origem": "api",
                  "criado_em": "2026-11-13T14:02:11.482Z",
                  "atualizado_em": "2026-11-13T14:02:11.482Z",
                  "status": "processando",
                  "nfse": null,
                  "emitida_em": null,
                  "cancelada_em": null,
                  "acoes": {
                    "cancelar": false,
                    "substituir": false,
                    "reprocessar": false,
                    "baixar_xml": false,
                    "baixar_pdf": false
                  },
                  "links": {
                    "self": "/v1/notas/7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25"
                  }
                }
              }
            }
          },
          "400": {
            "$ref": "#/components/responses/RequisicaoInvalida"
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "402": {
            "$ref": "#/components/responses/PagamentoNecessario"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "409": {
            "$ref": "#/components/responses/Conflito"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "notas:emitir"
            ]
          }
        ],
        "x-escopo": "notas:emitir",
        "x-codigos": [
          {
            "status": 400,
            "code": "cabecalho_idempotency_key_ausente",
            "quando": "Faltou o cabeçalho `Idempotency-Key`."
          },
          {
            "status": 400,
            "code": "cabecalho_sandbox_em_producao",
            "quando": "`X-Sandbox-Scenario` enviado com chave de produção."
          },
          {
            "status": 402,
            "code": "plano_sem_producao",
            "quando": "O plano não permite emitir em produção."
          },
          {
            "status": 402,
            "code": "assinatura_inadimplente",
            "quando": "Há fatura em aberto (planos de assinatura)."
          },
          {
            "status": 402,
            "code": "saldo_insuficiente",
            "quando": "Créditos insuficientes (plano pré-pago)."
          },
          {
            "status": 409,
            "code": "referencia_externa_duplicada",
            "quando": "Já existe uma nota com esta `referencia_externa`; o erro traz `nota_id`."
          },
          {
            "status": 409,
            "code": "idempotencia_em_andamento",
            "quando": "A primeira requisição com esta chave ainda está em curso; repita em instantes."
          },
          {
            "status": 409,
            "code": "tomador_anonimizado",
            "quando": "O tomador foi anonimizado e não serve para notas novas."
          },
          {
            "status": 409,
            "code": "conector_fiscal_nao_configurado",
            "quando": "Produção indisponível na plataforma (conector fiscal em simulador ou sem as raízes ICP-Brasil). Nada é criado nem cobrado; use o Sandbox."
          },
          {
            "status": 422,
            "code": "validacao",
            "quando": "Corpo inválido; veja `errors`."
          },
          {
            "status": 422,
            "code": "idempotencia_corpo_diferente",
            "quando": "A `Idempotency-Key` já foi usada com outro conteúdo."
          },
          {
            "status": 422,
            "code": "prestador_inativo",
            "quando": "O prestador está inativo."
          },
          {
            "status": 422,
            "code": "municipio_nao_atendido",
            "quando": "Município fora da cobertura (produção)."
          },
          {
            "status": 422,
            "code": "regime_nao_atendido_no_municipio",
            "quando": "O regime tributário ainda não é atendido no município."
          },
          {
            "status": 422,
            "code": "autorizacao_expirada",
            "quando": "O certificado A1 do prestador expirou (produção)."
          },
          {
            "status": 422,
            "code": "certificado_ausente_ou_invalido",
            "quando": "Produção: o prestador não tem certificado A1, ele não é da empresa (CNPJ) ou não vem da cadeia ICP-Brasil; o erro traz `motivo` e `acao`."
          },
          {
            "status": 422,
            "code": "autorizacao_revogada",
            "quando": "O certificado A1 do prestador foi removido (produção)."
          },
          {
            "status": 422,
            "code": "competencia_futura",
            "quando": "A competência é posterior a hoje."
          },
          {
            "status": 422,
            "code": "codigo_tributacao_desconhecido",
            "quando": "O código de tributação não consta na tabela nacional; `errors[].sugestoes` traz opções."
          },
          {
            "status": 422,
            "code": "codigo_tributacao_incompativel",
            "quando": "O código não corresponde aos CNAEs do prestador; `errors[].sugestoes` traz opções. Use `servico.forcar_codigo` para assumir o código."
          },
          {
            "status": 422,
            "code": "iss_retido_mei",
            "quando": "MEI não pode ter ISS retido."
          },
          {
            "status": 422,
            "code": "tomador_exterior_nao_suportado",
            "quando": "Tomador do exterior ainda não é suportado."
          }
        ]
      },
      "get": {
        "operationId": "listarNotas",
        "tags": [
          "Notas"
        ],
        "summary": "Listar notas",
        "description": "Lista as notas do ambiente da chave, da mais recente para a mais antiga, com paginação por cursor.\n\n**Escopo necessário:** `notas:ler`.",
        "parameters": [
          {
            "name": "limite",
            "in": "query",
            "required": false,
            "description": "Itens por página (1 a 100).",
            "schema": {
              "type": "integer",
              "minimum": 1,
              "maximum": 100,
              "default": 25
            }
          },
          {
            "name": "cursor",
            "in": "query",
            "required": false,
            "description": "Valor de `proximo_cursor` da página anterior.",
            "schema": {
              "type": "string",
              "maxLength": 500
            }
          },
          {
            "name": "status",
            "in": "query",
            "required": false,
            "description": "Filtra pelo status.",
            "schema": {
              "type": "string",
              "enum": [
                "processando",
                "autorizada",
                "rejeitada",
                "cancelada",
                "erro"
              ]
            }
          },
          {
            "name": "prestador_id",
            "in": "query",
            "required": false,
            "description": "Só as notas deste prestador. Omitido: de todos os prestadores da conta.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          },
          {
            "name": "tomador_id",
            "in": "query",
            "required": false,
            "description": "Identificador de um tomador cadastrado.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          },
          {
            "name": "referencia_externa",
            "in": "query",
            "required": false,
            "description": "O identificador da venda no **seu** sistema. É único por conta e ambiente (exceto notas rejeitadas): reenviar a mesma referência dá `409 referencia_externa_duplicada`.",
            "schema": {
              "type": "string",
              "minLength": 1,
              "maxLength": 100
            }
          },
          {
            "name": "competencia_de",
            "in": "query",
            "required": false,
            "description": "Competência a partir de (AAAA-MM-DD, inclusive).",
            "schema": {
              "type": "string",
              "pattern": "^\\d{4}-\\d{2}-\\d{2}$"
            }
          },
          {
            "name": "competencia_ate",
            "in": "query",
            "required": false,
            "description": "Competência até (AAAA-MM-DD, inclusive).",
            "schema": {
              "type": "string",
              "pattern": "^\\d{4}-\\d{2}-\\d{2}$"
            }
          },
          {
            "name": "criado_de",
            "in": "query",
            "required": false,
            "description": "Criada a partir de: data (AAAA-MM-DD, 00:00 em Brasília) ou data e hora ISO 8601.",
            "schema": {
              "type": "string",
              "pattern": "^\\d{4}-\\d{2}-\\d{2}(T[\\d:.]+(Z|[+-]\\d{2}:\\d{2}))?$"
            }
          },
          {
            "name": "criado_ate",
            "in": "query",
            "required": false,
            "description": "Criada até: data (vale o dia inteiro, Brasília) ou data e hora ISO 8601 (exclusivo).",
            "schema": {
              "type": "string",
              "pattern": "^\\d{4}-\\d{2}-\\d{2}(T[\\d:.]+(Z|[+-]\\d{2}:\\d{2}))?$"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Página de notas.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ListaDeNotas"
                },
                "example": {
                  "dados": [
                    {
                      "id": "7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25",
                      "fase": null,
                      "ambiente": "sandbox",
                      "sem_validade_juridica": true,
                      "prestador_id": "0c1f7e3a-5d2b-4c8e-9a41-7b6d2e9f1a30",
                      "referencia_externa": "pedido-48213",
                      "competencia": "2026-11-13",
                      "tomador": {
                        "id": "3b8d0f52-91c4-4a7e-8f26-5e1c7a9d4b02",
                        "tipo_documento": "cpf",
                        "documento_mascarado": "***.982.247-**",
                        "nome": "Maria Souza"
                      },
                      "servico": {
                        "codigo_tributacao_nacional": "010701",
                        "codigo_tributacao_municipal": null,
                        "codigo_nbs": null,
                        "descricao": "Desenvolvimento de software sob encomenda",
                        "local_prestacao_ibge": "3550308"
                      },
                      "valores": {
                        "valor_servicos_centavos": 150000,
                        "desconto_incondicionado_centavos": 0,
                        "aliquota_iss": 2,
                        "valor_iss_centavos": 3000,
                        "iss_retido": false
                      },
                      "informacoes_complementares": null,
                      "metadados": {
                        "pedido": "48213"
                      },
                      "dps": {
                        "serie": "1",
                        "numero": 37,
                        "id": "DPS355030821122233300018100001000000000000037"
                      },
                      "cancelamento": null,
                      "substituicao": null,
                      "prazos": {
                        "cancelamento": {
                          "prazo_dias": 730,
                          "limite_em": "2028-11-12",
                          "dias_restantes": 730,
                          "dentro_do_prazo": true,
                          "explicacao": "Dá para cancelar até 12/11/2028 (730 dias contados da emissão)."
                        },
                        "substituicao": {
                          "prazo_dias": 730,
                          "limite_em": "2028-11-12",
                          "dias_restantes": 730,
                          "dentro_do_prazo": true,
                          "explicacao": "Dá para substituir até 12/11/2028 (730 dias contados da emissão).",
                          "sem_prazo_para": [
                            "desenquadramento_simples_nacional",
                            "enquadramento_simples_nacional"
                          ]
                        }
                      },
                      "erros": null,
                      "origem": "api",
                      "criado_em": "2026-11-13T14:02:11.482Z",
                      "atualizado_em": "2026-11-13T14:02:13.905Z",
                      "status": "autorizada",
                      "nfse": {
                        "numero": "37",
                        "chave_acesso": "35503082112223330001810000000000003710A4F1C9D2",
                        "codigo_verificacao": "A4F1C9D2",
                        "protocolo": "SIM3C9E1A7B52D4",
                        "conector": "simulador"
                      },
                      "emitida_em": "2026-11-13T14:02:13.905Z",
                      "cancelada_em": null,
                      "acoes": {
                        "cancelar": true,
                        "substituir": true,
                        "reprocessar": false,
                        "baixar_xml": true,
                        "baixar_pdf": true
                      },
                      "links": {
                        "self": "/v1/notas/7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25",
                        "xml": "/v1/notas/7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25/xml",
                        "pdf": "/v1/notas/7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25/pdf"
                      }
                    }
                  ],
                  "proximo_cursor": null
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "notas:ler"
            ]
          }
        ],
        "x-escopo": "notas:ler"
      }
    },
    "/v1/notas/{id}": {
      "get": {
        "operationId": "obterNota",
        "tags": [
          "Notas"
        ],
        "summary": "Consultar uma nota",
        "description": "Devolve a nota com a linha do tempo (`eventos`). Use para acompanhar uma emissão que ainda está `processando`.\n\n**Escopo necessário:** `notas:ler`.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "description": "Identificador do recurso.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "A nota.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Nota"
                },
                "example": {
                  "id": "7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25",
                  "fase": null,
                  "ambiente": "sandbox",
                  "sem_validade_juridica": true,
                  "prestador_id": "0c1f7e3a-5d2b-4c8e-9a41-7b6d2e9f1a30",
                  "referencia_externa": "pedido-48213",
                  "competencia": "2026-11-13",
                  "tomador": {
                    "id": "3b8d0f52-91c4-4a7e-8f26-5e1c7a9d4b02",
                    "tipo_documento": "cpf",
                    "documento_mascarado": "***.982.247-**",
                    "nome": "Maria Souza"
                  },
                  "servico": {
                    "codigo_tributacao_nacional": "010701",
                    "codigo_tributacao_municipal": null,
                    "codigo_nbs": null,
                    "descricao": "Desenvolvimento de software sob encomenda",
                    "local_prestacao_ibge": "3550308"
                  },
                  "valores": {
                    "valor_servicos_centavos": 150000,
                    "desconto_incondicionado_centavos": 0,
                    "aliquota_iss": 2,
                    "valor_iss_centavos": 3000,
                    "iss_retido": false
                  },
                  "informacoes_complementares": null,
                  "metadados": {
                    "pedido": "48213"
                  },
                  "dps": {
                    "serie": "1",
                    "numero": 37,
                    "id": "DPS355030821122233300018100001000000000000037"
                  },
                  "cancelamento": null,
                  "substituicao": null,
                  "prazos": {
                    "cancelamento": {
                      "prazo_dias": 730,
                      "limite_em": "2028-11-12",
                      "dias_restantes": 730,
                      "dentro_do_prazo": true,
                      "explicacao": "Dá para cancelar até 12/11/2028 (730 dias contados da emissão)."
                    },
                    "substituicao": {
                      "prazo_dias": 730,
                      "limite_em": "2028-11-12",
                      "dias_restantes": 730,
                      "dentro_do_prazo": true,
                      "explicacao": "Dá para substituir até 12/11/2028 (730 dias contados da emissão).",
                      "sem_prazo_para": [
                        "desenquadramento_simples_nacional",
                        "enquadramento_simples_nacional"
                      ]
                    }
                  },
                  "erros": null,
                  "origem": "api",
                  "criado_em": "2026-11-13T14:02:11.482Z",
                  "atualizado_em": "2026-11-13T14:02:13.905Z",
                  "status": "autorizada",
                  "nfse": {
                    "numero": "37",
                    "chave_acesso": "35503082112223330001810000000000003710A4F1C9D2",
                    "codigo_verificacao": "A4F1C9D2",
                    "protocolo": "SIM3C9E1A7B52D4",
                    "conector": "simulador"
                  },
                  "emitida_em": "2026-11-13T14:02:13.905Z",
                  "cancelada_em": null,
                  "acoes": {
                    "cancelar": true,
                    "substituir": true,
                    "reprocessar": false,
                    "baixar_xml": true,
                    "baixar_pdf": true
                  },
                  "links": {
                    "self": "/v1/notas/7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25",
                    "xml": "/v1/notas/7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25/xml",
                    "pdf": "/v1/notas/7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25/pdf"
                  },
                  "eventos": [
                    {
                      "tipo": "nota.criada",
                      "detalhe": {
                        "origem": "api",
                        "numero_dps": 37,
                        "serie_dps": "1"
                      },
                      "criado_em": "2026-11-13T14:02:11.482Z"
                    },
                    {
                      "tipo": "emissao.transmitindo",
                      "detalhe": {
                        "tentativa": 1,
                        "conector": "simulador"
                      },
                      "criado_em": "2026-11-13T14:02:13.905Z"
                    },
                    {
                      "tipo": "nota.autorizada",
                      "detalhe": {
                        "numero_nfse": "37",
                        "conector": "simulador"
                      },
                      "criado_em": "2026-11-13T14:02:13.905Z"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "notas:ler"
            ]
          }
        ],
        "x-escopo": "notas:ler"
      }
    },
    "/v1/notas/{id}/cancelar": {
      "post": {
        "operationId": "cancelarNota",
        "tags": [
          "Notas"
        ],
        "summary": "Cancelar uma nota",
        "description": "Pede o cancelamento de uma nota **autorizada**. Também é assíncrono: a resposta é `202` com `fase: \"cancelamento_pendente\"`; o resultado vem pelo webhook `nota.cancelada` (ou a nota volta a `autorizada` se o município negar). `Idempotency-Key` é opcional aqui, mas recomendado.\n\n**Prazo.** O cancelamento tem prazo contado da emissão: 730 dias por padrão (o prazo que o padrão nacional adota quando o município não define outro), configurável pela plataforma. Passado o prazo, a resposta é `422 prazo_cancelamento_expirado`, com `acao` dizendo o que fazer: pedir o cancelamento por substituição (`POST /v1/notas/{id}/substituir`, enquanto o prazo de substituição valer) ou pedir à prefeitura o cancelamento por solicitação de análise fiscal. `prazos` e `acoes.cancelar` na nota já mostram isso antes de tentar. Se o município do prestador fixar um prazo menor que o configurado, o município recusa o cancelamento e a nota volta a `autorizada` (evento `cancelamento.indeferido`, com a orientação em português).\n\n**Escopo necessário:** `notas:cancelar`.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "description": "Identificador do recurso.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          },
          {
            "name": "Idempotency-Key",
            "in": "header",
            "required": false,
            "description": "Identifica a intenção de emitir. Gere um UUID novo por nota e **reutilize-o em qualquer repetição** da mesma chamada: se a primeira tentativa chegou, você recebe a mesma resposta (com `Idempotent-Replayed: true`) e nada é emitido em duplicidade. Até 128 caracteres ASCII visíveis; vale por 7 dias.",
            "schema": {
              "type": "string"
            },
            "example": "3f2b8c1e-9a47-4d6e-b5c0-1e7a9d2f4b68"
          },
          {
            "name": "X-Sandbox-Scenario",
            "in": "header",
            "required": false,
            "description": "Só no Sandbox: força o resultado da operação. Valores: `autorizar`, `rejeitar:<codigo>`, `erro_tecnico`, `lento:<segundos>`, `timeout_incerto`, `cancelamento_negado`, `prazo_expirado` (em `cancelar` e `substituir`: trata a nota como emitida há mais tempo que os prazos, sem precisar esperar anos), `webhook_falha:<n>` (as n primeiras entregas de webhook dos eventos da nota falham de propósito, com intervalo de ~2 s entre as tentativas; a nota é autorizada normalmente). Com chave de produção a API responde `400 cabecalho_sandbox_em_producao`.",
            "schema": {
              "type": "string"
            },
            "example": "rejeitar:E160"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "motivo": {
                    "type": "string",
                    "enum": [
                      "erro_na_emissao",
                      "servico_nao_prestado",
                      "outros"
                    ],
                    "description": "Motivo do cancelamento (`erro_na_emissao`, `servico_nao_prestado` ou `outros`) ou, em `substituicao`, da substituição (`desenquadramento_simples_nacional`, `enquadramento_simples_nacional`, `inclusao_retroativa_imunidade_isencao`, `exclusao_retroativa_imunidade_isencao`, `rejeicao_tomador_intermediario` ou `outros`)."
                  },
                  "justificativa": {
                    "type": "string",
                    "minLength": 15,
                    "maxLength": 255,
                    "description": "Explicação do cancelamento ou da substituição (15 a 255 caracteres). Vai para o município. Na substituição é obrigatória com o motivo `outros`."
                  }
                },
                "required": [
                  "motivo",
                  "justificativa"
                ],
                "additionalProperties": false
              },
              "examples": {
                "padrao": {
                  "summary": "Serviço não prestado",
                  "value": {
                    "motivo": "servico_nao_prestado",
                    "justificativa": "Serviço não prestado: pedido cancelado pelo cliente antes da entrega."
                  }
                }
              }
            }
          }
        },
        "responses": {
          "202": {
            "description": "Cancelamento solicitado.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              },
              "Location": {
                "description": "URL da nota.",
                "schema": {
                  "type": "string"
                }
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Nota"
                },
                "example": {
                  "id": "7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25",
                  "fase": "cancelamento_pendente",
                  "ambiente": "sandbox",
                  "sem_validade_juridica": true,
                  "prestador_id": "0c1f7e3a-5d2b-4c8e-9a41-7b6d2e9f1a30",
                  "referencia_externa": "pedido-48213",
                  "competencia": "2026-11-13",
                  "tomador": {
                    "id": "3b8d0f52-91c4-4a7e-8f26-5e1c7a9d4b02",
                    "tipo_documento": "cpf",
                    "documento_mascarado": "***.982.247-**",
                    "nome": "Maria Souza"
                  },
                  "servico": {
                    "codigo_tributacao_nacional": "010701",
                    "codigo_tributacao_municipal": null,
                    "codigo_nbs": null,
                    "descricao": "Desenvolvimento de software sob encomenda",
                    "local_prestacao_ibge": "3550308"
                  },
                  "valores": {
                    "valor_servicos_centavos": 150000,
                    "desconto_incondicionado_centavos": 0,
                    "aliquota_iss": 2,
                    "valor_iss_centavos": 3000,
                    "iss_retido": false
                  },
                  "informacoes_complementares": null,
                  "metadados": {
                    "pedido": "48213"
                  },
                  "dps": {
                    "serie": "1",
                    "numero": 37,
                    "id": "DPS355030821122233300018100001000000000000037"
                  },
                  "cancelamento": null,
                  "substituicao": null,
                  "prazos": {
                    "cancelamento": {
                      "prazo_dias": 730,
                      "limite_em": "2028-11-12",
                      "dias_restantes": 730,
                      "dentro_do_prazo": true,
                      "explicacao": "Dá para cancelar até 12/11/2028 (730 dias contados da emissão)."
                    },
                    "substituicao": {
                      "prazo_dias": 730,
                      "limite_em": "2028-11-12",
                      "dias_restantes": 730,
                      "dentro_do_prazo": true,
                      "explicacao": "Dá para substituir até 12/11/2028 (730 dias contados da emissão).",
                      "sem_prazo_para": [
                        "desenquadramento_simples_nacional",
                        "enquadramento_simples_nacional"
                      ]
                    }
                  },
                  "erros": null,
                  "origem": "api",
                  "criado_em": "2026-11-13T14:02:11.482Z",
                  "atualizado_em": "2026-11-13T14:02:13.905Z",
                  "status": "autorizada",
                  "nfse": {
                    "numero": "37",
                    "chave_acesso": "35503082112223330001810000000000003710A4F1C9D2",
                    "codigo_verificacao": "A4F1C9D2",
                    "protocolo": "SIM3C9E1A7B52D4",
                    "conector": "simulador"
                  },
                  "emitida_em": "2026-11-13T14:02:13.905Z",
                  "cancelada_em": null,
                  "acoes": {
                    "cancelar": false,
                    "substituir": false,
                    "reprocessar": false,
                    "baixar_xml": true,
                    "baixar_pdf": true
                  },
                  "links": {
                    "self": "/v1/notas/7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25",
                    "xml": "/v1/notas/7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25/xml",
                    "pdf": "/v1/notas/7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25/pdf"
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "409": {
            "$ref": "#/components/responses/Conflito"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "notas:cancelar"
            ]
          }
        ],
        "x-escopo": "notas:cancelar",
        "x-codigos": [
          {
            "status": 409,
            "code": "nfse_estado_invalido",
            "quando": "Só dá para cancelar nota autorizada."
          },
          {
            "status": 409,
            "code": "cancelamento_em_andamento",
            "quando": "Já existe um pedido de cancelamento em curso."
          },
          {
            "status": 409,
            "code": "substituicao_em_andamento",
            "quando": "A nota está sendo substituída; aguarde o resultado da substituição."
          },
          {
            "status": 409,
            "code": "conector_fiscal_nao_configurado",
            "quando": "Produção indisponível na plataforma no momento."
          },
          {
            "status": 422,
            "code": "prazo_cancelamento_expirado",
            "quando": "O prazo para cancelar terminou. O erro traz `acao`, `prazo_dias`, `prazo_ate`, `substituicao_disponivel` e `alternativas`."
          }
        ]
      }
    },
    "/v1/notas/{id}/substituir": {
      "post": {
        "operationId": "substituirNota",
        "tags": [
          "Notas"
        ],
        "summary": "Substituir uma nota (cancelamento por substituição)",
        "description": "Emite uma **nota substituta** para uma nota **autorizada**: o cancelamento por substituição do padrão nacional (evento `e105102`). O corpo é uma emissão completa (os dados já corrigidos, como em `POST /v1/notas`) mais o grupo `substituicao` com o `motivo` e a `justificativa`. A DPS da nova nota leva a chave de acesso da nota substituída.\n\nÉ assíncrono como a emissão: a resposta é `202` com a **nota substituta** em `status: \"processando\"` (e `substituicao.substitui` apontando para a original). **A nota original só passa a `cancelada` quando a substituta for autorizada** (webhooks `nota.autorizada` da substituta e `nota.cancelada` da original). Se a substituta for rejeitada, a original continua `autorizada` e dá para tentar de novo.\n\n**Dados herdados.** O que o corpo não repetir (descrição, código de tributação, alíquota, local da prestação, competência) vem da nota original; tomador e valor do serviço são sempre obrigatórios no corpo.\n\n**O que não pode mudar** (Anexo I do leiaute nacional). Prestador Simples Nacional (ME/EPP) ou MEI: tomador, competência e valor do serviço. Demais regimes: competência, código de tributação nacional e municipal e local da prestação. Mudar algum deles dá `422 substituicao_campo_imutavel`, com `errors` listando os campos; se a mudança for mesmo necessária, peça o cancelamento à prefeitura e emita uma nota nova. O município pode ter regras próprias, aplicadas por ele.\n\n**Prazo.** Até 730 dias da emissão (limite do padrão nacional, configurável para menos). Passado o prazo, `422 prazo_substituicao_expirado`, exceto para os motivos `enquadramento_simples_nacional` e `desenquadramento_simples_nacional`, que não têm prazo.\n\nExige as permissões `notas:emitir` **e** `notas:cancelar`. A `referencia_externa` da nota original não pode ser reutilizada na substituta. Em produção, a substituta conta como uma nota emitida.\n\n⚠️ O envio do grupo `subst` ao ADN real (produção) foi implementado conforme o leiaute oficial, mas ainda não foi testado contra o ADN (exige certificado A1); no Sandbox o comportamento é simulado.\n\n**Escopos necessários (todos):** `notas:emitir`, `notas:cancelar`.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "description": "Identificador do recurso.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          },
          {
            "name": "Idempotency-Key",
            "in": "header",
            "required": true,
            "description": "Identifica a intenção de emitir. Gere um UUID novo por nota e **reutilize-o em qualquer repetição** da mesma chamada: se a primeira tentativa chegou, você recebe a mesma resposta (com `Idempotent-Replayed: true`) e nada é emitido em duplicidade. Até 128 caracteres ASCII visíveis; vale por 7 dias.",
            "schema": {
              "type": "string"
            },
            "example": "3f2b8c1e-9a47-4d6e-b5c0-1e7a9d2f4b68"
          },
          {
            "name": "X-Sandbox-Scenario",
            "in": "header",
            "required": false,
            "description": "Só no Sandbox: força o resultado da operação. Valores: `autorizar`, `rejeitar:<codigo>`, `erro_tecnico`, `lento:<segundos>`, `timeout_incerto`, `cancelamento_negado`, `prazo_expirado` (em `cancelar` e `substituir`: trata a nota como emitida há mais tempo que os prazos, sem precisar esperar anos), `webhook_falha:<n>` (as n primeiras entregas de webhook dos eventos da nota falham de propósito, com intervalo de ~2 s entre as tentativas; a nota é autorizada normalmente). Com chave de produção a API responde `400 cabecalho_sandbox_em_producao`.",
            "schema": {
              "type": "string"
            },
            "example": "rejeitar:E160"
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "prestador_id": {
                    "type": "string",
                    "format": "uuid",
                    "description": "Identificador do prestador (o CNPJ que emite). Se omitido e houver um único prestador ativo, ele é usado."
                  },
                  "referencia_externa": {
                    "type": "string",
                    "minLength": 1,
                    "maxLength": 100,
                    "description": "O identificador da venda no **seu** sistema. É único por conta e ambiente (exceto notas rejeitadas): reenviar a mesma referência dá `409 referencia_externa_duplicada`."
                  },
                  "competencia": {
                    "type": "string",
                    "pattern": "^\\d{4}-\\d{2}-\\d{2}$",
                    "description": "Mês de competência do serviço, no formato AAAA-MM-DD. Padrão: hoje (fuso de Brasília). Não pode ser futura."
                  },
                  "tomador": {
                    "type": "object",
                    "properties": {
                      "tomador_id": {
                        "type": "string",
                        "format": "uuid",
                        "description": "Identificador de um tomador cadastrado."
                      },
                      "tipo_documento": {
                        "type": "string",
                        "enum": [
                          "cpf",
                          "cnpj",
                          "estrangeiro",
                          "nenhum"
                        ],
                        "description": "Tipo do documento do tomador. Se omitido com `documento`, é detectado (11 dígitos = CPF, 14 = CNPJ)."
                      },
                      "documento": {
                        "type": "string",
                        "minLength": 3,
                        "maxLength": 30,
                        "description": "CPF ou CNPJ, com ou sem pontuação. Nunca volta em claro nas respostas."
                      },
                      "nome": {
                        "type": "string",
                        "minLength": 2,
                        "maxLength": 150,
                        "description": "Nome ou razão social."
                      },
                      "email": {
                        "type": "string",
                        "format": "email",
                        "maxLength": 200,
                        "description": "E-mail."
                      },
                      "telefone": {
                        "type": "string",
                        "pattern": "^[0-9]{10,11}$",
                        "description": "Telefone com DDD, só dígitos (10 ou 11)."
                      },
                      "endereco": {
                        "type": "object",
                        "properties": {
                          "cep": {
                            "type": "string",
                            "pattern": "^[0-9]{8}$"
                          },
                          "logradouro": {
                            "type": "string",
                            "minLength": 1,
                            "maxLength": 125
                          },
                          "numero": {
                            "type": "string",
                            "minLength": 1,
                            "maxLength": 10
                          },
                          "complemento": {
                            "anyOf": [
                              {
                                "type": "string",
                                "maxLength": 60
                              },
                              {
                                "type": "null"
                              }
                            ]
                          },
                          "bairro": {
                            "type": "string",
                            "minLength": 1,
                            "maxLength": 60
                          },
                          "municipio_ibge": {
                            "type": "string",
                            "pattern": "^[0-9]{7}$",
                            "description": "Município do prestador (IBGE, 7 dígitos). Precisa estar na cobertura."
                          }
                        },
                        "required": [
                          "cep",
                          "logradouro",
                          "numero",
                          "bairro",
                          "municipio_ibge"
                        ],
                        "additionalProperties": false,
                        "description": "Endereço completo."
                      }
                    },
                    "additionalProperties": false,
                    "description": "Quem contrata o serviço. Informe `tomador_id` **ou** os dados completos."
                  },
                  "servico": {
                    "type": "object",
                    "properties": {
                      "codigo_tributacao_nacional": {
                        "type": "string",
                        "pattern": "^[0-9]{6}$",
                        "description": "Código de tributação nacional (6 dígitos: item da LC 116 + subitem + desdobro). Ex.: `010701`. Na emissão ele é conferido com o catálogo nacional e com os CNAEs do prestador (veja `forcar_codigo`)."
                      },
                      "codigo_tributacao_municipal": {
                        "type": "string",
                        "minLength": 1,
                        "maxLength": 20,
                        "description": "Código de tributação municipal, quando o município exige."
                      },
                      "codigo_nbs": {
                        "type": "string",
                        "pattern": "^[0-9]{9}$",
                        "description": "Código NBS (9 dígitos)."
                      },
                      "descricao": {
                        "type": "string",
                        "minLength": 1,
                        "maxLength": 2000,
                        "description": "Descrição do serviço que aparece na nota."
                      },
                      "local_prestacao_ibge": {
                        "type": "string",
                        "pattern": "^[0-9]{7}$",
                        "description": "Município onde o serviço foi prestado (IBGE, 7 dígitos). Padrão: o município do prestador."
                      },
                      "forcar_codigo": {
                        "type": "boolean",
                        "description": "Dispensa a conferência do código com o catálogo e com os CNAEs do prestador. A responsabilidade pelo enquadramento passa a ser de quem emite, e a nota registra que o código foi forçado."
                      }
                    },
                    "additionalProperties": false,
                    "default": {},
                    "description": "O serviço prestado. Qualquer campo omitido cai no padrão fiscal do prestador."
                  },
                  "valores": {
                    "type": "object",
                    "properties": {
                      "valor_servicos_centavos": {
                        "type": "integer",
                        "exclusiveMinimum": 0,
                        "maximum": 9999999999999,
                        "description": "Valor do serviço em centavos: R$ 1.500,00 = `150000`."
                      },
                      "desconto_incondicionado_centavos": {
                        "type": "integer",
                        "minimum": 0,
                        "maximum": 9999999999999,
                        "description": "Desconto incondicionado em centavos. Precisa ser menor que o valor do serviço."
                      },
                      "iss_retido": {
                        "type": "boolean",
                        "description": "O tomador retém o ISS. MEI não pode ter ISS retido."
                      },
                      "aliquota_iss": {
                        "type": "number",
                        "minimum": 0,
                        "maximum": 5,
                        "description": "Alíquota do ISS em porcentagem (2 = 2%), de 0 a 5. Padrão: a do prestador."
                      }
                    },
                    "required": [
                      "valor_servicos_centavos"
                    ],
                    "additionalProperties": false,
                    "description": "Valores da nota. Todo dinheiro é em **centavos inteiros**."
                  },
                  "informacoes_complementares": {
                    "type": "string",
                    "minLength": 1,
                    "maxLength": 2000,
                    "description": "Texto livre impresso na nota (até 2.000 caracteres)."
                  },
                  "metadados": {
                    "type": "object",
                    "additionalProperties": {
                      "type": "string",
                      "maxLength": 500
                    },
                    "description": "Até 20 pares chave/valor (texto até 500 caracteres) para você correlacionar com o seu sistema. Voltam nas respostas e nos webhooks."
                  },
                  "substituicao": {
                    "type": "object",
                    "properties": {
                      "motivo": {
                        "type": "string",
                        "enum": [
                          "desenquadramento_simples_nacional",
                          "enquadramento_simples_nacional",
                          "inclusao_retroativa_imunidade_isencao",
                          "exclusao_retroativa_imunidade_isencao",
                          "rejeicao_tomador_intermediario",
                          "outros"
                        ],
                        "description": "Motivo do cancelamento (`erro_na_emissao`, `servico_nao_prestado` ou `outros`) ou, em `substituicao`, da substituição (`desenquadramento_simples_nacional`, `enquadramento_simples_nacional`, `inclusao_retroativa_imunidade_isencao`, `exclusao_retroativa_imunidade_isencao`, `rejeicao_tomador_intermediario` ou `outros`)."
                      },
                      "justificativa": {
                        "type": "string",
                        "minLength": 15,
                        "maxLength": 255,
                        "description": "Explicação do cancelamento ou da substituição (15 a 255 caracteres). Vai para o município. Na substituição é obrigatória com o motivo `outros`."
                      }
                    },
                    "required": [
                      "motivo"
                    ],
                    "additionalProperties": false,
                    "description": "Dados do cancelamento por substituição: o `motivo` (códigos 01 a 05 e 99 do padrão nacional) e a `justificativa`. A nota enviada nesta chamada é a nota **substituta**."
                  }
                },
                "required": [
                  "tomador",
                  "valores",
                  "substituicao"
                ],
                "additionalProperties": false
              },
              "examples": {
                "padrao": {
                  "summary": "Substituir corrigindo a descrição do serviço",
                  "value": {
                    "tomador": {
                      "tipo_documento": "cpf",
                      "documento": "52998224725",
                      "nome": "Maria Souza"
                    },
                    "servico": {
                      "descricao": "Desenvolvimento de software sob encomenda (módulo de relatórios)"
                    },
                    "valores": {
                      "valor_servicos_centavos": 150000,
                      "aliquota_iss": 2
                    },
                    "substituicao": {
                      "motivo": "outros",
                      "justificativa": "Descrição do serviço corrigida a pedido do cliente."
                    }
                  }
                },
                "simples-nacional": {
                  "summary": "Desenquadramento do Simples Nacional (sem prazo e sem justificativa obrigatória)",
                  "value": {
                    "tomador": {
                      "tipo_documento": "cpf",
                      "documento": "52998224725",
                      "nome": "Maria Souza"
                    },
                    "valores": {
                      "valor_servicos_centavos": 150000
                    },
                    "substituicao": {
                      "motivo": "desenquadramento_simples_nacional"
                    }
                  }
                }
              }
            }
          }
        },
        "responses": {
          "202": {
            "description": "Nota substituta aceita e na fila. A resposta é a nota **substituta**; a original segue `autorizada` até a substituta ser autorizada.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              },
              "Location": {
                "description": "URL da nota substituta (`/v1/notas/{id}`).",
                "schema": {
                  "type": "string"
                }
              },
              "Idempotent-Replayed": {
                "description": "`true` quando esta resposta é a repetição de uma chamada anterior com a mesma chave.",
                "schema": {
                  "type": "string"
                }
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Nota"
                },
                "example": {
                  "id": "2d9f5b83-6a1c-4e07-9b48-c5a3e1f7d609",
                  "fase": "enfileirada",
                  "ambiente": "sandbox",
                  "sem_validade_juridica": true,
                  "prestador_id": "0c1f7e3a-5d2b-4c8e-9a41-7b6d2e9f1a30",
                  "referencia_externa": null,
                  "competencia": "2026-11-13",
                  "tomador": {
                    "id": "3b8d0f52-91c4-4a7e-8f26-5e1c7a9d4b02",
                    "tipo_documento": "cpf",
                    "documento_mascarado": "***.982.247-**",
                    "nome": "Maria Souza"
                  },
                  "servico": {
                    "codigo_tributacao_nacional": "010701",
                    "codigo_tributacao_municipal": null,
                    "codigo_nbs": null,
                    "descricao": "Desenvolvimento de software sob encomenda",
                    "local_prestacao_ibge": "3550308"
                  },
                  "valores": {
                    "valor_servicos_centavos": 150000,
                    "desconto_incondicionado_centavos": 0,
                    "aliquota_iss": 2,
                    "valor_iss_centavos": 3000,
                    "iss_retido": false
                  },
                  "informacoes_complementares": null,
                  "metadados": {
                    "pedido": "48213"
                  },
                  "dps": {
                    "serie": "1",
                    "numero": 38,
                    "id": "DPS355030821122233300018100001000000000000038"
                  },
                  "cancelamento": null,
                  "substituicao": {
                    "substitui": {
                      "nota_id": "7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25",
                      "chave_acesso": "35503082112223330001810000000000003710A4F1C9D2",
                      "motivo": "outros",
                      "justificativa": "Descrição do serviço corrigida a pedido do cliente."
                    },
                    "substituida_por": null
                  },
                  "prazos": null,
                  "erros": null,
                  "origem": "api",
                  "criado_em": "2026-11-13T14:02:11.482Z",
                  "atualizado_em": "2026-11-13T14:02:11.482Z",
                  "status": "processando",
                  "nfse": null,
                  "emitida_em": null,
                  "cancelada_em": null,
                  "acoes": {
                    "cancelar": false,
                    "substituir": false,
                    "reprocessar": false,
                    "baixar_xml": false,
                    "baixar_pdf": false
                  },
                  "links": {
                    "self": "/v1/notas/2d9f5b83-6a1c-4e07-9b48-c5a3e1f7d609"
                  }
                }
              }
            }
          },
          "400": {
            "$ref": "#/components/responses/RequisicaoInvalida"
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "402": {
            "$ref": "#/components/responses/PagamentoNecessario"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "409": {
            "$ref": "#/components/responses/Conflito"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "notas:emitir",
              "notas:cancelar"
            ]
          }
        ],
        "x-escopo": "notas:emitir",
        "x-escopos-adicionais": [
          "notas:cancelar"
        ],
        "x-codigos": [
          {
            "status": 400,
            "code": "cabecalho_idempotency_key_ausente",
            "quando": "Faltou o cabeçalho `Idempotency-Key`."
          },
          {
            "status": 403,
            "code": "escopo_insuficiente",
            "quando": "A chave precisa das permissões `notas:emitir` e `notas:cancelar`."
          },
          {
            "status": 409,
            "code": "nfse_estado_invalido",
            "quando": "Só dá para substituir nota `autorizada`."
          },
          {
            "status": 409,
            "code": "nfse_ja_substituida",
            "quando": "A nota já foi substituída por outra; o erro traz `nota_substituta_id`. Substitua a nota substituta, se for o caso."
          },
          {
            "status": 409,
            "code": "substituicao_em_andamento",
            "quando": "Já existe uma nota substituta sendo emitida para esta nota; o erro traz `nota_substituta_id`."
          },
          {
            "status": 409,
            "code": "cancelamento_em_andamento",
            "quando": "Há um pedido de cancelamento em curso para a nota."
          },
          {
            "status": 409,
            "code": "referencia_externa_duplicada",
            "quando": "A `referencia_externa` já pertence a outra nota (inclusive à original)."
          },
          {
            "status": 422,
            "code": "prazo_substituicao_expirado",
            "quando": "O prazo para substituir terminou. O erro traz `acao`, `prazo_dias` e `prazo_ate`."
          },
          {
            "status": 422,
            "code": "substituicao_campo_imutavel",
            "quando": "O pedido muda um campo que não pode mudar na substituição; `errors` lista os campos."
          },
          {
            "status": 422,
            "code": "validacao",
            "quando": "Corpo inválido; veja `errors` (por exemplo, motivo `outros` sem `justificativa`)."
          }
        ]
      }
    },
    "/v1/notas/{id}/reprocessar": {
      "post": {
        "operationId": "reprocessarNota",
        "tags": [
          "Notas"
        ],
        "summary": "Reprocessar uma nota com erro",
        "description": "Recoloca na fila uma nota em `status: \"erro\"` (falha técnica depois de todas as tentativas), com a mesma DPS e sem gastar outro número. Notas `rejeitadas` não são reprocessadas: corrija os dados e emita de novo. No Sandbox, o reprocessamento é uma tentativa nova: vale o `X-Sandbox-Scenario` enviado agora e, sem o cabeçalho, o cenário da emissão original é descartado.\n\n**Escopo necessário:** `notas:emitir`.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "description": "Identificador do recurso.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          },
          {
            "name": "X-Sandbox-Scenario",
            "in": "header",
            "required": false,
            "description": "Só no Sandbox: força o resultado da operação. Valores: `autorizar`, `rejeitar:<codigo>`, `erro_tecnico`, `lento:<segundos>`, `timeout_incerto`, `cancelamento_negado`, `prazo_expirado` (em `cancelar` e `substituir`: trata a nota como emitida há mais tempo que os prazos, sem precisar esperar anos), `webhook_falha:<n>` (as n primeiras entregas de webhook dos eventos da nota falham de propósito, com intervalo de ~2 s entre as tentativas; a nota é autorizada normalmente). Com chave de produção a API responde `400 cabecalho_sandbox_em_producao`.",
            "schema": {
              "type": "string"
            },
            "example": "rejeitar:E160"
          }
        ],
        "responses": {
          "202": {
            "description": "Nota de volta à fila.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              },
              "Location": {
                "description": "URL da nota.",
                "schema": {
                  "type": "string"
                }
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Nota"
                },
                "example": {
                  "id": "7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25",
                  "fase": "enfileirada",
                  "ambiente": "sandbox",
                  "sem_validade_juridica": true,
                  "prestador_id": "0c1f7e3a-5d2b-4c8e-9a41-7b6d2e9f1a30",
                  "referencia_externa": "pedido-48213",
                  "competencia": "2026-11-13",
                  "tomador": {
                    "id": "3b8d0f52-91c4-4a7e-8f26-5e1c7a9d4b02",
                    "tipo_documento": "cpf",
                    "documento_mascarado": "***.982.247-**",
                    "nome": "Maria Souza"
                  },
                  "servico": {
                    "codigo_tributacao_nacional": "010701",
                    "codigo_tributacao_municipal": null,
                    "codigo_nbs": null,
                    "descricao": "Desenvolvimento de software sob encomenda",
                    "local_prestacao_ibge": "3550308"
                  },
                  "valores": {
                    "valor_servicos_centavos": 150000,
                    "desconto_incondicionado_centavos": 0,
                    "aliquota_iss": 2,
                    "valor_iss_centavos": 3000,
                    "iss_retido": false
                  },
                  "informacoes_complementares": null,
                  "metadados": {
                    "pedido": "48213"
                  },
                  "dps": {
                    "serie": "1",
                    "numero": 37,
                    "id": "DPS355030821122233300018100001000000000000037"
                  },
                  "cancelamento": null,
                  "substituicao": null,
                  "prazos": null,
                  "erros": null,
                  "origem": "api",
                  "criado_em": "2026-11-13T14:02:11.482Z",
                  "atualizado_em": "2026-11-13T14:02:11.482Z",
                  "status": "processando",
                  "nfse": null,
                  "emitida_em": null,
                  "cancelada_em": null,
                  "acoes": {
                    "cancelar": false,
                    "substituir": false,
                    "reprocessar": false,
                    "baixar_xml": false,
                    "baixar_pdf": false
                  },
                  "links": {
                    "self": "/v1/notas/7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25"
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "402": {
            "$ref": "#/components/responses/PagamentoNecessario"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "409": {
            "$ref": "#/components/responses/Conflito"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "notas:emitir"
            ]
          }
        ],
        "x-escopo": "notas:emitir",
        "x-codigos": [
          {
            "status": 409,
            "code": "nfse_estado_invalido",
            "quando": "Só dá para reprocessar nota com `status: \"erro\"`."
          },
          {
            "status": 409,
            "code": "conector_fiscal_nao_configurado",
            "quando": "Produção indisponível na plataforma (conector fiscal em simulador ou sem as raízes ICP-Brasil)."
          },
          {
            "status": 422,
            "code": "certificado_ausente_ou_invalido",
            "quando": "Produção: o A1 do prestador deixou de valer (removido, de outra empresa ou fora da ICP-Brasil)."
          },
          {
            "status": 422,
            "code": "autorizacao_expirada",
            "quando": "O certificado A1 do prestador expirou (produção)."
          }
        ]
      }
    },
    "/v1/notas/{id}/xml": {
      "get": {
        "operationId": "baixarXmlDaNota",
        "tags": [
          "Notas"
        ],
        "summary": "Baixar o XML",
        "description": "O XML da NFS-e (padrão nacional), assinado. Existe para nota `autorizada` ou `cancelada`.\n\n**Escopo necessário:** `notas:ler`.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "description": "Identificador do recurso.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "O XML.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/xml": {
                "schema": {
                  "type": "string"
                },
                "example": "<?xml version=\"1.0\" encoding=\"UTF-8\"?><NFSe xmlns=\"http://www.sped.fazenda.gov.br/nfse\">…</NFSe>"
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "409": {
            "$ref": "#/components/responses/Conflito"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "notas:ler"
            ]
          }
        ],
        "x-escopo": "notas:ler",
        "x-codigos": [
          {
            "status": 409,
            "code": "nfse_estado_invalido",
            "quando": "A nota ainda não foi autorizada."
          }
        ]
      }
    },
    "/v1/notas/{id}/pdf": {
      "get": {
        "operationId": "baixarPdfDaNota",
        "tags": [
          "Notas"
        ],
        "summary": "Baixar o PDF (DANFSe)",
        "description": "O PDF da nota, gerado na primeira consulta e guardado. Existe para nota `autorizada` ou `cancelada`.\n\n**Escopo necessário:** `notas:ler`.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "description": "Identificador do recurso.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "O PDF.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/pdf": {
                "schema": {
                  "type": "string",
                  "format": "binary"
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "409": {
            "$ref": "#/components/responses/Conflito"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "notas:ler"
            ]
          }
        ],
        "x-escopo": "notas:ler",
        "x-codigos": [
          {
            "status": 409,
            "code": "nfse_estado_invalido",
            "quando": "A nota ainda não foi autorizada."
          }
        ]
      }
    },
    "/v1/prestadores": {
      "post": {
        "operationId": "criarPrestador",
        "tags": [
          "Prestadores"
        ],
        "summary": "Cadastrar um prestador",
        "description": "Cadastra um CNPJ emissor. O município precisa estar na cobertura. O número de CNPJs ativos é limitado pelo plano.\n\n**Escopo necessário:** `prestadores:escrever`.",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "cnpj": {
                    "type": "string",
                    "minLength": 14,
                    "maxLength": 20,
                    "description": "CNPJ, com ou sem pontuação."
                  },
                  "importar_cnpj": {
                    "type": "boolean",
                    "default": false
                  },
                  "razao_social": {
                    "type": "string",
                    "minLength": 2,
                    "maxLength": 150,
                    "description": "Razão social."
                  },
                  "nome_fantasia": {
                    "type": "string",
                    "maxLength": 150,
                    "description": "Nome fantasia."
                  },
                  "municipio_ibge": {
                    "type": "string",
                    "pattern": "^[0-9]{7}$",
                    "description": "Município do prestador (IBGE, 7 dígitos). Precisa estar na cobertura."
                  },
                  "regime_tributario": {
                    "type": "string",
                    "enum": [
                      "mei",
                      "simples_nacional",
                      "lucro_presumido",
                      "lucro_real"
                    ],
                    "description": "Regime tributário do prestador."
                  },
                  "cnaes": {
                    "type": "array",
                    "items": {
                      "type": "object",
                      "properties": {
                        "codigo": {
                          "type": "string"
                        },
                        "descricao": {
                          "type": "string",
                          "minLength": 1,
                          "maxLength": 300,
                          "description": "Descrição do serviço que aparece na nota."
                        },
                        "principal": {
                          "type": "boolean"
                        }
                      },
                      "required": [
                        "codigo"
                      ],
                      "additionalProperties": false
                    },
                    "maxItems": 100
                  },
                  "inscricao_municipal": {
                    "type": "string",
                    "minLength": 1,
                    "maxLength": 15,
                    "description": "Inscrição municipal."
                  },
                  "email": {
                    "type": "string",
                    "format": "email",
                    "maxLength": 200,
                    "description": "E-mail."
                  },
                  "telefone": {
                    "type": "string",
                    "pattern": "^[0-9]{10,11}$",
                    "description": "Telefone com DDD, só dígitos (10 ou 11)."
                  },
                  "endereco": {
                    "type": "object",
                    "properties": {
                      "cep": {
                        "type": "string",
                        "pattern": "^[0-9]{8}$"
                      },
                      "logradouro": {
                        "type": "string",
                        "minLength": 1,
                        "maxLength": 125
                      },
                      "numero": {
                        "type": "string",
                        "minLength": 1,
                        "maxLength": 10
                      },
                      "complemento": {
                        "anyOf": [
                          {
                            "type": "string",
                            "maxLength": 60
                          },
                          {
                            "type": "null"
                          }
                        ]
                      },
                      "bairro": {
                        "type": "string",
                        "minLength": 1,
                        "maxLength": 60
                      },
                      "municipio_ibge": {
                        "type": "string",
                        "pattern": "^[0-9]{7}$",
                        "description": "Município do prestador (IBGE, 7 dígitos). Precisa estar na cobertura."
                      }
                    },
                    "required": [
                      "cep",
                      "logradouro",
                      "numero",
                      "bairro",
                      "municipio_ibge"
                    ],
                    "additionalProperties": false,
                    "description": "Endereço completo."
                  },
                  "serie_dps": {
                    "type": "string",
                    "pattern": "^[0-9]{1,5}$",
                    "default": "1",
                    "description": "Série da DPS (1 a 5 dígitos). Cada série tem a sua numeração sequencial."
                  },
                  "padroes_fiscais": {
                    "type": "object",
                    "properties": {
                      "codigo_tributacao_nacional": {
                        "type": "string",
                        "pattern": "^[0-9]{6}$",
                        "description": "Código de tributação nacional (6 dígitos: item da LC 116 + subitem + desdobro). Ex.: `010701`. Na emissão ele é conferido com o catálogo nacional e com os CNAEs do prestador (veja `forcar_codigo`)."
                      },
                      "codigo_nbs": {
                        "type": "string",
                        "pattern": "^[0-9]{9}$",
                        "description": "Código NBS (9 dígitos)."
                      },
                      "descricao_servico": {
                        "type": "string",
                        "minLength": 1,
                        "maxLength": 2000,
                        "description": "Descrição padrão do serviço, usada quando a emissão não traz uma."
                      },
                      "iss_retido": {
                        "type": "boolean",
                        "description": "O tomador retém o ISS. MEI não pode ter ISS retido."
                      },
                      "aliquota_iss": {
                        "type": "number",
                        "minimum": 0,
                        "maximum": 5,
                        "description": "Alíquota do ISS em porcentagem (2 = 2%), de 0 a 5. Padrão: a do prestador."
                      }
                    },
                    "additionalProperties": false,
                    "description": "Valores usados quando a emissão não informa os campos correspondentes."
                  },
                  "certificado_id": {
                    "type": "string",
                    "format": "uuid",
                    "description": "Certificado A1 usado para assinar. O CNPJ do certificado precisa ser do prestador (ou da mesma raiz)."
                  }
                },
                "required": [
                  "cnpj"
                ],
                "additionalProperties": false
              },
              "examples": {
                "simples": {
                  "summary": "Empresa do Simples Nacional",
                  "value": {
                    "cnpj": "11222333000181",
                    "razao_social": "Acme Tecnologia Ltda",
                    "nome_fantasia": "Acme",
                    "municipio_ibge": "3550308",
                    "regime_tributario": "simples_nacional",
                    "inscricao_municipal": "12345678",
                    "email": "fiscal@acme.example.com",
                    "endereco": {
                      "cep": "01310100",
                      "logradouro": "Avenida Paulista",
                      "numero": "1000",
                      "complemento": "Conjunto 42",
                      "bairro": "Bela Vista",
                      "municipio_ibge": "3550308"
                    },
                    "padroes_fiscais": {
                      "codigo_tributacao_nacional": "010701",
                      "descricao_servico": "Desenvolvimento de software sob encomenda",
                      "aliquota_iss": 2
                    }
                  }
                }
              }
            }
          }
        },
        "responses": {
          "201": {
            "description": "Prestador criado.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Prestador"
                },
                "example": {
                  "id": "0c1f7e3a-5d2b-4c8e-9a41-7b6d2e9f1a30",
                  "cnpj": "11222333000181",
                  "razao_social": "Acme Tecnologia Ltda",
                  "nome_fantasia": "Acme",
                  "municipio_ibge": "3550308",
                  "regime_tributario": "simples_nacional",
                  "inscricao_municipal": "12345678",
                  "email": "fiscal@acme.example.com",
                  "telefone": "1130001000",
                  "endereco": {
                    "cep": "01310100",
                    "logradouro": "Avenida Paulista",
                    "numero": "1000",
                    "complemento": "Conjunto 42",
                    "bairro": "Bela Vista",
                    "municipio_ibge": "3550308"
                  },
                  "serie_dps": "1",
                  "padroes_fiscais": {
                    "codigo_tributacao_nacional": "010701",
                    "descricao_servico": "Desenvolvimento de software sob encomenda",
                    "iss_retido": false,
                    "aliquota_iss": 2
                  },
                  "cnaes": [
                    {
                      "codigo": "6201501",
                      "descricao": "Desenvolvimento de programas de computador sob encomenda",
                      "principal": true,
                      "origem": "receita"
                    },
                    {
                      "codigo": "6311900",
                      "descricao": "Tratamento de dados, provedores de serviços de aplicação e serviços de hospedagem na internet",
                      "principal": false,
                      "origem": "receita"
                    }
                  ],
                  "receita": {
                    "situacao_cadastral": "ativa",
                    "data_abertura": "2015-03-02",
                    "natureza_juridica": "Sociedade Empresária Limitada",
                    "porte": "Demais",
                    "provedor": "brasilapi",
                    "consultado_em": "2026-11-13T14:02:11.482Z"
                  },
                  "status": "ativo",
                  "certificado": {
                    "id": "a2d96b4e-1c07-4f35-8e59-0b7c3a1d8f64",
                    "status": "ativo",
                    "validade_fim": "2027-08-30T23:59:59.000Z",
                    "dias_restantes": 290
                  },
                  "autorizacao": {
                    "status": "ativa",
                    "pode_emitir_sandbox": true,
                    "pode_emitir_producao": true
                  },
                  "criado_em": "2026-11-13T14:02:11.482Z",
                  "atualizado_em": "2026-11-13T14:02:11.482Z"
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "402": {
            "$ref": "#/components/responses/PagamentoNecessario"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "409": {
            "$ref": "#/components/responses/Conflito"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "prestadores:escrever"
            ]
          }
        ],
        "x-escopo": "prestadores:escrever",
        "x-codigos": [
          {
            "status": 402,
            "code": "limite_plano_cnpjs",
            "quando": "O plano não comporta mais um CNPJ ativo."
          },
          {
            "status": 409,
            "code": "cnpj_ja_cadastrado",
            "quando": "Este CNPJ já está na conta."
          },
          {
            "status": 422,
            "code": "municipio_nao_atendido",
            "quando": "Município fora da cobertura."
          },
          {
            "status": 422,
            "code": "certificado_titular_divergente",
            "quando": "O certificado informado é de outra empresa."
          },
          {
            "status": 422,
            "code": "certificado_expirado",
            "quando": "O certificado informado está expirado ou revogado."
          }
        ]
      },
      "get": {
        "operationId": "listarPrestadores",
        "tags": [
          "Prestadores"
        ],
        "summary": "Listar prestadores",
        "description": "Lista os prestadores da conta, do mais recente para o mais antigo.\n\n**Escopo necessário:** `prestadores:ler`.",
        "parameters": [
          {
            "name": "limite",
            "in": "query",
            "required": false,
            "description": "Itens por página (1 a 100).",
            "schema": {
              "type": "integer",
              "minimum": 1,
              "maximum": 100,
              "default": 25
            }
          },
          {
            "name": "cursor",
            "in": "query",
            "required": false,
            "description": "Valor de `proximo_cursor` da página anterior.",
            "schema": {
              "type": "string",
              "maxLength": 500
            }
          },
          {
            "name": "cnpj",
            "in": "query",
            "required": false,
            "description": "CNPJ, com ou sem pontuação.",
            "schema": {
              "type": "string",
              "minLength": 14,
              "maxLength": 20
            }
          },
          {
            "name": "status",
            "in": "query",
            "required": false,
            "description": "Filtra pelo status.",
            "schema": {
              "type": "string",
              "enum": [
                "ativo",
                "inativo"
              ]
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Página de prestadores.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ListaDePrestadores"
                },
                "example": {
                  "dados": [
                    {
                      "id": "0c1f7e3a-5d2b-4c8e-9a41-7b6d2e9f1a30",
                      "cnpj": "11222333000181",
                      "razao_social": "Acme Tecnologia Ltda",
                      "nome_fantasia": "Acme",
                      "municipio_ibge": "3550308",
                      "regime_tributario": "simples_nacional",
                      "inscricao_municipal": "12345678",
                      "email": "fiscal@acme.example.com",
                      "telefone": "1130001000",
                      "endereco": {
                        "cep": "01310100",
                        "logradouro": "Avenida Paulista",
                        "numero": "1000",
                        "complemento": "Conjunto 42",
                        "bairro": "Bela Vista",
                        "municipio_ibge": "3550308"
                      },
                      "serie_dps": "1",
                      "padroes_fiscais": {
                        "codigo_tributacao_nacional": "010701",
                        "descricao_servico": "Desenvolvimento de software sob encomenda",
                        "iss_retido": false,
                        "aliquota_iss": 2
                      },
                      "cnaes": [
                        {
                          "codigo": "6201501",
                          "descricao": "Desenvolvimento de programas de computador sob encomenda",
                          "principal": true,
                          "origem": "receita"
                        },
                        {
                          "codigo": "6311900",
                          "descricao": "Tratamento de dados, provedores de serviços de aplicação e serviços de hospedagem na internet",
                          "principal": false,
                          "origem": "receita"
                        }
                      ],
                      "receita": {
                        "situacao_cadastral": "ativa",
                        "data_abertura": "2015-03-02",
                        "natureza_juridica": "Sociedade Empresária Limitada",
                        "porte": "Demais",
                        "provedor": "brasilapi",
                        "consultado_em": "2026-11-13T14:02:11.482Z"
                      },
                      "status": "ativo",
                      "certificado": {
                        "id": "a2d96b4e-1c07-4f35-8e59-0b7c3a1d8f64",
                        "status": "ativo",
                        "validade_fim": "2027-08-30T23:59:59.000Z",
                        "dias_restantes": 290
                      },
                      "autorizacao": {
                        "status": "ativa",
                        "pode_emitir_sandbox": true,
                        "pode_emitir_producao": true
                      },
                      "criado_em": "2026-11-13T14:02:11.482Z",
                      "atualizado_em": "2026-11-13T14:02:11.482Z"
                    }
                  ],
                  "proximo_cursor": null
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "prestadores:ler"
            ]
          }
        ],
        "x-escopo": "prestadores:ler"
      }
    },
    "/v1/prestadores/importar": {
      "post": {
        "operationId": "importarPrestador",
        "tags": [
          "Prestadores"
        ],
        "summary": "Cadastrar um prestador a partir do CNPJ",
        "description": "Atalho para `POST /v1/prestadores` com `importar_cnpj: true`: consulta o CNPJ na Receita Federal e cadastra o prestador com razão social, nome fantasia, município, endereço, contato e CNAEs. O que você enviar no corpo **prevalece** sobre o que a Receita trouxe.\n\nA Receita só informa MEI e Simples Nacional. Para lucro presumido ou lucro real, envie `regime_tributario`. Se a Receita não trouxer o município, envie `municipio_ibge`. Os campos que faltarem voltam em `422 validacao`.\n\nPara ver o que seria importado antes de cadastrar, use `GET /v1/cnpj/{cnpj}`.\n\n**Escopo necessário:** `prestadores:escrever`.",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "cnpj": {
                    "type": "string",
                    "minLength": 14,
                    "maxLength": 20,
                    "description": "CNPJ, com ou sem pontuação."
                  },
                  "razao_social": {
                    "type": "string",
                    "minLength": 2,
                    "maxLength": 150,
                    "description": "Razão social."
                  },
                  "nome_fantasia": {
                    "type": "string",
                    "maxLength": 150,
                    "description": "Nome fantasia."
                  },
                  "municipio_ibge": {
                    "type": "string",
                    "pattern": "^[0-9]{7}$",
                    "description": "Município do prestador (IBGE, 7 dígitos). Precisa estar na cobertura."
                  },
                  "regime_tributario": {
                    "type": "string",
                    "enum": [
                      "mei",
                      "simples_nacional",
                      "lucro_presumido",
                      "lucro_real"
                    ],
                    "description": "Regime tributário do prestador."
                  },
                  "cnaes": {
                    "type": "array",
                    "items": {
                      "type": "object",
                      "properties": {
                        "codigo": {
                          "type": "string"
                        },
                        "descricao": {
                          "type": "string",
                          "minLength": 1,
                          "maxLength": 300,
                          "description": "Descrição do serviço que aparece na nota."
                        },
                        "principal": {
                          "type": "boolean"
                        }
                      },
                      "required": [
                        "codigo"
                      ],
                      "additionalProperties": false
                    },
                    "maxItems": 100
                  },
                  "inscricao_municipal": {
                    "type": "string",
                    "minLength": 1,
                    "maxLength": 15,
                    "description": "Inscrição municipal."
                  },
                  "email": {
                    "type": "string",
                    "format": "email",
                    "maxLength": 200,
                    "description": "E-mail."
                  },
                  "telefone": {
                    "type": "string",
                    "pattern": "^[0-9]{10,11}$",
                    "description": "Telefone com DDD, só dígitos (10 ou 11)."
                  },
                  "endereco": {
                    "type": "object",
                    "properties": {
                      "cep": {
                        "type": "string",
                        "pattern": "^[0-9]{8}$"
                      },
                      "logradouro": {
                        "type": "string",
                        "minLength": 1,
                        "maxLength": 125
                      },
                      "numero": {
                        "type": "string",
                        "minLength": 1,
                        "maxLength": 10
                      },
                      "complemento": {
                        "anyOf": [
                          {
                            "type": "string",
                            "maxLength": 60
                          },
                          {
                            "type": "null"
                          }
                        ]
                      },
                      "bairro": {
                        "type": "string",
                        "minLength": 1,
                        "maxLength": 60
                      },
                      "municipio_ibge": {
                        "type": "string",
                        "pattern": "^[0-9]{7}$",
                        "description": "Município do prestador (IBGE, 7 dígitos). Precisa estar na cobertura."
                      }
                    },
                    "required": [
                      "cep",
                      "logradouro",
                      "numero",
                      "bairro",
                      "municipio_ibge"
                    ],
                    "additionalProperties": false,
                    "description": "Endereço completo."
                  },
                  "serie_dps": {
                    "type": "string",
                    "pattern": "^[0-9]{1,5}$",
                    "default": "1",
                    "description": "Série da DPS (1 a 5 dígitos). Cada série tem a sua numeração sequencial."
                  },
                  "padroes_fiscais": {
                    "type": "object",
                    "properties": {
                      "codigo_tributacao_nacional": {
                        "type": "string",
                        "pattern": "^[0-9]{6}$",
                        "description": "Código de tributação nacional (6 dígitos: item da LC 116 + subitem + desdobro). Ex.: `010701`. Na emissão ele é conferido com o catálogo nacional e com os CNAEs do prestador (veja `forcar_codigo`)."
                      },
                      "codigo_nbs": {
                        "type": "string",
                        "pattern": "^[0-9]{9}$",
                        "description": "Código NBS (9 dígitos)."
                      },
                      "descricao_servico": {
                        "type": "string",
                        "minLength": 1,
                        "maxLength": 2000,
                        "description": "Descrição padrão do serviço, usada quando a emissão não traz uma."
                      },
                      "iss_retido": {
                        "type": "boolean",
                        "description": "O tomador retém o ISS. MEI não pode ter ISS retido."
                      },
                      "aliquota_iss": {
                        "type": "number",
                        "minimum": 0,
                        "maximum": 5,
                        "description": "Alíquota do ISS em porcentagem (2 = 2%), de 0 a 5. Padrão: a do prestador."
                      }
                    },
                    "additionalProperties": false,
                    "description": "Valores usados quando a emissão não informa os campos correspondentes."
                  },
                  "certificado_id": {
                    "type": "string",
                    "format": "uuid",
                    "description": "Certificado A1 usado para assinar. O CNPJ do certificado precisa ser do prestador (ou da mesma raiz)."
                  }
                },
                "required": [
                  "cnpj"
                ],
                "additionalProperties": false
              },
              "examples": {
                "so_cnpj": {
                  "summary": "Só o CNPJ (Simples Nacional ou MEI)",
                  "value": {
                    "cnpj": "11222333000181",
                    "padroes_fiscais": {
                      "codigo_tributacao_nacional": "010701",
                      "aliquota_iss": 2
                    }
                  }
                },
                "lucro_presumido": {
                  "summary": "Informando o regime que a Receita não traz",
                  "value": {
                    "cnpj": "11222333000181",
                    "regime_tributario": "lucro_presumido"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "201": {
            "description": "Prestador criado.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Prestador"
                },
                "example": {
                  "id": "0c1f7e3a-5d2b-4c8e-9a41-7b6d2e9f1a30",
                  "cnpj": "11222333000181",
                  "razao_social": "Acme Tecnologia Ltda",
                  "nome_fantasia": "Acme",
                  "municipio_ibge": "3550308",
                  "regime_tributario": "simples_nacional",
                  "inscricao_municipal": "12345678",
                  "email": "fiscal@acme.example.com",
                  "telefone": "1130001000",
                  "endereco": {
                    "cep": "01310100",
                    "logradouro": "Avenida Paulista",
                    "numero": "1000",
                    "complemento": "Conjunto 42",
                    "bairro": "Bela Vista",
                    "municipio_ibge": "3550308"
                  },
                  "serie_dps": "1",
                  "padroes_fiscais": {
                    "codigo_tributacao_nacional": "010701",
                    "descricao_servico": "Desenvolvimento de software sob encomenda",
                    "iss_retido": false,
                    "aliquota_iss": 2
                  },
                  "cnaes": [
                    {
                      "codigo": "6201501",
                      "descricao": "Desenvolvimento de programas de computador sob encomenda",
                      "principal": true,
                      "origem": "receita"
                    },
                    {
                      "codigo": "6311900",
                      "descricao": "Tratamento de dados, provedores de serviços de aplicação e serviços de hospedagem na internet",
                      "principal": false,
                      "origem": "receita"
                    }
                  ],
                  "receita": {
                    "situacao_cadastral": "ativa",
                    "data_abertura": "2015-03-02",
                    "natureza_juridica": "Sociedade Empresária Limitada",
                    "porte": "Demais",
                    "provedor": "brasilapi",
                    "consultado_em": "2026-11-13T14:02:11.482Z"
                  },
                  "status": "ativo",
                  "certificado": {
                    "id": "a2d96b4e-1c07-4f35-8e59-0b7c3a1d8f64",
                    "status": "ativo",
                    "validade_fim": "2027-08-30T23:59:59.000Z",
                    "dias_restantes": 290
                  },
                  "autorizacao": {
                    "status": "ativa",
                    "pode_emitir_sandbox": true,
                    "pode_emitir_producao": true
                  },
                  "criado_em": "2026-11-13T14:02:11.482Z",
                  "atualizado_em": "2026-11-13T14:02:11.482Z"
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "402": {
            "$ref": "#/components/responses/PagamentoNecessario"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "409": {
            "$ref": "#/components/responses/Conflito"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          },
          "503": {
            "$ref": "#/components/responses/Indisponivel"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "prestadores:escrever"
            ]
          }
        ],
        "x-escopo": "prestadores:escrever",
        "x-codigos": [
          {
            "status": 404,
            "code": "cnpj_nao_encontrado",
            "quando": "A Receita não tem este CNPJ."
          },
          {
            "status": 409,
            "code": "cnpj_ja_cadastrado",
            "quando": "Este CNPJ já está na conta."
          },
          {
            "status": 422,
            "code": "municipio_nao_atendido",
            "quando": "O município do CNPJ está fora da cobertura."
          },
          {
            "status": 503,
            "code": "cnpj_consulta_indisponivel",
            "quando": "Nenhuma fonte de consulta respondeu. Cadastre informando os dados à mão ou tente de novo."
          }
        ]
      }
    },
    "/v1/prestadores/{id}/sincronizar-cnpj": {
      "post": {
        "operationId": "sincronizarPrestador",
        "tags": [
          "Prestadores"
        ],
        "summary": "Sincronizar um prestador com a Receita",
        "description": "Consulta o CNPJ de novo (ignorando o cache) e atualiza só os campos que você escolher em `campos`. Sem corpo, atualiza razão social, nome fantasia, endereço e CNAEs. CNAEs que você incluiu à mão são mantidos. O **município nunca é alterado** por aqui: se mudou na Receita, a resposta traz `sincronizacao.municipio_divergente: true`.\n\n**Escopo necessário:** `prestadores:escrever`.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "description": "Identificador do recurso.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "campos": {
                    "type": "array",
                    "items": {
                      "type": "string",
                      "enum": [
                        "razao_social",
                        "nome_fantasia",
                        "endereco",
                        "contato",
                        "cnaes"
                      ]
                    },
                    "minItems": 1,
                    "default": [
                      "razao_social",
                      "nome_fantasia",
                      "endereco",
                      "cnaes"
                    ]
                  }
                },
                "additionalProperties": false
              },
              "examples": {
                "contato": {
                  "summary": "Atualizar também e-mail e telefone",
                  "value": {
                    "campos": [
                      "razao_social",
                      "endereco",
                      "contato",
                      "cnaes"
                    ]
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "O prestador atualizado e o resumo da sincronização.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/PrestadorSincronizado"
                },
                "example": {
                  "id": "0c1f7e3a-5d2b-4c8e-9a41-7b6d2e9f1a30",
                  "cnpj": "11222333000181",
                  "razao_social": "Acme Tecnologia Ltda",
                  "nome_fantasia": "Acme",
                  "municipio_ibge": "3550308",
                  "regime_tributario": "simples_nacional",
                  "inscricao_municipal": "12345678",
                  "email": "fiscal@acme.example.com",
                  "telefone": "1130001000",
                  "endereco": {
                    "cep": "01310100",
                    "logradouro": "Avenida Paulista",
                    "numero": "1000",
                    "complemento": "Conjunto 42",
                    "bairro": "Bela Vista",
                    "municipio_ibge": "3550308"
                  },
                  "serie_dps": "1",
                  "padroes_fiscais": {
                    "codigo_tributacao_nacional": "010701",
                    "descricao_servico": "Desenvolvimento de software sob encomenda",
                    "iss_retido": false,
                    "aliquota_iss": 2
                  },
                  "cnaes": [
                    {
                      "codigo": "6201501",
                      "descricao": "Desenvolvimento de programas de computador sob encomenda",
                      "principal": true,
                      "origem": "receita"
                    },
                    {
                      "codigo": "6311900",
                      "descricao": "Tratamento de dados, provedores de serviços de aplicação e serviços de hospedagem na internet",
                      "principal": false,
                      "origem": "receita"
                    }
                  ],
                  "receita": {
                    "situacao_cadastral": "ativa",
                    "data_abertura": "2015-03-02",
                    "natureza_juridica": "Sociedade Empresária Limitada",
                    "porte": "Demais",
                    "provedor": "brasilapi",
                    "consultado_em": "2026-11-13T14:02:11.482Z"
                  },
                  "status": "ativo",
                  "certificado": {
                    "id": "a2d96b4e-1c07-4f35-8e59-0b7c3a1d8f64",
                    "status": "ativo",
                    "validade_fim": "2027-08-30T23:59:59.000Z",
                    "dias_restantes": 290
                  },
                  "autorizacao": {
                    "status": "ativa",
                    "pode_emitir_sandbox": true,
                    "pode_emitir_producao": true
                  },
                  "criado_em": "2026-11-13T14:02:11.482Z",
                  "atualizado_em": "2026-11-13T14:02:11.482Z",
                  "sincronizacao": {
                    "campos_atualizados": [
                      "razao_social",
                      "nome_fantasia",
                      "endereco",
                      "cnaes"
                    ],
                    "municipio_divergente": false,
                    "situacao_cadastral": "ativa",
                    "provedor": "brasilapi",
                    "consultado_em": "2026-11-13T14:02:11.482Z",
                    "origem": "consulta"
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          },
          "503": {
            "$ref": "#/components/responses/Indisponivel"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "prestadores:escrever"
            ]
          }
        ],
        "x-escopo": "prestadores:escrever",
        "x-codigos": [
          {
            "status": 404,
            "code": "cnpj_nao_encontrado",
            "quando": "A Receita não tem este CNPJ."
          },
          {
            "status": 503,
            "code": "cnpj_consulta_indisponivel",
            "quando": "Nenhuma fonte de consulta respondeu."
          }
        ]
      }
    },
    "/v1/prestadores/{id}/cnaes": {
      "get": {
        "operationId": "listarCnaesDoPrestador",
        "tags": [
          "Prestadores"
        ],
        "summary": "Listar os CNAEs de um prestador",
        "description": "As atividades econômicas do prestador, principal primeiro. Elas alimentam a compatibilidade em `GET /v1/catalogo/ctribnac` e a sugestão em `POST /v1/tributacao/sugerir`.\n\n**Escopo necessário:** `prestadores:ler`.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "description": "Identificador do recurso.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Os CNAEs.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ListaDeCnaesDoPrestador"
                },
                "example": {
                  "dados": [
                    {
                      "codigo": "6201501",
                      "descricao": "Desenvolvimento de programas de computador sob encomenda",
                      "principal": true,
                      "origem": "receita"
                    },
                    {
                      "codigo": "6311900",
                      "descricao": "Tratamento de dados, provedores de serviços de aplicação e serviços de hospedagem na internet",
                      "principal": false,
                      "origem": "receita"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "prestadores:ler"
            ]
          }
        ],
        "x-escopo": "prestadores:ler"
      },
      "put": {
        "operationId": "substituirCnaesDoPrestador",
        "tags": [
          "Prestadores"
        ],
        "summary": "Substituir os CNAEs de um prestador",
        "description": "Troca a **lista inteira**. Mande só o `codigo` de cada CNAE do catálogo (a descrição é completada); para um CNAE fora do catálogo, envie também a `descricao`. Se nenhum for marcado como `principal`, o primeiro vira o principal. CNAEs vindos da Receita e não alterados continuam marcados como `receita`.\n\n**Escopo necessário:** `prestadores:escrever`.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "description": "Identificador do recurso.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "cnaes": {
                    "type": "array",
                    "items": {
                      "type": "object",
                      "properties": {
                        "codigo": {
                          "type": "string"
                        },
                        "descricao": {
                          "type": "string",
                          "minLength": 1,
                          "maxLength": 300,
                          "description": "Descrição do serviço que aparece na nota."
                        },
                        "principal": {
                          "type": "boolean"
                        }
                      },
                      "required": [
                        "codigo"
                      ],
                      "additionalProperties": false
                    },
                    "maxItems": 100
                  }
                },
                "required": [
                  "cnaes"
                ],
                "additionalProperties": false
              },
              "examples": {
                "lista": {
                  "summary": "Dois CNAEs",
                  "value": {
                    "cnaes": [
                      {
                        "codigo": "6201501",
                        "principal": true
                      },
                      {
                        "codigo": "6209100"
                      }
                    ]
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "A lista gravada.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ListaDeCnaesDoPrestador"
                },
                "example": {
                  "dados": [
                    {
                      "codigo": "6201501",
                      "descricao": "Desenvolvimento de programas de computador sob encomenda",
                      "principal": true,
                      "origem": "receita"
                    },
                    {
                      "codigo": "6311900",
                      "descricao": "Tratamento de dados, provedores de serviços de aplicação e serviços de hospedagem na internet",
                      "principal": false,
                      "origem": "receita"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "prestadores:escrever"
            ]
          }
        ],
        "x-escopo": "prestadores:escrever"
      }
    },
    "/v1/prestadores/{id}": {
      "get": {
        "operationId": "obterPrestador",
        "tags": [
          "Prestadores"
        ],
        "summary": "Consultar um prestador",
        "description": "Devolve o prestador com o estado do certificado e da autorização para emitir.\n\n**Escopo necessário:** `prestadores:ler`.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "description": "Identificador do recurso.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "O prestador.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Prestador"
                },
                "example": {
                  "id": "0c1f7e3a-5d2b-4c8e-9a41-7b6d2e9f1a30",
                  "cnpj": "11222333000181",
                  "razao_social": "Acme Tecnologia Ltda",
                  "nome_fantasia": "Acme",
                  "municipio_ibge": "3550308",
                  "regime_tributario": "simples_nacional",
                  "inscricao_municipal": "12345678",
                  "email": "fiscal@acme.example.com",
                  "telefone": "1130001000",
                  "endereco": {
                    "cep": "01310100",
                    "logradouro": "Avenida Paulista",
                    "numero": "1000",
                    "complemento": "Conjunto 42",
                    "bairro": "Bela Vista",
                    "municipio_ibge": "3550308"
                  },
                  "serie_dps": "1",
                  "padroes_fiscais": {
                    "codigo_tributacao_nacional": "010701",
                    "descricao_servico": "Desenvolvimento de software sob encomenda",
                    "iss_retido": false,
                    "aliquota_iss": 2
                  },
                  "cnaes": [
                    {
                      "codigo": "6201501",
                      "descricao": "Desenvolvimento de programas de computador sob encomenda",
                      "principal": true,
                      "origem": "receita"
                    },
                    {
                      "codigo": "6311900",
                      "descricao": "Tratamento de dados, provedores de serviços de aplicação e serviços de hospedagem na internet",
                      "principal": false,
                      "origem": "receita"
                    }
                  ],
                  "receita": {
                    "situacao_cadastral": "ativa",
                    "data_abertura": "2015-03-02",
                    "natureza_juridica": "Sociedade Empresária Limitada",
                    "porte": "Demais",
                    "provedor": "brasilapi",
                    "consultado_em": "2026-11-13T14:02:11.482Z"
                  },
                  "status": "ativo",
                  "certificado": {
                    "id": "a2d96b4e-1c07-4f35-8e59-0b7c3a1d8f64",
                    "status": "ativo",
                    "validade_fim": "2027-08-30T23:59:59.000Z",
                    "dias_restantes": 290
                  },
                  "autorizacao": {
                    "status": "ativa",
                    "pode_emitir_sandbox": true,
                    "pode_emitir_producao": true
                  },
                  "criado_em": "2026-11-13T14:02:11.482Z",
                  "atualizado_em": "2026-11-13T14:02:11.482Z"
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "prestadores:ler"
            ]
          }
        ],
        "x-escopo": "prestadores:ler"
      },
      "patch": {
        "operationId": "atualizarPrestador",
        "tags": [
          "Prestadores"
        ],
        "summary": "Atualizar um prestador",
        "description": "Altera apenas os campos enviados (ao menos um). O CNPJ não muda. `status: \"inativo\"` desativa; `\"ativo\"` reativa (respeitando o limite do plano). `null` limpa campos opcionais. **`padroes_fiscais` é mesclado** com os padrões atuais: só as chaves enviadas mudam e `null` remove a chave (`{ \"padroes_fiscais\": { \"aliquota_iss\": null } }` apaga só a alíquota padrão).\n\n**Escopo necessário:** `prestadores:escrever`.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "description": "Identificador do recurso.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "razao_social": {
                    "type": "string",
                    "minLength": 2,
                    "maxLength": 150,
                    "description": "Razão social."
                  },
                  "nome_fantasia": {
                    "anyOf": [
                      {
                        "type": "string",
                        "maxLength": 150
                      },
                      {
                        "type": "null"
                      }
                    ],
                    "description": "Nome fantasia."
                  },
                  "municipio_ibge": {
                    "type": "string",
                    "pattern": "^[0-9]{7}$",
                    "description": "Município do prestador (IBGE, 7 dígitos). Precisa estar na cobertura."
                  },
                  "regime_tributario": {
                    "type": "string",
                    "enum": [
                      "mei",
                      "simples_nacional",
                      "lucro_presumido",
                      "lucro_real"
                    ],
                    "description": "Regime tributário do prestador."
                  },
                  "inscricao_municipal": {
                    "anyOf": [
                      {
                        "type": "string",
                        "minLength": 1,
                        "maxLength": 15
                      },
                      {
                        "type": "null"
                      }
                    ],
                    "description": "Inscrição municipal."
                  },
                  "email": {
                    "anyOf": [
                      {
                        "type": "string",
                        "format": "email",
                        "maxLength": 200
                      },
                      {
                        "type": "null"
                      }
                    ],
                    "description": "E-mail."
                  },
                  "telefone": {
                    "anyOf": [
                      {
                        "type": "string",
                        "pattern": "^[0-9]{10,11}$"
                      },
                      {
                        "type": "null"
                      }
                    ],
                    "description": "Telefone com DDD, só dígitos (10 ou 11)."
                  },
                  "endereco": {
                    "anyOf": [
                      {
                        "type": "object",
                        "properties": {
                          "cep": {
                            "type": "string",
                            "pattern": "^[0-9]{8}$"
                          },
                          "logradouro": {
                            "type": "string",
                            "minLength": 1,
                            "maxLength": 125
                          },
                          "numero": {
                            "type": "string",
                            "minLength": 1,
                            "maxLength": 10
                          },
                          "complemento": {
                            "anyOf": [
                              {
                                "type": "string",
                                "maxLength": 60
                              },
                              {
                                "type": "null"
                              }
                            ]
                          },
                          "bairro": {
                            "type": "string",
                            "minLength": 1,
                            "maxLength": 60
                          },
                          "municipio_ibge": {
                            "type": "string",
                            "pattern": "^[0-9]{7}$",
                            "description": "Município do prestador (IBGE, 7 dígitos). Precisa estar na cobertura."
                          }
                        },
                        "required": [
                          "cep",
                          "logradouro",
                          "numero",
                          "bairro",
                          "municipio_ibge"
                        ],
                        "additionalProperties": false
                      },
                      {
                        "type": "null"
                      }
                    ],
                    "description": "Endereço completo."
                  },
                  "padroes_fiscais": {
                    "type": "object",
                    "properties": {
                      "codigo_tributacao_nacional": {
                        "anyOf": [
                          {
                            "anyOf": [
                              {
                                "not": {}
                              },
                              {
                                "type": "string",
                                "pattern": "^[0-9]{6}$"
                              }
                            ]
                          },
                          {
                            "type": "null"
                          }
                        ],
                        "description": "Código de tributação nacional (6 dígitos: item da LC 116 + subitem + desdobro). Ex.: `010701`. Na emissão ele é conferido com o catálogo nacional e com os CNAEs do prestador (veja `forcar_codigo`)."
                      },
                      "codigo_nbs": {
                        "anyOf": [
                          {
                            "anyOf": [
                              {
                                "not": {}
                              },
                              {
                                "type": "string",
                                "pattern": "^[0-9]{9}$"
                              }
                            ]
                          },
                          {
                            "type": "null"
                          }
                        ],
                        "description": "Código NBS (9 dígitos)."
                      },
                      "descricao_servico": {
                        "anyOf": [
                          {
                            "anyOf": [
                              {
                                "not": {}
                              },
                              {
                                "type": "string",
                                "minLength": 1,
                                "maxLength": 2000
                              }
                            ]
                          },
                          {
                            "type": "null"
                          }
                        ],
                        "description": "Descrição padrão do serviço, usada quando a emissão não traz uma."
                      },
                      "iss_retido": {
                        "anyOf": [
                          {
                            "anyOf": [
                              {
                                "not": {}
                              },
                              {
                                "type": "boolean"
                              }
                            ]
                          },
                          {
                            "type": "null"
                          }
                        ],
                        "description": "O tomador retém o ISS. MEI não pode ter ISS retido."
                      },
                      "aliquota_iss": {
                        "anyOf": [
                          {
                            "anyOf": [
                              {
                                "not": {}
                              },
                              {
                                "type": "number",
                                "minimum": 0,
                                "maximum": 5
                              }
                            ]
                          },
                          {
                            "type": "null"
                          }
                        ],
                        "description": "Alíquota do ISS em porcentagem (2 = 2%), de 0 a 5. Padrão: a do prestador."
                      }
                    },
                    "additionalProperties": false,
                    "description": "Valores usados quando a emissão não informa os campos correspondentes."
                  },
                  "certificado_id": {
                    "anyOf": [
                      {
                        "type": "string",
                        "format": "uuid"
                      },
                      {
                        "type": "null"
                      }
                    ],
                    "description": "Certificado A1 usado para assinar. O CNPJ do certificado precisa ser do prestador (ou da mesma raiz)."
                  },
                  "status": {
                    "type": "string",
                    "enum": [
                      "ativo",
                      "inativo"
                    ],
                    "description": "`inativo` desativa o prestador; `ativo` reativa."
                  }
                },
                "additionalProperties": false
              },
              "examples": {
                "padroes": {
                  "summary": "Trocar a alíquota padrão",
                  "value": {
                    "padroes_fiscais": {
                      "codigo_tributacao_nacional": "010701",
                      "aliquota_iss": 3
                    }
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "O prestador atualizado.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Prestador"
                },
                "example": {
                  "id": "0c1f7e3a-5d2b-4c8e-9a41-7b6d2e9f1a30",
                  "cnpj": "11222333000181",
                  "razao_social": "Acme Tecnologia Ltda",
                  "nome_fantasia": "Acme",
                  "municipio_ibge": "3550308",
                  "regime_tributario": "simples_nacional",
                  "inscricao_municipal": "12345678",
                  "email": "fiscal@acme.example.com",
                  "telefone": "1130001000",
                  "endereco": {
                    "cep": "01310100",
                    "logradouro": "Avenida Paulista",
                    "numero": "1000",
                    "complemento": "Conjunto 42",
                    "bairro": "Bela Vista",
                    "municipio_ibge": "3550308"
                  },
                  "serie_dps": "1",
                  "padroes_fiscais": {
                    "codigo_tributacao_nacional": "010701",
                    "descricao_servico": "Desenvolvimento de software sob encomenda",
                    "iss_retido": false,
                    "aliquota_iss": 2
                  },
                  "cnaes": [
                    {
                      "codigo": "6201501",
                      "descricao": "Desenvolvimento de programas de computador sob encomenda",
                      "principal": true,
                      "origem": "receita"
                    },
                    {
                      "codigo": "6311900",
                      "descricao": "Tratamento de dados, provedores de serviços de aplicação e serviços de hospedagem na internet",
                      "principal": false,
                      "origem": "receita"
                    }
                  ],
                  "receita": {
                    "situacao_cadastral": "ativa",
                    "data_abertura": "2015-03-02",
                    "natureza_juridica": "Sociedade Empresária Limitada",
                    "porte": "Demais",
                    "provedor": "brasilapi",
                    "consultado_em": "2026-11-13T14:02:11.482Z"
                  },
                  "status": "ativo",
                  "certificado": {
                    "id": "a2d96b4e-1c07-4f35-8e59-0b7c3a1d8f64",
                    "status": "ativo",
                    "validade_fim": "2027-08-30T23:59:59.000Z",
                    "dias_restantes": 290
                  },
                  "autorizacao": {
                    "status": "ativa",
                    "pode_emitir_sandbox": true,
                    "pode_emitir_producao": true
                  },
                  "criado_em": "2026-11-13T14:02:11.482Z",
                  "atualizado_em": "2026-11-13T14:02:11.482Z"
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "402": {
            "$ref": "#/components/responses/PagamentoNecessario"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "prestadores:escrever"
            ]
          }
        ],
        "x-escopo": "prestadores:escrever",
        "x-codigos": [
          {
            "status": 402,
            "code": "limite_plano_cnpjs",
            "quando": "Reativar passaria do limite de CNPJs do plano."
          }
        ]
      },
      "delete": {
        "operationId": "inativarPrestador",
        "tags": [
          "Prestadores"
        ],
        "summary": "Inativar um prestador",
        "description": "Inativa o prestador. O histórico de notas permanece. Para reativar: `PATCH` com `{ \"status\": \"ativo\" }`. É idempotente.\n\n**Escopo necessário:** `prestadores:escrever`.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "description": "Identificador do recurso.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Sem conteúdo.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "prestadores:escrever"
            ]
          }
        ],
        "x-escopo": "prestadores:escrever"
      }
    },
    "/v1/tomadores": {
      "post": {
        "operationId": "criarTomador",
        "tags": [
          "Tomadores"
        ],
        "summary": "Cadastrar um tomador",
        "description": "Cadastra quem contrata o serviço, para reutilizar nas emissões por `tomador_id`. O documento é guardado cifrado.\n\n**Escopo necessário:** `tomadores:escrever`.",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "tipo_documento": {
                    "type": "string",
                    "enum": [
                      "cpf",
                      "cnpj",
                      "estrangeiro",
                      "nenhum"
                    ],
                    "description": "Tipo do documento do tomador. Se omitido com `documento`, é detectado (11 dígitos = CPF, 14 = CNPJ)."
                  },
                  "documento": {
                    "type": "string",
                    "minLength": 3,
                    "maxLength": 30,
                    "description": "CPF ou CNPJ, com ou sem pontuação. Nunca volta em claro nas respostas."
                  },
                  "importar_cnpj": {
                    "type": "boolean",
                    "default": false
                  },
                  "nome": {
                    "type": "string",
                    "minLength": 2,
                    "maxLength": 150,
                    "description": "Nome ou razão social."
                  },
                  "email": {
                    "type": "string",
                    "format": "email",
                    "maxLength": 200,
                    "description": "E-mail."
                  },
                  "telefone": {
                    "type": "string",
                    "pattern": "^[0-9]{10,11}$",
                    "description": "Telefone com DDD, só dígitos (10 ou 11)."
                  },
                  "endereco": {
                    "type": "object",
                    "properties": {
                      "cep": {
                        "type": "string",
                        "pattern": "^[0-9]{8}$"
                      },
                      "logradouro": {
                        "type": "string",
                        "minLength": 1,
                        "maxLength": 125
                      },
                      "numero": {
                        "type": "string",
                        "minLength": 1,
                        "maxLength": 10
                      },
                      "complemento": {
                        "anyOf": [
                          {
                            "type": "string",
                            "maxLength": 60
                          },
                          {
                            "type": "null"
                          }
                        ]
                      },
                      "bairro": {
                        "type": "string",
                        "minLength": 1,
                        "maxLength": 60
                      },
                      "municipio_ibge": {
                        "type": "string",
                        "pattern": "^[0-9]{7}$",
                        "description": "Município do prestador (IBGE, 7 dígitos). Precisa estar na cobertura."
                      }
                    },
                    "required": [
                      "cep",
                      "logradouro",
                      "numero",
                      "bairro",
                      "municipio_ibge"
                    ],
                    "additionalProperties": false,
                    "description": "Endereço completo."
                  }
                },
                "additionalProperties": false
              },
              "examples": {
                "pf": {
                  "summary": "Pessoa física",
                  "value": {
                    "tipo_documento": "cpf",
                    "documento": "52998224725",
                    "nome": "Maria Souza",
                    "email": "maria@example.com"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "201": {
            "description": "Tomador criado.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Tomador"
                },
                "example": {
                  "id": "3b8d0f52-91c4-4a7e-8f26-5e1c7a9d4b02",
                  "tipo_documento": "cpf",
                  "documento_mascarado": "***.982.247-**",
                  "nome": "Maria Souza",
                  "email": "maria@example.com",
                  "telefone": null,
                  "endereco": null,
                  "anonimizado": false,
                  "criado_em": "2026-11-13T14:02:11.482Z",
                  "atualizado_em": "2026-11-13T14:02:11.482Z"
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "409": {
            "$ref": "#/components/responses/Conflito"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "tomadores:escrever"
            ]
          }
        ],
        "x-escopo": "tomadores:escrever",
        "x-codigos": [
          {
            "status": 409,
            "code": "tomador_ja_cadastrado",
            "quando": "Já existe um tomador com este documento; o erro traz `tomador_id`."
          }
        ]
      },
      "get": {
        "operationId": "listarTomadores",
        "tags": [
          "Tomadores"
        ],
        "summary": "Listar tomadores",
        "description": "Lista os tomadores. Use `documento` para a busca exata (comparada por HMAC, sem expor o valor) ou `q` para buscar pelo nome/e-mail.\n\n**Escopo necessário:** `tomadores:ler`.",
        "parameters": [
          {
            "name": "limite",
            "in": "query",
            "required": false,
            "description": "Itens por página (1 a 100).",
            "schema": {
              "type": "integer",
              "minimum": 1,
              "maximum": 100,
              "default": 25
            }
          },
          {
            "name": "cursor",
            "in": "query",
            "required": false,
            "description": "Valor de `proximo_cursor` da página anterior.",
            "schema": {
              "type": "string",
              "maxLength": 500
            }
          },
          {
            "name": "q",
            "in": "query",
            "required": false,
            "description": "Busca por parte do nome ou do e-mail.",
            "schema": {
              "type": "string",
              "minLength": 1,
              "maxLength": 100
            }
          },
          {
            "name": "documento",
            "in": "query",
            "required": false,
            "description": "CPF ou CNPJ, com ou sem pontuação. Nunca volta em claro nas respostas.",
            "schema": {
              "type": "string",
              "minLength": 3,
              "maxLength": 30
            }
          },
          {
            "name": "tipo_documento",
            "in": "query",
            "required": false,
            "description": "Tipo do documento do tomador. Se omitido com `documento`, é detectado (11 dígitos = CPF, 14 = CNPJ).",
            "schema": {
              "type": "string",
              "enum": [
                "cpf",
                "cnpj",
                "estrangeiro",
                "nenhum"
              ]
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Página de tomadores.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ListaDeTomadores"
                },
                "example": {
                  "dados": [
                    {
                      "id": "3b8d0f52-91c4-4a7e-8f26-5e1c7a9d4b02",
                      "tipo_documento": "cpf",
                      "documento_mascarado": "***.982.247-**",
                      "nome": "Maria Souza",
                      "email": "maria@example.com",
                      "telefone": null,
                      "endereco": null,
                      "anonimizado": false,
                      "criado_em": "2026-11-13T14:02:11.482Z",
                      "atualizado_em": "2026-11-13T14:02:11.482Z"
                    }
                  ],
                  "proximo_cursor": null
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "tomadores:ler"
            ]
          }
        ],
        "x-escopo": "tomadores:ler"
      }
    },
    "/v1/tomadores/importar": {
      "post": {
        "operationId": "importarTomador",
        "tags": [
          "Tomadores"
        ],
        "summary": "Cadastrar um tomador a partir do CNPJ",
        "description": "Consulta o CNPJ na Receita Federal e cadastra o tomador pessoa jurídica com nome (razão social), e-mail, telefone e endereço. Equivale a `POST /v1/tomadores` com `importar_cnpj: true`.\n\n**Escopo necessário:** `tomadores:escrever`.",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "cnpj": {
                    "type": "string",
                    "minLength": 14,
                    "maxLength": 20,
                    "description": "CNPJ, com ou sem pontuação."
                  }
                },
                "required": [
                  "cnpj"
                ],
                "additionalProperties": false
              },
              "examples": {
                "cnpj": {
                  "summary": "Só o CNPJ",
                  "value": {
                    "cnpj": "11222333000181"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "201": {
            "description": "Tomador criado.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Tomador"
                },
                "example": {
                  "id": "3b8d0f52-91c4-4a7e-8f26-5e1c7a9d4b02",
                  "tipo_documento": "cnpj",
                  "documento_mascarado": "**.***.333/0001-**",
                  "nome": "ACME TECNOLOGIA LTDA",
                  "email": "maria@example.com",
                  "telefone": null,
                  "endereco": null,
                  "anonimizado": false,
                  "criado_em": "2026-11-13T14:02:11.482Z",
                  "atualizado_em": "2026-11-13T14:02:11.482Z"
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "409": {
            "$ref": "#/components/responses/Conflito"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          },
          "503": {
            "$ref": "#/components/responses/Indisponivel"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "tomadores:escrever"
            ]
          }
        ],
        "x-escopo": "tomadores:escrever",
        "x-codigos": [
          {
            "status": 404,
            "code": "cnpj_nao_encontrado",
            "quando": "A Receita não tem este CNPJ."
          },
          {
            "status": 409,
            "code": "tomador_ja_cadastrado",
            "quando": "Já existe um tomador com este documento; o erro traz `tomador_id`."
          },
          {
            "status": 503,
            "code": "cnpj_consulta_indisponivel",
            "quando": "Nenhuma fonte de consulta respondeu."
          }
        ]
      }
    },
    "/v1/tomadores/{id}": {
      "get": {
        "operationId": "obterTomador",
        "tags": [
          "Tomadores"
        ],
        "summary": "Consultar um tomador",
        "description": "Devolve o tomador. O documento volta só mascarado.\n\n**Escopo necessário:** `tomadores:ler`.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "description": "Identificador do recurso.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "O tomador.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Tomador"
                },
                "example": {
                  "id": "3b8d0f52-91c4-4a7e-8f26-5e1c7a9d4b02",
                  "tipo_documento": "cpf",
                  "documento_mascarado": "***.982.247-**",
                  "nome": "Maria Souza",
                  "email": "maria@example.com",
                  "telefone": null,
                  "endereco": null,
                  "anonimizado": false,
                  "criado_em": "2026-11-13T14:02:11.482Z",
                  "atualizado_em": "2026-11-13T14:02:11.482Z"
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "tomadores:ler"
            ]
          }
        ],
        "x-escopo": "tomadores:ler"
      },
      "patch": {
        "operationId": "atualizarTomador",
        "tags": [
          "Tomadores"
        ],
        "summary": "Atualizar um tomador",
        "description": "Altera apenas os campos enviados (ao menos um). Para trocar o documento, envie `tipo_documento` e `documento`. Notas já emitidas não mudam: elas guardam uma cópia dos dados da época. Tomador anonimizado não pode ser alterado (`409 tomador_anonimizado`).\n\n**Escopo necessário:** `tomadores:escrever`.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "description": "Identificador do recurso.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "tipo_documento": {
                    "type": "string",
                    "enum": [
                      "cpf",
                      "cnpj",
                      "estrangeiro",
                      "nenhum"
                    ],
                    "description": "Tipo do documento do tomador. Se omitido com `documento`, é detectado (11 dígitos = CPF, 14 = CNPJ)."
                  },
                  "documento": {
                    "type": "string",
                    "minLength": 3,
                    "maxLength": 30,
                    "description": "CPF ou CNPJ, com ou sem pontuação. Nunca volta em claro nas respostas."
                  },
                  "nome": {
                    "type": "string",
                    "minLength": 2,
                    "maxLength": 150,
                    "description": "Nome ou razão social."
                  },
                  "email": {
                    "anyOf": [
                      {
                        "type": "string",
                        "format": "email",
                        "maxLength": 200
                      },
                      {
                        "type": "null"
                      }
                    ],
                    "description": "E-mail."
                  },
                  "telefone": {
                    "anyOf": [
                      {
                        "type": "string",
                        "pattern": "^[0-9]{10,11}$"
                      },
                      {
                        "type": "null"
                      }
                    ],
                    "description": "Telefone com DDD, só dígitos (10 ou 11)."
                  },
                  "endereco": {
                    "anyOf": [
                      {
                        "type": "object",
                        "properties": {
                          "cep": {
                            "type": "string",
                            "pattern": "^[0-9]{8}$"
                          },
                          "logradouro": {
                            "type": "string",
                            "minLength": 1,
                            "maxLength": 125
                          },
                          "numero": {
                            "type": "string",
                            "minLength": 1,
                            "maxLength": 10
                          },
                          "complemento": {
                            "anyOf": [
                              {
                                "type": "string",
                                "maxLength": 60
                              },
                              {
                                "type": "null"
                              }
                            ]
                          },
                          "bairro": {
                            "type": "string",
                            "minLength": 1,
                            "maxLength": 60
                          },
                          "municipio_ibge": {
                            "type": "string",
                            "pattern": "^[0-9]{7}$",
                            "description": "Município do prestador (IBGE, 7 dígitos). Precisa estar na cobertura."
                          }
                        },
                        "required": [
                          "cep",
                          "logradouro",
                          "numero",
                          "bairro",
                          "municipio_ibge"
                        ],
                        "additionalProperties": false
                      },
                      {
                        "type": "null"
                      }
                    ],
                    "description": "Endereço completo."
                  }
                },
                "additionalProperties": false
              },
              "examples": {
                "email": {
                  "summary": "Corrigir o e-mail",
                  "value": {
                    "email": "maria.souza@example.com"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "O tomador atualizado.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Tomador"
                },
                "example": {
                  "id": "3b8d0f52-91c4-4a7e-8f26-5e1c7a9d4b02",
                  "tipo_documento": "cpf",
                  "documento_mascarado": "***.982.247-**",
                  "nome": "Maria Souza",
                  "email": "maria@example.com",
                  "telefone": null,
                  "endereco": null,
                  "anonimizado": false,
                  "criado_em": "2026-11-13T14:02:11.482Z",
                  "atualizado_em": "2026-11-13T14:02:11.482Z"
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "409": {
            "$ref": "#/components/responses/Conflito"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "tomadores:escrever"
            ]
          }
        ],
        "x-escopo": "tomadores:escrever",
        "x-codigos": [
          {
            "status": 409,
            "code": "tomador_ja_cadastrado",
            "quando": "O novo documento já pertence a outro tomador."
          },
          {
            "status": 409,
            "code": "tomador_anonimizado",
            "quando": "O tomador foi anonimizado e não pode ser alterado."
          }
        ]
      },
      "delete": {
        "operationId": "excluirTomador",
        "tags": [
          "Tomadores"
        ],
        "summary": "Excluir um tomador",
        "description": "Sem notas, remove de vez. **Com notas, anonimiza** (LGPD): nome, documento e contatos são apagados, mas o vínculo com as notas fica, porque a nota fiscal precisa ser guardada por lei.\n\n**Escopo necessário:** `tomadores:escrever`.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "description": "Identificador do recurso.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Sem conteúdo.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "tomadores:escrever"
            ]
          }
        ],
        "x-escopo": "tomadores:escrever"
      }
    },
    "/v1/cnpj/{cnpj}": {
      "get": {
        "operationId": "consultarCnpj",
        "tags": [
          "Consultas"
        ],
        "summary": "Consultar um CNPJ na Receita",
        "description": "Devolve os dados cadastrais do CNPJ no mesmo formato, qualquer que seja a fonte que respondeu: razão social, situação cadastral, regime sugerido, endereço, CNAEs e se o município está na cobertura do NFsPlus. O quadro de sócios nunca é lido nem guardado.\n\nOs dados ficam em cache. `consulta.origem` diz se vieram da fonte (`consulta`), do cache (`cache`) ou de uma cópia antiga porque as fontes estavam fora do ar (`cache_desatualizado`).\n\nHá um limite de consultas por minuto por conta (`429 limite_excedido`).\n\n**Escopo necessário:** `prestadores:ler`.",
        "parameters": [
          {
            "name": "cnpj",
            "in": "path",
            "required": true,
            "description": "CNPJ, com ou sem pontuação.",
            "schema": {
              "type": "string",
              "minLength": 14,
              "maxLength": 20
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Os dados da empresa.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/EmpresaCnpj"
                },
                "example": {
                  "cnpj": "11222333000181",
                  "razao_social": "ACME TECNOLOGIA LTDA",
                  "nome_fantasia": "Acme",
                  "situacao_cadastral": "ativa",
                  "data_situacao_cadastral": "2015-03-02",
                  "data_abertura": "2015-03-02",
                  "natureza_juridica": "Sociedade Empresária Limitada",
                  "porte": "Demais",
                  "optante_simples": true,
                  "optante_mei": false,
                  "regime_tributario_sugerido": "simples_nacional",
                  "email": "fiscal@acme.example.com",
                  "telefone": "1130001000",
                  "endereco": {
                    "cep": "01310100",
                    "logradouro": "Avenida Paulista",
                    "numero": "1000",
                    "complemento": "Conjunto 42",
                    "bairro": "Bela Vista",
                    "municipio": "São Paulo",
                    "uf": "SP",
                    "municipio_ibge": "3550308"
                  },
                  "cnae_principal": {
                    "codigo": "6201501",
                    "descricao": "Desenvolvimento de programas de computador sob encomenda"
                  },
                  "cnaes_secundarios": [
                    {
                      "codigo": "6311900",
                      "descricao": "Tratamento de dados, provedores de serviços de aplicação e serviços de hospedagem na internet"
                    }
                  ],
                  "consulta": {
                    "provedor": "brasilapi",
                    "consultado_em": "2026-11-13T14:02:11.482Z",
                    "origem": "consulta"
                  },
                  "cobertura": {
                    "municipio_atendido": true,
                    "municipio_ibge": "3550308",
                    "municipio_nome": "São Paulo",
                    "uf": "SP",
                    "regimes_atendidos": [
                      "mei",
                      "simples_nacional",
                      "lucro_presumido",
                      "lucro_real"
                    ]
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          },
          "503": {
            "$ref": "#/components/responses/Indisponivel"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "prestadores:ler"
            ]
          }
        ],
        "x-escopo": "prestadores:ler",
        "x-codigos": [
          {
            "status": 404,
            "code": "cnpj_nao_encontrado",
            "quando": "A Receita não tem este CNPJ."
          },
          {
            "status": 503,
            "code": "cnpj_consulta_indisponivel",
            "quando": "Nenhuma fonte de consulta respondeu e não há cópia guardada."
          }
        ]
      }
    },
    "/v1/catalogo/ctribnac": {
      "get": {
        "operationId": "buscarCodigosDeTributacao",
        "tags": [
          "Consultas"
        ],
        "summary": "Buscar códigos de tributação nacional",
        "description": "Busca no catálogo nacional de serviços (cTribNac). Use `q` para pesquisar pelo texto, `cnae` para listar os códigos ligados a um CNAE e `prestador_id` para saber quais são compatíveis com as atividades do prestador (compatíveis primeiro).\n\n`total` é quantos códigos casam; a lista traz até `limite`.\n\n**Escopo necessário:** `prestadores:ler`.",
        "parameters": [
          {
            "name": "q",
            "in": "query",
            "required": false,
            "description": "Texto a procurar na descrição do serviço (até 200 caracteres). Ignora acentos.",
            "schema": {
              "type": "string",
              "maxLength": 200
            }
          },
          {
            "name": "cnae",
            "in": "query",
            "required": false,
            "description": "CNAE com 7 dígitos (aceita pontuação): só os códigos ligados a ele.",
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "prestador_id",
            "in": "query",
            "required": false,
            "description": "Marca a compatibilidade dos códigos com os CNAEs deste prestador e coloca os compatíveis primeiro. Omitido: sem compatibilidade.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          },
          {
            "name": "limite",
            "in": "query",
            "required": false,
            "description": "Itens por página (1 a 100).",
            "schema": {
              "type": "integer",
              "minimum": 1,
              "maximum": 100,
              "default": 20
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Códigos encontrados.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ListaDeCtribnac"
                },
                "example": {
                  "dados": [
                    {
                      "codigo": "010701",
                      "descricao": "Suporte técnico em informática, inclusive instalação, configuração e manutenção de programas de computação e bancos de dados.",
                      "item_lc116": "01.07",
                      "item_descricao": "Serviços de informática e congêneres.",
                      "subitem_descricao": "Suporte técnico em informática, inclusive instalação, configuração e manutenção de programas de computação e bancos de dados.",
                      "compativel_com_prestador": true,
                      "nivel_compatibilidade": "cnae",
                      "cnaes_relacionados": [
                        {
                          "codigo": "6209100",
                          "descricao": "Suporte técnico, manutenção e outros serviços em tecnologia da informação"
                        }
                      ]
                    }
                  ],
                  "total": 1,
                  "catalogo": {
                    "versao": "2026.1"
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          },
          "503": {
            "$ref": "#/components/responses/Indisponivel"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "prestadores:ler"
            ]
          }
        ],
        "x-escopo": "prestadores:ler",
        "x-codigos": [
          {
            "status": 503,
            "code": "catalogo_indisponivel",
            "quando": "O catálogo nacional ainda não foi carregado neste ambiente."
          }
        ]
      }
    },
    "/v1/catalogo/cnae": {
      "get": {
        "operationId": "buscarCnaes",
        "tags": [
          "Consultas"
        ],
        "summary": "Buscar CNAEs",
        "description": "Busca no catálogo de CNAEs pelo texto (`q`) ou lista os primeiros. `possui_ctribnac` indica se o CNAE tem código de tributação ligado.\n\n**Escopo necessário:** `prestadores:ler`.",
        "parameters": [
          {
            "name": "q",
            "in": "query",
            "required": false,
            "description": "Texto a procurar na descrição da atividade (até 200 caracteres).",
            "schema": {
              "type": "string",
              "maxLength": 200
            }
          },
          {
            "name": "limite",
            "in": "query",
            "required": false,
            "description": "Itens por página (1 a 100).",
            "schema": {
              "type": "integer",
              "minimum": 1,
              "maximum": 100,
              "default": 20
            }
          }
        ],
        "responses": {
          "200": {
            "description": "CNAEs encontrados.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ListaDeCnaes"
                },
                "example": {
                  "dados": [
                    {
                      "codigo": "6201501",
                      "codigo_formatado": "6201-5/01",
                      "descricao": "Desenvolvimento de programas de computador sob encomenda",
                      "secao": "J",
                      "possui_ctribnac": true
                    }
                  ],
                  "catalogo": {
                    "versao": "2026.1"
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          },
          "503": {
            "$ref": "#/components/responses/Indisponivel"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "prestadores:ler"
            ]
          }
        ],
        "x-escopo": "prestadores:ler",
        "x-codigos": [
          {
            "status": 503,
            "code": "catalogo_indisponivel",
            "quando": "O catálogo nacional ainda não foi carregado neste ambiente."
          }
        ]
      }
    },
    "/v1/tributacao/sugerir": {
      "post": {
        "operationId": "sugerirTributacao",
        "tags": [
          "Consultas"
        ],
        "summary": "Sugerir o código de tributação",
        "description": "Dada a descrição do que você vende, sugere códigos de tributação nacional, o melhor primeiro, com o motivo e uma confiança de 0 a 1. Com `prestador_id`, as sugestões trazem a compatibilidade com os CNAEs do prestador e, quando o código é o dos padrões dele, a alíquota.\n\n**É uma ajuda, não uma decisão fiscal**: confirme o código com o contador antes de usá-lo. `provedor` diz quem respondeu (`local` ou `anthropic`); se o provedor configurado falhou, `fallback` é verdadeiro e `motivo_fallback` explica. Só o texto da descrição e candidatos do catálogo público vão ao provedor externo: nada do prestador ou da conta.\n\nHá um limite de pedidos por minuto por conta (`429 limite_excedido`).\n\n**Escopo necessário:** `prestadores:ler`.",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "descricao": {
                    "type": "string",
                    "minLength": 3,
                    "maxLength": 500,
                    "description": "Descrição do serviço que aparece na nota."
                  },
                  "prestador_id": {
                    "type": "string",
                    "format": "uuid",
                    "description": "Habilita a compatibilidade com os CNAEs do prestador e a alíquota dos padrões dele. Omitido: a sugestão vem só do catálogo."
                  },
                  "valor": {
                    "type": "number",
                    "exclusiveMinimum": 0,
                    "maximum": 1000000000
                  }
                },
                "required": [
                  "descricao"
                ],
                "additionalProperties": false
              },
              "examples": {
                "descricao": {
                  "summary": "Só a descrição",
                  "value": {
                    "descricao": "Manutenção mensal de sistema web para clientes"
                  }
                },
                "prestador": {
                  "summary": "Com o prestador",
                  "value": {
                    "descricao": "Consultoria em segurança da informação",
                    "prestador_id": "0c1f7e3a-5d2b-4c8e-9a41-7b6d2e9f1a30"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Sugestões, a melhor primeiro.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/RespostaDeSugestao"
                },
                "example": {
                  "provedor": "local",
                  "fallback": false,
                  "cache": false,
                  "catalogo": {
                    "versao": "2026.1"
                  },
                  "sugestoes": [
                    {
                      "posicao": 1,
                      "codigo": "010701",
                      "descricao": "Suporte técnico em informática, inclusive instalação, configuração e manutenção de programas de computação e bancos de dados.",
                      "item_lc116": "01.07",
                      "item_descricao": "Serviços de informática e congêneres.",
                      "subitem_descricao": "Suporte técnico em informática, inclusive instalação, configuração e manutenção de programas de computação e bancos de dados.",
                      "compativel_com_prestador": true,
                      "nivel_compatibilidade": "cnae",
                      "cnaes_relacionados": [
                        {
                          "codigo": "6209100",
                          "descricao": "Suporte técnico, manutenção e outros serviços em tecnologia da informação"
                        }
                      ],
                      "aliquota_iss": 2,
                      "motivo": "A descrição fala em manutenção de sistemas, que é suporte técnico em informática (item 01.07).",
                      "confianca": 0.86
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          },
          "503": {
            "$ref": "#/components/responses/Indisponivel"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "prestadores:ler"
            ]
          }
        ],
        "x-escopo": "prestadores:ler",
        "x-codigos": [
          {
            "status": 503,
            "code": "catalogo_indisponivel",
            "quando": "O catálogo nacional ainda não foi carregado neste ambiente."
          }
        ]
      }
    },
    "/v1/certificados": {
      "post": {
        "operationId": "enviarCertificado",
        "tags": [
          "Certificados"
        ],
        "summary": "Enviar um certificado A1",
        "description": "Envia o certificado digital A1 (arquivo `.pfx`/`.p12` em base64, até ~50 KB) e a senha. Ele é validado, cifrado e usado para assinar as notas em produção. Se informar `prestador_id`, o certificado já é vinculado ao prestador. **Nunca** devolvemos o arquivo nem a senha.\n\n**Escopo necessário:** `certificados:escrever`.",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "apelido": {
                    "type": "string",
                    "minLength": 1,
                    "maxLength": 80,
                    "description": "Nome para você reconhecer o certificado."
                  },
                  "pfx_base64": {
                    "type": "string",
                    "minLength": 100,
                    "maxLength": 80000,
                    "description": "Conteúdo do arquivo .pfx/.p12 em base64."
                  },
                  "senha": {
                    "type": "string",
                    "minLength": 1,
                    "maxLength": 200,
                    "description": "Senha do certificado. Nunca é registrada nem devolvida."
                  },
                  "prestador_id": {
                    "type": "string",
                    "format": "uuid",
                    "description": "Vincula o certificado a este prestador já no envio. Omitido: o certificado fica na conta, sem vínculo."
                  }
                },
                "required": [
                  "apelido",
                  "pfx_base64",
                  "senha"
                ],
                "additionalProperties": false
              },
              "examples": {
                "vinculado": {
                  "summary": "Enviar e vincular ao prestador",
                  "value": {
                    "apelido": "A1 da Acme (2027)",
                    "pfx_base64": "MIIKXQIBAzCCCicGCSqGSIb3DQEHAaCCChgEggoUMIIKEDCCBgcGCSqGSIb3DQEHBqCCBfgwggX0AgEAMIIF7QYJKoZIhvcNAQcBMBwGCiqGSIb3DQEMAQMwDgQI",
                    "senha": "senha-do-certificado",
                    "prestador_id": "0c1f7e3a-5d2b-4c8e-9a41-7b6d2e9f1a30"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "201": {
            "description": "Certificado cadastrado.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Certificado"
                },
                "example": {
                  "id": "a2d96b4e-1c07-4f35-8e59-0b7c3a1d8f64",
                  "apelido": "A1 da Acme (2027)",
                  "cnpj": "11222333000181",
                  "titular": "ACME TECNOLOGIA LTDA:11222333000181",
                  "numero_serie": "4F2A9C1E7B3D5A60",
                  "validade_inicio": "2026-08-30T00:00:00.000Z",
                  "validade_fim": "2027-08-30T23:59:59.000Z",
                  "dias_restantes": 290,
                  "expirando": false,
                  "status": "ativo",
                  "fingerprint_sha256": "9f2c4b7a1e8d3056a7c1b94e2d8f0a63517c9e4b2a8d6f10c3e5b7a9d1f24680",
                  "prestadores": [
                    "0c1f7e3a-5d2b-4c8e-9a41-7b6d2e9f1a30"
                  ],
                  "criado_em": "2026-11-13T14:02:11.482Z"
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "409": {
            "$ref": "#/components/responses/Conflito"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "certificados:escrever"
            ]
          }
        ],
        "x-escopo": "certificados:escrever",
        "x-codigos": [
          {
            "status": 422,
            "code": "certificado_invalido",
            "quando": "Arquivo ou senha inválidos, ou o certificado não é um A1 de pessoa jurídica."
          },
          {
            "status": 422,
            "code": "certificado_expirado",
            "quando": "O certificado está fora da validade."
          },
          {
            "status": 409,
            "code": "certificado_ja_cadastrado",
            "quando": "Este certificado já está cadastrado na conta."
          }
        ]
      },
      "get": {
        "operationId": "listarCertificados",
        "tags": [
          "Certificados"
        ],
        "summary": "Listar certificados",
        "description": "Lista os certificados, com a validade e os prestadores que os usam.\n\n**Escopo necessário:** `certificados:ler`.",
        "parameters": [
          {
            "name": "limite",
            "in": "query",
            "required": false,
            "description": "Itens por página (1 a 100).",
            "schema": {
              "type": "integer",
              "minimum": 1,
              "maximum": 100,
              "default": 25
            }
          },
          {
            "name": "cursor",
            "in": "query",
            "required": false,
            "description": "Valor de `proximo_cursor` da página anterior.",
            "schema": {
              "type": "string",
              "maxLength": 500
            }
          },
          {
            "name": "status",
            "in": "query",
            "required": false,
            "description": "Filtra pelo status.",
            "schema": {
              "type": "string",
              "enum": [
                "ativo",
                "expirado",
                "revogado"
              ]
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Página de certificados.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ListaDeCertificados"
                },
                "example": {
                  "dados": [
                    {
                      "id": "a2d96b4e-1c07-4f35-8e59-0b7c3a1d8f64",
                      "apelido": "A1 da Acme (2027)",
                      "cnpj": "11222333000181",
                      "titular": "ACME TECNOLOGIA LTDA:11222333000181",
                      "numero_serie": "4F2A9C1E7B3D5A60",
                      "validade_inicio": "2026-08-30T00:00:00.000Z",
                      "validade_fim": "2027-08-30T23:59:59.000Z",
                      "dias_restantes": 290,
                      "expirando": false,
                      "status": "ativo",
                      "fingerprint_sha256": "9f2c4b7a1e8d3056a7c1b94e2d8f0a63517c9e4b2a8d6f10c3e5b7a9d1f24680",
                      "prestadores": [
                        "0c1f7e3a-5d2b-4c8e-9a41-7b6d2e9f1a30"
                      ],
                      "criado_em": "2026-11-13T14:02:11.482Z"
                    }
                  ],
                  "proximo_cursor": null
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "certificados:ler"
            ]
          }
        ],
        "x-escopo": "certificados:ler"
      }
    },
    "/v1/certificados/{id}": {
      "get": {
        "operationId": "obterCertificado",
        "tags": [
          "Certificados"
        ],
        "summary": "Consultar um certificado",
        "description": "Devolve os metadados do certificado (nunca o arquivo).\n\n**Escopo necessário:** `certificados:ler`.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "description": "Identificador do recurso.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "O certificado.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Certificado"
                },
                "example": {
                  "id": "a2d96b4e-1c07-4f35-8e59-0b7c3a1d8f64",
                  "apelido": "A1 da Acme (2027)",
                  "cnpj": "11222333000181",
                  "titular": "ACME TECNOLOGIA LTDA:11222333000181",
                  "numero_serie": "4F2A9C1E7B3D5A60",
                  "validade_inicio": "2026-08-30T00:00:00.000Z",
                  "validade_fim": "2027-08-30T23:59:59.000Z",
                  "dias_restantes": 290,
                  "expirando": false,
                  "status": "ativo",
                  "fingerprint_sha256": "9f2c4b7a1e8d3056a7c1b94e2d8f0a63517c9e4b2a8d6f10c3e5b7a9d1f24680",
                  "prestadores": [
                    "0c1f7e3a-5d2b-4c8e-9a41-7b6d2e9f1a30"
                  ],
                  "criado_em": "2026-11-13T14:02:11.482Z"
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "certificados:ler"
            ]
          }
        ],
        "x-escopo": "certificados:ler"
      },
      "delete": {
        "operationId": "revogarCertificado",
        "tags": [
          "Certificados"
        ],
        "summary": "Remover um certificado",
        "description": "Revoga o certificado e apaga o material cifrado. Os prestadores que o usavam ficam sem autorização para emitir em produção até receberem outro.\n\n**Escopo necessário:** `certificados:escrever`.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "description": "Identificador do recurso.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Sem conteúdo.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "certificados:escrever"
            ]
          }
        ],
        "x-escopo": "certificados:escrever"
      }
    },
    "/v1/webhooks": {
      "post": {
        "operationId": "criarWebhook",
        "tags": [
          "Webhooks"
        ],
        "summary": "Criar um endpoint de webhook",
        "description": "Cadastra a URL que recebe os eventos. A resposta traz o `segredo` de assinatura (`whsec_…`) **uma única vez**: guarde-o. Em produção a URL precisa ser HTTPS e não pode apontar para endereços internos.\n\n**Escopo necessário:** `webhooks:gerir`.",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "url": {
                    "type": "string",
                    "minLength": 8,
                    "maxLength": 2000,
                    "description": "URL HTTPS que receberá os eventos. Endereços internos ou reservados são recusados."
                  },
                  "eventos": {
                    "type": "array",
                    "items": {
                      "type": "string",
                      "enum": [
                        "nota.processando",
                        "nota.autorizada",
                        "nota.rejeitada",
                        "nota.cancelada",
                        "nota.erro",
                        "certificado.expirando",
                        "exportacao.pronta",
                        "*"
                      ]
                    },
                    "minItems": 1,
                    "maxItems": 8,
                    "description": "Tipos de evento recebidos; `*` = todos."
                  },
                  "descricao": {
                    "anyOf": [
                      {
                        "type": "string",
                        "maxLength": 200
                      },
                      {
                        "type": "null"
                      }
                    ],
                    "description": "Texto livre para você reconhecer o endpoint."
                  },
                  "ambiente": {
                    "type": "string",
                    "enum": [
                      "sandbox",
                      "producao"
                    ],
                    "description": "Ambiente dos eventos. Padrão: o da chave que cria o endpoint."
                  }
                },
                "required": [
                  "url",
                  "eventos"
                ],
                "additionalProperties": false
              },
              "examples": {
                "notas": {
                  "summary": "Eventos de nota",
                  "value": {
                    "url": "https://erp.acme.example.com/webhooks/nfsplus",
                    "eventos": [
                      "nota.autorizada",
                      "nota.rejeitada",
                      "nota.cancelada"
                    ],
                    "descricao": "ERP de produção"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "201": {
            "description": "Endpoint criado, com o segredo.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/WebhookComSegredo"
                },
                "example": {
                  "id": "d5f1a8c3-6e92-4b07-a3d4-2c8e9b1f7a50",
                  "url": "https://erp.acme.example.com/webhooks/nfsplus",
                  "descricao": "ERP de produção",
                  "eventos": [
                    "nota.autorizada",
                    "nota.rejeitada",
                    "nota.cancelada"
                  ],
                  "ambiente": "sandbox",
                  "segredo_prefixo": "whsec_9fK2",
                  "falhas_consecutivas": 0,
                  "desativado_auto_em": null,
                  "desativado_motivo": null,
                  "criado_em": "2026-11-13T14:02:11.482Z",
                  "atualizado_em": "2026-11-13T14:02:11.482Z",
                  "status": "ativo",
                  "segredo": "whsec_9fK2xQ7mLpR4vT1bYc8aNd3sHe6uJgW0oZiXtVkA5Cn",
                  "aviso": "Guarde o segredo agora: ele não será exibido novamente."
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "402": {
            "$ref": "#/components/responses/PagamentoNecessario"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "webhooks:gerir"
            ]
          }
        ],
        "x-escopo": "webhooks:gerir",
        "x-codigos": [
          {
            "status": 402,
            "code": "limite_plano_webhooks",
            "quando": "O plano não comporta mais endpoints."
          },
          {
            "status": 422,
            "code": "webhook_url_invalida",
            "quando": "URL fora do padrão (HTTPS em produção, sem destino interno)."
          }
        ]
      },
      "get": {
        "operationId": "listarWebhooks",
        "tags": [
          "Webhooks"
        ],
        "summary": "Listar endpoints de webhook",
        "description": "Lista os endpoints ativos da conta (não paginado), o limite do plano e os eventos disponíveis.\n\n**Escopo necessário:** `webhooks:ler`.",
        "responses": {
          "200": {
            "description": "Endpoints.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ListaDeWebhooks"
                },
                "example": {
                  "dados": [
                    {
                      "id": "d5f1a8c3-6e92-4b07-a3d4-2c8e9b1f7a50",
                      "url": "https://erp.acme.example.com/webhooks/nfsplus",
                      "descricao": "ERP de produção",
                      "eventos": [
                        "nota.autorizada",
                        "nota.rejeitada",
                        "nota.cancelada"
                      ],
                      "ambiente": "sandbox",
                      "segredo_prefixo": "whsec_9fK2",
                      "falhas_consecutivas": 0,
                      "desativado_auto_em": null,
                      "desativado_motivo": null,
                      "criado_em": "2026-11-13T14:02:11.482Z",
                      "atualizado_em": "2026-11-13T14:02:11.482Z",
                      "status": "ativo"
                    }
                  ],
                  "proximo_cursor": null,
                  "limite": 5,
                  "eventos_disponiveis": [
                    "nota.processando",
                    "nota.autorizada",
                    "nota.rejeitada",
                    "nota.cancelada",
                    "nota.erro",
                    "certificado.expirando",
                    "exportacao.pronta",
                    "*"
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "webhooks:ler"
            ]
          }
        ],
        "x-escopo": "webhooks:ler"
      }
    },
    "/v1/webhooks/{id}": {
      "get": {
        "operationId": "obterWebhook",
        "tags": [
          "Webhooks"
        ],
        "summary": "Consultar um endpoint",
        "description": "Devolve o endpoint e a contagem de entregas por status.\n\n**Escopo necessário:** `webhooks:ler`.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "description": "Identificador do recurso.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "O endpoint.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/WebhookDetalhe"
                },
                "example": {
                  "id": "d5f1a8c3-6e92-4b07-a3d4-2c8e9b1f7a50",
                  "url": "https://erp.acme.example.com/webhooks/nfsplus",
                  "descricao": "ERP de produção",
                  "eventos": [
                    "nota.autorizada",
                    "nota.rejeitada",
                    "nota.cancelada"
                  ],
                  "ambiente": "sandbox",
                  "segredo_prefixo": "whsec_9fK2",
                  "falhas_consecutivas": 0,
                  "desativado_auto_em": null,
                  "desativado_motivo": null,
                  "criado_em": "2026-11-13T14:02:11.482Z",
                  "atualizado_em": "2026-11-13T14:02:11.482Z",
                  "status": "ativo",
                  "entregas_resumo": {
                    "entregue": 12,
                    "falhou": 1
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "webhooks:ler"
            ]
          }
        ],
        "x-escopo": "webhooks:ler"
      },
      "patch": {
        "operationId": "atualizarWebhook",
        "tags": [
          "Webhooks"
        ],
        "summary": "Alterar um endpoint",
        "description": "Altera URL, eventos, descrição ou o estado. `status: \"ativo\"` reativa e zera o contador de falhas, inclusive de um endpoint desativado automaticamente.\n\n**Escopo necessário:** `webhooks:gerir`.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "description": "Identificador do recurso.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "url": {
                    "type": "string",
                    "minLength": 8,
                    "maxLength": 2000,
                    "description": "URL HTTPS que receberá os eventos. Endereços internos ou reservados são recusados."
                  },
                  "eventos": {
                    "type": "array",
                    "items": {
                      "type": "string",
                      "enum": [
                        "nota.processando",
                        "nota.autorizada",
                        "nota.rejeitada",
                        "nota.cancelada",
                        "nota.erro",
                        "certificado.expirando",
                        "exportacao.pronta",
                        "*"
                      ]
                    },
                    "minItems": 1,
                    "maxItems": 8,
                    "description": "Tipos de evento recebidos; `*` = todos."
                  },
                  "descricao": {
                    "anyOf": [
                      {
                        "type": "string",
                        "maxLength": 200
                      },
                      {
                        "type": "null"
                      }
                    ],
                    "description": "Texto livre para você reconhecer o endpoint."
                  },
                  "status": {
                    "type": "string",
                    "enum": [
                      "ativo",
                      "pausado"
                    ],
                    "description": "`ativo` reativa (e zera as falhas); `pausado` suspende as entregas."
                  }
                },
                "additionalProperties": false
              },
              "examples": {
                "pausar": {
                  "summary": "Pausar",
                  "value": {
                    "status": "pausado"
                  }
                },
                "reativar": {
                  "summary": "Reativar",
                  "value": {
                    "status": "ativo"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "O endpoint.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Webhook"
                },
                "example": {
                  "id": "d5f1a8c3-6e92-4b07-a3d4-2c8e9b1f7a50",
                  "url": "https://erp.acme.example.com/webhooks/nfsplus",
                  "descricao": "ERP de produção",
                  "eventos": [
                    "nota.autorizada",
                    "nota.rejeitada",
                    "nota.cancelada"
                  ],
                  "ambiente": "sandbox",
                  "segredo_prefixo": "whsec_9fK2",
                  "falhas_consecutivas": 0,
                  "desativado_auto_em": null,
                  "desativado_motivo": null,
                  "criado_em": "2026-11-13T14:02:11.482Z",
                  "atualizado_em": "2026-11-13T14:02:11.482Z",
                  "status": "ativo"
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "webhooks:gerir"
            ]
          }
        ],
        "x-escopo": "webhooks:gerir"
      },
      "delete": {
        "operationId": "removerWebhook",
        "tags": [
          "Webhooks"
        ],
        "summary": "Remover um endpoint",
        "description": "Remove o endpoint. O histórico de entregas permanece.\n\n**Escopo necessário:** `webhooks:gerir`.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "description": "Identificador do recurso.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Sem conteúdo.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "webhooks:gerir"
            ]
          }
        ],
        "x-escopo": "webhooks:gerir"
      }
    },
    "/v1/webhooks/{id}/rotacao-segredo": {
      "post": {
        "operationId": "rotacionarSegredoDoWebhook",
        "tags": [
          "Webhooks"
        ],
        "summary": "Rotacionar o segredo",
        "description": "Gera um segredo novo (mostrado uma única vez). O anterior continua valendo por **24 horas**: nesse período a assinatura traz dois `v1`, e você troca sem perder eventos.\n\n**Escopo necessário:** `webhooks:gerir`.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "description": "Identificador do recurso.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Segredo novo.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/WebhookRotacionado"
                },
                "example": {
                  "id": "d5f1a8c3-6e92-4b07-a3d4-2c8e9b1f7a50",
                  "url": "https://erp.acme.example.com/webhooks/nfsplus",
                  "descricao": "ERP de produção",
                  "eventos": [
                    "nota.autorizada",
                    "nota.rejeitada",
                    "nota.cancelada"
                  ],
                  "ambiente": "sandbox",
                  "segredo_prefixo": "whsec_9fK2",
                  "falhas_consecutivas": 0,
                  "desativado_auto_em": null,
                  "desativado_motivo": null,
                  "criado_em": "2026-11-13T14:02:11.482Z",
                  "atualizado_em": "2026-11-13T14:02:11.482Z",
                  "status": "ativo",
                  "segredo": "whsec_Qm4vT8xK1pLr7nYc2aBd9sHe3uJgW6oZiXtVkA0Cf5",
                  "segredo_anterior_valido_ate": "2026-11-14T14:05:00.000Z",
                  "aviso": "Guarde o segredo agora: ele não será exibido novamente."
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "webhooks:gerir"
            ]
          }
        ],
        "x-escopo": "webhooks:gerir"
      }
    },
    "/v1/webhooks/{id}/testar": {
      "post": {
        "operationId": "testarWebhook",
        "tags": [
          "Webhooks"
        ],
        "summary": "Enviar um evento de teste",
        "description": "Envia na hora um evento `webhook.teste` assinado e devolve o resultado (status HTTP, tempo e começo da resposta). Serve para validar a URL e a verificação de assinatura.\n\n**Escopo necessário:** `webhooks:gerir`.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "description": "Identificador do recurso.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Resultado do envio. `sucesso: false` não é erro da API: indica que o seu servidor não respondeu 2xx.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ResultadoTeste"
                },
                "example": {
                  "sucesso": true,
                  "evento_id": "f4c8a2d6-7b13-4e95-8c60-3a9d1e7b5f82",
                  "status_http": 200,
                  "duracao_ms": 84,
                  "resposta": "ok",
                  "erro": null
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "webhooks:gerir"
            ]
          }
        ],
        "x-escopo": "webhooks:gerir"
      }
    },
    "/v1/webhooks/{id}/teste": {
      "post": {
        "operationId": "testarWebhookApelido",
        "tags": [
          "Webhooks"
        ],
        "summary": "Enviar um evento de teste (nome antigo)",
        "description": "**Obsoleta.** Mantida por compatibilidade; não será removida sem aviso prévio, mas novas integrações devem usar a operação indicada abaixo.\n\nMesmo comportamento, corpo e resposta de `POST /v1/webhooks/{id}/testar`, que é o nome canônico. Use-o em integrações novas.\n\n**Escopo necessário:** `webhooks:gerir`.",
        "deprecated": true,
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "description": "Identificador do recurso.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Resultado do envio.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ResultadoTeste"
                },
                "example": {
                  "sucesso": true,
                  "evento_id": "f4c8a2d6-7b13-4e95-8c60-3a9d1e7b5f82",
                  "status_http": 200,
                  "duracao_ms": 84,
                  "resposta": "ok",
                  "erro": null
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "webhooks:gerir"
            ]
          }
        ],
        "x-escopo": "webhooks:gerir"
      }
    },
    "/v1/webhooks/{id}/entregas": {
      "get": {
        "operationId": "listarEntregasDoWebhook",
        "tags": [
          "Webhooks"
        ],
        "summary": "Listar entregas",
        "description": "Histórico de entregas do endpoint, da mais recente para a mais antiga.\n\n**Escopo necessário:** `webhooks:ler`.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "description": "Identificador do recurso.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          },
          {
            "name": "limite",
            "in": "query",
            "required": false,
            "description": "Itens por página (1 a 100).",
            "schema": {
              "type": "integer",
              "minimum": 1,
              "maximum": 100,
              "default": 25
            }
          },
          {
            "name": "cursor",
            "in": "query",
            "required": false,
            "description": "Valor de `proximo_cursor` da página anterior.",
            "schema": {
              "type": "string",
              "maxLength": 500
            }
          },
          {
            "name": "status",
            "in": "query",
            "required": false,
            "description": "Filtra pelo status.",
            "schema": {
              "type": "string",
              "enum": [
                "pendente",
                "entregue",
                "falhou",
                "desistiu"
              ]
            }
          },
          {
            "name": "evento",
            "in": "query",
            "required": false,
            "description": "Filtra pelo tipo de evento.",
            "schema": {
              "type": "string",
              "maxLength": 80
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Página de entregas.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ListaDeEntregas"
                },
                "example": {
                  "dados": [
                    {
                      "id": "e9b3c7a1-4d58-4f62-9a0e-6d1b8c2f5a37",
                      "evento": "nota.autorizada",
                      "evento_id": "f4c8a2d6-7b13-4e95-8c60-3a9d1e7b5f82",
                      "status": "entregue",
                      "tentativas": 1,
                      "proxima_tentativa_em": null,
                      "ultimo_status_http": 200,
                      "ultima_resposta": "ok",
                      "ultimo_erro": null,
                      "criado_em": "2026-11-13T14:02:13.905Z",
                      "entregue_em": "2026-11-13T14:02:13.905Z"
                    }
                  ],
                  "proximo_cursor": null
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "webhooks:ler"
            ]
          }
        ],
        "x-escopo": "webhooks:ler"
      }
    },
    "/v1/webhooks/{id}/entregas/{entregaId}": {
      "get": {
        "operationId": "obterEntregaDoWebhook",
        "tags": [
          "Webhooks"
        ],
        "summary": "Consultar uma entrega",
        "description": "Devolve a entrega com o corpo (`payload`) que foi enviado.\n\n**Escopo necessário:** `webhooks:ler`.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "description": "Identificador do recurso.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          },
          {
            "name": "entregaId",
            "in": "path",
            "required": true,
            "description": "Identificador da entrega.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "A entrega.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/EntregaDetalhe"
                },
                "example": {
                  "id": "e9b3c7a1-4d58-4f62-9a0e-6d1b8c2f5a37",
                  "evento": "nota.autorizada",
                  "evento_id": "f4c8a2d6-7b13-4e95-8c60-3a9d1e7b5f82",
                  "status": "entregue",
                  "tentativas": 1,
                  "proxima_tentativa_em": null,
                  "ultimo_status_http": 200,
                  "ultima_resposta": "ok",
                  "ultimo_erro": null,
                  "criado_em": "2026-11-13T14:02:13.905Z",
                  "entregue_em": "2026-11-13T14:02:13.905Z",
                  "payload": {
                    "id": "f4c8a2d6-7b13-4e95-8c60-3a9d1e7b5f82",
                    "tipo": "nota.autorizada",
                    "criado_em": "2026-11-13T14:02:13.905Z",
                    "ambiente": "sandbox",
                    "api_versao": "v1",
                    "dados": {
                      "nota": {
                        "id": "7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25",
                        "fase": null,
                        "ambiente": "sandbox",
                        "sem_validade_juridica": true,
                        "prestador_id": "0c1f7e3a-5d2b-4c8e-9a41-7b6d2e9f1a30",
                        "referencia_externa": "pedido-48213",
                        "competencia": "2026-11-13",
                        "tomador": {
                          "id": "3b8d0f52-91c4-4a7e-8f26-5e1c7a9d4b02",
                          "tipo_documento": "cpf",
                          "documento_mascarado": "***.982.247-**",
                          "nome": "Maria Souza"
                        },
                        "servico": {
                          "codigo_tributacao_nacional": "010701",
                          "codigo_tributacao_municipal": null,
                          "codigo_nbs": null,
                          "descricao": "Desenvolvimento de software sob encomenda",
                          "local_prestacao_ibge": "3550308"
                        },
                        "valores": {
                          "valor_servicos_centavos": 150000,
                          "desconto_incondicionado_centavos": 0,
                          "aliquota_iss": 2,
                          "valor_iss_centavos": 3000,
                          "iss_retido": false
                        },
                        "informacoes_complementares": null,
                        "metadados": {
                          "pedido": "48213"
                        },
                        "dps": {
                          "serie": "1",
                          "numero": 37,
                          "id": "DPS355030821122233300018100001000000000000037"
                        },
                        "cancelamento": null,
                        "substituicao": null,
                        "prazos": {
                          "cancelamento": {
                            "prazo_dias": 730,
                            "limite_em": "2028-11-12",
                            "dias_restantes": 730,
                            "dentro_do_prazo": true,
                            "explicacao": "Dá para cancelar até 12/11/2028 (730 dias contados da emissão)."
                          },
                          "substituicao": {
                            "prazo_dias": 730,
                            "limite_em": "2028-11-12",
                            "dias_restantes": 730,
                            "dentro_do_prazo": true,
                            "explicacao": "Dá para substituir até 12/11/2028 (730 dias contados da emissão).",
                            "sem_prazo_para": [
                              "desenquadramento_simples_nacional",
                              "enquadramento_simples_nacional"
                            ]
                          }
                        },
                        "erros": null,
                        "origem": "api",
                        "criado_em": "2026-11-13T14:02:11.482Z",
                        "atualizado_em": "2026-11-13T14:02:13.905Z",
                        "status": "autorizada",
                        "nfse": {
                          "numero": "37",
                          "chave_acesso": "35503082112223330001810000000000003710A4F1C9D2",
                          "codigo_verificacao": "A4F1C9D2",
                          "protocolo": "SIM3C9E1A7B52D4",
                          "conector": "simulador"
                        },
                        "emitida_em": "2026-11-13T14:02:13.905Z",
                        "cancelada_em": null,
                        "acoes": {
                          "cancelar": true,
                          "substituir": true,
                          "reprocessar": false,
                          "baixar_xml": true,
                          "baixar_pdf": true
                        },
                        "links": {
                          "self": "/v1/notas/7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25",
                          "xml": "/v1/notas/7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25/xml",
                          "pdf": "/v1/notas/7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25/pdf"
                        }
                      }
                    }
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "webhooks:ler"
            ]
          }
        ],
        "x-escopo": "webhooks:ler"
      }
    },
    "/v1/webhooks/{id}/entregas/{entregaId}/reenvio": {
      "post": {
        "operationId": "reenviarEntrega",
        "tags": [
          "Webhooks"
        ],
        "summary": "Reenviar uma entrega",
        "description": "Recoloca a entrega na fila com o **mesmo `evento_id`** (a assinatura é recalculada com o horário atual). O endpoint precisa estar ativo.\n\n**Escopo necessário:** `webhooks:gerir`.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "description": "Identificador do recurso.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          },
          {
            "name": "entregaId",
            "in": "path",
            "required": true,
            "description": "Identificador da entrega.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "202": {
            "description": "Entrega na fila.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "id",
                    "status"
                  ],
                  "properties": {
                    "id": {
                      "type": "string",
                      "format": "uuid"
                    },
                    "status": {
                      "type": "string",
                      "enum": [
                        "pendente"
                      ]
                    }
                  }
                },
                "example": {
                  "id": "e9b3c7a1-4d58-4f62-9a0e-6d1b8c2f5a37",
                  "status": "pendente"
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "409": {
            "$ref": "#/components/responses/Conflito"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "webhooks:gerir"
            ]
          }
        ],
        "x-escopo": "webhooks:gerir",
        "x-codigos": [
          {
            "status": 409,
            "code": "webhook_inativo",
            "quando": "O endpoint está pausado ou desativado."
          },
          {
            "status": 409,
            "code": "entrega_pendente",
            "quando": "A entrega já está na fila."
          }
        ]
      }
    },
    "/v1/exportacoes": {
      "post": {
        "operationId": "criarExportacao",
        "tags": [
          "Exportações"
        ],
        "summary": "Pedir uma exportação",
        "description": "Gera, em segundo plano, um arquivo com as notas de um período (pela competência): `zip` com os XMLs e PDFs, ou `csv`/`json` com a tabela de notas (o documento do tomador sai mascarado, como na API; os XMLs do `zip` trazem o documento completo, por serem o documento fiscal). Acompanhe por `GET /v1/exportacoes/{id}` ou pelo webhook `exportacao.pronta`. Limites: período de até 366 dias; 5.000 notas no ZIP e 50.000 na tabela; até 3 exportações simultâneas.\n\n**Escopo necessário:** `exportacoes:gerir`.",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "periodo_inicio": {
                    "type": "string",
                    "pattern": "^\\d{4}-\\d{2}-\\d{2}$",
                    "description": "Primeiro dia (AAAA-MM-DD, pela competência das notas)."
                  },
                  "periodo_fim": {
                    "type": "string",
                    "pattern": "^\\d{4}-\\d{2}-\\d{2}$",
                    "description": "Último dia (AAAA-MM-DD). Período máximo: 366 dias."
                  },
                  "prestador_id": {
                    "anyOf": [
                      {
                        "type": "string",
                        "format": "uuid"
                      },
                      {
                        "type": "null"
                      }
                    ],
                    "description": "Só as notas deste prestador. Omitido (ou `null`): de todos os prestadores da conta."
                  },
                  "formato": {
                    "type": "string",
                    "enum": [
                      "zip",
                      "csv",
                      "json"
                    ],
                    "default": "zip",
                    "description": "Formato do arquivo: `zip` (XML e PDF das notas), `csv` ou `json` (tabela de notas)."
                  },
                  "conteudo": {
                    "type": "array",
                    "items": {
                      "type": "string",
                      "enum": [
                        "xml",
                        "pdf"
                      ]
                    },
                    "minItems": 1,
                    "maxItems": 2,
                    "default": [
                      "xml",
                      "pdf"
                    ],
                    "description": "O que vai dentro do ZIP."
                  },
                  "status": {
                    "type": "array",
                    "items": {
                      "type": "string",
                      "enum": [
                        "processando",
                        "autorizada",
                        "rejeitada",
                        "cancelada",
                        "erro"
                      ]
                    },
                    "maxItems": 5,
                    "description": "Só as notas com estes status. Omitido: no `zip`, as `autorizada` e `cancelada`; em `csv` e `json`, todas."
                  },
                  "ambiente": {
                    "type": "string",
                    "enum": [
                      "sandbox",
                      "producao"
                    ],
                    "description": "Ambiente das notas. Padrão: o da chave de API."
                  }
                },
                "required": [
                  "periodo_inicio",
                  "periodo_fim"
                ],
                "additionalProperties": false
              },
              "examples": {
                "zip": {
                  "summary": "ZIP do mês",
                  "value": {
                    "periodo_inicio": "2026-11-01",
                    "periodo_fim": "2026-11-30",
                    "formato": "zip",
                    "conteudo": [
                      "xml",
                      "pdf"
                    ]
                  }
                },
                "csv": {
                  "summary": "Tabela CSV",
                  "value": {
                    "periodo_inicio": "2026-11-01",
                    "periodo_fim": "2026-11-30",
                    "formato": "csv"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "202": {
            "description": "Exportação aceita.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              },
              "Location": {
                "description": "URL da exportação.",
                "schema": {
                  "type": "string"
                }
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Exportacao"
                },
                "example": {
                  "id": "5a7d3e9b-8c14-4f20-b6a5-1e9c4d2f7b83",
                  "status": "processando",
                  "formato": "zip",
                  "ambiente": "sandbox",
                  "prestador_id": "0c1f7e3a-5d2b-4c8e-9a41-7b6d2e9f1a30",
                  "periodo_inicio": "2026-11-01",
                  "periodo_fim": "2026-11-30",
                  "conteudo": [
                    "xml",
                    "pdf"
                  ],
                  "total_documentos": null,
                  "tamanho_bytes": null,
                  "sha256": null,
                  "nome_arquivo": null,
                  "url_download": null,
                  "expira_em": null,
                  "erro": null,
                  "criado_em": "2026-11-13T14:02:11.482Z",
                  "concluido_em": null
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "exportacoes:gerir"
            ]
          }
        ],
        "x-escopo": "exportacoes:gerir",
        "x-codigos": [
          {
            "status": 422,
            "code": "exportacao_grande_demais",
            "quando": "O filtro passa do limite de notas; o erro traz `total` e `limite`."
          }
        ]
      },
      "get": {
        "operationId": "listarExportacoes",
        "tags": [
          "Exportações"
        ],
        "summary": "Listar exportações",
        "description": "Lista as exportações da conta.\n\n**Escopo necessário:** `exportacoes:gerir`.",
        "parameters": [
          {
            "name": "limite",
            "in": "query",
            "required": false,
            "description": "Itens por página (1 a 100).",
            "schema": {
              "type": "integer",
              "minimum": 1,
              "maximum": 100,
              "default": 25
            }
          },
          {
            "name": "cursor",
            "in": "query",
            "required": false,
            "description": "Valor de `proximo_cursor` da página anterior.",
            "schema": {
              "type": "string",
              "maxLength": 500
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Página de exportações.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ListaDeExportacoes"
                },
                "example": {
                  "dados": [
                    {
                      "id": "5a7d3e9b-8c14-4f20-b6a5-1e9c4d2f7b83",
                      "status": "pronta",
                      "formato": "zip",
                      "ambiente": "sandbox",
                      "prestador_id": "0c1f7e3a-5d2b-4c8e-9a41-7b6d2e9f1a30",
                      "periodo_inicio": "2026-11-01",
                      "periodo_fim": "2026-11-30",
                      "conteudo": [
                        "xml",
                        "pdf"
                      ],
                      "total_documentos": 42,
                      "tamanho_bytes": 1894213,
                      "sha256": "3d7f1a9c5e2b8406d1a7c3e95b2f8d4061a9c7e3b5d2f84106a9c1e7b3d5f280",
                      "nome_arquivo": "nfse-documentos_2026-11-01_2026-11-30_5a7d3e9b.zip",
                      "url_download": "https://api.nfsplus.com.br/v1/exportacoes/5a7d3e9b-8c14-4f20-b6a5-1e9c4d2f7b83/download?exp=1794582000&sig=Zk3mQ9vT1b7LxR4aYp2nWc8sHdE6uJfA0gVtKiOo5Xs",
                      "expira_em": "2026-11-20T14:05:00.000Z",
                      "erro": null,
                      "criado_em": "2026-11-13T14:02:11.482Z",
                      "concluido_em": "2026-11-13T14:02:13.905Z"
                    }
                  ],
                  "proximo_cursor": null
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "exportacoes:gerir"
            ]
          }
        ],
        "x-escopo": "exportacoes:gerir"
      }
    },
    "/v1/exportacoes/{id}": {
      "get": {
        "operationId": "obterExportacao",
        "tags": [
          "Exportações"
        ],
        "summary": "Consultar uma exportação",
        "description": "Devolve o estado. Quando `status` é `pronta`, `url_download` traz um link assinado, válido por até 24 h e utilizável sem credencial: dá para entregá-lo a um contador ou ao ERP. Peça outro link consultando de novo.\n\n**Escopo necessário:** `exportacoes:gerir`.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "description": "Identificador do recurso.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "A exportação.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Exportacao"
                },
                "example": {
                  "id": "5a7d3e9b-8c14-4f20-b6a5-1e9c4d2f7b83",
                  "status": "pronta",
                  "formato": "zip",
                  "ambiente": "sandbox",
                  "prestador_id": "0c1f7e3a-5d2b-4c8e-9a41-7b6d2e9f1a30",
                  "periodo_inicio": "2026-11-01",
                  "periodo_fim": "2026-11-30",
                  "conteudo": [
                    "xml",
                    "pdf"
                  ],
                  "total_documentos": 42,
                  "tamanho_bytes": 1894213,
                  "sha256": "3d7f1a9c5e2b8406d1a7c3e95b2f8d4061a9c7e3b5d2f84106a9c1e7b3d5f280",
                  "nome_arquivo": "nfse-documentos_2026-11-01_2026-11-30_5a7d3e9b.zip",
                  "url_download": "https://api.nfsplus.com.br/v1/exportacoes/5a7d3e9b-8c14-4f20-b6a5-1e9c4d2f7b83/download?exp=1794582000&sig=Zk3mQ9vT1b7LxR4aYp2nWc8sHdE6uJfA0gVtKiOo5Xs",
                  "expira_em": "2026-11-20T14:05:00.000Z",
                  "erro": null,
                  "criado_em": "2026-11-13T14:02:11.482Z",
                  "concluido_em": "2026-11-13T14:02:13.905Z"
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "exportacoes:gerir"
            ]
          }
        ],
        "x-escopo": "exportacoes:gerir"
      }
    },
    "/v1/exportacoes/{id}/download": {
      "get": {
        "operationId": "baixarExportacao",
        "tags": [
          "Exportações"
        ],
        "summary": "Baixar o arquivo",
        "description": "Baixa o arquivo. Aceita a chave de API (escopo `exportacoes:gerir`) **ou** o link assinado `?exp=&sig=` de `url_download`. O cabeçalho `X-Content-SHA256` traz o hash para conferência. Depois de `expira_em` (7 dias) responde `410`.\n\nEsta operação também aceita o link assinado (sem chave).",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "description": "Identificador do recurso.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          },
          {
            "name": "exp",
            "in": "query",
            "required": false,
            "description": "Validade do link (instante Unix, em segundos).",
            "schema": {
              "type": "string",
              "maxLength": 20
            }
          },
          {
            "name": "sig",
            "in": "query",
            "required": false,
            "description": "Assinatura do link, como veio em `url_download`.",
            "schema": {
              "type": "string",
              "maxLength": 100
            }
          }
        ],
        "responses": {
          "200": {
            "description": "O arquivo. O tipo segue o formato pedido na exportação: `application/zip` (XML), `text/csv`, `application/json`.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              },
              "X-Content-SHA256": {
                "description": "SHA-256 do arquivo, em hexadecimal.",
                "schema": {
                  "type": "string"
                }
              }
            },
            "content": {
              "application/zip": {
                "schema": {
                  "type": "string",
                  "format": "binary"
                }
              },
              "text/csv": {
                "schema": {
                  "type": "string",
                  "format": "binary"
                }
              },
              "application/json": {
                "schema": {
                  "type": "string",
                  "format": "binary"
                }
              },
              "application/octet-stream": {
                "schema": {
                  "type": "string",
                  "format": "binary"
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "409": {
            "$ref": "#/components/responses/Conflito"
          },
          "410": {
            "$ref": "#/components/responses/Expirado"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          },
          "503": {
            "$ref": "#/components/responses/Indisponivel"
          }
        },
        "security": [
          {
            "bearerAuth": []
          },
          {}
        ],
        "x-codigos": [
          {
            "status": 403,
            "code": "link_invalido",
            "quando": "Link de download inválido ou vencido."
          },
          {
            "status": 409,
            "code": "exportacao_nao_pronta",
            "quando": "A exportação ainda está sendo gerada ou falhou."
          },
          {
            "status": 410,
            "code": "exportacao_expirada",
            "quando": "A exportação passou de 7 dias; gere outra."
          },
          {
            "status": 503,
            "code": "exportacao_integridade",
            "quando": "O arquivo guardado não confere com o hash registrado. Tente de novo em instantes."
          }
        ]
      }
    },
    "/v1/sandbox/cenarios": {
      "get": {
        "operationId": "listarCenarios",
        "tags": [
          "Sandbox"
        ],
        "summary": "Listar cenários do simulador",
        "description": "Lista os cenários que você programou para o Sandbox, em ordem de prioridade, mais os campos e operadores aceitos nos gatilhos.\n\n**Escopo necessário:** `notas:ler`.",
        "responses": {
          "200": {
            "description": "Cenários.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ListaDeCenarios"
                },
                "example": {
                  "dados": [
                    {
                      "id": "8c2e6a4d-3f71-4b59-9d08-7a5c1e3b9f46",
                      "nome": "Recusar descrições de teste",
                      "gatilho": {
                        "descricao_contem": "[recusar]"
                      },
                      "resultado": "rejeitar",
                      "codigo_erro": "E160",
                      "mensagem": "Código de tributação incompatível com a atividade do prestador.",
                      "atraso_ms": 0,
                      "falhas": 1,
                      "prioridade": 100,
                      "ativo": true,
                      "criado_em": "2026-11-13T14:02:11.482Z",
                      "atualizado_em": "2026-11-13T14:02:11.482Z"
                    }
                  ],
                  "proximo_cursor": null,
                  "campos_gatilho": [
                    "valor_servico_centavos",
                    "descricao",
                    "tomador_nome",
                    "tomador_documento",
                    "prestador_cnpj",
                    "inscricao_municipal",
                    "ibge",
                    "codigo_tributacao",
                    "referencia_externa"
                  ],
                  "operadores": [
                    "igual",
                    "diferente",
                    "contem",
                    "comeca_com",
                    "termina_com",
                    "maior_que",
                    "menor_que",
                    "em"
                  ],
                  "limite": 50
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "notas:ler"
            ]
          }
        ],
        "x-escopo": "notas:ler"
      },
      "post": {
        "operationId": "criarCenario",
        "tags": [
          "Sandbox"
        ],
        "summary": "Criar um cenário",
        "description": "Programa o simulador: quando uma nota do Sandbox casar com o `gatilho`, o resultado escolhido é aplicado. Alternativa persistente ao cabeçalho `X-Sandbox-Scenario`. Até 50 cenários por conta.\n\n**Escopo necessário:** `notas:emitir`.",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "nome": {
                    "type": "string",
                    "minLength": 2,
                    "maxLength": 120,
                    "description": "Nome do cenário."
                  },
                  "gatilho": {
                    "type": "object",
                    "additionalProperties": {},
                    "description": "Condições (unidas por E) que a nota precisa cumprir. Aceita `{ \"campo\": \"...\", \"<operador>\": valor }`, `{ \"todos\": [ ... ] }` ou o atalho `{ \"<campo>_<operador>\": valor }`."
                  },
                  "resultado": {
                    "type": "string",
                    "enum": [
                      "autorizar",
                      "rejeitar",
                      "atrasar",
                      "erro_transitorio"
                    ],
                    "description": "O que o simulador faz quando o gatilho casa."
                  },
                  "codigo_erro": {
                    "anyOf": [
                      {
                        "type": "string",
                        "minLength": 1,
                        "maxLength": 80
                      },
                      {
                        "type": "null"
                      }
                    ],
                    "description": "Código devolvido na rejeição ou no erro simulado."
                  },
                  "mensagem": {
                    "anyOf": [
                      {
                        "type": "string",
                        "minLength": 1,
                        "maxLength": 500
                      },
                      {
                        "type": "null"
                      }
                    ],
                    "description": "Mensagem devolvida na rejeição ou no erro simulado."
                  },
                  "atraso_ms": {
                    "type": "integer",
                    "minimum": 0,
                    "maximum": 60000,
                    "description": "Atraso (0 a 60000 ms) antes de agir."
                  },
                  "falhas": {
                    "type": "integer",
                    "minimum": 1,
                    "maximum": 20,
                    "description": "Em `erro_transitorio`: quantas tentativas falham antes de passar a funcionar."
                  },
                  "prioridade": {
                    "type": "integer",
                    "minimum": 1,
                    "maximum": 1000,
                    "description": "Menor número vence quando mais de um cenário casa. Padrão 100."
                  },
                  "ativo": {
                    "type": "boolean",
                    "description": "Desligue para pausar o cenário sem apagá-lo."
                  }
                },
                "required": [
                  "nome",
                  "gatilho",
                  "resultado"
                ],
                "additionalProperties": false
              },
              "examples": {
                "rejeitar": {
                  "summary": "Rejeitar descrições com [recusar]",
                  "value": {
                    "nome": "Recusar descrições de teste",
                    "gatilho": {
                      "descricao_contem": "[recusar]"
                    },
                    "resultado": "rejeitar",
                    "codigo_erro": "E160",
                    "mensagem": "Código de tributação incompatível com a atividade do prestador."
                  }
                },
                "atrasar": {
                  "summary": "Demorar 5 s em valores altos",
                  "value": {
                    "nome": "Valores altos demoram",
                    "gatilho": {
                      "campo": "valor_servico_centavos",
                      "maior_que": 1000000
                    },
                    "resultado": "atrasar",
                    "atraso_ms": 5000
                  }
                },
                "transitorio": {
                  "summary": "Falhar duas vezes e depois autorizar",
                  "value": {
                    "nome": "Instabilidade do município",
                    "gatilho": {
                      "tomador_nome_contem": "instavel"
                    },
                    "resultado": "erro_transitorio",
                    "falhas": 2
                  }
                }
              }
            }
          }
        },
        "responses": {
          "201": {
            "description": "Cenário criado.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Cenario"
                },
                "example": {
                  "id": "8c2e6a4d-3f71-4b59-9d08-7a5c1e3b9f46",
                  "nome": "Recusar descrições de teste",
                  "gatilho": {
                    "descricao_contem": "[recusar]"
                  },
                  "resultado": "rejeitar",
                  "codigo_erro": "E160",
                  "mensagem": "Código de tributação incompatível com a atividade do prestador.",
                  "atraso_ms": 0,
                  "falhas": 1,
                  "prioridade": 100,
                  "ativo": true,
                  "criado_em": "2026-11-13T14:02:11.482Z",
                  "atualizado_em": "2026-11-13T14:02:11.482Z"
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "409": {
            "$ref": "#/components/responses/Conflito"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "notas:emitir"
            ]
          }
        ],
        "x-escopo": "notas:emitir",
        "x-codigos": [
          {
            "status": 409,
            "code": "limite_cenarios",
            "quando": "Já são 50 cenários."
          }
        ]
      }
    },
    "/v1/sandbox/cenarios/simular": {
      "post": {
        "operationId": "simularCenario",
        "tags": [
          "Sandbox"
        ],
        "summary": "Simular um cenário",
        "description": "Mostra o que o simulador faria com estes dados, sem emitir nada.\n\n**Escopo necessário:** `notas:ler`.",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "valor_servico_centavos": {
                    "type": "integer",
                    "minimum": 0
                  },
                  "descricao": {
                    "anyOf": [
                      {
                        "type": "string",
                        "maxLength": 2000
                      },
                      {
                        "type": "null"
                      }
                    ],
                    "description": "Descrição do serviço que aparece na nota."
                  },
                  "tomador_nome": {
                    "anyOf": [
                      {
                        "type": "string",
                        "maxLength": 200
                      },
                      {
                        "type": "null"
                      }
                    ]
                  },
                  "tomador_documento": {
                    "anyOf": [
                      {
                        "type": "string",
                        "maxLength": 30
                      },
                      {
                        "type": "null"
                      }
                    ]
                  },
                  "prestador_cnpj": {
                    "anyOf": [
                      {
                        "type": "string",
                        "maxLength": 20
                      },
                      {
                        "type": "null"
                      }
                    ]
                  },
                  "inscricao_municipal": {
                    "anyOf": [
                      {
                        "type": "string",
                        "maxLength": 40
                      },
                      {
                        "type": "null"
                      }
                    ],
                    "description": "Inscrição municipal."
                  },
                  "ibge": {
                    "anyOf": [
                      {
                        "type": "string",
                        "maxLength": 10
                      },
                      {
                        "type": "null"
                      }
                    ]
                  },
                  "codigo_tributacao": {
                    "anyOf": [
                      {
                        "type": "string",
                        "maxLength": 20
                      },
                      {
                        "type": "null"
                      }
                    ]
                  },
                  "referencia_externa": {
                    "anyOf": [
                      {
                        "type": "string",
                        "maxLength": 100
                      },
                      {
                        "type": "null"
                      }
                    ],
                    "description": "O identificador da venda no **seu** sistema. É único por conta e ambiente (exceto notas rejeitadas): reenviar a mesma referência dá `409 referencia_externa_duplicada`."
                  },
                  "tentativa": {
                    "type": "integer",
                    "minimum": 1,
                    "maximum": 100
                  }
                },
                "additionalProperties": false
              },
              "examples": {
                "descricao": {
                  "summary": "Testar uma descrição",
                  "value": {
                    "descricao": "Consultoria [recusar]",
                    "valor_servico_centavos": 50000
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "A ação que seria aplicada.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ResultadoCenario"
                },
                "example": {
                  "acao": "rejeitar",
                  "codigo": "E160",
                  "mensagem": "Código de tributação incompatível com a atividade do prestador.",
                  "cenarioId": "8c2e6a4d-3f71-4b59-9d08-7a5c1e3b9f46",
                  "cenarioNome": "Recusar descrições de teste"
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "notas:ler"
            ]
          }
        ],
        "x-escopo": "notas:ler"
      }
    },
    "/v1/sandbox/cenarios/{id}": {
      "get": {
        "operationId": "obterCenario",
        "tags": [
          "Sandbox"
        ],
        "summary": "Consultar um cenário",
        "description": "Devolve o cenário.\n\n**Escopo necessário:** `notas:ler`.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "description": "Identificador do recurso.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "O cenário.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Cenario"
                },
                "example": {
                  "id": "8c2e6a4d-3f71-4b59-9d08-7a5c1e3b9f46",
                  "nome": "Recusar descrições de teste",
                  "gatilho": {
                    "descricao_contem": "[recusar]"
                  },
                  "resultado": "rejeitar",
                  "codigo_erro": "E160",
                  "mensagem": "Código de tributação incompatível com a atividade do prestador.",
                  "atraso_ms": 0,
                  "falhas": 1,
                  "prioridade": 100,
                  "ativo": true,
                  "criado_em": "2026-11-13T14:02:11.482Z",
                  "atualizado_em": "2026-11-13T14:02:11.482Z"
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "notas:ler"
            ]
          }
        ],
        "x-escopo": "notas:ler"
      },
      "patch": {
        "operationId": "atualizarCenario",
        "tags": [
          "Sandbox"
        ],
        "summary": "Alterar um cenário",
        "description": "Altera os campos enviados (ao menos um).\n\n**Escopo necessário:** `notas:emitir`.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "description": "Identificador do recurso.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "nome": {
                    "type": "string",
                    "minLength": 2,
                    "maxLength": 120,
                    "description": "Nome do cenário."
                  },
                  "gatilho": {
                    "type": "object",
                    "additionalProperties": {},
                    "description": "Condições (unidas por E) que a nota precisa cumprir. Aceita `{ \"campo\": \"...\", \"<operador>\": valor }`, `{ \"todos\": [ ... ] }` ou o atalho `{ \"<campo>_<operador>\": valor }`."
                  },
                  "resultado": {
                    "type": "string",
                    "enum": [
                      "autorizar",
                      "rejeitar",
                      "atrasar",
                      "erro_transitorio"
                    ],
                    "description": "O que o simulador faz quando o gatilho casa."
                  },
                  "codigo_erro": {
                    "anyOf": [
                      {
                        "type": "string",
                        "minLength": 1,
                        "maxLength": 80
                      },
                      {
                        "type": "null"
                      }
                    ],
                    "description": "Código devolvido na rejeição ou no erro simulado."
                  },
                  "mensagem": {
                    "anyOf": [
                      {
                        "type": "string",
                        "minLength": 1,
                        "maxLength": 500
                      },
                      {
                        "type": "null"
                      }
                    ],
                    "description": "Mensagem devolvida na rejeição ou no erro simulado."
                  },
                  "atraso_ms": {
                    "type": "integer",
                    "minimum": 0,
                    "maximum": 60000,
                    "description": "Atraso (0 a 60000 ms) antes de agir."
                  },
                  "falhas": {
                    "type": "integer",
                    "minimum": 1,
                    "maximum": 20,
                    "description": "Em `erro_transitorio`: quantas tentativas falham antes de passar a funcionar."
                  },
                  "prioridade": {
                    "type": "integer",
                    "minimum": 1,
                    "maximum": 1000,
                    "description": "Menor número vence quando mais de um cenário casa. Padrão 100."
                  },
                  "ativo": {
                    "type": "boolean",
                    "description": "Desligue para pausar o cenário sem apagá-lo."
                  }
                },
                "additionalProperties": false
              },
              "examples": {
                "desligar": {
                  "summary": "Pausar o cenário",
                  "value": {
                    "ativo": false
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "O cenário.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Cenario"
                },
                "example": {
                  "id": "8c2e6a4d-3f71-4b59-9d08-7a5c1e3b9f46",
                  "nome": "Recusar descrições de teste",
                  "gatilho": {
                    "descricao_contem": "[recusar]"
                  },
                  "resultado": "rejeitar",
                  "codigo_erro": "E160",
                  "mensagem": "Código de tributação incompatível com a atividade do prestador.",
                  "atraso_ms": 0,
                  "falhas": 1,
                  "prioridade": 100,
                  "ativo": true,
                  "criado_em": "2026-11-13T14:02:11.482Z",
                  "atualizado_em": "2026-11-13T14:02:11.482Z"
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "notas:emitir"
            ]
          }
        ],
        "x-escopo": "notas:emitir"
      },
      "delete": {
        "operationId": "removerCenario",
        "tags": [
          "Sandbox"
        ],
        "summary": "Remover um cenário",
        "description": "Remove o cenário.\n\n**Escopo necessário:** `notas:emitir`.",
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "description": "Identificador do recurso.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "204": {
            "description": "Sem conteúdo.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "notas:emitir"
            ]
          }
        ],
        "x-escopo": "notas:emitir"
      }
    },
    "/v1/openapi.json": {
      "get": {
        "operationId": "obterOpenApi",
        "tags": [
          "Documentação"
        ],
        "summary": "Obter o documento OpenAPI",
        "description": "O contrato desta API em OpenAPI 3.1, gerado do código. Público: não exige chave. Serve para importar no Postman/Insomnia ou gerar um cliente.",
        "responses": {
          "200": {
            "description": "O documento OpenAPI.",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "additionalProperties": true
                }
              }
            }
          }
        },
        "security": []
      }
    },
    "/v1/uso": {
      "get": {
        "operationId": "consultarUso",
        "tags": [
          "Uso"
        ],
        "summary": "Consultar o uso do plano",
        "description": "Notas emitidas no período (padrão: o ciclo atual do plano), franquia, excedente estimado, prestadores ativos e os limites da conta. Todos os valores monetários são inteiros em centavos (campos com sufixo `_centavos`). `limites` traz também os tetos do plano para webhooks, chaves de API e usuários; chaves e usuários são criados só no painel, por isso os erros `limite_plano_chaves` e `limite_plano_usuarios` não aparecem na API.\n\n**Escopo necessário:** `uso:ler`.",
        "parameters": [
          {
            "name": "inicio",
            "in": "query",
            "required": false,
            "description": "Primeiro dia do período (AAAA-MM-DD).",
            "schema": {
              "type": "string",
              "pattern": "^\\d{4}-\\d{2}-\\d{2}$"
            }
          },
          {
            "name": "fim",
            "in": "query",
            "required": false,
            "description": "Último dia do período (AAAA-MM-DD).",
            "schema": {
              "type": "string",
              "pattern": "^\\d{4}-\\d{2}-\\d{2}$"
            }
          },
          {
            "name": "prestador_id",
            "in": "query",
            "required": false,
            "description": "Só o consumo deste prestador. Omitido: de todos os prestadores da conta.",
            "schema": {
              "type": "string",
              "format": "uuid"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Uso do período.",
            "headers": {
              "X-Request-Id": {
                "$ref": "#/components/headers/XRequestId"
              },
              "X-RateLimit-Limit": {
                "$ref": "#/components/headers/XRateLimitLimit"
              },
              "X-RateLimit-Remaining": {
                "$ref": "#/components/headers/XRateLimitRemaining"
              },
              "X-RateLimit-Reset": {
                "$ref": "#/components/headers/XRateLimitReset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Uso"
                },
                "example": {
                  "periodo": {
                    "inicio": "2026-11-01",
                    "fim": "2026-11-30"
                  },
                  "plano": {
                    "codigo": "crescimento",
                    "nome": "Crescimento",
                    "tipo_cobranca": "assinatura"
                  },
                  "notas": {
                    "autorizadas": 128,
                    "incluidas_no_plano": 200,
                    "excedente": 0,
                    "rejeitadas": 3,
                    "canceladas": 1,
                    "valor_estimado_excedente_centavos": 0
                  },
                  "prestadores": {
                    "ativos": 2,
                    "limite": 5
                  },
                  "limites": {
                    "requisicoes_por_minuto": 600,
                    "tamanho_maximo_corpo_kb": 1024,
                    "tamanho_maximo_certificado_kb": 50,
                    "webhooks_max": 5,
                    "chaves_api_max": 10,
                    "usuarios_max": 3
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/NaoAutenticado"
          },
          "403": {
            "$ref": "#/components/responses/Proibido"
          },
          "404": {
            "$ref": "#/components/responses/NaoEncontrado"
          },
          "422": {
            "$ref": "#/components/responses/Validacao"
          },
          "429": {
            "$ref": "#/components/responses/LimiteExcedido"
          }
        },
        "security": [
          {
            "bearerAuth": [
              "uso:ler"
            ]
          }
        ],
        "x-escopo": "uso:ler"
      }
    }
  },
  "webhooks": {
    "nota.processando": {
      "post": {
        "operationId": "evento_nota_processando",
        "tags": [
          "Webhooks"
        ],
        "summary": "nota.processando",
        "description": "A nota entrou na fila de emissão (e a cada reprocessamento).\n\nA API envia um `POST` com este corpo ao endpoint cadastrado. Cabeçalhos: `NFsPlus-Signature` (`t=<unix>,v1=<hex>`), `NFsPlus-Event-Id` e `User-Agent: NFsPlus-Webhooks/1`.\nResponda `2xx` em até 10 segundos. Qualquer outra resposta, ou o tempo esgotado, agenda nova tentativa (até ~25 h). Veja o guia \"Verificar assinaturas\".",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/Evento"
              },
              "example": {
                "id": "f4c8a2d6-7b13-4e95-8c60-3a9d1e7b5f82",
                "tipo": "nota.processando",
                "criado_em": "2026-11-13T14:02:13.905Z",
                "ambiente": "sandbox",
                "api_versao": "v1",
                "dados": {
                  "nota": {
                    "id": "7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25",
                    "fase": "enfileirada",
                    "ambiente": "sandbox",
                    "sem_validade_juridica": true,
                    "prestador_id": "0c1f7e3a-5d2b-4c8e-9a41-7b6d2e9f1a30",
                    "referencia_externa": "pedido-48213",
                    "competencia": "2026-11-13",
                    "tomador": {
                      "id": "3b8d0f52-91c4-4a7e-8f26-5e1c7a9d4b02",
                      "tipo_documento": "cpf",
                      "documento_mascarado": "***.982.247-**",
                      "nome": "Maria Souza"
                    },
                    "servico": {
                      "codigo_tributacao_nacional": "010701",
                      "codigo_tributacao_municipal": null,
                      "codigo_nbs": null,
                      "descricao": "Desenvolvimento de software sob encomenda",
                      "local_prestacao_ibge": "3550308"
                    },
                    "valores": {
                      "valor_servicos_centavos": 150000,
                      "desconto_incondicionado_centavos": 0,
                      "aliquota_iss": 2,
                      "valor_iss_centavos": 3000,
                      "iss_retido": false
                    },
                    "informacoes_complementares": null,
                    "metadados": {
                      "pedido": "48213"
                    },
                    "dps": {
                      "serie": "1",
                      "numero": 37,
                      "id": "DPS355030821122233300018100001000000000000037"
                    },
                    "cancelamento": null,
                    "substituicao": null,
                    "prazos": null,
                    "erros": null,
                    "origem": "api",
                    "criado_em": "2026-11-13T14:02:11.482Z",
                    "atualizado_em": "2026-11-13T14:02:11.482Z",
                    "status": "processando",
                    "nfse": null,
                    "emitida_em": null,
                    "cancelada_em": null,
                    "acoes": {
                      "cancelar": false,
                      "substituir": false,
                      "reprocessar": false,
                      "baixar_xml": false,
                      "baixar_pdf": false
                    },
                    "links": {
                      "self": "/v1/notas/7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25"
                    }
                  }
                }
              }
            }
          }
        },
        "responses": {
          "2XX": {
            "description": "Recebido. O conteúdo da resposta é ignorado (só os primeiros 500 caracteres ficam no histórico)."
          }
        }
      }
    },
    "nota.autorizada": {
      "post": {
        "operationId": "evento_nota_autorizada",
        "tags": [
          "Webhooks"
        ],
        "summary": "nota.autorizada",
        "description": "O município autorizou a nota: já existe número, chave de acesso, XML e PDF.\n\nA API envia um `POST` com este corpo ao endpoint cadastrado. Cabeçalhos: `NFsPlus-Signature` (`t=<unix>,v1=<hex>`), `NFsPlus-Event-Id` e `User-Agent: NFsPlus-Webhooks/1`.\nResponda `2xx` em até 10 segundos. Qualquer outra resposta, ou o tempo esgotado, agenda nova tentativa (até ~25 h). Veja o guia \"Verificar assinaturas\".",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/Evento"
              },
              "example": {
                "id": "f4c8a2d6-7b13-4e95-8c60-3a9d1e7b5f82",
                "tipo": "nota.autorizada",
                "criado_em": "2026-11-13T14:02:13.905Z",
                "ambiente": "sandbox",
                "api_versao": "v1",
                "dados": {
                  "nota": {
                    "id": "7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25",
                    "fase": null,
                    "ambiente": "sandbox",
                    "sem_validade_juridica": true,
                    "prestador_id": "0c1f7e3a-5d2b-4c8e-9a41-7b6d2e9f1a30",
                    "referencia_externa": "pedido-48213",
                    "competencia": "2026-11-13",
                    "tomador": {
                      "id": "3b8d0f52-91c4-4a7e-8f26-5e1c7a9d4b02",
                      "tipo_documento": "cpf",
                      "documento_mascarado": "***.982.247-**",
                      "nome": "Maria Souza"
                    },
                    "servico": {
                      "codigo_tributacao_nacional": "010701",
                      "codigo_tributacao_municipal": null,
                      "codigo_nbs": null,
                      "descricao": "Desenvolvimento de software sob encomenda",
                      "local_prestacao_ibge": "3550308"
                    },
                    "valores": {
                      "valor_servicos_centavos": 150000,
                      "desconto_incondicionado_centavos": 0,
                      "aliquota_iss": 2,
                      "valor_iss_centavos": 3000,
                      "iss_retido": false
                    },
                    "informacoes_complementares": null,
                    "metadados": {
                      "pedido": "48213"
                    },
                    "dps": {
                      "serie": "1",
                      "numero": 37,
                      "id": "DPS355030821122233300018100001000000000000037"
                    },
                    "cancelamento": null,
                    "substituicao": null,
                    "prazos": {
                      "cancelamento": {
                        "prazo_dias": 730,
                        "limite_em": "2028-11-12",
                        "dias_restantes": 730,
                        "dentro_do_prazo": true,
                        "explicacao": "Dá para cancelar até 12/11/2028 (730 dias contados da emissão)."
                      },
                      "substituicao": {
                        "prazo_dias": 730,
                        "limite_em": "2028-11-12",
                        "dias_restantes": 730,
                        "dentro_do_prazo": true,
                        "explicacao": "Dá para substituir até 12/11/2028 (730 dias contados da emissão).",
                        "sem_prazo_para": [
                          "desenquadramento_simples_nacional",
                          "enquadramento_simples_nacional"
                        ]
                      }
                    },
                    "erros": null,
                    "origem": "api",
                    "criado_em": "2026-11-13T14:02:11.482Z",
                    "atualizado_em": "2026-11-13T14:02:13.905Z",
                    "status": "autorizada",
                    "nfse": {
                      "numero": "37",
                      "chave_acesso": "35503082112223330001810000000000003710A4F1C9D2",
                      "codigo_verificacao": "A4F1C9D2",
                      "protocolo": "SIM3C9E1A7B52D4",
                      "conector": "simulador"
                    },
                    "emitida_em": "2026-11-13T14:02:13.905Z",
                    "cancelada_em": null,
                    "acoes": {
                      "cancelar": true,
                      "substituir": true,
                      "reprocessar": false,
                      "baixar_xml": true,
                      "baixar_pdf": true
                    },
                    "links": {
                      "self": "/v1/notas/7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25",
                      "xml": "/v1/notas/7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25/xml",
                      "pdf": "/v1/notas/7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25/pdf"
                    }
                  }
                }
              }
            }
          }
        },
        "responses": {
          "2XX": {
            "description": "Recebido. O conteúdo da resposta é ignorado (só os primeiros 500 caracteres ficam no histórico)."
          }
        }
      }
    },
    "nota.rejeitada": {
      "post": {
        "operationId": "evento_nota_rejeitada",
        "tags": [
          "Webhooks"
        ],
        "summary": "nota.rejeitada",
        "description": "O município recusou a nota. `nota.erros` diz o motivo; corrija os dados e emita de novo.\n\nA API envia um `POST` com este corpo ao endpoint cadastrado. Cabeçalhos: `NFsPlus-Signature` (`t=<unix>,v1=<hex>`), `NFsPlus-Event-Id` e `User-Agent: NFsPlus-Webhooks/1`.\nResponda `2xx` em até 10 segundos. Qualquer outra resposta, ou o tempo esgotado, agenda nova tentativa (até ~25 h). Veja o guia \"Verificar assinaturas\".",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/Evento"
              },
              "example": {
                "id": "f4c8a2d6-7b13-4e95-8c60-3a9d1e7b5f82",
                "tipo": "nota.rejeitada",
                "criado_em": "2026-11-13T14:02:13.905Z",
                "ambiente": "sandbox",
                "api_versao": "v1",
                "dados": {
                  "nota": {
                    "id": "7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25",
                    "fase": null,
                    "ambiente": "sandbox",
                    "sem_validade_juridica": true,
                    "prestador_id": "0c1f7e3a-5d2b-4c8e-9a41-7b6d2e9f1a30",
                    "referencia_externa": "pedido-48213",
                    "competencia": "2026-11-13",
                    "tomador": {
                      "id": "3b8d0f52-91c4-4a7e-8f26-5e1c7a9d4b02",
                      "tipo_documento": "cpf",
                      "documento_mascarado": "***.982.247-**",
                      "nome": "Maria Souza"
                    },
                    "servico": {
                      "codigo_tributacao_nacional": "010701",
                      "codigo_tributacao_municipal": null,
                      "codigo_nbs": null,
                      "descricao": "Desenvolvimento de software sob encomenda",
                      "local_prestacao_ibge": "3550308"
                    },
                    "valores": {
                      "valor_servicos_centavos": 150000,
                      "desconto_incondicionado_centavos": 0,
                      "aliquota_iss": 2,
                      "valor_iss_centavos": 3000,
                      "iss_retido": false
                    },
                    "informacoes_complementares": null,
                    "metadados": {
                      "pedido": "48213"
                    },
                    "dps": {
                      "serie": "1",
                      "numero": 37,
                      "id": "DPS355030821122233300018100001000000000000037"
                    },
                    "cancelamento": null,
                    "substituicao": null,
                    "prazos": null,
                    "erros": [
                      {
                        "codigo": "E160",
                        "mensagem": "Código de tributação incompatível com a atividade do prestador.",
                        "campo": "servico.codigo_tributacao_nacional"
                      }
                    ],
                    "origem": "api",
                    "criado_em": "2026-11-13T14:02:11.482Z",
                    "atualizado_em": "2026-11-13T14:02:13.905Z",
                    "status": "rejeitada",
                    "nfse": null,
                    "emitida_em": null,
                    "cancelada_em": null,
                    "acoes": {
                      "cancelar": false,
                      "substituir": false,
                      "reprocessar": false,
                      "baixar_xml": false,
                      "baixar_pdf": false
                    },
                    "links": {
                      "self": "/v1/notas/7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25"
                    }
                  }
                }
              }
            }
          }
        },
        "responses": {
          "2XX": {
            "description": "Recebido. O conteúdo da resposta é ignorado (só os primeiros 500 caracteres ficam no histórico)."
          }
        }
      }
    },
    "nota.cancelada": {
      "post": {
        "operationId": "evento_nota_cancelada",
        "tags": [
          "Webhooks"
        ],
        "summary": "nota.cancelada",
        "description": "O cancelamento foi aceito pelo município.\n\nA API envia um `POST` com este corpo ao endpoint cadastrado. Cabeçalhos: `NFsPlus-Signature` (`t=<unix>,v1=<hex>`), `NFsPlus-Event-Id` e `User-Agent: NFsPlus-Webhooks/1`.\nResponda `2xx` em até 10 segundos. Qualquer outra resposta, ou o tempo esgotado, agenda nova tentativa (até ~25 h). Veja o guia \"Verificar assinaturas\".",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/Evento"
              },
              "example": {
                "id": "f4c8a2d6-7b13-4e95-8c60-3a9d1e7b5f82",
                "tipo": "nota.cancelada",
                "criado_em": "2026-11-13T14:02:13.905Z",
                "ambiente": "sandbox",
                "api_versao": "v1",
                "dados": {
                  "nota": {
                    "id": "7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25",
                    "fase": null,
                    "ambiente": "sandbox",
                    "sem_validade_juridica": true,
                    "prestador_id": "0c1f7e3a-5d2b-4c8e-9a41-7b6d2e9f1a30",
                    "referencia_externa": "pedido-48213",
                    "competencia": "2026-11-13",
                    "tomador": {
                      "id": "3b8d0f52-91c4-4a7e-8f26-5e1c7a9d4b02",
                      "tipo_documento": "cpf",
                      "documento_mascarado": "***.982.247-**",
                      "nome": "Maria Souza"
                    },
                    "servico": {
                      "codigo_tributacao_nacional": "010701",
                      "codigo_tributacao_municipal": null,
                      "codigo_nbs": null,
                      "descricao": "Desenvolvimento de software sob encomenda",
                      "local_prestacao_ibge": "3550308"
                    },
                    "valores": {
                      "valor_servicos_centavos": 150000,
                      "desconto_incondicionado_centavos": 0,
                      "aliquota_iss": 2,
                      "valor_iss_centavos": 3000,
                      "iss_retido": false
                    },
                    "informacoes_complementares": null,
                    "metadados": {
                      "pedido": "48213"
                    },
                    "dps": {
                      "serie": "1",
                      "numero": 37,
                      "id": "DPS355030821122233300018100001000000000000037"
                    },
                    "cancelamento": null,
                    "substituicao": null,
                    "prazos": null,
                    "erros": null,
                    "origem": "api",
                    "criado_em": "2026-11-13T14:02:11.482Z",
                    "atualizado_em": "2026-11-13T14:02:13.905Z",
                    "status": "cancelada",
                    "nfse": {
                      "numero": "37",
                      "chave_acesso": "35503082112223330001810000000000003710A4F1C9D2",
                      "codigo_verificacao": "A4F1C9D2",
                      "protocolo": "SIM3C9E1A7B52D4",
                      "conector": "simulador"
                    },
                    "emitida_em": "2026-11-13T14:02:13.905Z",
                    "cancelada_em": "2026-11-13T15:30:00.000Z",
                    "acoes": {
                      "cancelar": false,
                      "substituir": false,
                      "reprocessar": false,
                      "baixar_xml": true,
                      "baixar_pdf": true
                    },
                    "links": {
                      "self": "/v1/notas/7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25",
                      "xml": "/v1/notas/7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25/xml",
                      "pdf": "/v1/notas/7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25/pdf"
                    }
                  }
                }
              }
            }
          }
        },
        "responses": {
          "2XX": {
            "description": "Recebido. O conteúdo da resposta é ignorado (só os primeiros 500 caracteres ficam no histórico)."
          }
        }
      }
    },
    "nota.erro": {
      "post": {
        "operationId": "evento_nota_erro",
        "tags": [
          "Webhooks"
        ],
        "summary": "nota.erro",
        "description": "Falha técnica depois de todas as tentativas. A nota pode ser reprocessada (`POST /v1/notas/{id}/reprocessar`).\n\nA API envia um `POST` com este corpo ao endpoint cadastrado. Cabeçalhos: `NFsPlus-Signature` (`t=<unix>,v1=<hex>`), `NFsPlus-Event-Id` e `User-Agent: NFsPlus-Webhooks/1`.\nResponda `2xx` em até 10 segundos. Qualquer outra resposta, ou o tempo esgotado, agenda nova tentativa (até ~25 h). Veja o guia \"Verificar assinaturas\".",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/Evento"
              },
              "example": {
                "id": "f4c8a2d6-7b13-4e95-8c60-3a9d1e7b5f82",
                "tipo": "nota.erro",
                "criado_em": "2026-11-13T14:02:13.905Z",
                "ambiente": "sandbox",
                "api_versao": "v1",
                "dados": {
                  "nota": {
                    "id": "7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25",
                    "fase": null,
                    "ambiente": "sandbox",
                    "sem_validade_juridica": true,
                    "prestador_id": "0c1f7e3a-5d2b-4c8e-9a41-7b6d2e9f1a30",
                    "referencia_externa": "pedido-48213",
                    "competencia": "2026-11-13",
                    "tomador": {
                      "id": "3b8d0f52-91c4-4a7e-8f26-5e1c7a9d4b02",
                      "tipo_documento": "cpf",
                      "documento_mascarado": "***.982.247-**",
                      "nome": "Maria Souza"
                    },
                    "servico": {
                      "codigo_tributacao_nacional": "010701",
                      "codigo_tributacao_municipal": null,
                      "codigo_nbs": null,
                      "descricao": "Desenvolvimento de software sob encomenda",
                      "local_prestacao_ibge": "3550308"
                    },
                    "valores": {
                      "valor_servicos_centavos": 150000,
                      "desconto_incondicionado_centavos": 0,
                      "aliquota_iss": 2,
                      "valor_iss_centavos": 3000,
                      "iss_retido": false
                    },
                    "informacoes_complementares": null,
                    "metadados": {
                      "pedido": "48213"
                    },
                    "dps": {
                      "serie": "1",
                      "numero": 37,
                      "id": "DPS355030821122233300018100001000000000000037"
                    },
                    "cancelamento": null,
                    "substituicao": null,
                    "prazos": null,
                    "erros": [
                      {
                        "codigo": "TIMEOUT",
                        "mensagem": "O município não respondeu dentro do prazo, depois de todas as tentativas."
                      }
                    ],
                    "origem": "api",
                    "criado_em": "2026-11-13T14:02:11.482Z",
                    "atualizado_em": "2026-11-13T14:02:11.482Z",
                    "status": "erro",
                    "nfse": null,
                    "emitida_em": null,
                    "cancelada_em": null,
                    "acoes": {
                      "cancelar": false,
                      "substituir": false,
                      "reprocessar": true,
                      "baixar_xml": false,
                      "baixar_pdf": false
                    },
                    "links": {
                      "self": "/v1/notas/7e4a9c10-2f6b-4d83-b5a1-9c3e8d7f6a25"
                    }
                  }
                }
              }
            }
          }
        },
        "responses": {
          "2XX": {
            "description": "Recebido. O conteúdo da resposta é ignorado (só os primeiros 500 caracteres ficam no histórico)."
          }
        }
      }
    },
    "certificado.expirando": {
      "post": {
        "operationId": "evento_certificado_expirando",
        "tags": [
          "Webhooks"
        ],
        "summary": "certificado.expirando",
        "description": "Um certificado A1 vence em até 30 dias (ou já venceu). Enviado nos limiares de 30, 15, 7, 3 e 1 dia, e ao expirar. Sempre `ambiente: \"producao\"`.\n\nA API envia um `POST` com este corpo ao endpoint cadastrado. Cabeçalhos: `NFsPlus-Signature` (`t=<unix>,v1=<hex>`), `NFsPlus-Event-Id` e `User-Agent: NFsPlus-Webhooks/1`.\nResponda `2xx` em até 10 segundos. Qualquer outra resposta, ou o tempo esgotado, agenda nova tentativa (até ~25 h). Veja o guia \"Verificar assinaturas\".",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/Evento"
              },
              "example": {
                "id": "f4c8a2d6-7b13-4e95-8c60-3a9d1e7b5f82",
                "tipo": "certificado.expirando",
                "criado_em": "2026-11-13T14:02:13.905Z",
                "ambiente": "producao",
                "api_versao": "v1",
                "dados": {
                  "certificado": {
                    "id": "a2d96b4e-1c07-4f35-8e59-0b7c3a1d8f64",
                    "apelido": "A1 da Acme (2027)",
                    "cnpj": "11222333000181",
                    "validade_fim": "2026-11-28T23:59:59.000Z",
                    "dias_restantes": 15,
                    "expirado": false
                  }
                }
              }
            }
          }
        },
        "responses": {
          "2XX": {
            "description": "Recebido. O conteúdo da resposta é ignorado (só os primeiros 500 caracteres ficam no histórico)."
          }
        }
      }
    },
    "exportacao.pronta": {
      "post": {
        "operationId": "evento_exportacao_pronta",
        "tags": [
          "Webhooks"
        ],
        "summary": "exportacao.pronta",
        "description": "Uma exportação terminou. `dados` é o próprio objeto da exportação, já com `url_download`.\n\nA API envia um `POST` com este corpo ao endpoint cadastrado. Cabeçalhos: `NFsPlus-Signature` (`t=<unix>,v1=<hex>`), `NFsPlus-Event-Id` e `User-Agent: NFsPlus-Webhooks/1`.\nResponda `2xx` em até 10 segundos. Qualquer outra resposta, ou o tempo esgotado, agenda nova tentativa (até ~25 h). Veja o guia \"Verificar assinaturas\".",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/Evento"
              },
              "example": {
                "id": "f4c8a2d6-7b13-4e95-8c60-3a9d1e7b5f82",
                "tipo": "exportacao.pronta",
                "criado_em": "2026-11-13T14:02:13.905Z",
                "ambiente": "sandbox",
                "api_versao": "v1",
                "dados": {
                  "id": "5a7d3e9b-8c14-4f20-b6a5-1e9c4d2f7b83",
                  "status": "pronta",
                  "formato": "zip",
                  "ambiente": "sandbox",
                  "prestador_id": "0c1f7e3a-5d2b-4c8e-9a41-7b6d2e9f1a30",
                  "periodo_inicio": "2026-11-01",
                  "periodo_fim": "2026-11-30",
                  "conteudo": [
                    "xml",
                    "pdf"
                  ],
                  "total_documentos": 42,
                  "tamanho_bytes": 1894213,
                  "sha256": "3d7f1a9c5e2b8406d1a7c3e95b2f8d4061a9c7e3b5d2f84106a9c1e7b3d5f280",
                  "nome_arquivo": "nfse-documentos_2026-11-01_2026-11-30_5a7d3e9b.zip",
                  "url_download": "https://api.nfsplus.com.br/v1/exportacoes/5a7d3e9b-8c14-4f20-b6a5-1e9c4d2f7b83/download?exp=1794582000&sig=Zk3mQ9vT1b7LxR4aYp2nWc8sHdE6uJfA0gVtKiOo5Xs",
                  "expira_em": "2026-11-20T14:05:00.000Z",
                  "erro": null,
                  "criado_em": "2026-11-13T14:02:11.482Z",
                  "concluido_em": "2026-11-13T14:02:13.905Z"
                }
              }
            }
          }
        },
        "responses": {
          "2XX": {
            "description": "Recebido. O conteúdo da resposta é ignorado (só os primeiros 500 caracteres ficam no histórico)."
          }
        }
      }
    }
  },
  "components": {
    "securitySchemes": {
      "bearerAuth": {
        "type": "http",
        "scheme": "bearer",
        "bearerFormat": "nfsp_(test|live)_<id>_<segredo>",
        "description": "Chave de API criada no painel (Desenvolvedores → Chaves de API). Cada chave tem escopos e um ambiente (`test` ou `live`)."
      }
    },
    "headers": {
      "XRequestId": {
        "description": "Identificador da requisição. Envie-o ao suporte ao relatar um problema. Se você mandar `X-Request-Id`, ele é reaproveitado.",
        "schema": {
          "type": "string"
        }
      },
      "XRateLimitLimit": {
        "description": "Requisições permitidas por minuto para esta chave.",
        "schema": {
          "type": "integer"
        }
      },
      "XRateLimitRemaining": {
        "description": "Requisições restantes na janela atual.",
        "schema": {
          "type": "integer"
        }
      },
      "XRateLimitReset": {
        "description": "Segundos até a janela reiniciar.",
        "schema": {
          "type": "integer"
        }
      }
    },
    "schemas": {
      "RelatorioEmissao": {
        "type": "object",
        "properties": {
          "periodo": {
            "type": "object",
            "properties": {
              "de": {
                "type": "string",
                "format": "date"
              },
              "ate": {
                "type": "string",
                "format": "date"
              },
              "dias": {
                "type": "integer"
              },
              "fuso": {
                "type": "string"
              }
            },
            "required": [
              "de",
              "ate",
              "dias",
              "fuso"
            ],
            "additionalProperties": true
          },
          "ambiente": {
            "type": "string",
            "enum": [
              "sandbox",
              "producao"
            ],
            "description": "Ambiente dos dados: o da chave de API que fez a chamada."
          },
          "agrupar": {
            "type": "string",
            "enum": [
              "dia",
              "semana",
              "mes"
            ],
            "description": "Granularidade da série."
          },
          "filtros": {
            "type": "object",
            "additionalProperties": true,
            "description": "Eco dos filtros aplicados (inclusive os padrões), para reproduzir o relatório."
          },
          "valores_ocultos": {
            "type": "boolean",
            "description": "`true` quando a chave não tem `relatorios:financeiro`: os campos de valor vêm `null`."
          },
          "resumo": {
            "type": "object",
            "properties": {
              "notas": {
                "type": "object",
                "properties": {
                  "total": {
                    "type": "integer"
                  },
                  "autorizadas": {
                    "type": "integer"
                  },
                  "canceladas": {
                    "type": "integer"
                  },
                  "rejeitadas": {
                    "type": "integer"
                  },
                  "erro": {
                    "type": "integer"
                  },
                  "processando": {
                    "type": "integer"
                  },
                  "rascunho": {
                    "type": "integer"
                  }
                },
                "required": [
                  "total",
                  "autorizadas",
                  "canceladas",
                  "rejeitadas",
                  "erro",
                  "processando",
                  "rascunho"
                ]
              },
              "taxa_sucesso_pct": {
                "type": [
                  "number",
                  "null"
                ],
                "description": "(autorizadas + canceladas) / (autorizadas + canceladas + rejeitadas + com erro), em %. `null` sem notas concluídas."
              },
              "tempo_medio_autorizacao_s": {
                "type": [
                  "number",
                  "null"
                ],
                "description": "Segundos entre criar e autorizar a nota (média)."
              },
              "tempo_p95_autorizacao_s": {
                "type": [
                  "number",
                  "null"
                ],
                "description": "Segundos entre criar e autorizar a nota (percentil 95)."
              },
              "valor_emitido_centavos": {
                "type": [
                  "integer",
                  "null"
                ],
                "description": "Soma das notas autorizadas. Em centavos inteiros. `null` quando a chave só tem `relatorios:ler` (valores ocultos)."
              },
              "valor_cancelado_centavos": {
                "type": [
                  "integer",
                  "null"
                ],
                "description": "Soma das notas canceladas. Em centavos inteiros. `null` quando a chave só tem `relatorios:ler` (valores ocultos)."
              },
              "desconto_centavos": {
                "type": [
                  "integer",
                  "null"
                ],
                "description": "Descontos das notas autorizadas. Em centavos inteiros. `null` quando a chave só tem `relatorios:ler` (valores ocultos)."
              },
              "iss_total_centavos": {
                "type": [
                  "integer",
                  "null"
                ],
                "description": "ISS das notas autorizadas. Em centavos inteiros. `null` quando a chave só tem `relatorios:ler` (valores ocultos)."
              },
              "iss_retido_centavos": {
                "type": [
                  "integer",
                  "null"
                ],
                "description": "Parte do ISS retida pelo tomador. Em centavos inteiros. `null` quando a chave só tem `relatorios:ler` (valores ocultos)."
              },
              "iss_a_recolher_centavos": {
                "type": [
                  "integer",
                  "null"
                ],
                "description": "ISS total menos o retido. Em centavos inteiros. `null` quando a chave só tem `relatorios:ler` (valores ocultos)."
              },
              "ticket_medio_centavos": {
                "type": [
                  "integer",
                  "null"
                ],
                "description": "Valor emitido dividido pelas autorizadas. Em centavos inteiros. `null` quando a chave só tem `relatorios:ler` (valores ocultos)."
              }
            },
            "required": [
              "notas",
              "taxa_sucesso_pct",
              "tempo_medio_autorizacao_s",
              "tempo_p95_autorizacao_s",
              "valor_emitido_centavos",
              "valor_cancelado_centavos",
              "desconto_centavos",
              "iss_total_centavos",
              "iss_retido_centavos",
              "iss_a_recolher_centavos",
              "ticket_medio_centavos"
            ]
          },
          "comparacao": {
            "type": [
              "object",
              "null"
            ],
            "additionalProperties": true,
            "description": "Só com `comparar=true`: o período anterior de mesma duração e as variações (%, ou pontos para a taxa de sucesso)."
          },
          "serie": {
            "type": "array",
            "items": {
              "type": "object",
              "properties": {
                "inicio": {
                  "type": "string",
                  "format": "date",
                  "description": "Primeiro dia do período do ponto (AAAA-MM-DD)."
                },
                "total": {
                  "type": "integer"
                },
                "autorizadas": {
                  "type": "integer"
                },
                "canceladas": {
                  "type": "integer"
                },
                "rejeitadas": {
                  "type": "integer"
                },
                "erro": {
                  "type": "integer"
                },
                "processando": {
                  "type": "integer"
                },
                "valor_centavos": {
                  "type": [
                    "integer",
                    "null"
                  ],
                  "description": "Valor das notas autorizadas. Em centavos inteiros. `null` quando a chave só tem `relatorios:ler` (valores ocultos)."
                },
                "iss_centavos": {
                  "type": [
                    "integer",
                    "null"
                  ],
                  "description": "ISS das notas autorizadas. Em centavos inteiros. `null` quando a chave só tem `relatorios:ler` (valores ocultos)."
                }
              },
              "required": [
                "inicio",
                "total",
                "autorizadas",
                "canceladas",
                "rejeitadas",
                "erro",
                "processando",
                "valor_centavos",
                "iss_centavos"
              ]
            }
          },
          "por_empresa": {
            "type": "array",
            "items": {
              "type": "object",
              "properties": {
                "prestador_id": {
                  "type": "string",
                  "format": "uuid"
                },
                "razao_social": {
                  "type": "string"
                },
                "cnpj": {
                  "type": "string"
                },
                "total": {
                  "type": "integer"
                },
                "autorizadas": {
                  "type": "integer"
                },
                "canceladas": {
                  "type": "integer"
                },
                "rejeitadas": {
                  "type": "integer"
                },
                "erro": {
                  "type": "integer"
                },
                "taxa_sucesso_pct": {
                  "type": [
                    "number",
                    "null"
                  ]
                },
                "valor_emitido_centavos": {
                  "type": [
                    "integer",
                    "null"
                  ]
                },
                "iss_total_centavos": {
                  "type": [
                    "integer",
                    "null"
                  ]
                }
              },
              "required": [
                "prestador_id",
                "razao_social",
                "cnpj",
                "total",
                "autorizadas",
                "canceladas",
                "rejeitadas",
                "erro",
                "taxa_sucesso_pct",
                "valor_emitido_centavos",
                "iss_total_centavos"
              ]
            }
          }
        },
        "required": [
          "periodo",
          "ambiente",
          "agrupar",
          "filtros",
          "valores_ocultos",
          "resumo",
          "comparacao",
          "serie",
          "por_empresa"
        ]
      },
      "RelatorioFaturamento": {
        "type": "object",
        "properties": {
          "periodo": {
            "type": "object",
            "properties": {
              "de": {
                "type": "string",
                "format": "date"
              },
              "ate": {
                "type": "string",
                "format": "date"
              },
              "dias": {
                "type": "integer"
              },
              "fuso": {
                "type": "string"
              }
            },
            "required": [
              "de",
              "ate",
              "dias",
              "fuso"
            ],
            "additionalProperties": true
          },
          "ambiente": {
            "type": "string",
            "enum": [
              "sandbox",
              "producao"
            ],
            "description": "Ambiente dos dados: o da chave de API que fez a chamada."
          },
          "dimensao": {
            "type": "string",
            "enum": [
              "tomador",
              "servico",
              "municipio",
              "empresa",
              "periodo"
            ],
            "description": "O que foi agrupado."
          },
          "filtros": {
            "type": "object",
            "additionalProperties": true,
            "description": "Eco dos filtros aplicados (inclusive os padrões), para reproduzir o relatório."
          },
          "total": {
            "type": "object",
            "properties": {
              "notas": {
                "type": "integer"
              },
              "valor_centavos": {
                "type": "integer"
              },
              "iss_centavos": {
                "type": "integer"
              },
              "ticket_medio_centavos": {
                "type": "integer"
              }
            },
            "required": [
              "notas",
              "valor_centavos",
              "iss_centavos",
              "ticket_medio_centavos"
            ]
          },
          "agrupar": {
            "type": [
              "string",
              "null"
            ],
            "description": "Só na dimensão `periodo`: a granularidade."
          },
          "itens": {
            "type": "array",
            "items": {
              "type": "object",
              "properties": {
                "chave": {
                  "type": "string",
                  "description": "Identificador estável do item (documento mascarado, código, IBGE, id ou data)."
                },
                "rotulo": {
                  "type": "string"
                },
                "detalhe": {
                  "type": [
                    "string",
                    "null"
                  ]
                },
                "notas": {
                  "type": "integer"
                },
                "valor_centavos": {
                  "type": "integer"
                },
                "iss_centavos": {
                  "type": "integer"
                },
                "ticket_medio_centavos": {
                  "type": "integer"
                },
                "participacao_pct": {
                  "type": [
                    "number",
                    "null"
                  ]
                },
                "variacao_pct": {
                  "type": [
                    "number",
                    "null"
                  ],
                  "description": "Com `comparar=true`: variação do valor contra o período anterior, em %."
                }
              },
              "required": [
                "chave",
                "rotulo",
                "detalhe",
                "notas",
                "valor_centavos",
                "iss_centavos",
                "ticket_medio_centavos",
                "participacao_pct",
                "variacao_pct"
              ]
            }
          },
          "outros": {
            "type": [
              "object",
              "null"
            ],
            "properties": {
              "notas": {
                "type": "integer"
              },
              "valor_centavos": {
                "type": "integer"
              },
              "iss_centavos": {
                "type": "integer"
              },
              "participacao_pct": {
                "type": [
                  "number",
                  "null"
                ]
              }
            },
            "required": [
              "notas",
              "valor_centavos",
              "iss_centavos",
              "participacao_pct"
            ],
            "description": "Soma do que ficou fora do top `limite`; `null` quando tudo coube."
          }
        },
        "required": [
          "periodo",
          "ambiente",
          "dimensao",
          "filtros",
          "total",
          "agrupar",
          "itens",
          "outros"
        ]
      },
      "RelatorioImpostos": {
        "type": "object",
        "properties": {
          "periodo": {
            "type": "object",
            "properties": {
              "de": {
                "type": "string",
                "format": "date"
              },
              "ate": {
                "type": "string",
                "format": "date"
              },
              "base": {
                "type": "string",
                "enum": [
                  "competencia"
                ]
              }
            },
            "required": [
              "de",
              "ate",
              "base"
            ],
            "additionalProperties": true
          },
          "ambiente": {
            "type": "string",
            "enum": [
              "sandbox",
              "producao"
            ],
            "description": "Ambiente dos dados: o da chave de API que fez a chamada."
          },
          "filtros": {
            "type": "object",
            "additionalProperties": true,
            "description": "Eco dos filtros aplicados (inclusive os padrões), para reproduzir o relatório."
          },
          "total": {
            "type": "object",
            "properties": {
              "notas": {
                "type": "integer"
              },
              "valor_servicos_centavos": {
                "type": "integer"
              },
              "desconto_centavos": {
                "type": "integer"
              },
              "base_calculo_centavos": {
                "type": "integer"
              },
              "iss_total_centavos": {
                "type": "integer"
              },
              "iss_retido_centavos": {
                "type": "integer"
              },
              "iss_a_recolher_centavos": {
                "type": "integer"
              },
              "aliquota_efetiva_pct": {
                "type": [
                  "number",
                  "null"
                ],
                "description": "ISS sobre a base de cálculo, em %."
              },
              "notas_sem_valor_de_iss": {
                "type": "integer",
                "description": "Notas autorizadas sem valor de ISS registrado (não entram na soma)."
              }
            },
            "required": [
              "notas",
              "valor_servicos_centavos",
              "desconto_centavos",
              "base_calculo_centavos",
              "iss_total_centavos",
              "iss_retido_centavos",
              "iss_a_recolher_centavos",
              "aliquota_efetiva_pct",
              "notas_sem_valor_de_iss"
            ]
          },
          "por_competencia": {
            "type": "array",
            "items": {
              "type": "object",
              "properties": {
                "competencia": {
                  "type": "string",
                  "pattern": "^[0-9]{4}-[0-9]{2}$",
                  "description": "Mês de competência, no formato AAAA-MM."
                },
                "notas": {
                  "type": "integer"
                },
                "valor_servicos_centavos": {
                  "type": "integer"
                },
                "desconto_centavos": {
                  "type": "integer"
                },
                "base_calculo_centavos": {
                  "type": "integer"
                },
                "iss_total_centavos": {
                  "type": "integer"
                },
                "iss_retido_centavos": {
                  "type": "integer"
                },
                "iss_a_recolher_centavos": {
                  "type": "integer"
                },
                "aliquota_efetiva_pct": {
                  "type": [
                    "number",
                    "null"
                  ],
                  "description": "ISS sobre a base de cálculo, em %."
                },
                "notas_sem_valor_de_iss": {
                  "type": "integer",
                  "description": "Notas autorizadas sem valor de ISS registrado (não entram na soma)."
                }
              },
              "required": [
                "competencia",
                "notas",
                "valor_servicos_centavos",
                "desconto_centavos",
                "base_calculo_centavos",
                "iss_total_centavos",
                "iss_retido_centavos",
                "iss_a_recolher_centavos",
                "aliquota_efetiva_pct",
                "notas_sem_valor_de_iss"
              ]
            }
          },
          "detalhe": {
            "type": "array",
            "items": {
              "type": "object",
              "additionalProperties": true
            },
            "description": "Competência por empresa e município (mais recentes primeiro)."
          },
          "canceladas_no_periodo": {
            "type": "object",
            "properties": {
              "notas": {
                "type": "integer"
              },
              "valor_servicos_centavos": {
                "type": "integer"
              }
            },
            "required": [
              "notas",
              "valor_servicos_centavos"
            ]
          },
          "retencoes_federais": {
            "type": "object",
            "properties": {
              "disponivel": {
                "type": "boolean"
              },
              "motivo": {
                "type": "string"
              }
            },
            "required": [
              "disponivel",
              "motivo"
            ],
            "description": "PIS, COFINS, CSLL, IRRF e INSS retidos não são registrados pelo NFsPlus; `disponivel` é `false` e `motivo` explica."
          }
        },
        "required": [
          "periodo",
          "ambiente",
          "filtros",
          "total",
          "por_competencia",
          "detalhe",
          "canceladas_no_periodo",
          "retencoes_federais"
        ]
      },
      "RelatorioOcorrencias": {
        "type": "object",
        "properties": {
          "periodo": {
            "type": "object",
            "properties": {
              "de": {
                "type": "string",
                "format": "date"
              },
              "ate": {
                "type": "string",
                "format": "date"
              }
            },
            "required": [
              "de",
              "ate"
            ],
            "additionalProperties": true
          },
          "ambiente": {
            "type": "string",
            "enum": [
              "sandbox",
              "producao"
            ],
            "description": "Ambiente dos dados: o da chave de API que fez a chamada."
          },
          "filtros": {
            "type": "object",
            "additionalProperties": true,
            "description": "Eco dos filtros aplicados (inclusive os padrões), para reproduzir o relatório."
          },
          "valores_ocultos": {
            "type": "boolean",
            "description": "`true` quando a chave não tem `relatorios:financeiro`: os campos de valor vêm `null`."
          },
          "resumo": {
            "type": "object",
            "properties": {
              "rejeitadas": {
                "type": "integer"
              },
              "com_erro": {
                "type": "integer"
              },
              "valor_nao_emitido_centavos": {
                "type": [
                  "integer",
                  "null"
                ],
                "description": "Valor das notas rejeitadas ou com erro. Em centavos inteiros. `null` quando a chave só tem `relatorios:ler` (valores ocultos)."
              },
              "canceladas": {
                "type": "integer"
              },
              "valor_cancelado_centavos": {
                "type": [
                  "integer",
                  "null"
                ],
                "description": "Valor das notas canceladas. Em centavos inteiros. `null` quando a chave só tem `relatorios:ler` (valores ocultos)."
              }
            },
            "required": [
              "rejeitadas",
              "com_erro",
              "valor_nao_emitido_centavos",
              "canceladas",
              "valor_cancelado_centavos"
            ]
          },
          "rejeicoes": {
            "type": "array",
            "items": {
              "type": "object",
              "properties": {
                "codigo": {
                  "type": [
                    "string",
                    "null"
                  ]
                },
                "mensagem": {
                  "type": [
                    "string",
                    "null"
                  ]
                },
                "campo": {
                  "type": [
                    "string",
                    "null"
                  ]
                },
                "tipo": {
                  "type": "string",
                  "enum": [
                    "rejeitada",
                    "erro"
                  ]
                },
                "notas": {
                  "type": "integer"
                },
                "ocorrencias": {
                  "type": "integer"
                },
                "valor_centavos": {
                  "type": [
                    "integer",
                    "null"
                  ]
                },
                "ultima_em": {
                  "type": "string",
                  "format": "date-time"
                },
                "orientacao": {
                  "type": [
                    "string",
                    "null"
                  ],
                  "description": "O que fazer para corrigir."
                },
                "exemplos": {
                  "type": "array",
                  "items": {
                    "type": "string",
                    "format": "uuid"
                  },
                  "description": "Ids de algumas notas com este motivo (as mais recentes), para abrir em `GET /v1/notas/{id}`."
                }
              },
              "required": [
                "codigo",
                "mensagem",
                "campo",
                "tipo",
                "notas",
                "ocorrencias",
                "valor_centavos",
                "ultima_em",
                "orientacao",
                "exemplos"
              ]
            },
            "description": "Motivos agrupados por código, do mais frequente ao menos."
          },
          "cancelamentos": {
            "type": "object",
            "properties": {
              "por_tipo": {
                "type": "array",
                "items": {
                  "type": "object",
                  "properties": {
                    "tipo": {
                      "type": "string"
                    },
                    "notas": {
                      "type": "integer"
                    },
                    "valor_centavos": {
                      "type": [
                        "integer",
                        "null"
                      ]
                    }
                  },
                  "required": [
                    "tipo",
                    "notas",
                    "valor_centavos"
                  ]
                }
              },
              "motivos": {
                "type": "array",
                "items": {
                  "type": "object",
                  "properties": {
                    "motivo": {
                      "type": [
                        "string",
                        "null"
                      ]
                    },
                    "notas": {
                      "type": "integer"
                    }
                  },
                  "required": [
                    "motivo",
                    "notas"
                  ]
                }
              }
            },
            "required": [
              "por_tipo",
              "motivos"
            ]
          }
        },
        "required": [
          "periodo",
          "ambiente",
          "filtros",
          "valores_ocultos",
          "resumo",
          "rejeicoes",
          "cancelamentos"
        ]
      },
      "RelatorioUso": {
        "type": "object",
        "properties": {
          "periodo": {
            "type": "object",
            "properties": {
              "de": {
                "type": "string",
                "format": "date"
              },
              "ate": {
                "type": "string",
                "format": "date"
              },
              "dias": {
                "type": "integer"
              },
              "em_andamento": {
                "type": "boolean"
              },
              "fuso": {
                "type": "string"
              }
            },
            "required": [
              "de",
              "ate",
              "dias",
              "em_andamento",
              "fuso"
            ],
            "additionalProperties": true
          },
          "plano": {
            "type": "object",
            "properties": {
              "codigo": {
                "type": "string"
              },
              "nome": {
                "type": "string"
              },
              "tipo_cobranca": {
                "type": "string"
              },
              "notas_incluidas": {
                "type": [
                  "integer",
                  "null"
                ]
              },
              "preco_excedente_centavos": {
                "type": [
                  "integer",
                  "null"
                ]
              },
              "preco_nota_prepago_centavos": {
                "type": [
                  "integer",
                  "null"
                ]
              },
              "mensalidade_centavos": {
                "type": [
                  "integer",
                  "null"
                ]
              }
            },
            "required": [
              "codigo",
              "nome",
              "tipo_cobranca",
              "notas_incluidas",
              "preco_excedente_centavos",
              "preco_nota_prepago_centavos",
              "mensalidade_centavos"
            ]
          },
          "consumo": {
            "type": "object",
            "properties": {
              "notas_autorizadas": {
                "type": "integer"
              },
              "na_franquia": {
                "type": "integer"
              },
              "excedentes": {
                "type": "integer"
              },
              "pre_pagas": {
                "type": "integer"
              },
              "rejeitadas": {
                "type": "integer"
              },
              "canceladas": {
                "type": "integer"
              },
              "custo_excedente_centavos": {
                "type": "integer"
              },
              "custo_prepago_centavos": {
                "type": "integer"
              },
              "custo_total_centavos": {
                "type": "integer",
                "description": "Mensalidade + excedente + notas pré-pagas."
              }
            },
            "required": [
              "notas_autorizadas",
              "na_franquia",
              "excedentes",
              "pre_pagas",
              "rejeitadas",
              "canceladas",
              "custo_excedente_centavos",
              "custo_prepago_centavos",
              "custo_total_centavos"
            ]
          },
          "limite": {
            "type": "object",
            "properties": {
              "percentual_usado": {
                "type": [
                  "number",
                  "null"
                ]
              },
              "restantes": {
                "type": [
                  "integer",
                  "null"
                ]
              },
              "nivel": {
                "type": "string"
              },
              "alerta": {
                "type": [
                  "string",
                  "null"
                ]
              }
            },
            "required": [
              "percentual_usado",
              "restantes",
              "nivel",
              "alerta"
            ]
          },
          "projecao": {
            "type": [
              "object",
              "null"
            ],
            "additionalProperties": true,
            "description": "Só com o período em andamento: ritmo diário e fechamento estimado do ciclo."
          },
          "creditos": {
            "type": [
              "object",
              "null"
            ],
            "properties": {
              "saldo_centavos": {
                "type": "integer"
              },
              "notas_restantes_estimadas": {
                "type": [
                  "integer",
                  "null"
                ]
              }
            },
            "required": [
              "saldo_centavos",
              "notas_restantes_estimadas"
            ]
          },
          "comparacao": {
            "type": [
              "object",
              "null"
            ],
            "additionalProperties": true
          },
          "serie": {
            "type": "array",
            "items": {
              "type": "object",
              "additionalProperties": true
            }
          },
          "historico": {
            "type": "array",
            "items": {
              "type": "object",
              "properties": {
                "competencia": {
                  "type": "string",
                  "format": "date"
                },
                "notas": {
                  "type": "integer"
                },
                "excedentes": {
                  "type": "integer"
                },
                "valor_centavos": {
                  "type": "integer"
                }
              },
              "required": [
                "competencia",
                "notas",
                "excedentes",
                "valor_centavos"
              ]
            }
          }
        },
        "required": [
          "periodo",
          "plano",
          "consumo",
          "limite",
          "projecao",
          "creditos",
          "comparacao",
          "serie",
          "historico"
        ]
      },
      "ErroCampo": {
        "type": "object",
        "properties": {
          "campo": {
            "type": "string",
            "description": "Caminho do campo inválido, com pontos (`valores.aliquota_iss`)."
          },
          "mensagem": {
            "type": "string"
          }
        },
        "required": [
          "campo",
          "mensagem"
        ]
      },
      "Problema": {
        "type": "object",
        "properties": {
          "type": {
            "type": "string",
            "format": "uri",
            "description": "URL de documentação do tipo de erro."
          },
          "title": {
            "type": "string"
          },
          "status": {
            "type": "integer",
            "description": "O mesmo código HTTP da resposta."
          },
          "detail": {
            "type": "string",
            "description": "Explicação legível para a pessoa que integra."
          },
          "code": {
            "type": "string",
            "description": "Identificador estável do erro (snake_case). Ver o guia de erros."
          },
          "request_id": {
            "type": "string",
            "description": "Identificador da requisição: informe-o ao suporte."
          },
          "errors": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/ErroCampo"
            },
            "description": "Presente em `422 validacao`: um item por campo inválido."
          },
          "retry_after": {
            "type": "integer",
            "description": "Em 429 e 409 `idempotencia_em_andamento`: segundos até tentar de novo (também no cabeçalho `Retry-After`)."
          }
        },
        "required": [
          "type",
          "title",
          "status",
          "code"
        ],
        "additionalProperties": true,
        "description": "Erro no formato Problem Details (RFC 9457), servido como `application/problem+json`. O campo estável para tratar o erro em código é `code`."
      },
      "Endereco": {
        "type": "object",
        "properties": {
          "cep": {
            "type": "string",
            "pattern": "^[0-9]{8}$",
            "description": "CEP só com dígitos."
          },
          "logradouro": {
            "type": "string"
          },
          "numero": {
            "type": "string"
          },
          "complemento": {
            "type": [
              "string",
              "null"
            ]
          },
          "bairro": {
            "type": "string"
          },
          "municipio_ibge": {
            "type": "string",
            "pattern": "^[0-9]{7}$",
            "description": "Código IBGE do município (7 dígitos)."
          }
        },
        "required": [
          "cep",
          "logradouro",
          "numero",
          "bairro",
          "municipio_ibge"
        ]
      },
      "PadroesFiscais": {
        "type": "object",
        "properties": {
          "codigo_tributacao_nacional": {
            "type": "string",
            "pattern": "^[0-9]{6}$"
          },
          "codigo_nbs": {
            "type": "string",
            "pattern": "^[0-9]{9}$"
          },
          "descricao_servico": {
            "type": "string"
          },
          "iss_retido": {
            "type": "boolean"
          },
          "aliquota_iss": {
            "type": "number",
            "minimum": 0,
            "maximum": 5,
            "description": "Porcentagem: 2 significa 2%."
          }
        }
      },
      "Nota": {
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "status": {
            "type": "string",
            "enum": [
              "processando",
              "autorizada",
              "rejeitada",
              "cancelada",
              "erro"
            ],
            "description": "`processando` até o município responder; depois `autorizada`, `rejeitada` ou `erro` (falha técnica, pode ser reprocessada). `cancelada` após o cancelamento."
          },
          "fase": {
            "type": [
              "string",
              "null"
            ],
            "enum": [
              "enfileirada",
              "transmitindo",
              "aguardando_retry",
              "cancelamento_pendente",
              null
            ],
            "description": "Etapa interna enquanto a nota ainda não é definitiva."
          },
          "ambiente": {
            "type": "string",
            "enum": [
              "sandbox",
              "producao"
            ]
          },
          "sem_validade_juridica": {
            "type": "boolean",
            "description": "Verdadeiro no Sandbox: o documento é de teste e não vale perante o fisco."
          },
          "prestador_id": {
            "type": "string",
            "format": "uuid"
          },
          "referencia_externa": {
            "type": [
              "string",
              "null"
            ],
            "description": "O seu identificador da venda/pedido, se foi enviado na emissão."
          },
          "competencia": {
            "type": "string",
            "format": "date"
          },
          "tomador": {
            "type": "object",
            "properties": {
              "id": {
                "type": [
                  "string",
                  "null"
                ],
                "format": "uuid"
              },
              "tipo_documento": {
                "type": "string",
                "enum": [
                  "cpf",
                  "cnpj",
                  "estrangeiro",
                  "nenhum"
                ]
              },
              "documento_mascarado": {
                "type": [
                  "string",
                  "null"
                ]
              },
              "nome": {
                "type": "string"
              }
            },
            "required": [
              "id",
              "tipo_documento",
              "documento_mascarado",
              "nome"
            ]
          },
          "servico": {
            "type": "object",
            "properties": {
              "codigo_tributacao_nacional": {
                "type": "string",
                "pattern": "^[0-9]{6}$"
              },
              "codigo_tributacao_municipal": {
                "type": [
                  "string",
                  "null"
                ]
              },
              "codigo_nbs": {
                "type": [
                  "string",
                  "null"
                ]
              },
              "descricao": {
                "type": "string"
              },
              "local_prestacao_ibge": {
                "type": "string"
              }
            },
            "required": [
              "codigo_tributacao_nacional",
              "codigo_tributacao_municipal",
              "codigo_nbs",
              "descricao",
              "local_prestacao_ibge"
            ]
          },
          "valores": {
            "type": "object",
            "properties": {
              "valor_servicos_centavos": {
                "type": "integer",
                "description": "Em centavos: R$ 1.500,00 = 150000."
              },
              "desconto_incondicionado_centavos": {
                "type": "integer"
              },
              "aliquota_iss": {
                "type": [
                  "number",
                  "null"
                ],
                "description": "Porcentagem (2 = 2%)."
              },
              "valor_iss_centavos": {
                "type": [
                  "integer",
                  "null"
                ]
              },
              "iss_retido": {
                "type": "boolean"
              }
            },
            "required": [
              "valor_servicos_centavos",
              "desconto_incondicionado_centavos",
              "aliquota_iss",
              "valor_iss_centavos",
              "iss_retido"
            ]
          },
          "informacoes_complementares": {
            "type": [
              "string",
              "null"
            ]
          },
          "metadados": {
            "type": "object",
            "additionalProperties": {
              "type": "string"
            },
            "description": "Os pares chave/valor enviados na emissão, devolvidos como estão."
          },
          "dps": {
            "type": "object",
            "properties": {
              "serie": {
                "type": "string"
              },
              "numero": {
                "type": "integer"
              },
              "id": {
                "type": [
                  "string",
                  "null"
                ]
              }
            },
            "required": [
              "serie",
              "numero",
              "id"
            ]
          },
          "nfse": {
            "type": [
              "object",
              "null"
            ],
            "properties": {
              "numero": {
                "type": [
                  "string",
                  "null"
                ]
              },
              "chave_acesso": {
                "type": [
                  "string",
                  "null"
                ]
              },
              "codigo_verificacao": {
                "type": [
                  "string",
                  "null"
                ]
              },
              "protocolo": {
                "type": [
                  "string",
                  "null"
                ]
              },
              "conector": {
                "type": [
                  "string",
                  "null"
                ]
              }
            },
            "required": [
              "numero",
              "chave_acesso",
              "codigo_verificacao",
              "protocolo",
              "conector"
            ],
            "description": "Dados do documento fiscal. `null` até a nota ser autorizada."
          },
          "emitida_em": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time"
          },
          "cancelada_em": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time"
          },
          "cancelamento": {
            "type": [
              "object",
              "null"
            ],
            "properties": {
              "motivo": {
                "type": "string",
                "enum": [
                  "erro_na_emissao",
                  "servico_nao_prestado",
                  "outros",
                  "substituicao"
                ],
                "description": "`substituicao` quando a nota foi cancelada por ter sido substituída por outra."
              },
              "justificativa": {
                "type": [
                  "string",
                  "null"
                ]
              }
            },
            "required": [
              "motivo",
              "justificativa"
            ]
          },
          "substituicao": {
            "type": [
              "object",
              "null"
            ],
            "properties": {
              "substitui": {
                "type": [
                  "object",
                  "null"
                ],
                "properties": {
                  "nota_id": {
                    "type": "string",
                    "format": "uuid"
                  },
                  "chave_acesso": {
                    "type": [
                      "string",
                      "null"
                    ]
                  },
                  "motivo": {
                    "type": [
                      "string",
                      "null"
                    ],
                    "enum": [
                      "desenquadramento_simples_nacional",
                      "enquadramento_simples_nacional",
                      "inclusao_retroativa_imunidade_isencao",
                      "exclusao_retroativa_imunidade_isencao",
                      "rejeicao_tomador_intermediario",
                      "outros",
                      null
                    ]
                  },
                  "justificativa": {
                    "type": [
                      "string",
                      "null"
                    ]
                  }
                },
                "required": [
                  "nota_id",
                  "chave_acesso",
                  "motivo",
                  "justificativa"
                ]
              },
              "substituida_por": {
                "type": [
                  "object",
                  "null"
                ],
                "properties": {
                  "nota_id": {
                    "type": "string",
                    "format": "uuid"
                  }
                },
                "required": [
                  "nota_id"
                ]
              }
            },
            "required": [
              "substitui",
              "substituida_por"
            ],
            "description": "Vínculo de substituição. `substitui` vem preenchido na **nota substituta** (qual nota ela substitui e por quê); `substituida_por` vem na **nota substituída**, depois que a substituta é autorizada. `null` em notas sem substituição."
          },
          "prazos": {
            "type": [
              "object",
              "null"
            ],
            "properties": {
              "cancelamento": {
                "type": "object",
                "properties": {
                  "prazo_dias": {
                    "type": "integer"
                  },
                  "limite_em": {
                    "type": "string",
                    "format": "date"
                  },
                  "dias_restantes": {
                    "type": "integer"
                  },
                  "dentro_do_prazo": {
                    "type": "boolean"
                  },
                  "explicacao": {
                    "type": "string"
                  }
                },
                "required": [
                  "prazo_dias",
                  "limite_em",
                  "dias_restantes",
                  "dentro_do_prazo",
                  "explicacao"
                ]
              },
              "substituicao": {
                "type": "object",
                "properties": {
                  "prazo_dias": {
                    "type": "integer"
                  },
                  "limite_em": {
                    "type": "string",
                    "format": "date"
                  },
                  "dias_restantes": {
                    "type": "integer"
                  },
                  "dentro_do_prazo": {
                    "type": "boolean"
                  },
                  "explicacao": {
                    "type": "string"
                  },
                  "sem_prazo_para": {
                    "type": "array",
                    "items": {
                      "type": "string",
                      "enum": [
                        "desenquadramento_simples_nacional",
                        "enquadramento_simples_nacional",
                        "inclusao_retroativa_imunidade_isencao",
                        "exclusao_retroativa_imunidade_isencao",
                        "rejeicao_tomador_intermediario",
                        "outros"
                      ]
                    },
                    "description": "Motivos de substituição que não têm prazo (enquadramento e desenquadramento no Simples Nacional)."
                  }
                },
                "required": [
                  "prazo_dias",
                  "limite_em",
                  "dias_restantes",
                  "dentro_do_prazo",
                  "explicacao",
                  "sem_prazo_para"
                ]
              }
            },
            "required": [
              "cancelamento",
              "substituicao"
            ],
            "description": "Prazos para cancelar e para substituir a nota, contados da emissão em dias corridos (fuso de Brasília), já com o texto pronto para mostrar. Só vem em nota `autorizada`; nas demais é `null`."
          },
          "erros": {
            "type": [
              "array",
              "null"
            ],
            "items": {
              "type": "object",
              "properties": {
                "codigo": {
                  "type": "string"
                },
                "mensagem": {
                  "type": "string"
                },
                "campo": {
                  "type": [
                    "string",
                    "null"
                  ]
                }
              },
              "required": [
                "codigo",
                "mensagem"
              ]
            },
            "description": "Motivos da rejeição ou do erro, quando houver."
          },
          "origem": {
            "type": "string",
            "enum": [
              "api",
              "app",
              "importacao"
            ]
          },
          "acoes": {
            "type": "object",
            "properties": {
              "cancelar": {
                "type": "boolean"
              },
              "substituir": {
                "type": "boolean"
              },
              "reprocessar": {
                "type": "boolean"
              },
              "baixar_xml": {
                "type": "boolean"
              },
              "baixar_pdf": {
                "type": "boolean"
              }
            },
            "required": [
              "cancelar",
              "substituir",
              "reprocessar",
              "baixar_xml",
              "baixar_pdf"
            ],
            "description": "O que dá para fazer com a nota agora. `cancelar` fica `false` depois do prazo de cancelamento (veja `prazos`); `substituir` vale para nota autorizada sem outro pedido em andamento."
          },
          "links": {
            "type": "object",
            "properties": {
              "self": {
                "type": "string"
              },
              "xml": {
                "type": "string"
              },
              "pdf": {
                "type": "string"
              }
            },
            "required": [
              "self"
            ]
          },
          "eventos": {
            "type": "array",
            "items": {
              "type": "object",
              "properties": {
                "tipo": {
                  "type": "string"
                },
                "detalhe": {
                  "type": "object",
                  "additionalProperties": true
                },
                "criado_em": {
                  "type": "string",
                  "format": "date-time"
                }
              },
              "required": [
                "tipo",
                "detalhe",
                "criado_em"
              ]
            },
            "description": "Linha do tempo da nota. Só vem em `GET /v1/notas/{id}`."
          },
          "criado_em": {
            "type": "string",
            "format": "date-time"
          },
          "atualizado_em": {
            "type": "string",
            "format": "date-time"
          }
        },
        "required": [
          "id",
          "status",
          "fase",
          "ambiente",
          "sem_validade_juridica",
          "prestador_id",
          "referencia_externa",
          "competencia",
          "tomador",
          "servico",
          "valores",
          "informacoes_complementares",
          "metadados",
          "dps",
          "nfse",
          "emitida_em",
          "cancelada_em",
          "cancelamento",
          "substituicao",
          "prazos",
          "erros",
          "origem",
          "acoes",
          "links",
          "criado_em",
          "atualizado_em"
        ]
      },
      "ListaDeNotas": {
        "type": "object",
        "properties": {
          "dados": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/Nota"
            }
          },
          "proximo_cursor": {
            "type": [
              "string",
              "null"
            ],
            "description": "Cursor opaco da próxima página; `null` quando não há mais itens. Envie-o em `cursor`."
          }
        },
        "required": [
          "dados",
          "proximo_cursor"
        ]
      },
      "Prestador": {
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "cnpj": {
            "type": "string",
            "description": "Só caracteres do CNPJ, sem pontuação (14 posições; aceita o CNPJ alfanumérico)."
          },
          "razao_social": {
            "type": "string"
          },
          "nome_fantasia": {
            "type": [
              "string",
              "null"
            ]
          },
          "municipio_ibge": {
            "type": "string",
            "pattern": "^[0-9]{7}$"
          },
          "regime_tributario": {
            "type": "string",
            "enum": [
              "mei",
              "simples_nacional",
              "lucro_presumido",
              "lucro_real"
            ]
          },
          "inscricao_municipal": {
            "type": [
              "string",
              "null"
            ]
          },
          "email": {
            "type": [
              "string",
              "null"
            ]
          },
          "telefone": {
            "type": [
              "string",
              "null"
            ]
          },
          "endereco": {
            "anyOf": [
              {
                "$ref": "#/components/schemas/Endereco"
              },
              {
                "type": "null"
              }
            ]
          },
          "serie_dps": {
            "type": "string"
          },
          "padroes_fiscais": {
            "$ref": "#/components/schemas/PadroesFiscais"
          },
          "cnaes": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/CnaePrestador"
            },
            "description": "Atividades econômicas (CNAE) do prestador, principal primeiro. Vêm da Receita na importação ou são editadas à mão."
          },
          "receita": {
            "type": [
              "object",
              "null"
            ],
            "properties": {
              "situacao_cadastral": {
                "type": "string",
                "enum": [
                  "ativa",
                  "suspensa",
                  "inapta",
                  "baixada",
                  "nula",
                  "desconhecida"
                ]
              },
              "data_abertura": {
                "type": [
                  "string",
                  "null"
                ],
                "format": "date"
              },
              "natureza_juridica": {
                "type": [
                  "string",
                  "null"
                ]
              },
              "porte": {
                "type": [
                  "string",
                  "null"
                ]
              },
              "provedor": {
                "type": "string",
                "description": "Quem respondeu a consulta."
              },
              "consultado_em": {
                "type": "string",
                "format": "date-time"
              }
            },
            "required": [
              "situacao_cadastral",
              "data_abertura",
              "natureza_juridica",
              "porte",
              "provedor",
              "consultado_em"
            ],
            "description": "Resumo da última conferência na Receita Federal. `null` se o prestador nunca foi importado nem sincronizado."
          },
          "status": {
            "type": "string",
            "enum": [
              "ativo",
              "inativo"
            ]
          },
          "certificado": {
            "type": [
              "object",
              "null"
            ],
            "properties": {
              "id": {
                "type": "string",
                "format": "uuid"
              },
              "status": {
                "type": "string",
                "enum": [
                  "ativo",
                  "expirado",
                  "revogado"
                ]
              },
              "validade_fim": {
                "type": "string",
                "format": "date-time"
              },
              "dias_restantes": {
                "type": "integer"
              }
            },
            "required": [
              "id",
              "status",
              "validade_fim",
              "dias_restantes"
            ]
          },
          "autorizacao": {
            "type": "object",
            "properties": {
              "status": {
                "type": "string",
                "enum": [
                  "nao_configurada",
                  "ativa",
                  "expirada"
                ]
              },
              "pode_emitir_sandbox": {
                "type": "boolean"
              },
              "pode_emitir_producao": {
                "type": "boolean"
              }
            },
            "required": [
              "status",
              "pode_emitir_sandbox",
              "pode_emitir_producao"
            ],
            "description": "Se o prestador pode emitir. No Sandbox basta estar ativo; em produção precisa de certificado A1 vigente."
          },
          "criado_em": {
            "type": "string",
            "format": "date-time"
          },
          "atualizado_em": {
            "type": "string",
            "format": "date-time"
          }
        },
        "required": [
          "id",
          "cnpj",
          "razao_social",
          "nome_fantasia",
          "municipio_ibge",
          "regime_tributario",
          "inscricao_municipal",
          "email",
          "telefone",
          "endereco",
          "serie_dps",
          "padroes_fiscais",
          "cnaes",
          "receita",
          "status",
          "certificado",
          "autorizacao",
          "criado_em",
          "atualizado_em"
        ]
      },
      "PrestadorSincronizado": {
        "allOf": [
          {
            "$ref": "#/components/schemas/Prestador"
          },
          {
            "type": "object",
            "properties": {
              "sincronizacao": {
                "type": "object",
                "properties": {
                  "campos_atualizados": {
                    "type": "array",
                    "items": {
                      "type": "string"
                    },
                    "description": "O que foi gravado: `razao_social`, `nome_fantasia`, `endereco`, `contato`, `cnaes`."
                  },
                  "municipio_divergente": {
                    "type": "boolean",
                    "description": "O município na Receita é outro. O município do prestador **não** é alterado: confira."
                  },
                  "situacao_cadastral": {
                    "type": "string",
                    "enum": [
                      "ativa",
                      "suspensa",
                      "inapta",
                      "baixada",
                      "nula",
                      "desconhecida"
                    ]
                  },
                  "provedor": {
                    "type": "string"
                  },
                  "consultado_em": {
                    "type": "string",
                    "format": "date-time"
                  },
                  "origem": {
                    "type": "string",
                    "enum": [
                      "consulta",
                      "cache",
                      "cache_desatualizado"
                    ]
                  }
                },
                "required": [
                  "campos_atualizados",
                  "municipio_divergente",
                  "situacao_cadastral",
                  "provedor",
                  "consultado_em",
                  "origem"
                ]
              }
            },
            "required": [
              "sincronizacao"
            ]
          }
        ]
      },
      "ListaDePrestadores": {
        "type": "object",
        "properties": {
          "dados": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/Prestador"
            }
          },
          "proximo_cursor": {
            "type": [
              "string",
              "null"
            ],
            "description": "Cursor opaco da próxima página; `null` quando não há mais itens. Envie-o em `cursor`."
          }
        },
        "required": [
          "dados",
          "proximo_cursor"
        ]
      },
      "CnaePrestador": {
        "type": "object",
        "properties": {
          "codigo": {
            "type": "string",
            "pattern": "^[0-9]{7}$",
            "description": "CNAE só com dígitos (7)."
          },
          "descricao": {
            "type": "string"
          },
          "principal": {
            "type": "boolean",
            "description": "No máximo um CNAE é o principal."
          },
          "origem": {
            "type": "string",
            "enum": [
              "receita",
              "manual"
            ],
            "description": "`receita`: veio da consulta de CNPJ e não foi alterado; `manual`: informado ou editado por você."
          }
        },
        "required": [
          "codigo",
          "descricao",
          "principal",
          "origem"
        ]
      },
      "ListaDeCnaesDoPrestador": {
        "type": "object",
        "properties": {
          "dados": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/CnaePrestador"
            }
          }
        },
        "required": [
          "dados"
        ]
      },
      "EmpresaCnpj": {
        "type": "object",
        "properties": {
          "cnpj": {
            "type": "string"
          },
          "razao_social": {
            "type": "string"
          },
          "nome_fantasia": {
            "type": [
              "string",
              "null"
            ]
          },
          "situacao_cadastral": {
            "type": "string",
            "enum": [
              "ativa",
              "suspensa",
              "inapta",
              "baixada",
              "nula",
              "desconhecida"
            ]
          },
          "data_situacao_cadastral": {
            "type": [
              "string",
              "null"
            ],
            "format": "date"
          },
          "data_abertura": {
            "type": [
              "string",
              "null"
            ],
            "format": "date"
          },
          "natureza_juridica": {
            "type": [
              "string",
              "null"
            ]
          },
          "porte": {
            "type": [
              "string",
              "null"
            ]
          },
          "optante_simples": {
            "type": [
              "boolean",
              "null"
            ]
          },
          "optante_mei": {
            "type": [
              "boolean",
              "null"
            ]
          },
          "regime_tributario_sugerido": {
            "type": [
              "string",
              "null"
            ],
            "enum": [
              "mei",
              "simples_nacional",
              null
            ],
            "description": "Só o que a Receita permite concluir: MEI ou Simples Nacional. Lucro presumido e lucro real você informa."
          },
          "email": {
            "type": [
              "string",
              "null"
            ]
          },
          "telefone": {
            "type": [
              "string",
              "null"
            ],
            "description": "Só dígitos, com DDD."
          },
          "endereco": {
            "type": [
              "object",
              "null"
            ],
            "properties": {
              "cep": {
                "type": [
                  "string",
                  "null"
                ]
              },
              "logradouro": {
                "type": [
                  "string",
                  "null"
                ]
              },
              "numero": {
                "type": [
                  "string",
                  "null"
                ]
              },
              "complemento": {
                "type": [
                  "string",
                  "null"
                ]
              },
              "bairro": {
                "type": [
                  "string",
                  "null"
                ]
              },
              "municipio": {
                "type": [
                  "string",
                  "null"
                ]
              },
              "uf": {
                "type": [
                  "string",
                  "null"
                ]
              },
              "municipio_ibge": {
                "type": [
                  "string",
                  "null"
                ],
                "pattern": "^[0-9]{7}$"
              }
            },
            "required": [
              "cep",
              "logradouro",
              "numero",
              "complemento",
              "bairro",
              "municipio",
              "uf",
              "municipio_ibge"
            ]
          },
          "cnae_principal": {
            "type": [
              "object",
              "null"
            ],
            "properties": {
              "codigo": {
                "type": "string",
                "pattern": "^[0-9]{7}$"
              },
              "descricao": {
                "type": "string"
              }
            },
            "required": [
              "codigo",
              "descricao"
            ]
          },
          "cnaes_secundarios": {
            "type": "array",
            "items": {
              "type": "object",
              "properties": {
                "codigo": {
                  "type": "string",
                  "pattern": "^[0-9]{7}$"
                },
                "descricao": {
                  "type": "string"
                }
              },
              "required": [
                "codigo",
                "descricao"
              ]
            }
          },
          "consulta": {
            "type": "object",
            "properties": {
              "provedor": {
                "type": "string"
              },
              "consultado_em": {
                "type": "string",
                "format": "date-time",
                "description": "Quando os dados foram obtidos na fonte (não quando você os leu do cache)."
              },
              "origem": {
                "type": "string",
                "enum": [
                  "consulta",
                  "cache",
                  "cache_desatualizado"
                ],
                "description": "`cache_desatualizado`: as fontes estavam fora do ar e esta é a última cópia guardada."
              },
              "aviso": {
                "type": "string"
              }
            },
            "required": [
              "provedor",
              "consultado_em",
              "origem"
            ]
          },
          "cobertura": {
            "type": "object",
            "properties": {
              "municipio_atendido": {
                "type": "boolean"
              },
              "municipio_ibge": {
                "type": [
                  "string",
                  "null"
                ]
              },
              "municipio_nome": {
                "type": [
                  "string",
                  "null"
                ]
              },
              "uf": {
                "type": [
                  "string",
                  "null"
                ]
              },
              "regimes_atendidos": {
                "type": "array",
                "items": {
                  "type": "string"
                }
              }
            },
            "required": [
              "municipio_atendido",
              "municipio_ibge",
              "municipio_nome",
              "uf",
              "regimes_atendidos"
            ],
            "description": "Se o município do CNPJ já está na cobertura do NFsPlus (só nele o prestador pode ser cadastrado)."
          }
        },
        "required": [
          "cnpj",
          "razao_social",
          "nome_fantasia",
          "situacao_cadastral",
          "data_situacao_cadastral",
          "data_abertura",
          "natureza_juridica",
          "porte",
          "optante_simples",
          "optante_mei",
          "regime_tributario_sugerido",
          "email",
          "telefone",
          "endereco",
          "cnae_principal",
          "cnaes_secundarios",
          "consulta",
          "cobertura"
        ]
      },
      "Ctribnac": {
        "type": "object",
        "properties": {
          "codigo": {
            "type": "string",
            "pattern": "^[0-9]{6}$",
            "description": "Código de tributação nacional (cTribNac), 6 dígitos."
          },
          "descricao": {
            "type": "string"
          },
          "item_lc116": {
            "type": "string",
            "description": "Item e subitem da lista de serviços da LC 116/2003 (ex.: `01.07`)."
          },
          "item_descricao": {
            "type": "string"
          },
          "subitem_descricao": {
            "type": "string"
          },
          "compativel_com_prestador": {
            "type": [
              "boolean",
              "null"
            ],
            "description": "`null` sem `prestador_id`, ou quando nenhum CNAE do prestador tem ligação conhecida com a lista de serviços (não dá para afirmar)."
          },
          "nivel_compatibilidade": {
            "type": [
              "string",
              "null"
            ],
            "enum": [
              "cnae",
              "item",
              null
            ],
            "description": "`cnae`: algum CNAE do prestador leva a este código; `item`: só o item da LC 116 coincide."
          },
          "cnaes_relacionados": {
            "type": "array",
            "items": {
              "type": "object",
              "properties": {
                "codigo": {
                  "type": "string",
                  "pattern": "^[0-9]{7}$"
                },
                "descricao": {
                  "type": "string"
                }
              },
              "required": [
                "codigo",
                "descricao"
              ]
            },
            "description": "CNAEs do prestador que levam a este código."
          }
        },
        "required": [
          "codigo",
          "descricao",
          "item_lc116",
          "item_descricao",
          "subitem_descricao",
          "compativel_com_prestador",
          "nivel_compatibilidade",
          "cnaes_relacionados"
        ]
      },
      "ListaDeCtribnac": {
        "type": "object",
        "properties": {
          "dados": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/Ctribnac"
            }
          },
          "total": {
            "type": "integer",
            "description": "Quantos códigos casam com o filtro (a lista traz até `limite`)."
          },
          "catalogo": {
            "type": "object",
            "properties": {
              "versao": {
                "type": "string"
              }
            },
            "required": [
              "versao"
            ]
          }
        },
        "required": [
          "dados",
          "total",
          "catalogo"
        ]
      },
      "CnaeDoCatalogo": {
        "type": "object",
        "properties": {
          "codigo": {
            "type": "string",
            "pattern": "^[0-9]{7}$"
          },
          "codigo_formatado": {
            "type": "string",
            "description": "Com a pontuação usual: `6201-5/01`."
          },
          "descricao": {
            "type": "string"
          },
          "secao": {
            "type": [
              "string",
              "null"
            ]
          },
          "possui_ctribnac": {
            "type": "boolean",
            "description": "Se existe ao menos um código de tributação ligado a este CNAE."
          }
        },
        "required": [
          "codigo",
          "codigo_formatado",
          "descricao",
          "secao",
          "possui_ctribnac"
        ]
      },
      "ListaDeCnaes": {
        "type": "object",
        "properties": {
          "dados": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/CnaeDoCatalogo"
            }
          },
          "catalogo": {
            "type": "object",
            "properties": {
              "versao": {
                "type": "string"
              }
            },
            "required": [
              "versao"
            ]
          }
        },
        "required": [
          "dados",
          "catalogo"
        ]
      },
      "SugestaoDeTributacao": {
        "allOf": [
          {
            "$ref": "#/components/schemas/Ctribnac"
          },
          {
            "type": "object",
            "properties": {
              "posicao": {
                "type": "integer",
                "description": "Ordem da sugestão, a melhor primeiro."
              },
              "aliquota_iss": {
                "type": [
                  "number",
                  "null"
                ],
                "description": "Só vem quando é a alíquota que o prestador já definiu nos padrões para este mesmo código."
              },
              "motivo": {
                "type": "string"
              },
              "confianca": {
                "type": "number",
                "minimum": 0,
                "maximum": 1
              }
            },
            "required": [
              "posicao",
              "aliquota_iss",
              "motivo",
              "confianca"
            ]
          }
        ]
      },
      "RespostaDeSugestao": {
        "type": "object",
        "properties": {
          "provedor": {
            "type": "string",
            "enum": [
              "local",
              "anthropic"
            ],
            "description": "Quem de fato respondeu."
          },
          "fallback": {
            "type": "boolean",
            "description": "O provedor configurado era outro e houve queda para o local."
          },
          "motivo_fallback": {
            "type": "string",
            "enum": [
              "sem_chave",
              "limite_diario",
              "erro_provedor",
              "resposta_invalida"
            ]
          },
          "cache": {
            "type": "boolean"
          },
          "modelo": {
            "type": "string"
          },
          "catalogo": {
            "type": "object",
            "properties": {
              "versao": {
                "type": "string"
              }
            },
            "required": [
              "versao"
            ]
          },
          "sugestoes": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/SugestaoDeTributacao"
            }
          }
        },
        "required": [
          "provedor",
          "fallback",
          "cache",
          "catalogo",
          "sugestoes"
        ]
      },
      "Tomador": {
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "tipo_documento": {
            "type": "string",
            "enum": [
              "cpf",
              "cnpj",
              "estrangeiro",
              "nenhum"
            ]
          },
          "documento_mascarado": {
            "type": [
              "string",
              "null"
            ],
            "description": "O documento nunca volta em claro: só a máscara (`***.456.789-**`)."
          },
          "nome": {
            "type": "string"
          },
          "email": {
            "type": [
              "string",
              "null"
            ]
          },
          "telefone": {
            "type": [
              "string",
              "null"
            ]
          },
          "endereco": {
            "anyOf": [
              {
                "$ref": "#/components/schemas/Endereco"
              },
              {
                "type": "null"
              }
            ]
          },
          "anonimizado": {
            "type": "boolean",
            "description": "Verdadeiro depois de excluir um tomador que já tem notas (LGPD): os dados pessoais saem, o vínculo com as notas fica."
          },
          "criado_em": {
            "type": "string",
            "format": "date-time"
          },
          "atualizado_em": {
            "type": "string",
            "format": "date-time"
          }
        },
        "required": [
          "id",
          "tipo_documento",
          "documento_mascarado",
          "nome",
          "email",
          "telefone",
          "endereco",
          "anonimizado",
          "criado_em",
          "atualizado_em"
        ]
      },
      "ListaDeTomadores": {
        "type": "object",
        "properties": {
          "dados": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/Tomador"
            }
          },
          "proximo_cursor": {
            "type": [
              "string",
              "null"
            ],
            "description": "Cursor opaco da próxima página; `null` quando não há mais itens. Envie-o em `cursor`."
          }
        },
        "required": [
          "dados",
          "proximo_cursor"
        ]
      },
      "Certificado": {
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "apelido": {
            "type": "string"
          },
          "cnpj": {
            "type": "string"
          },
          "titular": {
            "type": "string"
          },
          "numero_serie": {
            "type": "string"
          },
          "validade_inicio": {
            "type": "string",
            "format": "date-time"
          },
          "validade_fim": {
            "type": "string",
            "format": "date-time"
          },
          "dias_restantes": {
            "type": "integer"
          },
          "expirando": {
            "type": "boolean",
            "description": "Vence em até 30 dias."
          },
          "status": {
            "type": "string",
            "enum": [
              "ativo",
              "expirado",
              "revogado"
            ]
          },
          "fingerprint_sha256": {
            "type": "string"
          },
          "prestadores": {
            "type": "array",
            "items": {
              "type": "string",
              "format": "uuid"
            },
            "description": "Prestadores que usam este certificado."
          },
          "criado_em": {
            "type": "string",
            "format": "date-time"
          }
        },
        "required": [
          "id",
          "apelido",
          "cnpj",
          "titular",
          "numero_serie",
          "validade_inicio",
          "validade_fim",
          "dias_restantes",
          "expirando",
          "status",
          "fingerprint_sha256",
          "prestadores",
          "criado_em"
        ]
      },
      "ListaDeCertificados": {
        "type": "object",
        "properties": {
          "dados": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/Certificado"
            }
          },
          "proximo_cursor": {
            "type": [
              "string",
              "null"
            ],
            "description": "Cursor opaco da próxima página; `null` quando não há mais itens. Envie-o em `cursor`."
          }
        },
        "required": [
          "dados",
          "proximo_cursor"
        ]
      },
      "Evento": {
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid",
            "description": "Identificador do evento. É o mesmo em todas as tentativas: use-o para deduplicar."
          },
          "tipo": {
            "type": "string",
            "enum": [
              "nota.processando",
              "nota.autorizada",
              "nota.rejeitada",
              "nota.cancelada",
              "nota.erro",
              "certificado.expirando",
              "exportacao.pronta",
              "webhook.teste"
            ]
          },
          "criado_em": {
            "type": "string",
            "format": "date-time"
          },
          "ambiente": {
            "type": "string",
            "enum": [
              "sandbox",
              "producao"
            ]
          },
          "api_versao": {
            "type": "string",
            "enum": [
              "v1"
            ]
          },
          "dados": {
            "type": "object",
            "additionalProperties": true,
            "description": "Depende do evento: `{ \"nota\": Nota }` nos eventos de nota; `{ \"certificado\": {...} }`; ou a exportação."
          }
        },
        "required": [
          "id",
          "tipo",
          "criado_em",
          "ambiente",
          "api_versao",
          "dados"
        ],
        "description": "O corpo POST de todo webhook: o mesmo formato para qualquer evento. A assinatura cobre exatamente estes bytes."
      },
      "Webhook": {
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "url": {
            "type": "string"
          },
          "descricao": {
            "type": [
              "string",
              "null"
            ]
          },
          "eventos": {
            "type": "array",
            "items": {
              "type": "string",
              "enum": [
                "nota.processando",
                "nota.autorizada",
                "nota.rejeitada",
                "nota.cancelada",
                "nota.erro",
                "certificado.expirando",
                "exportacao.pronta",
                "*"
              ]
            }
          },
          "ambiente": {
            "type": "string",
            "enum": [
              "sandbox",
              "producao"
            ]
          },
          "segredo_prefixo": {
            "type": "string",
            "description": "Começo do segredo, só para identificar qual está em uso."
          },
          "falhas_consecutivas": {
            "type": "integer"
          },
          "desativado_auto_em": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time"
          },
          "desativado_motivo": {
            "type": [
              "string",
              "null"
            ]
          },
          "criado_em": {
            "type": "string",
            "format": "date-time"
          },
          "atualizado_em": {
            "type": "string",
            "format": "date-time"
          },
          "status": {
            "type": "string",
            "enum": [
              "ativo",
              "pausado",
              "desativado",
              "removido"
            ],
            "description": "`desativado` = desligado automaticamente após falhas seguidas; `pausado` = pausado por você."
          }
        },
        "required": [
          "id",
          "url",
          "descricao",
          "eventos",
          "ambiente",
          "segredo_prefixo",
          "falhas_consecutivas",
          "desativado_auto_em",
          "desativado_motivo",
          "criado_em",
          "atualizado_em",
          "status"
        ]
      },
      "WebhookComSegredo": {
        "allOf": [
          {
            "$ref": "#/components/schemas/Webhook"
          },
          {
            "type": "object",
            "properties": {
              "segredo": {
                "type": "string",
                "description": "Mostrado uma única vez."
              },
              "aviso": {
                "type": "string"
              }
            },
            "required": [
              "segredo",
              "aviso"
            ]
          }
        ]
      },
      "WebhookRotacionado": {
        "allOf": [
          {
            "$ref": "#/components/schemas/Webhook"
          },
          {
            "type": "object",
            "properties": {
              "segredo": {
                "type": "string",
                "description": "O novo segredo, mostrado uma única vez."
              },
              "segredo_anterior_valido_ate": {
                "type": "string",
                "format": "date-time"
              },
              "aviso": {
                "type": "string"
              }
            },
            "required": [
              "segredo",
              "segredo_anterior_valido_ate",
              "aviso"
            ]
          }
        ]
      },
      "WebhookDetalhe": {
        "allOf": [
          {
            "$ref": "#/components/schemas/Webhook"
          },
          {
            "type": "object",
            "properties": {
              "entregas_resumo": {
                "type": "object",
                "additionalProperties": {
                  "type": "integer"
                },
                "description": "Contagem de entregas por status."
              }
            },
            "required": [
              "entregas_resumo"
            ]
          }
        ]
      },
      "ListaDeWebhooks": {
        "type": "object",
        "properties": {
          "dados": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/Webhook"
            }
          },
          "proximo_cursor": {
            "type": [
              "string",
              "null"
            ],
            "description": "Cursor opaco da próxima página; `null` quando não há mais itens. Envie-o em `cursor`."
          },
          "limite": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Máximo de endpoints do plano (`null` = ilimitado)."
          },
          "eventos_disponiveis": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Tipos de evento aceitos em `eventos`, mais `*`."
          }
        },
        "required": [
          "dados",
          "proximo_cursor",
          "limite",
          "eventos_disponiveis"
        ]
      },
      "ResultadoTeste": {
        "type": "object",
        "properties": {
          "sucesso": {
            "type": "boolean"
          },
          "evento_id": {
            "type": "string",
            "format": "uuid"
          },
          "status_http": {
            "type": [
              "integer",
              "null"
            ]
          },
          "duracao_ms": {
            "type": "integer"
          },
          "resposta": {
            "type": [
              "string",
              "null"
            ]
          },
          "erro": {
            "type": [
              "string",
              "null"
            ]
          }
        },
        "required": [
          "sucesso",
          "evento_id",
          "status_http",
          "duracao_ms",
          "resposta",
          "erro"
        ]
      },
      "Entrega": {
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "evento": {
            "type": "string"
          },
          "evento_id": {
            "type": "string",
            "format": "uuid"
          },
          "status": {
            "type": "string",
            "enum": [
              "pendente",
              "entregue",
              "falhou",
              "desistiu"
            ]
          },
          "tentativas": {
            "type": "integer"
          },
          "proxima_tentativa_em": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time"
          },
          "ultimo_status_http": {
            "type": [
              "integer",
              "null"
            ]
          },
          "ultima_resposta": {
            "type": [
              "string",
              "null"
            ],
            "description": "Começo do corpo que o seu servidor respondeu (até 500 caracteres)."
          },
          "ultimo_erro": {
            "type": [
              "string",
              "null"
            ]
          },
          "criado_em": {
            "type": "string",
            "format": "date-time"
          },
          "entregue_em": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time"
          }
        },
        "required": [
          "id",
          "evento",
          "evento_id",
          "status",
          "tentativas",
          "proxima_tentativa_em",
          "ultimo_status_http",
          "ultima_resposta",
          "ultimo_erro",
          "criado_em",
          "entregue_em"
        ]
      },
      "EntregaDetalhe": {
        "allOf": [
          {
            "$ref": "#/components/schemas/Entrega"
          },
          {
            "type": "object",
            "properties": {
              "payload": {
                "$ref": "#/components/schemas/Evento"
              }
            },
            "required": [
              "payload"
            ]
          }
        ]
      },
      "ListaDeEntregas": {
        "type": "object",
        "properties": {
          "dados": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/Entrega"
            }
          },
          "proximo_cursor": {
            "type": [
              "string",
              "null"
            ],
            "description": "Cursor opaco da próxima página; `null` quando não há mais itens. Envie-o em `cursor`."
          }
        },
        "required": [
          "dados",
          "proximo_cursor"
        ]
      },
      "Exportacao": {
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "status": {
            "type": "string",
            "enum": [
              "processando",
              "pronta",
              "falhou",
              "expirada"
            ],
            "description": "`processando` → `pronta`. Depois de `expira_em`, `expirada`."
          },
          "formato": {
            "type": "string",
            "enum": [
              "zip",
              "csv",
              "json"
            ]
          },
          "ambiente": {
            "type": "string",
            "enum": [
              "sandbox",
              "producao"
            ]
          },
          "prestador_id": {
            "type": [
              "string",
              "null"
            ],
            "format": "uuid"
          },
          "periodo_inicio": {
            "type": "string",
            "format": "date"
          },
          "periodo_fim": {
            "type": "string",
            "format": "date"
          },
          "conteudo": {
            "type": "array",
            "items": {
              "type": "string",
              "enum": [
                "xml",
                "pdf"
              ]
            }
          },
          "total_documentos": {
            "type": [
              "integer",
              "null"
            ]
          },
          "tamanho_bytes": {
            "type": [
              "integer",
              "null"
            ]
          },
          "sha256": {
            "type": [
              "string",
              "null"
            ],
            "description": "Hash do arquivo, para conferir a integridade."
          },
          "nome_arquivo": {
            "type": [
              "string",
              "null"
            ]
          },
          "url_download": {
            "type": [
              "string",
              "null"
            ],
            "format": "uri",
            "description": "Link assinado, válido sem credencial por até 24 h. Só existe quando `status` é `pronta`."
          },
          "expira_em": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time"
          },
          "erro": {
            "type": [
              "string",
              "null"
            ]
          },
          "criado_em": {
            "type": "string",
            "format": "date-time"
          },
          "concluido_em": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time"
          }
        },
        "required": [
          "id",
          "status",
          "formato",
          "ambiente",
          "prestador_id",
          "periodo_inicio",
          "periodo_fim",
          "conteudo",
          "total_documentos",
          "tamanho_bytes",
          "sha256",
          "nome_arquivo",
          "url_download",
          "expira_em",
          "erro",
          "criado_em",
          "concluido_em"
        ]
      },
      "ListaDeExportacoes": {
        "type": "object",
        "properties": {
          "dados": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/Exportacao"
            }
          },
          "proximo_cursor": {
            "type": [
              "string",
              "null"
            ],
            "description": "Cursor opaco da próxima página; `null` quando não há mais itens. Envie-o em `cursor`."
          }
        },
        "required": [
          "dados",
          "proximo_cursor"
        ]
      },
      "Cenario": {
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "format": "uuid"
          },
          "nome": {
            "type": "string"
          },
          "gatilho": {
            "type": "object",
            "additionalProperties": true,
            "description": "Condições que a nota precisa atender para o cenário valer. Ver o guia do Sandbox."
          },
          "resultado": {
            "type": "string",
            "enum": [
              "autorizar",
              "rejeitar",
              "atrasar",
              "erro_transitorio"
            ]
          },
          "codigo_erro": {
            "type": [
              "string",
              "null"
            ]
          },
          "mensagem": {
            "type": [
              "string",
              "null"
            ]
          },
          "atraso_ms": {
            "type": "integer"
          },
          "falhas": {
            "type": "integer"
          },
          "prioridade": {
            "type": "integer",
            "description": "Menor valor vence quando mais de um cenário casa."
          },
          "ativo": {
            "type": "boolean"
          },
          "criado_em": {
            "type": "string",
            "format": "date-time"
          },
          "atualizado_em": {
            "type": "string",
            "format": "date-time"
          }
        },
        "required": [
          "id",
          "nome",
          "gatilho",
          "resultado",
          "codigo_erro",
          "mensagem",
          "atraso_ms",
          "falhas",
          "prioridade",
          "ativo",
          "criado_em",
          "atualizado_em"
        ]
      },
      "ListaDeCenarios": {
        "type": "object",
        "properties": {
          "dados": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/Cenario"
            }
          },
          "proximo_cursor": {
            "type": [
              "string",
              "null"
            ],
            "description": "Cursor opaco da próxima página; `null` quando não há mais itens. Envie-o em `cursor`."
          },
          "campos_gatilho": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Campos da nota que um gatilho pode examinar."
          },
          "operadores": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Operadores aceitos nas condições."
          },
          "limite": {
            "type": "integer",
            "description": "Máximo de cenários por conta."
          }
        },
        "required": [
          "dados",
          "proximo_cursor",
          "campos_gatilho",
          "operadores",
          "limite"
        ]
      },
      "ResultadoCenario": {
        "type": "object",
        "properties": {
          "acao": {
            "type": "string",
            "enum": [
              "autorizar",
              "rejeitar",
              "erro",
              "atrasar"
            ]
          },
          "codigo": {
            "type": "string"
          },
          "mensagem": {
            "type": "string"
          },
          "atrasoS": {
            "type": "number",
            "description": "Atraso (segundos) aplicado antes da ação."
          },
          "cenarioId": {
            "type": "string",
            "format": "uuid"
          },
          "cenarioNome": {
            "type": "string"
          }
        },
        "required": [
          "acao"
        ]
      },
      "Uso": {
        "type": "object",
        "properties": {
          "periodo": {
            "type": "object",
            "properties": {
              "inicio": {
                "type": "string",
                "format": "date"
              },
              "fim": {
                "type": "string",
                "format": "date"
              }
            },
            "required": [
              "inicio",
              "fim"
            ]
          },
          "plano": {
            "type": "object",
            "properties": {
              "codigo": {
                "type": "string"
              },
              "nome": {
                "type": "string"
              },
              "tipo_cobranca": {
                "type": "string",
                "enum": [
                  "assinatura",
                  "prepago"
                ]
              }
            },
            "required": [
              "codigo",
              "nome",
              "tipo_cobranca"
            ]
          },
          "notas": {
            "type": "object",
            "properties": {
              "autorizadas": {
                "type": "integer"
              },
              "incluidas_no_plano": {
                "type": [
                  "integer",
                  "null"
                ]
              },
              "excedente": {
                "type": "integer"
              },
              "rejeitadas": {
                "type": "integer"
              },
              "canceladas": {
                "type": "integer"
              },
              "valor_estimado_excedente_centavos": {
                "type": "integer",
                "description": "Excedente estimado do período, em centavos (inteiro), como em todo o restante da API."
              }
            },
            "required": [
              "autorizadas",
              "incluidas_no_plano",
              "excedente",
              "rejeitadas",
              "canceladas",
              "valor_estimado_excedente_centavos"
            ]
          },
          "creditos": {
            "type": "object",
            "properties": {
              "consumo_no_periodo_centavos": {
                "type": "integer",
                "description": "Consumo do período, em centavos."
              },
              "saldo_centavos": {
                "type": "integer",
                "description": "Saldo atual, em centavos."
              }
            },
            "required": [
              "consumo_no_periodo_centavos",
              "saldo_centavos"
            ],
            "description": "Só em planos pré-pagos."
          },
          "prestadores": {
            "type": "object",
            "properties": {
              "ativos": {
                "type": "integer"
              },
              "limite": {
                "type": [
                  "integer",
                  "null"
                ]
              }
            },
            "required": [
              "ativos",
              "limite"
            ]
          },
          "limites": {
            "type": "object",
            "properties": {
              "requisicoes_por_minuto": {
                "type": [
                  "integer",
                  "null"
                ]
              },
              "tamanho_maximo_corpo_kb": {
                "type": "integer"
              },
              "tamanho_maximo_certificado_kb": {
                "type": "integer"
              },
              "webhooks_max": {
                "type": [
                  "integer",
                  "null"
                ],
                "description": "Endpoints de webhook ativos que o plano permite. Acima disso: `402 limite_plano_webhooks`. `null`: sem limite."
              },
              "chaves_api_max": {
                "type": [
                  "integer",
                  "null"
                ],
                "description": "Chaves de API ativas que o plano permite (criadas no painel; a API não cria chaves). `null`: sem limite."
              },
              "usuarios_max": {
                "type": [
                  "integer",
                  "null"
                ],
                "description": "Usuários da conta que o plano permite (gerenciados no painel). `null`: sem limite."
              }
            },
            "required": [
              "requisicoes_por_minuto",
              "tamanho_maximo_corpo_kb",
              "tamanho_maximo_certificado_kb",
              "webhooks_max",
              "chaves_api_max",
              "usuarios_max"
            ]
          }
        },
        "required": [
          "periodo",
          "plano",
          "notas",
          "prestadores",
          "limites"
        ]
      }
    },
    "responses": {
      "RequisicaoInvalida": {
        "description": "A requisição está malformada (cabeçalho ausente, JSON inválido, parâmetro fora do formato).",
        "content": {
          "application/problem+json": {
            "schema": {
              "$ref": "#/components/schemas/Problema"
            },
            "example": {
              "type": "https://nfsplus.com.br/erros/cabecalho_idempotency_key_ausente",
              "title": "Requisição inválida",
              "status": 400,
              "detail": "Envie o cabeçalho Idempotency-Key.",
              "code": "cabecalho_idempotency_key_ausente",
              "request_id": "6f1d2c9e-3b84-4a57-91c0-d8e2a4b7c915"
            }
          }
        }
      },
      "NaoAutenticado": {
        "description": "Chave de API ausente, inválida, revogada ou expirada.",
        "content": {
          "application/problem+json": {
            "schema": {
              "$ref": "#/components/schemas/Problema"
            },
            "example": {
              "type": "https://nfsplus.com.br/erros/nao_autenticado",
              "title": "Não autenticado",
              "status": 401,
              "detail": "Credenciais ausentes ou inválidas.",
              "code": "nao_autenticado",
              "request_id": "6f1d2c9e-3b84-4a57-91c0-d8e2a4b7c915"
            }
          }
        }
      },
      "PagamentoNecessario": {
        "description": "O plano da conta não permite a operação (limite, saldo ou fatura em aberto).",
        "content": {
          "application/problem+json": {
            "schema": {
              "$ref": "#/components/schemas/Problema"
            },
            "example": {
              "type": "https://nfsplus.com.br/erros/saldo_insuficiente",
              "title": "Pagamento necessário",
              "status": 402,
              "detail": "Créditos insuficientes para emitir.",
              "code": "saldo_insuficiente",
              "request_id": "6f1d2c9e-3b84-4a57-91c0-d8e2a4b7c915"
            }
          }
        }
      },
      "Proibido": {
        "description": "A chave não tem o escopo necessário, ou a conta não pode executar a ação.",
        "content": {
          "application/problem+json": {
            "schema": {
              "$ref": "#/components/schemas/Problema"
            },
            "example": {
              "type": "https://nfsplus.com.br/erros/escopo_insuficiente",
              "title": "Acesso negado",
              "status": 403,
              "detail": "Falta a permissão \"notas:emitir\".",
              "code": "escopo_insuficiente",
              "request_id": "6f1d2c9e-3b84-4a57-91c0-d8e2a4b7c915"
            }
          }
        }
      },
      "NaoEncontrado": {
        "description": "O recurso não existe nesta conta e ambiente.",
        "content": {
          "application/problem+json": {
            "schema": {
              "$ref": "#/components/schemas/Problema"
            },
            "example": {
              "type": "https://nfsplus.com.br/erros/nao_encontrado",
              "title": "Não encontrado",
              "status": 404,
              "detail": "Nota não encontrada.",
              "code": "nao_encontrado",
              "request_id": "6f1d2c9e-3b84-4a57-91c0-d8e2a4b7c915"
            }
          }
        }
      },
      "Conflito": {
        "description": "O estado atual do recurso não permite a operação, ou ela conflita com outra.",
        "content": {
          "application/problem+json": {
            "schema": {
              "$ref": "#/components/schemas/Problema"
            },
            "example": {
              "type": "https://nfsplus.com.br/erros/nfse_estado_invalido",
              "title": "Conflito",
              "status": 409,
              "detail": "Só é possível cancelar uma nota autorizada.",
              "code": "nfse_estado_invalido",
              "request_id": "6f1d2c9e-3b84-4a57-91c0-d8e2a4b7c915"
            }
          }
        }
      },
      "Expirado": {
        "description": "O recurso existiu, mas expirou.",
        "content": {
          "application/problem+json": {
            "schema": {
              "$ref": "#/components/schemas/Problema"
            },
            "example": {
              "type": "https://nfsplus.com.br/erros/exportacao_expirada",
              "title": "Conflito",
              "status": 410,
              "detail": "Esta exportação expirou. Gere uma nova.",
              "code": "exportacao_expirada",
              "request_id": "6f1d2c9e-3b84-4a57-91c0-d8e2a4b7c915"
            }
          }
        }
      },
      "Validacao": {
        "description": "Os dados não passaram na validação. `errors` lista cada campo.",
        "content": {
          "application/problem+json": {
            "schema": {
              "$ref": "#/components/schemas/Problema"
            },
            "example": {
              "type": "https://nfsplus.com.br/erros/validacao",
              "title": "Dados inválidos",
              "status": 422,
              "detail": "Corrija os campos indicados.",
              "code": "validacao",
              "request_id": "6f1d2c9e-3b84-4a57-91c0-d8e2a4b7c915",
              "errors": [
                {
                  "campo": "valores.valor_servicos_centavos",
                  "mensagem": "use centavos inteiros"
                },
                {
                  "campo": "tomador.nome",
                  "mensagem": "informe o nome do tomador (ou o tomador_id de um tomador cadastrado)"
                }
              ]
            }
          }
        }
      },
      "Indisponivel": {
        "description": "Um serviço de que a operação depende está indisponível agora. Tente de novo em instantes.",
        "content": {
          "application/problem+json": {
            "schema": {
              "$ref": "#/components/schemas/Problema"
            },
            "example": {
              "type": "https://nfsplus.com.br/erros/cnpj_consulta_indisponivel",
              "title": "Serviço indisponível",
              "status": 503,
              "detail": "Os serviços de consulta de CNPJ estão indisponíveis agora. Preencha os dados manualmente ou tente de novo em instantes.",
              "code": "cnpj_consulta_indisponivel",
              "request_id": "6f1d2c9e-3b84-4a57-91c0-d8e2a4b7c915"
            }
          }
        }
      },
      "LimiteExcedido": {
        "description": "Limite de requisições por minuto excedido. Espere `Retry-After` segundos.",
        "headers": {
          "Retry-After": {
            "description": "Segundos até poder tentar de novo.",
            "schema": {
              "type": "integer"
            }
          },
          "X-Request-Id": {
            "$ref": "#/components/headers/XRequestId"
          },
          "X-RateLimit-Limit": {
            "$ref": "#/components/headers/XRateLimitLimit"
          },
          "X-RateLimit-Remaining": {
            "$ref": "#/components/headers/XRateLimitRemaining"
          },
          "X-RateLimit-Reset": {
            "$ref": "#/components/headers/XRateLimitReset"
          }
        },
        "content": {
          "application/problem+json": {
            "schema": {
              "$ref": "#/components/schemas/Problema"
            },
            "example": {
              "type": "https://nfsplus.com.br/erros/limite_excedido",
              "title": "Limite excedido",
              "status": 429,
              "detail": "Muitas requisições. Tente de novo em instantes.",
              "code": "limite_excedido",
              "request_id": "6f1d2c9e-3b84-4a57-91c0-d8e2a4b7c915",
              "retry_after": 12
            }
          }
        }
      }
    }
  },
  "x-codigos-de-erro": [
    {
      "status": 400,
      "code": "cabecalho_idempotency_key_ausente",
      "descricao": "Faltou o cabeçalho `Idempotency-Key`.",
      "operacoes": [
        "emitirNota",
        "substituirNota"
      ]
    },
    {
      "status": 400,
      "code": "cabecalho_sandbox_em_producao",
      "descricao": "`X-Sandbox-Scenario` enviado com chave de produção.",
      "operacoes": [
        "emitirNota"
      ]
    },
    {
      "status": 400,
      "code": "parametro_invalido",
      "descricao": "Parâmetro em formato inválido que só o banco detecta, como um cursor de paginação alterado. Use o `proximo_cursor` devolvido, sem modificá-lo.",
      "operacoes": []
    },
    {
      "status": 400,
      "code": "requisicao_invalida",
      "descricao": "JSON malformado ou parâmetro fora do formato.",
      "operacoes": []
    },
    {
      "status": 401,
      "code": "nao_autenticado",
      "descricao": "Chave de API ausente, inválida, revogada ou expirada.",
      "operacoes": []
    },
    {
      "status": 402,
      "code": "assinatura_inadimplente",
      "descricao": "Há fatura em aberto (planos de assinatura).",
      "operacoes": [
        "emitirNota"
      ]
    },
    {
      "status": 402,
      "code": "limite_plano_cnpjs",
      "descricao": "O plano não comporta mais um CNPJ ativo.",
      "operacoes": [
        "criarPrestador",
        "atualizarPrestador"
      ]
    },
    {
      "status": 402,
      "code": "limite_plano_webhooks",
      "descricao": "O plano não comporta mais endpoints.",
      "operacoes": [
        "criarWebhook"
      ]
    },
    {
      "status": 402,
      "code": "plano_sem_producao",
      "descricao": "O plano não permite emitir em produção.",
      "operacoes": [
        "emitirNota"
      ]
    },
    {
      "status": 402,
      "code": "saldo_insuficiente",
      "descricao": "Créditos insuficientes (plano pré-pago).",
      "operacoes": [
        "emitirNota"
      ]
    },
    {
      "status": 403,
      "code": "conta_encerrada",
      "descricao": "A conta foi encerrada.",
      "operacoes": []
    },
    {
      "status": 403,
      "code": "conta_suspensa",
      "descricao": "A conta está suspensa: só leituras são permitidas.",
      "operacoes": []
    },
    {
      "status": 403,
      "code": "credencial_nao_aceita",
      "descricao": "Este recurso não aceita este tipo de credencial.",
      "operacoes": []
    },
    {
      "status": 403,
      "code": "escopo_insuficiente",
      "descricao": "A chave não tem o escopo exigido pela operação.",
      "operacoes": [
        "substituirNota"
      ]
    },
    {
      "status": 403,
      "code": "ip_nao_permitido",
      "descricao": "O IP de origem não está na lista de IPs permitidos da chave.",
      "operacoes": []
    },
    {
      "status": 403,
      "code": "link_invalido",
      "descricao": "Link de download inválido ou vencido.",
      "operacoes": [
        "baixarExportacao"
      ]
    },
    {
      "status": 404,
      "code": "cnpj_nao_encontrado",
      "descricao": "A Receita não tem este CNPJ.",
      "operacoes": [
        "importarPrestador",
        "sincronizarPrestador",
        "importarTomador",
        "consultarCnpj"
      ]
    },
    {
      "status": 404,
      "code": "nao_encontrado",
      "descricao": "O recurso não existe nesta conta e ambiente.",
      "operacoes": []
    },
    {
      "status": 409,
      "code": "cancelamento_em_andamento",
      "descricao": "Já existe um pedido de cancelamento em curso.",
      "operacoes": [
        "cancelarNota",
        "substituirNota"
      ]
    },
    {
      "status": 409,
      "code": "certificado_ja_cadastrado",
      "descricao": "Este certificado já está cadastrado na conta.",
      "operacoes": [
        "enviarCertificado"
      ]
    },
    {
      "status": 409,
      "code": "cnpj_ja_cadastrado",
      "descricao": "Este CNPJ já está na conta.",
      "operacoes": [
        "criarPrestador",
        "importarPrestador"
      ]
    },
    {
      "status": 409,
      "code": "conector_fiscal_nao_configurado",
      "descricao": "Produção indisponível na plataforma (conector fiscal em simulador ou sem as raízes ICP-Brasil). Nada é criado nem cobrado; use o Sandbox.",
      "operacoes": [
        "emitirNota",
        "cancelarNota",
        "reprocessarNota"
      ]
    },
    {
      "status": 409,
      "code": "entrega_pendente",
      "descricao": "A entrega já está na fila.",
      "operacoes": [
        "reenviarEntrega"
      ]
    },
    {
      "status": 409,
      "code": "exportacao_nao_pronta",
      "descricao": "A exportação ainda está sendo gerada ou falhou.",
      "operacoes": [
        "baixarExportacao"
      ]
    },
    {
      "status": 409,
      "code": "idempotencia_em_andamento",
      "descricao": "A primeira requisição com esta chave ainda está em curso; repita em instantes.",
      "operacoes": [
        "emitirNota"
      ]
    },
    {
      "status": 409,
      "code": "limite_cenarios",
      "descricao": "Já são 50 cenários.",
      "operacoes": [
        "criarCenario"
      ]
    },
    {
      "status": 409,
      "code": "nfse_estado_invalido",
      "descricao": "Só dá para cancelar nota autorizada.",
      "operacoes": [
        "cancelarNota",
        "substituirNota",
        "reprocessarNota",
        "baixarXmlDaNota",
        "baixarPdfDaNota"
      ]
    },
    {
      "status": 409,
      "code": "nfse_ja_substituida",
      "descricao": "A nota já foi substituída por outra; o erro traz `nota_substituta_id`. Substitua a nota substituta, se for o caso.",
      "operacoes": [
        "substituirNota"
      ]
    },
    {
      "status": 409,
      "code": "referencia_externa_duplicada",
      "descricao": "Já existe uma nota com esta `referencia_externa`; o erro traz `nota_id`.",
      "operacoes": [
        "emitirNota",
        "substituirNota"
      ]
    },
    {
      "status": 409,
      "code": "substituicao_em_andamento",
      "descricao": "A nota está sendo substituída; aguarde o resultado da substituição.",
      "operacoes": [
        "cancelarNota",
        "substituirNota"
      ]
    },
    {
      "status": 409,
      "code": "tomador_anonimizado",
      "descricao": "O tomador foi anonimizado e não serve para notas novas.",
      "operacoes": [
        "emitirNota",
        "atualizarTomador"
      ]
    },
    {
      "status": 409,
      "code": "tomador_ja_cadastrado",
      "descricao": "Já existe um tomador com este documento; o erro traz `tomador_id`.",
      "operacoes": [
        "criarTomador",
        "importarTomador",
        "atualizarTomador"
      ]
    },
    {
      "status": 409,
      "code": "webhook_inativo",
      "descricao": "O endpoint está pausado ou desativado.",
      "operacoes": [
        "reenviarEntrega"
      ]
    },
    {
      "status": 410,
      "code": "exportacao_expirada",
      "descricao": "A exportação passou de 7 dias; gere outra.",
      "operacoes": [
        "baixarExportacao"
      ]
    },
    {
      "status": 413,
      "code": "corpo_grande_demais",
      "descricao": "O corpo passa de 1 MB (certificados: ~50 KB).",
      "operacoes": []
    },
    {
      "status": 415,
      "code": "tipo_nao_suportado",
      "descricao": "Use `Content-Type: application/json`.",
      "operacoes": []
    },
    {
      "status": 422,
      "code": "autorizacao_expirada",
      "descricao": "O certificado A1 do prestador expirou (produção).",
      "operacoes": [
        "emitirNota",
        "reprocessarNota"
      ]
    },
    {
      "status": 422,
      "code": "autorizacao_revogada",
      "descricao": "O certificado A1 do prestador foi removido (produção).",
      "operacoes": [
        "emitirNota"
      ]
    },
    {
      "status": 422,
      "code": "certificado_ausente_ou_invalido",
      "descricao": "Produção: o prestador não tem certificado A1, ele não é da empresa (CNPJ) ou não vem da cadeia ICP-Brasil; o erro traz `motivo` e `acao`.",
      "operacoes": [
        "emitirNota",
        "reprocessarNota"
      ]
    },
    {
      "status": 422,
      "code": "certificado_expirado",
      "descricao": "O certificado informado está expirado ou revogado.",
      "operacoes": [
        "criarPrestador",
        "enviarCertificado"
      ]
    },
    {
      "status": 422,
      "code": "certificado_invalido",
      "descricao": "Arquivo ou senha inválidos, ou o certificado não é um A1 de pessoa jurídica.",
      "operacoes": [
        "enviarCertificado"
      ]
    },
    {
      "status": 422,
      "code": "certificado_titular_divergente",
      "descricao": "O certificado informado é de outra empresa.",
      "operacoes": [
        "criarPrestador"
      ]
    },
    {
      "status": 422,
      "code": "codigo_tributacao_desconhecido",
      "descricao": "O código de tributação não consta na tabela nacional; `errors[].sugestoes` traz opções.",
      "operacoes": [
        "emitirNota"
      ]
    },
    {
      "status": 422,
      "code": "codigo_tributacao_incompativel",
      "descricao": "O código não corresponde aos CNAEs do prestador; `errors[].sugestoes` traz opções. Use `servico.forcar_codigo` para assumir o código.",
      "operacoes": [
        "emitirNota"
      ]
    },
    {
      "status": 422,
      "code": "competencia_futura",
      "descricao": "A competência é posterior a hoje.",
      "operacoes": [
        "emitirNota"
      ]
    },
    {
      "status": 422,
      "code": "exportacao_grande_demais",
      "descricao": "O filtro passa do limite de notas; o erro traz `total` e `limite`.",
      "operacoes": [
        "criarExportacao"
      ]
    },
    {
      "status": 422,
      "code": "idempotencia_corpo_diferente",
      "descricao": "A `Idempotency-Key` já foi usada com outro conteúdo.",
      "operacoes": [
        "emitirNota"
      ]
    },
    {
      "status": 422,
      "code": "iss_retido_mei",
      "descricao": "MEI não pode ter ISS retido.",
      "operacoes": [
        "emitirNota"
      ]
    },
    {
      "status": 422,
      "code": "municipio_nao_atendido",
      "descricao": "Município fora da cobertura (produção).",
      "operacoes": [
        "emitirNota",
        "criarPrestador",
        "importarPrestador"
      ]
    },
    {
      "status": 422,
      "code": "prazo_cancelamento_expirado",
      "descricao": "O prazo para cancelar terminou. O erro traz `acao`, `prazo_dias`, `prazo_ate`, `substituicao_disponivel` e `alternativas`.",
      "operacoes": [
        "cancelarNota"
      ]
    },
    {
      "status": 422,
      "code": "prazo_substituicao_expirado",
      "descricao": "O prazo para substituir terminou. O erro traz `acao`, `prazo_dias` e `prazo_ate`.",
      "operacoes": [
        "substituirNota"
      ]
    },
    {
      "status": 422,
      "code": "prestador_inativo",
      "descricao": "O prestador está inativo.",
      "operacoes": [
        "emitirNota"
      ]
    },
    {
      "status": 422,
      "code": "regime_nao_atendido_no_municipio",
      "descricao": "O regime tributário ainda não é atendido no município.",
      "operacoes": [
        "emitirNota"
      ]
    },
    {
      "status": 422,
      "code": "substituicao_campo_imutavel",
      "descricao": "O pedido muda um campo que não pode mudar na substituição; `errors` lista os campos.",
      "operacoes": [
        "substituirNota"
      ]
    },
    {
      "status": 422,
      "code": "tomador_exterior_nao_suportado",
      "descricao": "Tomador do exterior ainda não é suportado.",
      "operacoes": [
        "emitirNota"
      ]
    },
    {
      "status": 422,
      "code": "validacao",
      "descricao": "Os dados não passaram na validação; `errors` lista os campos.",
      "operacoes": [
        "emitirNota",
        "substituirNota"
      ]
    },
    {
      "status": 422,
      "code": "webhook_url_invalida",
      "descricao": "URL fora do padrão (HTTPS em produção, sem destino interno).",
      "operacoes": [
        "criarWebhook"
      ]
    },
    {
      "status": 429,
      "code": "limite_excedido",
      "descricao": "Limite de requisições por minuto excedido, ou muitas credenciais inválidas vindas do mesmo IP (aguarde o `Retry-After`).",
      "operacoes": []
    },
    {
      "status": 500,
      "code": "erro_interno",
      "descricao": "Falha do nosso lado. Informe o `request_id` ao suporte.",
      "operacoes": []
    },
    {
      "status": 503,
      "code": "catalogo_indisponivel",
      "descricao": "O catálogo nacional ainda não foi carregado neste ambiente.",
      "operacoes": [
        "buscarCodigosDeTributacao",
        "buscarCnaes",
        "sugerirTributacao"
      ]
    },
    {
      "status": 503,
      "code": "cnpj_consulta_indisponivel",
      "descricao": "Nenhuma fonte de consulta respondeu. Cadastre informando os dados à mão ou tente de novo.",
      "operacoes": [
        "importarPrestador",
        "sincronizarPrestador",
        "importarTomador",
        "consultarCnpj"
      ]
    },
    {
      "status": 503,
      "code": "exportacao_integridade",
      "descricao": "O arquivo guardado não confere com o hash registrado. Tente de novo em instantes.",
      "operacoes": [
        "baixarExportacao"
      ]
    },
    {
      "status": 503,
      "code": "indisponivel",
      "descricao": "Serviço temporariamente indisponível. Tente de novo.",
      "operacoes": []
    }
  ],
  "x-eventos": [
    "nota.processando",
    "nota.autorizada",
    "nota.rejeitada",
    "nota.cancelada",
    "nota.erro",
    "certificado.expirando",
    "exportacao.pronta",
    "webhook.teste"
  ]
}
