Descrição das Tecnologias — SafeStreets
Este documento descreve as tecnologias complementares utilizadas no projeto SafeStreets, detalhando o que são, como funcionam e qual papel exercem dentro do sistema.
Nominatim
O que é
Nominatim é um serviço de geocodificação de código aberto mantido pelo projeto OpenStreetMap. Geocodificação é o processo de converter um endereço ou nome de local em coordenadas geográficas — latitude e longitude — que podem ser plotadas em um mapa.
Como funciona
O serviço recebe um texto descrevendo uma localização (como "QNL 8, Taguatinga, Brasília") e retorna as coordenadas geográficas correspondentes. Também suporta o processo inverso, chamado geocodificação reversa: recebe coordenadas e retorna o endereço correspondente.
A comunicação é feita por meio de uma API REST simples. Uma requisição de exemplo:
GET https://nominatim.openstreetmap.org/search?q=Taguatinga,+Brasília&format=json
Retorno:
[
{
"lat": "-15.8397",
"lon": "-48.0536",
"display_name": "Taguatinga, Região Administrativa III, Distrito Federal, Brasil"
}
]
Papel no SafeStreets
Após o Gemini extrair a localidade de uma notícia — por exemplo, "acidente ocorreu na EPNB próximo ao Gama" — o Nominatim converte esse texto em coordenadas geográficas. Essas coordenadas são salvas no banco de dados e usadas pelo Leaflet.js para posicionar o marcador correto no mapa.
Observações importantes
- O servidor público do Nominatim impõe um limite de 1 requisição por segundo e exige que a aplicação se identifique por meio do cabeçalho
User-Agent. - Para volumes maiores de requisições, recomenda-se implementar cache no back-end ou hospedar uma instância própria do Nominatim via Docker.
- O uso deve respeitar a política de uso do Nominatim, que proíbe o uso em aplicações de alta escala sem instância própria.
Leaflet.js
O que é
Leaflet.js é uma biblioteca JavaScript de código aberto para criação de mapas interativos em aplicações web. É amplamente utilizada em projetos que precisam exibir dados geográficos de forma visual, leve e responsiva.
Como funciona
O Leaflet renderiza mapas no navegador utilizando tiles — pequenas imagens que formam o mapa ao serem combinadas. Esses tiles são carregados de provedores externos, sendo o OpenStreetMap o mais comum e gratuito. A biblioteca permite adicionar marcadores, popups, camadas e eventos de interação diretamente sobre o mapa.
Exemplo básico de uso com React:
import { MapContainer, TileLayer, Marker, Popup } from "react-leaflet";
<MapContainer center={[-15.7801, -47.9292]} zoom={12}>
<TileLayer url="https://{s}.tile.openstreetmap.org/{z}/{x}/{y}.png" />
<Marker position={[-15.8397, -48.0536]}>
<Popup>Acidente registrado em Taguatinga</Popup>
</Marker>
</MapContainer>
Papel no SafeStreets
O Leaflet.js é a camada de visualização geográfica do projeto. Ele recebe as coordenadas salvas no banco de dados — obtidas via Nominatim — e exibe cada ocorrência como um marcador no mapa. O usuário pode interagir com os marcadores para ver detalhes da ocorrência, como tipo de crime, data e fonte da notícia.
Observações importantes
- Por acessar o objeto
windowdo navegador durante a inicialização, o Leaflet.js é incompatível com o SSR (Server-Side Rendering) do Next.js. O componente de mapa deve ser carregado comdynamic importessr: falsepara evitar erros de build. - A biblioteca
react-leafletoferece uma camada de componentes React sobre o Leaflet, facilitando a integração com o Next.js.
API do Gemini
O que é
Gemini é o modelo de linguagem de grande escala (LLM) desenvolvido pelo Google. Sua API permite que aplicações enviem textos e recebam respostas geradas por inteligência artificial, podendo realizar tarefas como análise de texto, classificação, extração de informações e geração de conteúdo.
Como funciona
A comunicação é feita por meio da biblioteca oficial google-generativeai para Python. A aplicação envia um prompt — uma instrução em linguagem natural junto com o texto a ser processado — e recebe uma resposta estruturada do modelo.
Exemplo de chamada:
import google.generativeai as genai
genai.configure(api_key="SUA_CHAVE")
model = genai.GenerativeModel("gemini-1.5-flash")
resposta = model.generate_content("""
Extraia do texto abaixo a localidade e o tipo de ocorrência.
Responda apenas em JSON.
Texto: "Homem é preso após roubo a mão armada na QNL 8, em Taguatinga."
""")
print(resposta.text)
# {"local": "QNL 8", "bairro": "Taguatinga", "tipo": "roubo"}
Papel no SafeStreets
O Gemini é o componente de inteligência do projeto. Ele recebe o título e o resumo de cada notícia coletada via RSS e extrai de forma estruturada as informações relevantes: localidade, bairro, tipo de ocorrência e se a notícia é de fato relevante para o SafeStreets. Sem essa etapa, os dados chegariam como texto livre e seria inviável posicioná-los no mapa automaticamente.
Observações importantes
- O modelo recomendado para essa tarefa é o
gemini-1.5-flash, por ser mais rápido e econômico, sendo mais do que suficiente para extração de informações de textos curtos. - O plano gratuito da API do Gemini oferece uma cota generosa de requisições mensais, adequada para a escala inicial do SafeStreets.
- As chamadas ao Gemini devem ser feitas pelo back-end (FastAPI), nunca diretamente pelo front-end, para proteger a chave de API.
RSS de Notícias
O que é
RSS (Really Simple Syndication) é um formato padrão baseado em XML que sites de notícias utilizam para distribuir seu conteúdo de forma estruturada e automática. Funciona como uma "janela" que os veículos de comunicação deixam aberta para que sistemas externos possam ler as publicações mais recentes sem precisar acessar o site manualmente.
Como funciona
Cada veículo mantém um arquivo RSS em uma URL fixa. Esse arquivo é atualizado automaticamente a cada nova publicação e contém os dados estruturados das notícias mais recentes: título, resumo, link e data de publicação.
Exemplo de estrutura de um item RSS:
<item>
<title>Homem é preso após roubo em Taguatinga</title>
<description>A PMDF deteve o suspeito na QNL 8 após denúncia de moradores da região.</description>
<link>https://metropoles.com/noticia/...</link>
<pubDate>Fri, 22 May 2026 14:30:00 GMT</pubDate>
</item>
No SafeStreets, a leitura dos feeds é feita com a biblioteca Python feedparser, que converte o XML do RSS em dicionários Python prontos para uso:
import feedparser
feed = feedparser.parse("https://www.metropoles.com/distrito-federal/seguranca-df/feed")
for noticia in feed.entries:
print(noticia.title)
print(noticia.summary)
print(noticia.link)
Fontes utilizadas no SafeStreets
| Veículo | URL do Feed | Cobertura |
|---|---|---|
| Metrópoles — Segurança DF | https://www.metropoles.com/distrito-federal/seguranca-df/feed |
Crimes e ocorrências policiais no DF |
| Correio Braziliense — Cidades DF | https://www.correiobraziliense.com.br/cidades-df/feed |
Notícias gerais do DF, incluindo acidentes e crimes |
Papel no SafeStreets
Os feeds RSS são a fonte primária de dados do SafeStreets. O back-end coleta automaticamente as notícias publicadas nesses veículos em intervalos regulares, sem necessidade de acesso manual ao site. O conteúdo coletado é então enviado ao Gemini para extração de localidade e tipo de ocorrência, dando início ao fluxo de processamento que culmina na exibição do dado no mapa.
Observações importantes
- O RSS entrega título e resumo, mas não o corpo completo da matéria. Na maioria dos casos, essas informações são suficientes para identificar a localidade e o tipo de ocorrência.
- O uso de feeds RSS é público e gratuito. No entanto, o conteúdo das notícias pertence aos veículos de comunicação e não deve ser reproduzido integralmente. O SafeStreets utiliza apenas os metadados para processamento interno, sem armazenar ou exibir o texto original das matérias.
- A coleta periódica deve ser implementada com
APSchedulerno back-end, garantindo que novos dados sejam processados automaticamente sem intervenção manual.
Fluxo integrado das tecnologias
As quatro tecnologias descritas neste documento atuam em sequência dentro do SafeStreets:
RSS de Notícias → coleta título e resumo das ocorrências
↓
API do Gemini → extrai localidade e tipo de ocorrência do texto
↓
Nominatim → converte o endereço em coordenadas geográficas
↓
Leaflet.js → exibe o marcador no mapa com os detalhes da ocorrência
Cada tecnologia resolve uma etapa específica do problema, e juntas formam o pipeline central de inteligência e visualização do projeto.