turicas / brasil.io

Backend do Brasil.IO (para código dos scripts de coleta de dados, veja o link na página de cada dataset)
https://brasil.io/
GNU General Public License v3.0
921 stars 145 forks source link

Bug em filtro de campos ofuscados #500

Open turicas opened 3 years ago

turicas commented 3 years ago

O Brasil.IO ofusca parte dos dados que publica, com o objetivo de proteger a privacidade de pessoas eventualmente descritas em nossos datasets. Exemplos:

No primeiro exemplo acima a ofuscação dos dados é feita durante a conversão dos dados, ou seja, no script que baixa e converte os dados da Receita Federal. Já no segundo exemplo, a ofuscação acontece na hora de servir os dados pelo backend do Brasil.IO, porque precisamos do dado completo na nossa base para fazer alguns cruzamentos (exemplo: identificar todas as candidaturas dessa pessoa) - isso é necessário pois a versão ofuscada desse dado pode aparecer também para outras pessoas e gerar ambiguidades.

O problema relatado nessa issue é relativo ao segundo exemplo, ou seja: o dado está completo em nossa base e ofuscamos na hora de serví-lo (seja via interface ou via API).

Se um determinado Field (core.models.Field) tem o campo obfuscate como True, ele não será exibido integralmente (exemplo: o cpf 12345678901 seria exibido como ***456789**). Porém, se esse Field possui o campo frontend_filter como True, o usuário do site e da API poderá filtrar os registros por esse campo e, aí, temos 2 possíveis cenários:

Hoje apenas o cenário B funcionará, dado que o filtro da query-string ignora se o Field é ofuscado ou não e faz a consulta equivalente a algo como: X.objects.filter(fieldname="12345678901") (onde X é o model criado dinamicamente para a tabela com os dados).

Para contornar esse problema, precisamos:

turicas commented 3 years ago

Acabei de encontrar um outro problema que não ficou descrito acima: considerei que se uma coluna está ofuscada, todos os registros da tabela estarão e, caso ela não esteja, nenhum registro estará. Acontece que em alguns datasets alguns campos são ofuscados diretamente na fonte de dados (e não temos acesso ao dado completo em nosso backend), porém nem todos os registros são ofuscados.

Essa ofuscação parcial acontece com a coluna cpf_cnpj_socio da tabela socio do dataset socios-brasil: para os casos em que o sócio descrito é uma empresa, o campo aparece com o CNPJ completo (ou seja, sem ofuscação), já no caso de uma pessoa física, o CPF já vem ofuscado da fonte. Nesse caso, para corrigir o problema no cenário A, precisaríamos fazer uma busca OR: .filter(Q(campo=valor) | Q(campo__contains=valor.replace("*", ""))) (lembrando que idealmente deveríamos usar substring em vez de contains).