corrigido
USP virava 2 depositantes, EMBRAPA virava 5. Corrigido agrupando pela raiz do CNPJ (8 dígitos).
Pipeline de dados de patentes do INPI — depósito, publicação, despachos e anuidades — tratado e normalizado para responder perguntas de BI sobre tramitação processual. Recorte atual: pedidos depositados nos últimos 3 anos, sem filtro de depositante ou IPC.
Testado antes de escrever qualquer pipeline: o que o portal de dados abertos cobre, e se a extranet permite automação.
Últimos 3 anos por data de depósito (2023-08-12 a 2026-08-12), sem filtro de depositante ou IPC — recorte exploratório antes de restringir por negócio.
Reescrito via Selenium replicando o fluxo de clique real (busca → resultado → modal de anuidades) — a causa do "endpoint vazio" nunca foi bot detection, era o servidor só liberar o detalhe depois da busca ser submetida naquela sessão. Último lote: 50/50 processos, 0 erros, ~22s/processo, sem degradação ao longo do lote.
CodPedido é o codigo_interno dos dados abertos, mas numero_pedido (o que se digita na busca) é outro campo — precisa dos dois.Download dos 9 CSVs de dados abertos (~1,9 GB), filtro pelo recorte via semi-join por codigo_interno, montagem do modelo estrela.
Depositante resolvido por raiz de CNPJ (8 dígitos, agrupa filiais) quando disponível; senão por nome normalizado (acento + pontuação removidos).
dim_processo, dim_depositante, fato_processo_depositante, fato_despacho e agora fato_anuidade (166 processos) prontos em data/gold/, mais um banco DuckDB persistente (inpi.duckdb) com views e macros parametrizadas.
Docker Desktop instalado (via winget, sem reiniciar), Airflow 3.3.1 rodando via docker-compose com LocalExecutor. DAG completo (download → bronze → silver → gold → validate) testado ao vivo — passou ponta a ponta em ~16s.
Dois painéis calculam ao vivo, em JavaScript puro no navegador (sem backend): "tempo entre despacho X e Y" (com filtro opcional de depositante) e "quantos casos do depositante F tiveram despacho Z na janela T" — pra qualquer código/nome/data, não só exemplos fixos. Dados de despacho (128k linhas) e vínculo processo-depositante (246k linhas) embutidos na página.
USP virava 2 depositantes, EMBRAPA virava 5. Corrigido agrupando pela raiz do CNPJ (8 dígitos).
8.873 empresas estrangeiras diferentes colapsaram num único depositante fictício de 29 mil processos. Corrigido: só dígitos puros contam como identificador.
INSERM (instituto francês) aparecia como 3 depositantes por variação de encoding no nome. Corrigido com normalização de acento e pontuação.
WHERE NOT sigiloso filtrava a tabela inteira — NULL não é TRUE em SQL de três valores. Corrigido com coalesce(..., false).
As views de tempo/contagem agrupam por depositante — somar qtd_processos pra achar um total geral conta processos com múltiplos depositantes várias vezes. 7.1→9.2 tinha sido reportado como 1.284 processos; o real (por codigo_interno) é 282. Corrigido com macros que contam por processo.
Testado requests, Playwright (headless/headed/anti-detecção) e undetected-chromedriver — todos vazios. Causa real: o servidor só libera Action=detail depois da busca ser submetida naquela sessão. Resolvido replicando o fluxo de clique completo via Selenium comum.
166 de 56.329 (0,3%) até agora, ritmo confiável (~22s/processo, 0 erros no último lote de 50). Rodar em lotes ao longo dos próximos dias, não um batch único de ~2 semanas.
4 registros vieram com status "Tipo: Anuidade" em vez do status real — bug pontual de parsing a rastrear em process_detail.py.
Publicado fora do claude.ai (Cloudflare Pages) e no artifact. Considerar Metabase de verdade se as perguntas ad-hoc crescerem além do que os dois painéis cobrem.