DEV Community

Cover image for Python + OpenSearch: O Guia Definitivo de Mapeamento e Governança de Dados 🛡️
Francisco Júnior
Francisco Júnior

Posted on

Python + OpenSearch: O Guia Definitivo de Mapeamento e Governança de Dados 🛡️

Se você trabalha com Análise de Dados, Business Intelligence ou Melhoria de Processos, sabe que a regra de ouro de qualquer arquitetura é: lixo que entra, é lixo que sai (Garbage In, Garbage Out).

Nos artigos anteriores, vimos como o OpenSearch é incrível para buscas rápidas e criação de dashboards em tempo real. Nós simplesmente jogamos um dicionário Python (JSON) lá dentro e ele aceitou. Isso se chama Dynamic Mapping (Mapeamento Dinâmico).

É ótimo para testes rápidos no seu terminal (usando Zsh ou Fish, por exemplo), mas em produção, deixar o banco adivinhar o tipo do seu dado é um pesadelo de Governança de Dados. O campo que deveria ser um número inteiro (integer) de repente vira um texto (text) só porque um erro na sua aplicação enviou "100" em vez de 100. E adeus métricas precisas no seu dashboard!

Hoje, vamos aprender a criar um contrato de dados rigoroso usando Mappings no OpenSearch antes de injetar qualquer coisa com Python.

O que é o Mapping no OpenSearch?

Se você vem do mundo do SQL (como PostgreSQL) ou de Data Warehouses (como BigQuery), você está acostumado a rodar um CREATE TABLE definindo colunas e tipos (VARCHAR, INT, TIMESTAMP).

No OpenSearch, o equivalente ao Schema da tabela é o Mapping. É ele que diz ao motor de busca:

  • Quais campos existem no documento.
  • Qual é o tipo de dado de cada campo (ex: texto livre, palavra-chave exata, número, data).
  • Como esses campos devem ser indexados para a busca.

A Diferença Crucial: Text vs Keyword 🔍

Antes de irmos para o código, você precisa entender a diferença entre os dois principais tipos de string no OpenSearch, pois isso afeta diretamente o Business Intelligence:

  1. Text: Usado para texto longo (descrições, e-mails, logs extensos). O OpenSearch "quebra" esse texto em palavras separadas. Se o campo tiver "Analista de Dados", você consegue buscar apenas por "Dados". Não serve para agregações ou gráficos de pizza.
  2. Keyword: Usado para valores exatos (IDs, status, categorias, e-mails exatos). Ele salva a string inteira como um bloco só. É obrigatório usar keyword se você quiser fazer filtros estritos ou montar gráficos e dashboards.

Passo 1: Definindo o Contrato (Governança na Prática) 📜

Vamos imaginar que estamos criando um índice para monitorar a Melhoria de Processos da empresa. Queremos garantir que os dados entrem perfeitamente tipados.

Vamos usar o uv e o Python para criar esse índice com um Mapping explícito.

from opensearchpy import OpenSearch

# Conectando ao cluster (assumindo que já está rodando via contêiner/OrbStack)
cliente = OpenSearch(
    hosts=[{'host': 'localhost', 'port': 9200}],
    use_ssl=False,
    verify_certs=False
)

nome_indice = 'processos_governados_v1'

# Aqui está a nossa Governança de Dados: O Mapping!
mapeamento = {
    "mappings": {
        "properties": {
            # Keyword: Perfeito para IDs e filtros exatos
            "processo_id": {
                "type": "keyword"
            },
            # Text + Keyword: Queremos buscar parte do nome, mas também agrupar em gráficos!
            "analista_responsavel": {
                "type": "text",
                "fields": {
                    "exato": {
                        "type": "keyword"
                    }
                }
            },
            # Integer: Para calcularmos médias de tempo depois no BI
            "tempo_execucao_ms": {
                "type": "integer"
            },
            # Date: O formato ISO8601 é o padrão ouro
            "data_execucao": {
                "type": "date",
                "format": "strict_date_optional_time||epoch_millis"
            },
            # Boolean: Apenas true ou false
            "sucesso": {
                "type": "boolean"
            }
        }
    }
}

# Criando o índice COM o mapeamento definido
if not cliente.indices.exists(index=nome_indice):
    cliente.indices.create(index=nome_indice, body=mapeamento)
    print(f"✅ Índice '{nome_indice}' criado com regras estritas de Governança!")
else:
    print(f"⚠️ O índice '{nome_indice}' já existe.")

Enter fullscreen mode Exit fullscreen mode

Passo 2: Testando a Injeção de Dados 🧪

Agora que temos um contrato, o OpenSearch vai nos ajudar a manter a qualidade dos dados. Vamos tentar inserir dois documentos: um correto e um "sujo".

from datetime import datetime

# 1. Dado Correto (Vai passar liso)
dado_limpo = {
    "processo_id": "PROC-2026-001",
    "analista_responsavel": "Francisco",
    "tempo_execucao_ms": 1450,
    "data_execucao": datetime.utcnow().isoformat(),
    "sucesso": True
}

cliente.index(index=nome_indice, body=dado_limpo, refresh=True)
print("✅ Dado limpo indexado com sucesso!")

# 2. Dado Sujo (Vai forçar um erro de Governança)
dado_sujo = {
    "processo_id": "PROC-2026-002",
    "analista_responsavel": "Larissa",
    "tempo_execucao_ms": "quatrocentos", # ERRO INTENCIONAL: Enviando texto no lugar de número
    "data_execucao": datetime.utcnow().isoformat(),
    "sucesso": True
}

try:
    cliente.index(index=nome_indice, body=dado_sujo)
except Exception as e:
    print("\n❌ ERRO DE GOVERNANÇA DETECTADO PELO OPENSEARCH:")
    print("O motor rejeitou o documento porque o tipo do dado estava errado.")
    # Isso impede que o seu dashboard quebre no futuro!

Enter fullscreen mode Exit fullscreen mode

Passo 3: O Poder do Campo "Multi-field" no BI 📊

Note que no nosso mapeamento, o campo analista_responsavel foi definido como text, mas ganhou um subcampo chamado exato do tipo keyword. Essa é a técnica mais poderosa para quem trabalha com dados!

Na hora de fazer buscas livres no Python (para encontrar qualquer log do Francisco, por exemplo), você busca assim:
analista_responsavel: "Francisco"

Mas, na hora de ir para o OpenSearch Dashboards criar um gráfico de barras com a volumetria de processos por analista, você vai apontar o eixo X do seu gráfico para:
analista_responsavel.exato

Isso garante que o nome não seja fatiado e as agregações do seu Business Intelligence sejam 100% precisas.

Conclusão

Governança de dados não é apenas sobre ter regras chatas, é sobre confiabilidade. Ao definir o mapeamento (Mapping) no OpenSearch antes de começar a injetar dados com seus scripts em Python, você garante que as métricas que chegam à diretoria ou aos times operacionais sejam sempre precisas, tipadas corretamente e prontas para análise em tempo real.

O mapeamento dinâmico é legal para protótipos, mas Mapeamento Explícito é a marca de um profissional de dados sênior.


Você costuma definir esquemas estritos nos seus bancos de dados NoSQL ou prefere deixar tudo dinâmico? Conta aí nos comentários!

Top comments (0)