Plano mestre — VPSNOVA: serviço de odds pré-live e assistente operacional Hermes
1. Objetivo, limites e fontes de verdade
A nova VPS será um nó único inicialmente, preparado para expansão, responsável por:
- Capturar e organizar odds pré-live de futebol.
- Suportar as 24 fontes do catálogo, ativando-as gradualmente por prontidão técnica.
- Entregar odds canônicas a um painel hospedado em outro servidor.
- Fornecer REST para carga/recuperação e SSE para atualizações contínuas.
- Hospedar Hermes como assistente dessa perna, com Telegram, dashboard web e autonomia limitada.
- Manter Grafana como painel operacional.
- Desenvolver em paralelo memória compartilhada com OpenViking, sem colocá-la no caminho crítico das odds.
Ficam fora da primeira entrega:
- Arbitragem, EV ou decisões de aposta.
- Alterações no painel externo.
- Compatibilidade com a API antiga.
- Usuários finais conversando com LLM.
- Obrigação de colocar as 24 fontes online simultaneamente.
- AdsPower.
A referência conceitual do contrato será USOS_V2_PROPOSTA.md, corrigindo as ambiguidades identificadas na revisão. O corpus bruto do PACIFICADORPROP será evidência e conjunto golden; o harmonizador antigo não será promovido a runtime.
2. Gate 0 — segurança e preparação obrigatória
Antes de instalar aplicações:
Rotacionar credenciais expostas
- Revogar o token Hostinger enviado no chat.
- Rotacionar a chave pessoal Bitwarden em
Settings → Security → Keys → Rotate API Key. - Nenhuma das duas credenciais expostas poderá ser usada nem no bootstrap.
- Criar depois credenciais específicas de machine account no Bitwarden Secrets Manager.
Resolver a raiz Git local
F:\PROGRAMADOR\VPSNOVAserá um repositório novo, privado e autônomo.- Como hoje a pasta ainda resolve para o repositório-pai perigoso
F:\PROGRAMADOR, nenhum comando Git ou documento importante será gravado ali antes da autorização específica para criar a raiz isolada. - Após a criação,
git rev-parse --show-topleveldeverá retornar exatamenteF:\PROGRAMADOR\VPSNOVA. - O remoto canônico será um repositório privado no GitHub.
Atualizar e proteger a VPS
- Aplicar atualizações pendentes e reiniciar antes do runtime.
- Criar usuários separados:
admin,deploy,odds,hermesebackup. - Instalar chave SSH e validar uma segunda sessão independente.
- Instalar Tailscale e validar acesso e console de emergência.
- Só depois desativar login de
roote autenticação por senha. - UFW com política
denyde entrada; SSH e API somente pela tailnet. - Nenhum dashboard ou banco escutando publicamente.
Migrar
oddsbet.techpara Cloudflare- Como a zona não possui serviço ativo, executar a migração no início.
- Exportar/inventariar primeiro todos os registros da Hostinger.
- Cadastrar a zona na Cloudflare, comparar registros e trocar nameservers.
- Validar propagação e manter procedimento de reversão.
- Reservar:
hermes.oddsbet.techops.oddsbet.techmemory.oddsbet.tech
- Os três serão publicados apenas via Cloudflare Tunnel + Access; o túnel usa conexões de saída e não exige portas web abertas na origem. Cloudflare Tunnel
Hostinger MCP somente no plano administrativo
- Instalar no computador administrativo, não dentro da VPS de produção.
- Habilitar apenas
hostinger-domains-mcp,hostinger-dns-mcpehostinger-vps-mcp. - Não habilitar
billing,reachouhosting. - Preferir OAuth interativo para ações manuais; automação futura usa token novo vindo do Bitwarden.
- Toda alteração DNS passa antes por inventário, validação e diff. MCP oficial da Hostinger
3. Arquitetura de execução
collector-<fonte> ─┐
collector-<fonte> ─┼─> ingest-core ─> estado/deltas ─> api-read ─> Tailscale ─> backend do painel
OddsPapi ─ resolver┘ │
└─> raw comprimido ─> compactação horária ─> S3
systemd/watchdogs ─> saúde e reinícios determinísticos
Hermes ─> diagnóstico, insights, diffs e remediações allowlisted
Runtime híbrido
- Hermes roda nativamente sob usuário próprio e systemd.
- Odds, API, armazenamento, simulador e observabilidade rodam em Docker Compose.
- Contêineres não reservam CPU/RAM antecipadamente; recebem limites máximos.
- Cada fonte ativa tem um serviço/contêiner próprio, reutilizando a mesma imagem e runtime comum.
- Fontes desligadas não consomem CPU/RAM.
- Collectors nunca acessam o banco diretamente; enviam envelopes ao
ingest-core, único escritor lógico. - Watchdogs, healthchecks e reinícios permanecem determinísticos e independentes de LLM.
Serviços
ingest-core: valida, resolve identidades, persiste captura, estado e outbox de eventos.api-read: API somente leitura para painel e simulador.collector-<source>: transporte e parser isolados por fonte lógica.history-compactor: gera histórico horário em Parquet.backup-sync: sincroniza raw, manifests e backups para S3.contract-simulator: simula um backend consumidor, quedas e retomadas.grafana+prometheus+ exporters: painel operacional inicial.- Logs inicialmente estruturados em JSON, com rotação local; Loki só entra após medir recursos. Se entrar, usará Grafana Alloy, pois Promtail já está EOL. Grafana Alloy
- OpenViking fica em um perfil Compose separado.
Catálogo das 24 fontes
O registry canônico conterá os aliases comprovados:
Altenar/EstrelaBet, DataBet/Pitaco, BetConstruct/VBet, NGX/Lottu, Betano, Bet365, BaseHub/EnergiaBet, BrasilBet, Superbet, Betnacional, BWIN/Sportingbet, Kaya/WJ, FSSB/Betão/7K, SA Esportes/Lance de Sorte, BetBy/Betboom, BetMGM, Esporte da Sorte, KTO, Brazino777, Sporty, Milhão, Pinnacle, BetMexico/Aposta.bet e Matchbook.
4. Contrato USOS-2 e API pública interna
Identidades
fixtureId: UUID estável interno, independente de qualquer fornecedor.identities[]: IDs externos comnamespace,provider,nativeId, evidência e confiança.- OddsPapi e Sportradar, quando disponíveis, são evidências de resolução; nenhum ID externo substitui silenciosamente o ID canônico.
- Fuzzy matching nunca gera correspondência final automaticamente; resultados incertos ficam em
UNMATCHED/NEEDS_REVIEW.
A identidade do mercado será uma tupla estruturada, não um label:
- esporte;
- período;
- família/stat unit;
- escopo;
- linha;
- variante;
- combinação;
- UOF ID e specifiers quando existentes.
marketKey será uma representação derivada dessa tupla. Os campos estruturados permanecem autoritativos.
outcomeKey será derivado de lado/designação estruturada e nunca apenas do texto exibido.
Observações de odds
Cada outcome conterá observations[]. Cada observação inclui:
- origem própria ou OddsPapi;
- casa/provedor e IDs nativos;
- preço decimal validado e preço nativo preservado;
- estado
OPEN,SUSPENDED,CLOSEDouREMOVED; capturedAt,fetchedAte idade calculada na leitura;- limite/order book/betslip quando disponíveis;
rawRefe SHA-256 da captura;- confiança, warnings e flags de validação.
Política de seleção:
- usar a observação própria mais recente e válida;
- se ela não existir, permitir OddsPapi como fallback;
- marcar sempre
fallbackUsed, origem e idade; - preservar ambas quando existirem, sem sobrescrever divergências;
- nunca arredondar preços no pipeline intermediário.
Observações com decimal <= 1, overround fora de [1.00, 1.25], LABEL_FALLBACK ou baixa confiança ficam preservadas em quarentena, mas não viram observação efetiva.
Frescor
- Coletor direto: alvo inicial em torno de 60 segundos.
- Fonte frágil/browser: alvo inicial em torno de 180 segundos.
- Jitter e backoff específicos por fonte.
- Após 5 minutos sem captura válida, a fonte/observação vira
stale. - Dados stale continuam auditáveis, mas
effectiveObservationpassa anull. - O consumidor decide visualmente o que mostrar; o serviço garante estado e tombstone.
Endpoints v1
GET /api/v1/health/liveGET /api/v1/health/readyGET /api/v1/sourcesGET /api/v1/fixturesGET /api/v1/fixtures/{fixtureId}GET /api/v1/offers?fixtureId=&source=&marketKey=GET /api/v1/delta?cursor=GET /api/v1/stream?cursor=— SSEGET /api/v1/unmatched— somente administraçãoGET /metrics— somente rede interna
Regras de transporte:
- REST é a autoridade para snapshot e recuperação.
- SSE entrega
upsert,remove,source_statuse heartbeat. - Cada evento SSE possui um cursor monotônico.
- Heartbeat a cada 15 segundos.
- Reconexão curta usa
Last-Event-ID. - Gap ou cursor expirado obriga
GET /delta; se necessário, novo snapshot. - Eventos delta ficam recuperáveis por 7 dias.
- Paginação padrão de 100 e máximo de 500 registros.
- Toda resposta informa
schemaVersionesnapshotVersion. - Autenticação servidor-a-servidor combina ACL Tailscale e token read-only armazenado no Bitwarden.
- O navegador nunca acessa diretamente a VPS de odds.
O contrato será entregue em JSON Schema, modelos Python, OpenAPI, exemplos golden e consumidor de referência.
5. Persistência, retenção e benchmark
Escolha SQLite versus PostgreSQL
A implementação terá uma interface de persistência única e migrations equivalentes. O benchmark decidirá mecanicamente:
SQLite WAL será aceito somente se, sob replay a quatro vezes a carga esperada e até oito fontes simultâneas:
- houver exatamente um escritor lógico;
p95de transação de escrita ficar abaixo de 30 ms;- erros
busy/lockedficarem abaixo de 0,1%; p95de leitura principal ficar abaixo de 250 ms;- banco quente projetado ficar abaixo de 20 GiB;
- backup consistente e restore limpo passarem;
- API/SSE mantiverem cursor sem gap;
- restarem ao menos 30% de RAM e disco livres.
Se qualquer limite falhar, se o resultado for inconclusivo ou se mais de oito fontes forem promovidas, a primeira produção usa PostgreSQL.
Retenção
- Estado atual: permanente enquanto relevante.
- Raw comprimido local: 7 dias.
- Raw comprimido no S3: 30 dias.
- Histórico normalizado: Parquet particionado por
date/hour/source. - Compactação horária com baixa prioridade de CPU/I/O.
- Backup diário das odds e estado.
- Backup antes de deploy/migração.
- Hermes e OpenViking: backup diário consistente.
- Configuração, mapas e decisões: GitHub privado.
- Nenhuma remoção local ocorre antes de upload, manifesto e hash verificados.
- Um restore isolado deve concluir em até quatro horas.
- Como não haverá dados de usuários nesta fase, aceita-se perda máxima de 24 horas para odds históricas; isso deverá ser revisto antes de armazenar dados pessoais.
6. Hermes, memória e painéis
Hermes
- Instalação oficial fixada em versão, sob usuário
hermes. - Login ChatGPT/Codex por device OAuth;
~/.hermes/auth.jsone~/.codex/auth.jsontratados como senhas. - Dashboard oficial em
127.0.0.1:9119, publicado somente por Cloudflare Access. Dashboard Hermes - Telegram no primeiro go-live.
- WhatsApp somente depois de o Telegram estar estável; a integração usa ponte Web/baileys e será tratada como experimental.
- SSH/CLI permanece canal de contingência.
Permissões:
- Ler métricas, health e logs sanitizados.
- Executar wrappers allowlisted para
statuse restart de coletores específicos. - Preparar alterações em clone de desenvolvimento isolado, rodar testes e gerar diff.
- Não acessar Docker socket.
- Não ler todos os segredos.
- Não alterar firewall, SSH, DNS ou pacotes.
- Não fazer push, merge, deploy ou rollback de produção.
- Toda remediação automática gera log, motivo, serviço, resultado e recuperação.
Memória compartilhada
- Memória built-in do Hermes continua privada.
- A instância começa vazia.
- O pacote inicial será inserido manualmente: arquitetura, contrato, catálogo, limites do agente e runbooks aprovados.
- Git continua sendo a fonte de verdade; memória nunca substitui documentação versionada.
- OpenViking self-hosted será desenvolvido em paralelo, com:
- conta
oddsbet; - recursos compartilhados do projeto
vpsnova; - usuários e peers separados para Hermes, Codex, Claude e futuros agentes;
- acesso MCP/API somente por rede privada/BFF;
- Web Studio atrás de Cloudflare Access;
- export/backup testado.
- conta
- O front administrativo nunca recebe chave do OpenViking.
- OpenViking só é ativado permanentemente na VPS se o modelo local e o serviço permanecerem dentro de 1 vCPU, 3 GiB de RAM e não degradarem a API em mais de 10%.
- Caso falhe, permanece no desenvolvimento local ou migra para outra máquina; nenhuma API paga será contratada implicitamente. OpenViking multi-tenant
Observabilidade
- Grafana OSS auto-hospedado, sem assinatura, acessível por
ops.oddsbet.tech. Grafana OSS - Prometheus com retenção limitada a 7 dias/2 GiB.
- Dashboards:
- CPU, RAM, disco e rede;
- estado dos contêineres;
- captura válida por fonte;
- frescor, falhas e backoff;
- raw/parsed/valid/rejected;
- volume de unmatched/quarentena;
- latência ingestão→API/SSE;
- crescimento diário de disco;
- status de backup e último restore.
- Alertas e recuperações enviados ao Telegram.
7. Desenvolvimento, documentação e deploy sem sobreposição
Depois do gate Git, F:\PROGRAMADOR\VPSNOVA conterá:
READMEe estado atual validado.- ADRs e arquitetura.
- Contrato/schema/OpenAPI.
- Registry e dossier das 24 fontes.
- Runbooks de SSH, Tailscale, Cloudflare, Hermes, backup, restore, incidente e rollback.
- Evidências de probes, benchmarks e soak.
- Infraestrutura Compose/systemd.
- Código, testes, corpus golden reduzido e simulador.
- Ledger cronológico de mudanças e deploys.
Fluxo multidev:
- Uma branch e worktree por pessoa/agente.
mainprotegida e sem push direto.- PR com replay, schema, contrato e testes.
- Proibição de force-push e de
git add ./git add -A. - Alterações derivadas de BETMONITOR/PACIFICADORPROP são copiadas conscientemente, com origem documentada; esses repositórios não viram runtime.
Deploy inicial:
- Exigir commit limpo e revisado.
- Construir imagens imutáveis e manifest com commit/tag/hashes.
- Adquirir lock exclusivo de deploy na VPS.
- Rejeitar deploy concorrente ou release divergente.
- Instalar em
/opt/vpsnova/releases/<commit>. - Testar migrations e canário.
- Promover atomicamente
current. - Manter
previouspara rollback. - Registrar operador, horário, release e resultado.
- Migrar depois para GitHub Actions reutilizando exatamente o mesmo pipeline e mantendo promoção manual.
8. Rollout das fontes
Estados oficiais por fonte:
catalogued: inventário/raw identificado.structured_only: parser passa corpus golden e schema.network_ready: transporte direto funciona a partir da nova VPS.runtime_ready: serviço contínuo e soak individual de 24 horas.panel_ready: contrato e simulador passam sem perda.prod_enabled: promoção explícita e monitorada.
Regras:
- Schema e replayer vêm antes de qualquer monitor.
- Direct HTTP/WS/SSE primeiro.
- Proxy residencial somente após bloqueio comprovado e aprovação.
- Browser/Chrome/Playwright apenas por análise individual, isolado e sem AdsPower.
- Uma fonte entra por vez.
- A primeira onda não tem número ou nomes obrigatórios; é formada pelas fontes que passarem os gates.
- Empates de prontidão priorizam: daemon direto existente, maior cobertura golden, menor dependência de browser e menor consumo.
- Após a primeira fonte: soak de 24 h.
- Após o primeiro lote: soak conjunto de 72 h.
- A expansão para novas fontes para quando RAM sustentada superar 70%, CPU p95 superar 65%, disco livre cair abaixo de 30% ou a API sair dos SLOs.
- As 24 fontes podem permanecer em estágios diferentes; “estrutura para 24” não significa “24 online”.
9. Testes e critérios de aceite
Segurança
- As duas credenciais expostas foram revogadas.
- Nenhum segredo aparece em Git, documentação, logs ou imagem Docker.
- Bitwarden Secrets Manager usa machine accounts separadas para
local-deploy,vps-prode futuragithub-actions. Bitwarden machine accounts - Login por chave validado em segunda sessão.
- Root e senha SSH desabilitados.
- Nenhuma porta de API/dashboard/banco pública.
- Cloudflare Access e ACL Tailscale testados.
- Hermes não consegue acessar Docker socket, segredo de produção ou deploy.
Contrato e dados
- Todo raw golden das 24 fontes é reproduzível por hash.
- Nenhuma odd publicada sem origem,
fetchedAt, estado e raw reference. - OddsPapi nunca mascara captura própria.
- Fuzzy incerto nunca produz match automático.
UNMATCHEDpermanece preservado.- Duplicação e reprocessamento são idempotentes.
- Preço nativo não sofre arredondamento intermediário.
- Tombstone remove odds fantasmas.
Desempenho e operação
- Ingestão validada→estado: p95 abaixo de 100 ms.
- Consulta principal: p95 abaixo de 250 ms.
- Estado commitado→SSE: p95 abaixo de 3 s.
- Metas de captura: aproximadamente 60 s direto e 180 s frágil/browser.
- Reinício forçado de contêiner não perde cursor.
- Reboot da VPS recompõe os serviços aprovados.
- Desconexão SSE forçada recupera estado terminal sem buraco nem duplicação semântica.
- Crescimento diário de disco é medido antes de promover nova fonte.
- Backup S3 e restore completo são provados antes do go-live.
Aceite final da primeira fase
A primeira fase estará pronta quando:
- host estiver endurecido;
- repositório e documentação estiverem seguros;
- contrato USOS-2 v1 estiver congelado;
- benchmark tiver escolhido banco;
- API REST/SSE e simulador estiverem aprovados;
- ao menos uma fonte tiver chegado a
prod_enabled; - Grafana, Hermes/Telegram, backups e rollback estiverem operacionais;
- OpenViking puder continuar em paralelo sem impactar a entrega de odds.
Premissas finais
- A VPS atual é Ubuntu 24.04, 4 vCPU, 15 GiB RAM, ~193 GiB e Docker já instalado.
- O painel externo permite Tailscale.
oddsbet.technão possui serviço atual a preservar.- Operador inicial único; RBAC preparado para equipe.
- Não haverá dados de usuários nesta fase.
- Não há alta disponibilidade física; expansão futura poderá separar banco, API, browsers, observabilidade e memória sem mudar o contrato.
- Este turno não executa mudanças nem escreve documentação; a primeira ação de execução será resolver credenciais e a raiz Git segura.