Atendimento: Obrigações

Endpoints da WebApiAlcance para gerenciar obrigações acessórias dos clientes - os compromissos fiscais e contábeis (declarações, guias, entregas) controlados por cliente, competência e prazo de entrega. Cobrem criação individual, importação em lote com deduplicação, listagem com filtros e paginação, detalhamento por ID, atualização parcial e exclusão.

Todos os endpoints exigem autenticação. Veja Autenticação para o fluxo de API Key. O Swagger oficial está em api.contabilidadealcance.com.br/docs.

Base path

/api/v1/obrigacoes

A URL completa em produção é https://api.contabilidadealcance.com.br/api/v1/obrigacoes.

Escopos necessários

  • obrigacoes:read - listagem e detalhamento por ID
  • obrigacoes:write - criação, importação em lote, atualização e exclusão

O escopo é derivado da rota: o prefixo /obrigacoes vira o recurso obrigacoes, e o método HTTP define a ação (read para GET, write para POST/PUT/DELETE).

Endpoints

POST /obrigacoes/

Cria uma nova obrigação acessória vinculada a um cliente. O único campo obrigatório é id_cliente; os demais são opcionais.

Parâmetros

Este endpoint não recebe parâmetros de rota ou query - os dados vão no corpo da requisição (ObrigacaoCreate): id_cliente (obrigatório) e os demais campos do schema (opcionais).

Request

{
  "id_cliente": 1234,
  "departamento_id": 3,
  "nome": "DCTFWeb Mensal",
  "tipo": "Declaração",
  "competencia": "2026-06",
  "ent_dt_prazo": "2026-07-15",
  "status": "pendente"
}

Response 201 Created

{
  "success": true,
  "message": "Obrigação criada com sucesso",
  "data": {
    "id": 87,
    "id_cliente": 1234,
    "departamento_id": 3,
    "nome": "DCTFWeb Mensal",
    "tipo": "Declaração",
    "competencia": "2026-06",
    "ent_dt_prazo": "2026-07-15",
    "ent_multa": false,
    "status": "pendente",
    "legacy_uuid": null,
    "data_hora_criacao": "2026-07-03T09:12:00",
    "data_hora_atualizacao": "2026-07-03T09:12:00"
  }
}

Validações de negócio retornam 422 Unprocessable Entity - inclusive quando o id_cliente informado não existe: a existência do cliente é validada antes do insert (evitando um 500 por violação de FK) e a resposta lista os IDs inexistentes (ex.: "Cliente(s) inexistente(s): [1234].").

Escopo: obrigacoes:write

POST /obrigacoes/import

Importa obrigações em lote com upsert e deduplicação explícita (substitui a RPC import_obrigacoes_bulk). O dedup é feito por acessorias_ent_id (quando houver) ou pela tupla (id_cliente, nome, ent_dt_prazo, competencia). O lote é limitado a 2000 itens por requisição - lotes maiores devem ser paginados pelo cliente.

Parâmetros

Este endpoint não recebe parâmetros de rota ou query - os dados vão no corpo da requisição (ObrigacaoImportRequest): objeto com o array obrigacoes, em que cada item é um ObrigacaoImportItem que exige id_cliente.

Request

{
  "obrigacoes": [
    {
      "id_cliente": 1234,
      "acessorias_ent_id": "ent-001",
      "nome": "DCTFWeb Mensal",
      "competencia": "2026-06",
      "ent_dt_prazo": "2026-07-15"
    },
    {
      "id_cliente": 1234,
      "acessorias_ent_id": "ent-002",
      "nome": "EFD Contribuições",
      "competencia": "2026-06",
      "ent_dt_prazo": "2026-07-10"
    }
  ]
}

Response 200 OK

{
  "success": true,
  "message": "Import de obrigações concluído com sucesso",
  "data": {
    "inseridos": 1,
    "atualizados": 1
  }
}

Lote vazio retorna 422 Unprocessable Entity ("Lista de obrigações vazia."). A existência de todos os id_cliente do lote é validada antes do upsert: qualquer cliente inexistente aborta o import inteiro com 422 ("Cliente(s) inexistente(s): [...]"), evitando 500 por violação de FK.

Escopo: obrigacoes:write

GET /obrigacoes/

Lista obrigações com filtros e paginação. Lista vazia é um estado válido - sempre retorna 200 OK, inclusive com data: [] e a mensagem "Nenhuma obrigação encontrada.".

Parâmetros

ParâmetroTipoLocalObrigatórioDescrição
id_clienteintquerynãoFiltra por cliente (customer.id).
departamento_idintquerynãoFiltra por departamento.
statusstrquerynãoFiltra por status.
limitintquerynãoLimite de itens por página. Default 100 (1-500).
offsetintquerynãoOffset de paginação. Default 0 (≥ 0).

Request

Sem corpo de requisição.

Response 200 OK

{
  "success": true,
  "message": "Obrigações recuperadas com sucesso",
  "data": [
    {
      "id": 87,
      "id_cliente": 1234,
      "departamento_id": 3,
      "nome": "DCTFWeb Mensal",
      "tipo": "Declaração",
      "competencia": "2026-06",
      "ent_dt_prazo": "2026-07-15",
      "ent_multa": false,
      "status": "pendente",
      "legacy_uuid": null,
      "data_hora_criacao": "2026-07-03T09:12:00",
      "data_hora_atualizacao": "2026-07-03T09:12:00"
    }
  ]
}

Escopo: obrigacoes:read

GET /obrigacoes/{obrigacao_id}

Detalha uma obrigação pelo ID inteiro. Quando não encontrada, retorna 404 Not Found.

Parâmetros

ParâmetroTipoLocalObrigatórioDescrição
obrigacao_idintpathsimID interno da obrigação

Request

Sem corpo de requisição.

Response 200 OK

{
  "success": true,
  "message": "Obrigação recuperada com sucesso",
  "data": {
    "id": 87,
    "id_cliente": 1234,
    "departamento_id": 3,
    "nome": "DCTFWeb Mensal",
    "tipo": "Declaração",
    "competencia": "2026-06",
    "ent_dt_prazo": "2026-07-15",
    "ent_multa": false,
    "status": "pendente",
    "legacy_uuid": null,
    "data_hora_criacao": "2026-07-03T09:12:00",
    "data_hora_atualizacao": "2026-07-03T09:12:00"
  }
}

Escopo: obrigacoes:read

PUT /obrigacoes/{obrigacao_id}

Atualiza uma obrigação existente. O body é um ObrigacaoUpdate com campos parciais - somente o que vier preenchido é alterado. Os campos id_cliente e legacy_uuid são omitidos do body para evitar mass-assignment.

Parâmetros

ParâmetroTipoLocalObrigatórioDescrição
obrigacao_idintpathsimID da obrigação

Request (ObrigacaoUpdate - todos os campos opcionais)

{
  "status": "entregue",
  "ent_dt_entrega": "2026-07-12"
}

Response 200 OK

{
  "success": true,
  "message": "Obrigação atualizada com sucesso",
  "data": {
    "id": 87,
    "id_cliente": 1234,
    "departamento_id": 3,
    "nome": "DCTFWeb Mensal",
    "tipo": "Declaração",
    "competencia": "2026-06",
    "ent_dt_prazo": "2026-07-15",
    "ent_dt_entrega": "2026-07-12",
    "ent_multa": false,
    "status": "entregue",
    "legacy_uuid": null,
    "data_hora_criacao": "2026-07-03T09:12:00",
    "data_hora_atualizacao": "2026-07-12T14:30:00"
  }
}

Retorna 404 Not Found quando a obrigação não existe e 422 Unprocessable Entity para demais erros de validação.

Escopo: obrigacoes:write

DELETE /obrigacoes/{obrigacao_id}

Remove uma obrigação pelo ID. Quando não encontrada, retorna 404 Not Found.

Parâmetros

ParâmetroTipoLocalObrigatórioDescrição
obrigacao_idintpathsimID da obrigação

Request

Sem corpo de requisição.

Response 200 OK

{
  "success": true,
  "message": "Obrigação removida com sucesso",
  "data": null
}

Escopo: obrigacoes:write

Schemas

ObrigacaoCreate

Estende o ObrigacaoBase adicionando id_cliente obrigatório.

CampoTipoObrigatórioObservações
id_clienteintsimCliente ao qual a obrigação está vinculada.
departamento_idint | nullnãoDepartamento responsável.
acessorias_ent_idstr | nullnãoID de origem (integração Acessórias). Máx. 64 caracteres.
nomestr | nullnãoNome da obrigação. Máx. 255 caracteres.
tipostr | nullnãoTipo da obrigação. Máx. 100 caracteres.
competenciastr | nullnãoCompetência de referência (ex: 2026-06). Máx. 20 caracteres.
protocolostr | nullnãoProtocolo de entrega. Máx. 100 caracteres.
ent_dt_prazodate | nullnãoPrazo legal de entrega.
ent_dt_prazo_tecnicodate | nullnãoPrazo técnico interno.
ent_dt_atrasodate | nullnãoData a partir da qual passa a constar como em atraso.
ent_dt_entregadate | nullnãoData efetiva de entrega.
ent_multaboolnãoIndica incidência de multa. Default false.
statusstr | nullnãoSituação da obrigação. Máx. 50 caracteres.
ent_guia_lidastr | nullnãoIndicador de leitura da guia. Máx. 100 caracteres.
ent_last_dhdatetime | nullnãoÚltimo processamento/atualização de origem.
resp_prazostr | nullnãoResponsável pelo prazo. Máx. 200 caracteres.
resp_entregastr | nullnãoResponsável pela entrega. Máx. 200 caracteres.

ObrigacaoUpdate

Todos os campos são opcionais; apenas os enviados são atualizados. Não aceita id_cliente nem legacy_uuid.

CampoTipoObservações
departamento_idint | nullDepartamento responsável.
acessorias_ent_idstr | nullID de origem. Máx. 64 caracteres.
nomestr | nullNome da obrigação. Máx. 255 caracteres.
tipostr | nullTipo da obrigação. Máx. 100 caracteres.
competenciastr | nullCompetência. Máx. 20 caracteres.
protocolostr | nullProtocolo. Máx. 100 caracteres.
ent_dt_prazodate | nullPrazo legal.
ent_dt_prazo_tecnicodate | nullPrazo técnico.
ent_dt_atrasodate | nullData de atraso.
ent_dt_entregadate | nullData de entrega.
ent_multabool | nullIncidência de multa.
statusstr | nullSituação. Máx. 50 caracteres.
ent_guia_lidastr | nullIndicador de leitura da guia. Máx. 100 caracteres.
ent_last_dhdatetime | nullÚltimo processamento de origem.
resp_prazostr | nullResponsável pelo prazo. Máx. 200 caracteres.
resp_entregastr | nullResponsável pela entrega. Máx. 200 caracteres.

ObrigacaoRead

Estende o ObrigacaoBase com os campos de identificação e auditoria.

CampoTipoNotas
idintIdentificador da obrigação.
id_clienteintCliente vinculado.
legacy_uuidstr | nullUUID de sistema legado, quando existir.
data_hora_criacaodatetimeTimestamp de criação.
data_hora_atualizacaodatetimeTimestamp da última atualização.

Além destes, retorna todos os campos do ObrigacaoBase (departamento_id, acessorias_ent_id, nome, tipo, competencia, protocolo, ent_dt_prazo, ent_dt_prazo_tecnico, ent_dt_atraso, ent_dt_entrega, ent_multa, status, ent_guia_lida, ent_last_dh, resp_prazo, resp_entrega).

ObrigacaoImportRequest

CampoTipoObrigatórioObservações
obrigacoesList[ObrigacaoImportItem]nãoLote de itens a importar. Default []. Máximo 2000 itens.

Cada ObrigacaoImportItem tem os mesmos campos do ObrigacaoBase e exige id_cliente por linha.

ObrigacaoImportResult

CampoTipoNotas
inseridosintQuantidade de obrigações novas inseridas.
atualizadosintQuantidade de obrigações existentes atualizadas.

Notas

  • Toda resposta segue o envelope { success, message, data } (ou { success: false, message, details } em erro).
  • GET /obrigacoes/{obrigacao_id} é declarado depois de GET /obrigacoes/, então a listagem estática não conflita com a rota dinâmica por ID.
  • O import em lote (POST /obrigacoes/import) faz upsert com dedup explícito por acessorias_ent_id ou pela tupla (id_cliente, nome, ent_dt_prazo, competencia), tratando NULL de forma determinística (diferente do comportamento padrão do MySQL, que trata NULL como distinto).

Limite de lote

O POST /obrigacoes/import aceita no máximo 2000 itens por requisição - limite que protege contra payloads gigantes e o consequente N+1 no upsert. Volumes maiores devem ser paginados pelo cliente.