OMNI-PROD
Documentação do Sistema
Plataforma web para gestão de contratos de telecom — calculadora de reajustes, conciliação financeira VIVO/CLARO, extração automática de PDFs e base cadastral de contratos.
O que é o OMNI-PROD?
Uma visão direta e objetiva do sistema — ideal para novos usuários ou gestores.
O OMNI-PROD é o sistema web interno da Sites Latam para gestão financeira de contratos de telecom. Roda localmente via Python/FastAPI e é acessado pelo navegador em omni.cobra.ninja.
Calculadora de Reajustes
Calcula reajustes contratuais aplicando índices IPCA, IGP-M ou INPC com múltiplos períodos, exceções e visão mensal/anual. Exporta Excel com memória de cálculo.
Conciliação VIVO
Cruza automaticamente o extrato SAP (FBL5N) com a Composição de Pagamento VIVO. Gera Excel com status de baixa linha a linha e resumo gráfico consolidado.
Conciliação CLARO
Mesmo fluxo da VIVO, adaptado para o padrão CLARO. Usa normalização inteligente de colunas (Raio-X) e match em cascata em 2 níveis para cobrir divergências.
Robot — Extração de PDFs
Lê PDFs de contratos e extrai automaticamente valor mensal, índice, vigência, dados do locador e cláusulas financeiras. Gera planilha com score de confiança por arquivo.
Database
Cadastro mestre de contratos (De-Para Financeiro). Gerencia siglas VIVO e CLARO, dados de OCR por ID TBSA, auditoria completa de ações e lookup para a calculadora.
Administração
Gestão completa de usuários: criar, bloquear, resetar senha e excluir. Controle de acesso em 3 perfis: admin, analista e cliente.
Perfis de Acesso
Admin — acesso total. Analista — calculadora, conciliação, database, robot. Cliente — visualização das próprias análises (inputs congelados).
Fluxo típico de uso — Conciliação
Como acessar o sistema
& "C:\Users\LucasGomesMoura\anaconda3\python.exe" -m uvicorn main:app --reload --use-colors a partir do diretório do projeto. Acesse em http://localhost:8000.Stack Técnica
Tecnologias usadas em cada camada do sistema.
FastAPI
Framework backend — rotas REST + SSE
SQLAlchemy
ORM + gerenciamento de conexões MySQL
MySQL (PyMySQL)
Banco de dados — db_pythonExtract_mysql
Pandas
Normalização e cruzamento de dados Excel
openpyxl
Leitura de arquivos Excel (.xlsx)
xlsxwriter
Geração do Excel de resultado com gráficos
Vanilla JS
Frontend SPA (fetch API + EventSource SSE)
Outfit® / Brand
Tipografia única — Manual de Marca 2022
Uvicorn
Servidor ASGI — execução local (Anaconda)
pdfplumber
Extração de texto nativo de PDFs (Robot Manual)
Identidade Visual — Variáveis CSS obrigatórias
Arquitetura do Sistema
Estrutura de arquivos e responsabilidade de cada componente.
| Arquivo | Responsabilidade | Tamanho |
|---|---|---|
main.py |
Entrypoint FastAPI — 29 rotas (auth, análises, índices, admin, conciliação). Configura CORS, SSE e serve arquivos estáticos. | ~527 linhas |
database.py |
Engine SQLAlchemy com MySQL (pool_pre_ping=True, pool_recycle=3600s, base=5, overflow=10). Factory de sessão get_db(). |
~40 linhas |
models.py |
11 modelos ORM ativos: Usuario, IndiceFinanceiro, Analise, DadoRobo, LogAcesso, DeparaFinanceiro, SiglasVivo, SiglasClaro, LogBaseTotal, HistoricoConciliacao. Legado mantido temporariamente: DimBaseTotal, MapVivo, MapClaro. |
~230 linhas |
routers/base_total.py |
20 rotas para CRUD de DIM/VIVO/CLARO, importação em lote otimizada, logs de auditoria e lookup para a calculadora. | ~761 linhas |
routers/conciliacao_vivo.py |
Robô VIVO — 9 etapas de processamento: leitura, normalização, match Seguro (ID+Sigla+Mês) + Flexível (valor ±0.05), geração Excel com 7 abas. | ~594 linhas |
routers/conciliacao_claro.py |
Robô CLARO — 9 etapas: Raio-X de colunas, match em cascata (Macro→Micro→Salva-vidas), geração Excel com 8 abas. | ~755 linhas |
routers/robot_manual.py |
Módulo Robot — processamento paralelo de PDFs, SSE de progresso, histórico por sessão, re-exportação Excel. | ~400 linhas |
Robov22/extractor.py |
Core de extração de PDFs via regex — reutilizado pelo Robot Manual. NÃO alterar sem alinhar com robot_manual.py. | ~600 linhas |
index.html |
SPA completa — 8 views, 100+ funções JS, sistema de autenticação, upload de arquivos, progresso SSE, tabelas paginadas, modais e drawers. | ~256 KB |
.env |
Credenciais do banco MySQL (não versionado). DATABASE_URL e configurações de ambiente. | — |
Fluxo de requisição completo
(index.html)
(main.py)
específico
ORM
db_pythonExtract
Tabelas e Modelos
Estrutura completa do banco MySQL — modelos ORM definidos em models.py.
depara_financeiro é a base única de cruzamento para VIVO e CLARO. As tabelas legadas dim_base_total, map_vivo e map_claro permanecem no banco por compatibilidade mas não são mais utilizadas pelos robôs.Tabelas do sistema
person usuarios — Autenticação e perfis
admin | analista | clientetrending_up indices_financeiros — IPCA, IGP-M, INPC
IPCA | IGP-M | INPC | IGP-DI | IPCA-E | IPC-BRASIL | IPC-SPYYYY-MM (ex: 2024-01)POST /api/sincronizar-indices. Usado pela calculadora para calcular acumulados de 12 meses.folder_open analises — Memórias de cálculo salvas
Tabelas — Data Base
hub depara_financeiro — Tabela mestra única de cruzamento
contrato_re_cliente (RE da VIVO na Composição). CLARO filtra por sub_grupo = 'CLARO' e cruza por contrato_re_cliente.CLARO, VIVO)swap_horiz siglas_vivo + siglas_claro — De-Para de tipos (editável)
RJ, RH, RF)picture_as_pdf robot_manual — Resultados de extração de PDFs
✅ LIBERADO | 🟡 REVISAR | 🔴 PRIORITÁRIAhistory historico_conciliacao + log_base_total — Auditoria
qtd_divergente_totais e val_divergente_totais já estão definidos no model e são criados automaticamente via metadata.create_all() ao iniciar o servidor.| Campo | Descrição |
|---|---|
tipo_robo | VIVO ou CLARO |
status | SUCESSO ou ERRO |
qtd_baixar / val_baixar | Quantidade e valor com status BAIXAR |
qtd_baixar_pos / val_baixar_pos | Baixar com Saldo Positivo |
qtd_baixa_parc / val_baixa_parc | Baixa Parcial (falta pagamento) |
qtd_conf_sap / val_conf_sap | Conferir — não achou no SAP |
qtd_conf_depara / val_conf_depara | Conferir — sem De-Para |
qtd_divergente_totais / val_divergente_totais | ⚠️ Exclusivo CLARO — Divergente no SAP |
log_base_total registra toda ação na base: INSERT, UPDATE, DELETE, TENTATIVA_DUPLICADA, IMPORTACAO_LOTE — com usuario, tabela, campo alterado e valores antes/depois.
Calculadora de Reajustes
Cálculo mensal de reajustes contratuais com múltiplos índices e períodos.
O que faz
Calcula o valor atualizado de um contrato mês a mês, aplicando IPCA, IGP-M ou INPC sobre um valor base. Suporta múltiplos períodos contratuais (mudança de índice/valor no meio do contrato) e exceções/acordos pontuais.
Fluxo de cálculo
Entrada de dados
Analista informa: ID TBSA, períodos (data início, mês base do índice, índice IPCA/IGP-M/INPC, valor, quantidade) e eventuais exceções.
Lookup automático
Ao digitar o ID TBSA, verificarRobo() consulta /api/base-total/lookup/{idTbsa} e exibe o contrato SAP, cliente e portfólio automaticamente.
Cálculo mensal
calcularMemoria() aplica o acumulado dos índices mês a mês via getIndiceAcumulado(), que busca os 12 meses anteriores no cacheIndices.
Visualização e exportação
Resultado exibido em visão mensal ou anual. Exportação via exportarExcel() gera XLSX com duas abas: Memória Vertical e Visão Corrida.
Índices disponíveis (7)
| Índice | Fonte | Cadência |
|---|---|---|
| IPCA | IBGE via BACEN SGS | Mensal |
| IGP-M | FGV via BACEN SGS | Mensal |
| INPC | IBGE via BACEN SGS | Mensal |
| IGP-DI | FGV via BACEN SGS | Mensal |
| IPCA-E | IBGE via BACEN SGS | Mensal |
| IPC-BRASIL | FIPE via BACEN SGS | Mensal |
| IPC-SP | FIPE via BACEN SGS | Mensal |
Controle de acesso
Principais funções JS
| Função | Descrição |
|---|---|
calcularMemoria() | Executa o cálculo e preenche dadosMemoriaAtual |
getIndiceAcumulado() | Retorna acumulado de 12 meses do índice selecionado |
renderizarTabela() | Exibe resultado em tabela mensal ou anual |
alternarVisao(modo) | Alterna entre 'mensal' e 'anual' |
exportarExcel() | Gera e baixa XLSX com Memória Vertical + Visão Corrida |
carregarFormulario(id) | Carrega análise salva do banco pelo ID |
Robô de Conciliação VIVO
Cruzamento automático do extrato SAP (FBL5N) com a Composição de Pagamento VIVO. Arquivo: routers/conciliacao_vivo.py
Entradas
| Arquivo | Campo-chave |
|---|---|
| FBL5N.xlsx | ChvRefer.(cabeç.) 1 = ID TBSA |
| Composição de Pagamento.xlsx | Contrato VIVO + tipo de movimentação |
Status de saída
Abas do Excel gerado (7)
| # | Aba | Conteúdo |
|---|---|---|
| 1 | Resumo Geral ★ | 4 gráficos grid 2×2 + tabelas por status/tipo/portfólio |
| 2 | comp formatada | Resultado linha a linha com status colorido |
| 3 | Glossário do Robô | Explicação de cada status e tipo |
| 4 | Template SAP | Colunas: Núm.Documento, Ano, Montante, Núm.Contrato, Atribuição, Cliente |
| 5 | FBL5N | Cópia do arquivo original |
| 6 | Composição | Cópia do arquivo original |
| 7 | _ref (oculta) | Dados auxiliares para os gráficos — nunca remover |
Etapas de processamento
Leitura e validação
Abre FBL5N e Composição. Verifica presença das colunas obrigatórias. Carrega dicionário de siglas via SiglasVivo em runtime.
Preparação FBL5N
Extrai Nº do contrato, tipo de documento, data e montante. Normaliza contratos (remove .0 e zeros à esquerda). Gera Chave = contrato + tipo + data.
Preparação Composição
Identifica colunas. Busca De-Para em depara_financeiro por contrato_re_cliente. Traduz denominações → siglas SAP. Gera Chave = contrato_re + sigla + calc_de.
Cruzamento Nível 1 — Chave Exata
Agrupa FBL5N e Composição por Chave e soma montantes (SOMASE). Calcula DIF = Comp − FBL. Se |DIF| ≤ 0,05 → BAIXAR. Sem match → Conferir Data.
Cruzamento Nível 2 — Aba Em Aberto
Para linhas "Conferir Data" (sem correspondência na FBL), aplica 2Chave = contrato_re + denominação original. Captura Montante Real e Nº Documento e reavalia diferença. Resultado: Maior na FBL / Menor na FBL.
Geração do Excel
Gera arquivo com 7 abas completas, 4 gráficos (pizza de status, tipos, saúde financeira, ticket médio) e formatação condicional por cor de status.
De-Para de tipos (VIVO → SAP)
O De-Para de tipos é mantido na tabela siglas_vivo e gerenciado pelo analista diretamente no módulo Data Base → aba Siglas VIVO. Exemplo básico de como a tabela deve estar preenchida:
| Denominação (Composição VIVO) | Sigla SAP |
|---|---|
| KL - ALUGUEL | RJ |
| KL - INFRA-ESTRUTUR / BASE FEE | RH |
| KL - INFRA ADICIONAL | RF |
| KL - REEMBOLSO ENERG | RI |
| KL - DESCONTO | NI |
| KL - TAXA REFORÇO | RL |
A coluna "Denominação" deve ser a cópia exata do valor que aparece na Composição de Pagamento — incluindo maiúsculas, traços e espaços.
siglas_vivo, a linha receberá status CONFERIR (SEM DE-PARA) no Excel de resultado.Robô de Conciliação CLARO
Cruzamento com normalização inteligente de colunas e match em cascata de 3 níveis. Arquivo: routers/conciliacao_claro.py
Diferenças em relação ao VIVO
| Aspecto | VIVO | CLARO |
|---|---|---|
| Chave de match | ID TBSA (campo ChvRefer) | Nº do contrato SAP |
| Normalização de colunas | Padrão | Raio-X (NFKD + regex) |
| Algoritmo de match | Seguro + Flexível | Cascata: Macro→Micro→Salva-vidas |
| Status exclusivo | — | DIVERGENTE NO SAP |
| Abas Excel | 7 | 8 (+ Auditoria CLARO) |
Status de saída (6)
Raio-X — Normalização de Colunas
Match em 2 Níveis
Nível 1 — Chave Exata
Gera a Chave na Composição: contrato_re + sigla + valor + calc_de. Cruza com a Chave da FBL5N (contrato + tipo + valor + data). Match exato → BAIXAR. Senão, segue ao Nível 2.
Nível 2 — 3Chave (Contrato + Tipo)
Para linhas sem match: usa 3Chave = contrato + tipo, ignorando valor e data. Busca na FBL5N e captura o Montante Real. Calcula DIF = Comp − FBL e atribui status final.
Auditoria de Diferenças
Se |DIF| ≤ 0,05 → BAIXAR. Se FBL maior → Maior na FBL. Se FBL menor → Menor na FBL. Se totalização diverge → Divergente (Totais). Sem De-Para → Sem De-Para.
Abas do Excel gerado (8)
| # | Aba | Conteúdo |
|---|---|---|
| 1 | Resumo Geral ★ | 4 gráficos grid 2×2 + tabelas de consolidação da saúde financeira |
| 2 | comp formatada | Resultado linha a linha com status colorido (Nível 1) |
| 3 | Auditoria CLARO | Casos Sem De-Para, anomalias e divergências de chave |
| 4 | Em Aberto | Análise Nível 2 — divergências financeiras com 3Chave |
| 5 | Template SAP | Linhas aptas a BAIXAR prontas para lançamento no SAP |
| 6 | Glossário do Robô | Explicação de cada status e parâmetro |
| 7 | FBL5N | Cópia do arquivo original |
| 8 | Composição/P1 | Cópia do arquivo original |
Robot — Extração de Contratos PDF
Leitura automática de PDFs de contratos: extrai dados financeiros, identifica cláusulas e gera planilha com score de confiança por arquivo. Arquivo: routers/robot_manual.py
Como funciona
Upload dos PDFs
Analista seleciona um ou mais arquivos PDF no módulo Robot. O sistema processa até 2 arquivos em paralelo.
Extração de texto
O pdfplumber extrai o texto nativo do PDF (sem OCR). Arquivos com menos de 50 caracteres legíveis são sinalizados como não processáveis.
Análise inteligente
O motor de extração busca cada campo usando âncoras, regex e dicionários de negócio. Cada campo extraído contribui para o Score de Confiança (0–100).
Validação de sanidade
Valor mensal aceito: R$500 a R$500.000. Vigência aceita: 12 a 120 meses. Valores fora desses limites geram alertas técnicos.
Resultado e exportação
Salva em robot_manual e gera Excel colorido: verde = LIBERADO, amarelo = REVISAR, vermelho = PRIORITÁRIA.
Ação sugerida por score
| Score | Ação | Significado |
|---|---|---|
| Alto | ✅ LIBERADO | Dados completos, valores dentro dos limites esperados |
| Médio | 🟡 REVISAR | Um ou mais campos faltando ou fora do padrão — conferir manualmente |
| Baixo | 🔴 PRIORITÁRIA | Múltiplos campos ausentes ou inválidos — requer atenção imediata |
Campos extraídos por contrato
| Campo | Descrição |
|---|---|
Tipo_Contrato | Locação, aditivo, renovação, rescisão, sublocação |
Valor_Mensal | Valor financeiro mensal do contrato |
Indice | Índice de reajuste identificado (IPCA, IGP-M, INPC…) |
Percentual_Reajuste | Percentual de reajuste contratual |
Data_Base_Reajuste | Data de referência para o reajuste |
Vigencia_Inicio | Data de início da vigência |
Vigencia_Fim | Data de fim da vigência |
Tem_Renovatoria | Se há cláusula de renovação automática |
Garantia | Tipo de garantia: caução, fiador, seguro fiança |
Multa_Rescisao | Percentual de multa por rescisão |
Locador_Nome | Nome do locador extraído do texto |
Locador_CPF_CNPJ | CPF ou CNPJ do locador |
Banco / Agencia / Conta | Dados bancários para pagamento |
Score_Confianca | Nota de 0 a 100 calculada pelo robô |
Alertas_Tecnicos | Lista de campos não encontrados ou fora do limite |
session_id. É possível re-exportar o Excel de qualquer sessão anterior.Database
Cadastro mestre e De-Para de contratos. Arquivo: routers/base_total.py
Abas do módulo
| Aba (painel) | Tabela | Finalidade |
|---|---|---|
| De-Para Financeiro | depara_financeiro | Base mestra — importação/exportação/busca por contrato_re_cliente |
| Siglas VIVO | siglas_vivo | De-Para de tipos VIVO → sigla SAP, editável por linha |
| Siglas CLARO | siglas_claro | De-Para de tipos CLARO → sigla SAP, editável por linha |
| Robô (OCR) | dados_robo | Resultados de OCR legado por ID TBSA — editável via drawer |
| Logs | log_base_total | Auditoria de todas as ações — exportável em Excel |
Importação De-Para — como funciona
Upload do Excel
Analista seleciona arquivo na aba De-Para Financeiro. Colunas esperadas: contrato_re_cliente, contrato_re_sap, sub_grupo, nome_cliente, id_tbsa, id_cliente, portfolio.
Leitura e normalização
Backend normaliza colunas, faz strip de strings e trata o bug .0 (pandas converte inteiros para float).
Upsert por contrato_re_cliente
Carrega chaves existentes em memória (set). Cada linha: se existe → update; se não → insert. Nunca 1 query por linha.
bulk_save_objects()
Salva tudo em uma única operação. Registra IMPORTACAO_LOTE em log_base_total com contagem de inserções e atualizações.
Lookup para a Calculadora
GET /api/base-total/lookup/{id_tbsa} busca todos os contratos vinculados em depara_financeiro e retorna contrato SAP, nome do cliente, portfólio e sub_grupo. Aparece como tooltip abaixo do campo.Portfólios VIVO padronizados
Fix crítico — bug do .0
1234 vira 1234.0. O código faz .split('.')[0] ou .replace('.0', '') antes de salvar no banco.Auditoria completa
Toda ação é registrada em log_base_total com: usuário, tabela, ação (EDITAR / IMPORTACAO_LOTE / EXPORTAR), dados enviados em JSON e mensagem de resultado.
Administração de Usuários
Gestão completa de usuários com controle de acesso em 3 perfis.
Perfis de acesso
| Perfil | Acesso |
|---|---|
| admin | Acesso total a todos os módulos + gestão de usuários + logs |
| analista | Calculadora, conciliação, base total. Vê apenas as próprias análises. |
| cliente | Apenas visualização — análises do próprio cliente com inputs congelados |
Operações disponíveis
- Criar usuário (email + nome + perfil + id_cliente_vinculado)
- Bloquear / Desbloquear (
ativo = false/true) - Resetar senha (admin define nova senha)
- Excluir usuário permanentemente
- Visualizar usuários online (heartbeat dos últimos 30s)
Heartbeat de sessão
O frontend envia um ping para GET /api/usuarios/{email}/status periodicamente. O campo ultimo_acesso é atualizado. A rota GET /api/admin/logs retorna usuários com acesso nos últimos 30 segundos.
Sincronização de Índices
POST /api/sincronizar-indices consulta o SGS do BACEN para cada série (IPCA: 433, IGP-M: 189, INPC: 188) e atualiza a tabela indices_financeiros com os valores mais recentes.Rotas da API
Todas as rotas REST expostas pelo FastAPI em http://localhost:8000/api/.
Frontend SPA — index.html
Single Page Application completa em um único arquivo HTML. Toda lógica de UI, autenticação e requisições API está em Vanilla JS.
Telas (Views)
| ID da View | Título | Perfil | Descrição |
|---|---|---|---|
viewHub | Início | todos | Cards de navegação para todos os módulos |
viewAnalises | Análises | todos | Grid de análises salvas com opções de carregar/excluir |
viewCalc | Calculadora | analista/admin | Calculadora interativa de reajustes contratuais |
viewConciliacao | Conciliação | analista/admin | Upload + processamento VIVO/CLARO + histórico |
viewBaseTota | Database | analista/admin | Abas De-Para/Siglas/Robô OCR/Logs com CRUD e importação |
viewRobotManual | Robot | analista/admin | Upload de PDFs, resultados com score, histórico de sessões |
viewAdmin | Administração | admin | Gestão de usuários + estatísticas + chips de online |
viewPerfil | Meu Perfil | todos | Dados do usuário + alteração de senha |
Variáveis globais de estado
Funções-chave de navegação
| Função | Descrição |
|---|---|
navegarPara(view) | Troca de tela, atualiza sidebar highlight |
fazerLogin(event) | Autentica via /api/login, salva sessão em localStorage |
fazerLogout() | Limpa sessão e retorna para tela de login |
toggleSidebar() | Colapsa/expande sidebar (240px ↔ 64px) |
Comportamento da Conciliação
_bytesResultadopersiste entre navegações — chip verde "Resultado disponível" fica visível até resetarresetarConciliacao()limpa tudo: arquivos + resultado + progresso- O
job_idé um UUID gerado viacrypto.randomUUID()— evita colisão entre execuções paralelas - Barra de progresso simulada (0→95%) enquanto o backend processa — não usa SSE diretamente
Regras Críticas de Desenvolvimento
Restrições e decisões técnicas que devem ser respeitadas em todo novo código.
Nunca usar merge_cells
O openpyxl com merge_cells em arquivos com gráficos dinâmicos causa erro de reparo no Excel. Solução: layouts sem mesclagem de células.
Dados de gráficos na aba _ref
Dados usados pelos gráficos ficam na aba _ref com sheet_state='hidden'. Colunas ocultas na mesma aba quebram os gráficos no Excel.
iterrows() — nunca itertuples()
Colunas do SAP têm espaços nos nomes. O itertuples() renomeia automaticamente essas colunas. Sempre usar iterrows() nos robôs.
Fix do .0 em contratos
Pandas converte inteiros para float ao ler Excel: 1234 → 1234.0. Sempre fazer str(val).replace('.0', '') antes de salvar contratos no banco.
Pool de conexões MySQL
pool_pre_ping=True + pool_recycle=3600 no database.py evita o erro "Lost connection to MySQL server". Nunca remover essas configurações.
Bulk operations em importações
Nunca fazer 1 query por linha. Preparar lista em memória com verificação de duplicatas via set e usar db.bulk_save_objects() para inserção.
Ordem de abas Excel
Usar wb._sheets = [wb[nome] for nome in lista_ordem] + wb.active = wb['Resumo Geral'] antes do save(). Nunca confiar na ordem de criação das abas.
Raio-X para colunas SAP
O SAP exporta colunas com nomes inconsistentes (acentos, espaços, pontos). Sempre usar _norm_col() + _find_col() do conciliacao_claro.py.
Progresso SSE usa job_id
A chave do progresso_global é o job_id (UUID), não o email do usuário. Garante que VIVO e CLARO rodando simultaneamente não conflitem.
Labels de gráficos — DataLabelList
Para exibir % em pizzas e valores em barras, usar DataLabelList de openpyxl.chart.label. Sem isso, os gráficos gerados saem sem anotações visíveis.