Skip to content

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

4 Commits
 
 
 
 
 
 
 
 

Repository files navigation

openaudit-search-api

API de busca do OpenAudit Brasil. Responsável por receber uma consulta textual, normalizar o termo e retornar uma lista de possíveis entidades (ex.: políticos) a partir de um catálogo canônico, com confidence e explanation para desambiguação humana.

Importante: esta API não executa cruzamento de fontes, não calcula indicadores e não produz conclusões.
Ela apenas resolve "quem o usuário quis dizer" e devolve candidatos para seleção.


Índice


Objetivo

  • Fornecer uma API rápida e previsível para busca por nome/termo e retorno de candidatos (entity_id) com desambiguação.
  • Garantir que a fase de "resolver entidade" seja:
    • auditável (versão do catálogo e explicação do match)
    • conservadora (sem auto-seleção)
    • segura (sem PII desnecessária; sem logs sensíveis)

Escopo

Inclui

  • Normalização de query (q) e geração de query_hash.
  • Consulta ao Entity Catalog (local/embutido ou via storage/index).
  • Ranking de candidatos por score de match.
  • Retorno de:
    • entity_id canônico
    • metadados públicos mínimos (UF, cargo, período)
    • match.confidence e match.explanation
    • catalog_source e catalog_version

Não inclui

  • Consultar múltiplas fontes públicas (conectores).
  • Transformar dados de outras bases.
  • Cruzar dados e identificar padrões/anomalias.
  • Qualquer linguagem acusatória, classificação moral ou "suspeição".

Princípios e segurança

  • Neutralidade: a API só retorna candidatos. Não interpreta condutas.
  • Minimização: não persiste nem loga termos sensíveis por padrão.
  • PII: busca por CPF não é objetivo do MVP. Se existir no futuro, deve ser local-only e sem persistência.
  • Anti-enumeração: aplicar rate limit e limites de paginação.
  • Auditabilidade: toda resposta deve informar catalog_version (e idealmente catalog_snapshot_id).

Referências do projeto:


Arquitetura (alto nível)

Fluxo:

  1. Recebe q
  2. Normaliza q (casefold, remoção de acentos, tokenização)
  3. Gera query_hash (não reversível)
  4. Consulta índice/catálogo
  5. Calcula score e confidence
  6. Retorna lista de candidatos com explanation

Componentes:

  • SearchController — HTTP
  • QueryNormalizer — normalização
  • CatalogClient — acesso ao catálogo (Parquet/DuckDB/SQLite/FTS)
  • Matcher — scoring e explicação
  • Cache — opcional (curto TTL)
  • Observability — logs estruturados sem PII

Endpoints

GET /health

Retorna status simples para readiness/liveness.

200

{ "status": "ok" }

GET /search

Retorna lista de candidatos para desambiguação humana.

Query params

  • q (string) — obrigatório
  • limit (number) — opcional (default: 10, max: 25)
  • offset (number) — opcional (default: 0)

Resposta

  • query.normalized (string)
  • query.hash (string)
  • catalog.version (string)
  • candidates[] (array)

Contrato de resposta (exemplo)

{
  "query": {
    "raw": "João Silva",
    "normalized": "joao silva",
    "hash": "sha256:6f3c... (hash do normalized)"
  },
  "catalog": {
    "name": "entity-catalog",
    "version": "2026-02-28",
    "snapshot_id": "cat:2026-02-28T03:00:00Z",
    "source": "TSE"
  },
  "candidates": [
    {
      "entity_id": "tse:SQ_CANDIDATO:123",
      "display_name": "JOÃO DA SILVA",
      "context": {
        "uf": "SP",
        "cargo": "DEPUTADO FEDERAL",
        "ano": 2022
      },
      "match": {
        "confidence": 0.82,
        "explanation": [
          "nome_normalizado ~= 'joao silva'",
          "UF = SP",
          "cargo = DEPUTADO FEDERAL",
          "ano = 2022"
        ]
      }
    }
  ]
}

Regras

  • confidence deve ser numérico e interpretável (0–1 ou 0–100).
  • explanation deve listar sinais usados no match (sem "mágica").
  • A API nunca deve "auto-selecionar" a entidade.

Cache

Cache recomendado apenas para acelerar buscas repetidas em curto período.

  • Cache key: sha256(normalized_q + catalog_version + limit + offset)
  • TTL: 60–300s (curto)
  • O cache não deve armazenar PII nem logar q bruto.

Se houver cache, o header deve indicar:

  • X-Cache: HIT|MISS
  • X-Catalog-Version: ...

Observabilidade

Logs devem ser estruturados e sem PII por padrão.

Campos recomendados por request:

  • request_id
  • query_hash
  • normalized_len
  • limit, offset
  • catalog_version
  • latency_ms
  • result_count
  • cache_hit

OpenTelemetry é opcional no MVP, mas o request_id deve existir desde o início.


Configuração

Exemplo de variáveis:

PORT=3001

# catálogo
CATALOG_PATH=./data/catalog.duckdb
CATALOG_VERSION=2026-02-28

# cache
CACHE_ENABLED=true
CACHE_TTL_SECONDS=120

# rate limit
RATE_LIMIT_ENABLED=true
RATE_LIMIT_WINDOW_SECONDS=60
RATE_LIMIT_MAX_REQUESTS=60

# logs
LOG_LEVEL=info
LOG_REDACT_PII=true

Execução local

Stack do projeto NodeJS.

# instalar
npm install

# dev
npm run dev

# build
npm run build

# start
npm run start

Execução com Docker

Pré-requisitos

Crie a pasta data/ na raiz do projeto e adicione os arquivos de catálogo:

data/
├── catalog.sqlite        # ou catalog.duckdb
└── catalog_meta.json

⚠️ Os arquivos de catálogo não são incluídos na imagem Docker.
O container não iniciará se o diretório data/ estiver vazio.

Subir com Docker Compose

docker compose up

A API estará disponível em: http://localhost:3001

Verificar se está rodando

curl http://localhost:3001/health
# Esperado: { "status": "ok" }

Configurar caminho do catálogo

Edite a variável CATALOG_PATH no docker-compose.yml conforme o formato do seu catálogo:

environment:
  CATALOG_PATH: /app/data/catalog.duckdb  # ou catalog.sqlite

Build manual da imagem

docker build -t openaudit-search-api .

docker run -p 3001:3001 \
  -v ./data:/app/data:ro \
  openaudit-search-api

Testes

Cenários Cobertos:

  • unit tests para QueryNormalizer e Matcher
  • fixtures sintéticas (não usar pessoas reais)
  • testes de performance (latência do /search)
npm test

Boas práticas para contribuição

  • Propostas relevantes devem abrir issue primeiro.
  • Não adicionar dados pessoais em exemplos, fixtures ou logs.
  • Qualquer mudança que altere o comportamento de match precisa:
    • atualizar explicação
    • adicionar testes de regressão
    • registrar decisão (quando aplicável)

Licença

Consulte LICENSE na organização.

About

API de busca do OpenAudit Brasil. Responsável por receber uma consulta textual, normalizar o termo e retornar uma lista de possíveis entidades (ex.: políticos) a partir de um catálogo canônico, com confidence e explanation para desambiguação humana.

Topics

Resources

Stars

Watchers

Forks

Releases

Packages

Contributors

Languages