Pular para o conteúdo principal

Tratamento do retorno da Receita Federal

API do validador Educacenso (app censo) para outro sistema (ex.: o educacao) tratar o retorno do INEP e obter as divergências da Receita Federal (o dado enviado e o dado correto que o INEP informou).

Escopo intencionalmente estreito: estas rotas não validam o arquivo inteiro. Elas olham somente as mensagens do retorno que citam explicitamente a Receita Federal — as que trazem o conteúdo no formato valor enviado -- valor correto.

Duas rotas

RotaEnviaRecebeQuando usar
POST /api/divergencias-rfsó o retorno (JSON/XLSX)divergências cruas por campo, com codigo_na_escolaRecomendada. Dispensa o TXT; a pessoa é casada pelo codigo_na_escola (estável entre versões). É o fluxo usado pelo educacao.
POST /api/retorno-rfretorno + txtuma pessoa por registro, já mescladaVariante que monta o registro completo mesclando com o TXT. Requer o mesmo TXT enviado ao INEP.

Por que a divergencias-rf é preferível. A retorno-rf casa a pessoa pela linha do TXT — que muda se o aviso for importado noutra versão do arquivo, gerando divergências erradas. A divergencias-rf usa o codigo_na_escola (coluna do próprio retorno do INEP), que é o identificador estável da pessoa na origem (no educacao, o pessoa_id).


POST /api/divergencias-rf (recomendada)

Recebe apenas o retorno do INEP e devolve as divergências da Receita Federal cruas — o valor enviado e o correto, por campo, com o codigo_na_escola para o consumidor localizar a pessoa.

  • Base URL / Auth / Content-Type: iguais aos da /api/retorno-rf (ver abaixo, incluindo o aviso do Cloudflare Access).

Parâmetros (form-data)

CampoTipoObrigatórioDescrição
retornofilesimRetorno do INEP em .json ou .xlsx. Não envie o TXT.

Resposta

200 OK, application/json:

{
"divergencias": [
{
"codigo_na_escola": "328229",
"linha": "28",
"campo": "Data de nascimento",
"enviado": "07/02/1960",
"correto": "07/03/1960",
"is_filiacao": false,
"chave": "data_nascimento"
}
]
}
CampoSignificado
codigo_na_escolaColuna "Código na Escola" do retorno — o identificador estável da pessoa na origem (no educacao, é o pessoa_id/Person). É a chave para localizar a pessoa, e não a linha.
linhaLinha do TXT (registro 30). Só referência — não use para casar a pessoa.
campoNome do campo como o INEP rotulou no retorno.
enviadoValor que você mandou (lado esquerdo de enviado -- correto).
corretoValor da base da Receita (lado direito).
is_filiacaotrue quando a divergência é de filiação (nome da mãe/pai).
chaveColuna de destino no consumidor: cpf/nome/data_nascimento/inep para os campos comuns; nome_mae/nome_pai para filiação (o INEP costuma rotular filiação como "Identificação única (Inep)" — a API resolve mãe×pai pela mensagem); null para campo não mapeado.

Exemplo — cURL

curl -sS -X POST \
-H "x-api-key: $API_KEY" \
-F "retorno=@Retorno_INEP.xlsx" \
https://validador-educacenso-27c68db3d752.herokuapp.com/api/divergencias-rf

Integração no educacao. O botão "Tratar retorno RF" sobe só o retorno do INEP; a action BuscarRetornoRf chama esta rota e carimba as colunas *_rf da Person localizada por codigo_na_escola (via chave → coluna), que então aparece em Divergências no Educacenso.


POST /api/retorno-rf (mescla com o TXT)

Envia o retorno do INEP + o TXT do Educacenso e recebe, já mescladas por pessoa, as divergências da Receita Federal.

Endpoint

POST /api/retorno-rf
  • Base URL (produção): https://validador-educacenso-27c68db3d752.herokuapp.com (URL direta do Heroku — ver aviso sobre Cloudflare abaixo).
  • Autenticação: header x-api-key: <API_KEY> (token compartilhado).
  • Content-Type: multipart/form-data.

Atenção — Cloudflare Access. O domínio bonito https://validador-educacenso.appolus.com.br está atrás do Cloudflare Access na borda, que redireciona /api/* para uma tela de login (HTTP 302) — ou seja, um sistema externo não consegue chamá-lo por ali. Duas opções:

  1. Usar a URL direta do Heroku (recomendado agora): https://validador-educacenso-27c68db3d752.herokuapp.com/api/retorno-rf. O app libera /api/* no seu próprio guard de Access e exige só o token.
  2. Liberar /api/* no Cloudflare Access (bypass policy ou service token) para poder usar o domínio appolus.com.br. Isso é configuração de infra, fora do código.

Parâmetros (form-data)

CampoTipoObrigatórioDescrição
retornofilesimRetorno do INEP em .json ou .xlsx.
txtfilesimTXT do Educacenso (o mesmo arquivo enviado ao INEP). É de onde saem nome_mae, inep e os campos sem divergência.
HeaderValor
x-api-keyO token configurado na env API_KEY do app censo.

Resposta

200 OK, application/json:

{
"pessoas": [
{
"cpf": "11122233344",
"nome": "FULANO DE TAL DA SILVA",
"data_nascimento": "15/03/2010",
"nome_mae": "BELTRANA DE TAL DA SILVA",
"inep": "123456789012"
}
]
}
  • Uma entrada por pessoa (cada registro 30 do TXT) que tenha ao menos uma divergência da Receita Federal.
  • data_nascimento no formato dd/mm/yyyy (o mesmo do TXT/retorno).

Regra de preenchimento de cada campo

Para cada campo o valor é o que consta no TXT, exceto quando aquele campo tem uma divergência da Receita Federal — aí usa-se o valor correto (lado direito de enviado -- correto). As correções de várias linhas do retorno para a mesma pessoa são mescladas num único objeto.

Campo de saídaOrigem
cpfTXT (campo 5) ou valor correto da RF se divergiu
nomeTXT (campo 6) ou valor correto da RF se divergiu
data_nascimentoTXT (campo 7) ou valor correto da RF se divergiu
inepTXT (campo 4) ou valor correto da RF se divergiu
nome_maesempre TXT (campo 9 — Filiação 1). Nunca é corrigido.

Exemplo: se um aluno tem 3 linhas no retorno (CPF divergente, data de nascimento divergente e INEP divergente), sai 1 objeto só, com esses três campos já com o valor correto e os demais (inclusive nome_mae) com o valor original do TXT.

Como uma divergência da Receita é reconhecida

Uma mensagem do retorno entra no cálculo quando:

  1. É do registro 30 (pessoa física); e
  2. A mensagem cita "Receita Federal" (ex.: "O campo não está de acordo com a base da Receita Federal."); e
  3. O conteúdo do campo vem como enviado -- correto (ex.: FULANO DE TAL DA SILVA OLIVEIRA -- FULANO DE TAL DA SILVA).

O campo corrigido é identificado pelo nome do campo informado no retorno (Número do CPFcpf, Nome completonome, Data de nascimentodata_nascimento, Identificação única (Inep)inep). Divergências de filiação não corrigem nome_mae.


Erros

HTTPQuandoCorpo
400Falta retorno ou txt, extensão inválida, ou arquivo ilegível{"erro": "..."}
401x-api-key ausente ou incorreto{"erro": "Credencial inválida (header x-api-key)."}
503App sem API_KEY configurada{"erro": "API não configurada (defina a env API_KEY)."}

Configuração (app censo)

Defina a env no Heroku:

heroku config:set API_KEY="<token-forte>" -a validador-educacenso

Sem API_KEY a rota responde 503 (fail-closed).


Exemplo — cURL

curl -sS -X POST \
-H "x-api-key: $API_KEY" \
-F "retorno=@Retorno_INEP.xlsx" \
-F "txt=@educacenso_escola.txt" \
https://validador-educacenso.appolus.com.br/api/retorno-rf

Exemplo — Ruby (Faraday, multipart)

conn = Faraday.new(url: base_url) { |f| f.request :multipart }
resp = conn.post("/api/retorno-rf") do |req|
req.headers["x-api-key"] = api_key
req.body = {
"retorno" => Faraday::Multipart::FilePart.new(retorno_io, "application/octet-stream", "retorno.xlsx"),
"txt" => Faraday::Multipart::FilePart.new(txt_io, "text/plain", "educacenso.txt"),
}
end
pessoas = JSON.parse(resp.body)["pessoas"]

Notas de implementação

  • Código: censo/retorno_rf.pyextrair_divergencias (cruas, só retorno) e extrair_pessoas (merge com TXT); rotas api_divergencias_rf e api_retorno_rf em app.py.
  • Reaproveita o parser do retorno (censo/retorno.py) e do TXT (censo/parser.py).
  • Testes: tests/test_api_retorno_rf.py.
  • Consumidor no educacao: app/actions/buscar_retorno_rf.rb (usa /api/divergencias-rf).
  • Limite de upload do app: 25 MB (MAX_CONTENT_LENGTH).