Cerebro Studio · Backlog · Changelog
Edmundo10 • /www/wwwroot/edmundo10.com.br/docs/BACKLOG.md
Abrir Studio Projeto externo em modo read-only; encaminhamento permitido, escrita bloqueada.

Backlog Unificado

Projeto: Edmundo10. Fonte principal: /www/wwwroot/edmundo10.com.br/docs/BACKLOG.md.

Modo read-only: ações de escrita ficam disponíveis apenas para o Cérebro.

Sem itens pendentes em /www/wwwroot/edmundo10.com.br/docs/BACKLOG.md.

Especificações Disponíveis (fora da fila pendente)

Detalhe do BK Selecionado

/www/wwwroot/edmundo10.com.br/docs/backlog/BK-205-migracao-vps-dedcado.md • 2026-04-23T01:49:17.086Z

BK-205 — Migração edmundo10.com.br para Novo VPS

Objetivo

Migrar o projeto edmundo10.com.br do VPS multi-tenant atual (Hostinger) para um VPS dedicado (Hostinger, specs idênticos), rodando apenas este projeto para reduzir superfície de ataque e risco de contenção de recursos.

Data: 2026-04-22 | Status: PRONTO PARA EXECUÇÃO (verificações da seção 5 resolvidas)

> Revisão 2026-04-22: o inventário original continha erros — corrigidos nas seções 1.5, 1.6, 2.1, 4.2, 5.1, 6 e 7.


1. INVENTÁRIO COMPLETO DO PROJETO

1.1 Stack Tecnológica (confirmada)

| Camada | Tecnologia | Detalhe |

|--------|-----------|---------|

| Web | PHP-FPM 8.3 | Painel admin, CRM, stats (puramente PHP, sem Python/Flask) |

| Bot WhatsApp | Node.js v22.17.0 | whatsapp-web.js usando Chrome do sistema (não Puppeteer bundle) |

| API WhatsApp | Node.js porta 3035 | server.js rodando como user www via systemd |

| Banco runtime | SQLite | runtime.sqlite (único DB vivo) |

| Proxy | Nginx 1.24 | vhost puro PHP, sem proxy_pass |

| Gerenciamento | BT-Panel (opcional) + systemd | BT-Panel só para conforto; systemd é o que sustenta o bot |

| Processo do bot | systemd (não PM2) | edmundo10-whatsapp.service com Restart=always |

1.2 Estrutura de Arquivos (apenas o que importa)

```

/www/wwwroot/edmundo10.com.br/

├── index.php, qrcode.php, qrcodes.php

├── .htaccess (vazio)

├── .user.ini (open_basedir apenas)

├── 404.html / 502.html

├── AGENTS.md / ARCHITECTURE.md / GUIDELINES.md / CHANGELOG.md / BACKLOG.md

├── bot/

│ └── whatsapp/ ← NÚCLEO DO BOT

│ ├── server.js (API porta 3035)

│ ├── package.json (whatsapp-web.js ^1.34.6, qrcode ^1.5.4)

│ ├── auth/session/ ← 245M — user-data-dir do Chrome; PRESERVAR para evitar re-scan do QR

│ ├── queue/, locks/

│ ├── watchdog.sh (redundante com systemd; manter por segurança)

│ └── node_modules/ (91M — NÃO migrar, reinstalar)

└── painel-novo/

├── includes/ (config.php, bootstrap.php, auth.php, runtime.php, migrate.php)

├── data/

│ ├── runtime.sqlite ← 3.7M, ÚNICO DB VIVO (escrita ativa)

│ ├── edmundo10.db (0 bytes — vazio, pode ignorar)

│ └── webhook_debug.log

├── storage/

│ ├── audio/ (~160KB, .ogg)

│ └── video/ (~3.8MB)

├── api/ (status.php, whatsapp_ingest.php)

├── migrations/

└── tools/ (import_legacy.php — LEGACY, não usado no runtime)

```

Repo Git: https://github.com/GeJoRei/edmundo10.git (main em sincronia com origin/main; só este BK-205 untracked).

1.3 Variáveis de Ambiente

Fonte canônica dos valores: /etc/systemd/system/edmundo10-whatsapp.service + /www/wwwroot/edmundo10.com.br/painel-novo/includes/config.php.

| Variável | Valor em uso | Notas |

|----------|--------------|-------|

| EDMUNDO10_ADMIN_PASSWORD | edmundo2026 | Recomendado trocar no cutover |

| EDMUNDO10_WA_API_URL | http://127.0.0.1:3035 | Mantém |

| EDMUNDO10_WA_API_KEY | edm10_secret_key_2026_v1 | Tem que bater com WPP_API_KEY do service — já bate hoje |

| EDMUNDO10_WA_INSTANCE | edmundo10 | |

| EDMUNDO10_WA_INGEST_TOKEN | vazio | (service usa WPP_WEBHOOK_TOKEN=edm10_api_token) |

| EDMUNDO10_WA_HMAC_SECRET | vazio | (service usa WPP_WEBHOOK_SECRET=edm10_webhook_secret_2026) |

| EDMUNDO10_LEGACY_MYSQL_* | — | NÃO MIGRAR — MySQL legacy confirmado morto; ver §2.1 |

| EDMUNDO10_LEGACY_AUDIO_ROOT | /opt/edmundo10/audio | Diretório nunca existiu; a env pode ficar vazia no destino |

Env vars do bot (no service file — têm de ser replicadas no service do destino):

```

PORT=3035

WPP_INSTANCE_LABEL=edmundo10-whatsapp

WPP_API_KEY=edm10_secret_key_2026_v1

WPP_WEBHOOK_URL=https://edmundo10.com.br/painel-novo/api/whatsapp_ingest.php

WPP_WEBHOOK_TOKEN=edm10_api_token

WPP_WEBHOOK_SECRET=edm10_webhook_secret_2026

```

1.4 Dependências Node.js

```json

{

"name": "rnt-whatsapp-service",

"version": "2.0.0",

"dependencies": {

"qrcode": "^1.5.4",

"qrcode-terminal": "^0.12.0",

"whatsapp-web.js": "^1.34.6"

},

"engines": { "node": ">=18.0.0" }

}

```

O nome "rnt-whatsapp-service" é vestígio de clone inicial do Rio no Teatro. O server.js foi divergido (diff >300 linhas do RNT) — é código específico do edmundo10. Tratar como fonte independente; não sincronizar com o RNT.

1.5 Portas em Uso (CORRIGIDO)

| Porta | Processo | Pertence ao edmundo10? |

|-------|---------|------------------------|

| 3035 | node server.js (user www) | Sim — API WhatsApp |

A porta 5001 existe no servidor atual, mas pertence a /opt/edmundo-campanha/webhook/app.py (projeto Flask/Python legacy, integração Evolution API). NÃO é parte do edmundo10.com.br e NÃO entra na migração.

1.6 Configuração Nginx (CORRIGIDO — o vhost real é simples)

Arquivo: /www/server/panel/vhost/nginx/edmundo10.com.br.conf

```

  • server_name: edmundo10.com.br, www.edmundo10.com.br
  • root: /www/wwwroot/edmundo10.com.br
  • PHP: include enable-php-83.conf (PHP-FPM 8.3 via BT-Panel)
  • SSL: /www/server/panel/vhost/cert/edmundo10.com.br/{fullchain,privkey}.pem
  • HTTP→HTTPS: rewrite permanente
  • HSTS: max-age 31536000
  • Access: /www/wwwlogs/edmundo10.com.br.log
  • Error: /www/wwwlogs/edmundo10.com.br.error.log
  • Proxies: NENHUM — o PHP fala com :3035 internamente via loopback

```

A versão anterior deste documento listava location /admin → localhost:5001, /audio_file → :5001, /webhook → :5001. Nenhuma dessas rotas existe no vhost atual. O painel é servido por PHP-FPM direto; a API 3035 é consumida server-side pelo próprio PHP.

1.7 Systemd Service (conferido)

Arquivo: /etc/systemd/system/edmundo10-whatsapp.service

```ini

[Unit]

Description=Edmundo10 WhatsApp Bot Service

After=network.target

[Service]

Type=simple

User=www

WorkingDirectory=/www/wwwroot/edmundo10.com.br/bot/whatsapp

Environment="PORT=3035"

Environment="WPP_INSTANCE_LABEL=edmundo10-whatsapp"

Environment="WPP_API_KEY=edm10_secret_key_2026_v1"

Environment="WPP_WEBHOOK_URL=https://edmundo10.com.br/painel-novo/api/whatsapp_ingest.php"

Environment="WPP_WEBHOOK_TOKEN=edm10_api_token"

Environment="WPP_WEBHOOK_SECRET=edm10_webhook_secret_2026"

ExecStart=/usr/bin/node server.js

Restart=always

RestartSec=10

[Install]

WantedBy=multi-user.target

```

Notar: Restart=always já garante auto-recovery. O watchdog.sh (§1.8) é redundância, não essencial.

1.8 Crontab Relacionado

Crontab do root:

```

/5 * /www/wwwroot/edmundo10.com.br/bot/whatsapp/watchdog.sh

```

Crontab do user www: vazio. Nenhuma outra linha do edmundo em root. Todas as demais linhas do crontab root são de outros projetos (RNT, legalizarj, cerebro, etc) — NÃO migrar.

1.9 Recursos do Sistema (VPS ATUAL — Hostinger KVM)

| Recurso | Valor |

|---------|-------|

| OS | Ubuntu 24.04.3 LTS (noble), kernel 6.8.0-85 |

| Virtualização | KVM / QEMU |

| CPU | AMD EPYC 9354P, 4 vCPUs |

| RAM | 15 GiB |

| Swap | 8 GiB (swapfile) |

| Disco | 193 GiB ext4 (52 GiB livres — a VPS está cheia porque hospeda 15+ projetos) |

| IPv6 | Disponível (nativo) |

| Timezone | America/Sao_Paulo (-03) |

| User www | UID 1000, GID 1000 |

| Projeto no disco | 961M total; 245M só em auth/session |


2. O QUE PRECISA SER MIGRADO

2.1 Essencial

  • [ ] Código do projeto — via git clone do GitHub no destino, depois rsync dos runtime assets
  • [ ] Runtime SQLite: painel-novo/data/runtime.sqlite (único DB vivo)
  • [ ] Auth WhatsApp: bot/whatsapp/auth/ inteiro (245M) — com o service parado antes do rsync
  • [ ] Storage: painel-novo/storage/ (audio + video, ~4M)
  • [ ] webhook_debug.log (opcional, só para histórico): painel-novo/data/webhook_debug.log
  • [ ] Vhost Nginx: /www/server/panel/vhost/nginx/edmundo10.com.br.conf (ou vhost Nginx plano equivalente)
  • [ ] SSL: /www/server/panel/vhost/cert/edmundo10.com.br/{fullchain,privkey}.pem (transferir e depois trocar por certbot nativo, opcional)
  • [ ] Systemd service: /etc/systemd/system/edmundo10-whatsapp.service
  • [ ] Crontab root: apenas a linha do watchdog.sh

2.2 Segurança

  • [ ] .user.ini (open_basedir=/www/wwwroot/edmundo10.com.br/:/tmp/)
  • [ ] .htaccess (arquivo existe mas está vazio — não crítico)
  • [ ] Confirmar paridade entre WPP_API_KEY (service) e EDMUNDO10_WA_API_KEY (config.php) — hoje ambas são edm10_secret_key_2026_v1

2.3 Dependências de Software no Destino

Stack mínima (Ubuntu 24.04 LTS):

| Pacote | Versão alvo | Por quê |

|--------|-------------|---------|

| nginx | 1.24+ | vhost idêntico |

| php8.3-fpm + php8.3-{curl,sqlite3,mbstring,gd,mysql} | 8.3.x | enable-php-83.conf esperado; mantemos pdo_mysql para caso de reimport legacy pontual |

| nodejs | v22.17.0 (exato, via NodeSource) | evitar regressões de whatsapp-web.js |

| google-chrome-stable | v144.x (mesma major) | o auth/session é user-data-dir do Chrome; mudança de major pode invalidar a sessão |

| certbot + python3-certbot-nginx | mais recente | renovar SSL após cutover |

| fonts-liberation, libnss3, libatk1.0-0, libxshmfence1, libgbm1 | — | libs runtime do Chrome headless |

| rsync, git, curl, ufw, htop | — | operacional |

| ~~mysql-server~~ | — | não instalar; MySQL legacy descontinuado |


3. O QUE NÃO MIGRA

3.1 Descartados

  • .bkp_original_, .bkp_, .backup, *.tar.gz — todo .gitignore já os exclui
  • node_modules/ — reinstalar com npm ci
  • edmundo10.db (arquivo vazio, 0 bytes) — irrelevante
  • Qualquer .log antigo (nginx, watchdog, healthcheck) — opcional levar amostra

3.2 Outros Projetos no VPS Atual (FICAM NO SERVIDOR ANTIGO)

  • /opt/edmundo-campanha/ — Flask/Python legacy na porta 5001, projeto separado
  • /www/wwwroot/rionoteatro.com.br/
  • /www/wwwroot/legalizarj.com.br/
  • /www/wwwroot/seuimovel.rio.br/
  • /www/wwwroot/sigaautobot.com.br/
  • /root/cerebro/
  • Qualquer outra coisa fora de /www/wwwroot/edmundo10.com.br/

3.3 MySQL edmundo_campanha (CONFIRMADO MORTO)

O único código que lê esse DB é painel-novo/tools/import_legacy.php (ferramenta one-shot, não roda em produção). Runtime do painel é 100% SQLite. Decisão: não migrar. Nada de mysql-server no destino.


4. DEPENDÊNCIAS EXTERNAS

4.1 API WhatsApp (Porta 3035)

Já coberto em 1.3/1.7. Ponto nevrálgico: o auth/session/ é o perfil Chrome da sessão WhatsApp — tem que ser copiado com o service parado e com a mesma major version de Chrome para reabrir sem QR.

4.2 MySQL Legacy — NÃO APLICÁVEL

Ver §3.3.

4.3 SQLite

| Arquivo | Conteúdo | Migrar? |

|---------|----------|---------|

| painel-novo/data/runtime.sqlite | Runtime vivo (fila, cache, dados operacionais) | Sim |

| painel-novo/data/edmundo10.db | Vazio (0 bytes) | Não (irrelevante) |

| painel-novo/data/home_videos.json | Config de vídeos (se existir) | Sim se existir |

4.4 Sem Dependência Externa Paga

  • Sem Redis / Elasticsearch / SQS
  • Sem serviço SaaS
  • WhatsApp Web (sessão local, em auth/)

5. VERIFICAÇÕES PRÉ-MIGRAÇÃO

5.1 Críticas — RESOLVIDAS ✅

  • [x] Porta 5001: é /opt/edmundo-campanha/webhook/app.py (Flask). Outro projeto. Não migra.
  • [x] /opt/edmundo10/audio: nunca existiu. Env legacy, sem efeito.
  • [x] MySQL edmundo_campanha: morto. Não migra.
  • [x] package.json "rnt-whatsapp-service": vestígio do clone inicial; server.js já divergiu >300 linhas, é código próprio do edmundo10.
  • [x] Diff bot edmundo10 vs RNT: significativo. Não há dependência compartilhada.
  • [x] systemd service: existe, ativo, Restart=always funcionando (4 dias up).
  • [x] Crontab: apenas watchdog.sh em root; user www sem crontab.
  • [x] PHP extensions: pdo_sqlite, sqlite3, mbstring, curl, gd, openssl ok. mysqli/pdo_mysql não precisam no destino.

5.2 Antes do Cutover

  • [ ] VPS destino provisionada (specs §8)
  • [ ] Snapshot/backup do VPS atual (Hostinger tem snapshot; rodar antes do start)
  • [ ] Dump extra: cp -a painel-novo/data/runtime.sqlite runtime.sqlite.predump
  • [ ] DNS: TTL de edmundo10.com.br e www.edmundo10.com.br abaixado para 300s pelo menos 24h antes
  • [ ] Chrome 144 instalado no destino (ou a major version que estiver disponível no canal stable no dia — validar que o bot conecta)
  • [ ] User www no destino com UID=1000, GID=1000 (idênticos ao origem)
  • [ ] Firewall do destino: 22, 80, 443 abertas; 3035 NÃO expor (só loopback)

6. PLANO DE MIGRAÇÃO

Fase 0: Validação (este documento)

  • [x] Inventário corrigido
  • [x] Verificações críticas resolvidas
  • [ ] Snapshot do VPS atual no painel Hostinger

Fase 1: Provisionar VPS Destino

```bash

No VPS destino — Ubuntu 24.04 LTS, root/sudo

1. Hostname e timezone

hostnamectl set-hostname edmundo10-prod

timedatectl set-timezone America/Sao_Paulo

2. Atualizar base

apt update && apt -y upgrade

apt -y install curl gnupg ca-certificates lsb-release rsync git ufw htop \

fonts-liberation libnss3 libatk1.0-0 libxshmfence1 libgbm1

3. User www com UID/GID 1000 (se o cloud-init já criou 'ubuntu' com 1000, remover antes)

id ubuntu 2>/dev/null && deluser --remove-home ubuntu

groupadd -g 1000 www

useradd -u 1000 -g 1000 -m -s /bin/bash www

4. Nginx

apt -y install nginx

5. PHP 8.3 (nativo do 24.04)

apt -y install php8.3-fpm php8.3-cli php8.3-curl php8.3-sqlite3 \

php8.3-mbstring php8.3-gd php8.3-xml php8.3-zip

6. Node.js 22 (NodeSource)

curl -fsSL https://deb.nodesource.com/setup_22.x | bash -

apt -y install nodejs

travar versão exata:

npm install -g corepack # opcional

7. Google Chrome stable (mesma major v144.x)

curl -fsSL https://dl.google.com/linux/linux_signing_key.pub | gpg --dearmor -o /usr/share/keyrings/google-chrome.gpg

echo "deb [arch=amd64 signed-by=/usr/share/keyrings/google-chrome.gpg] http://dl.google.com/linux/chrome/deb/ stable main" \

> /etc/apt/sources.list.d/google-chrome.list

apt update && apt -y install google-chrome-stable

google-chrome --version # conferir v144.x

8. Certbot

apt -y install certbot python3-certbot-nginx

9. Firewall

ufw default deny incoming

ufw default allow outgoing

ufw allow OpenSSH

ufw allow 'Nginx Full'

ufw --force enable

10. Estrutura de diretórios

install -d -o www -g www /www/wwwroot

install -d -o www -g www /www/wwwlogs

```

Fase 2: Transferir Código (hot, com produção rodando)

No VPS destino:

```bash

sudo -u www git clone https://github.com/GeJoRei/edmundo10.git /www/wwwroot/edmundo10.com.br

cd /www/wwwroot/edmundo10.com.br/bot/whatsapp

sudo -u www npm ci # reinstala node_modules do zero

```

No VPS origem:

```bash

Pré-sync (acelera o delta do cutover; repetir na hora H)

rsync -avP --delete \

/www/wwwroot/edmundo10.com.br/painel-novo/data/ \

root@NOVO_IP:/www/wwwroot/edmundo10.com.br/painel-novo/data/

rsync -avP --delete \

/www/wwwroot/edmundo10.com.br/painel-novo/storage/ \

root@NOVO_IP:/www/wwwroot/edmundo10.com.br/painel-novo/storage/

NÃO sincronizar auth/ ainda — só no cutover, com service parado

```

No destino, após o rsync:

```bash

chown -R www:www /www/wwwroot/edmundo10.com.br

```

Fase 3: Configurar Serviços no Destino

```bash

Nginx vhost (em /etc/nginx/sites-available/edmundo10.com.br — simplificado)

cat > /etc/nginx/sites-available/edmundo10.com.br <<'NGINX'

server {

listen 80;

listen [::]:80;

server_name edmundo10.com.br www.edmundo10.com.br;

root /www/wwwroot/edmundo10.com.br;

index index.php index.html;

access_log /www/wwwlogs/edmundo10.com.br.log;

error_log /www/wwwlogs/edmundo10.com.br.error.log;

location ~ ^/(\.user\.ini|\.htaccess|\.git|\.env)$ { return 404; }

location ~ \.php$ {

include snippets/fastcgi-php.conf;

fastcgi_pass unix:/run/php/php8.3-fpm.sock;

}

location ~ \.well-known { allow all; }

error_page 404 /404.html;

error_page 502 /502.html;

}

NGINX

ln -sf /etc/nginx/sites-available/edmundo10.com.br /etc/nginx/sites-enabled/

rm -f /etc/nginx/sites-enabled/default

nginx -t && systemctl reload nginx

.user.ini já vem do git, confirmar

cat /www/wwwroot/edmundo10.com.br/.user.ini

open_basedir=/www/wwwroot/edmundo10.com.br/:/tmp/

Systemd service — copiar IGUAL ao origem

scp root@ORIGEM:/etc/systemd/system/edmundo10-whatsapp.service /etc/systemd/system/

systemctl daemon-reload

systemctl enable edmundo10-whatsapp

Crontab root

(crontab -l 2>/dev/null; echo '/5 * /www/wwwroot/edmundo10.com.br/bot/whatsapp/watchdog.sh') | crontab -

Permissões dos dados do painel

chown -R www:www /www/wwwroot/edmundo10.com.br

find /www/wwwroot/edmundo10.com.br/painel-novo/data -type f -exec chmod 664 {} \;

find /www/wwwroot/edmundo10.com.br/painel-novo/data -type d -exec chmod 775 {} \;

chmod -R 700 /www/wwwroot/edmundo10.com.br/bot/whatsapp/auth

SSL — preferir certbot novo contra Let's Encrypt (só após DNS apontar)

Alternativa temporária: copiar certs do BT-Panel, mas renovação fica manual

```

Fase 4: CUTOVER (janela de 5–10 min)

Ordem precisa, com o service do origem parado durante o rsync do auth/:

```bash

1. [ORIGEM] Parar o bot

systemctl stop edmundo10-whatsapp

2. [ORIGEM → DESTINO] Rsync final (delta curto)

rsync -avP --delete /www/wwwroot/edmundo10.com.br/painel-novo/data/ \

root@NOVO_IP:/www/wwwroot/edmundo10.com.br/painel-novo/data/

rsync -avP --delete /www/wwwroot/edmundo10.com.br/painel-novo/storage/ \

root@NOVO_IP:/www/wwwroot/edmundo10.com.br/painel-novo/storage/

rsync -avP --delete /www/wwwroot/edmundo10.com.br/bot/whatsapp/auth/ \

root@NOVO_IP:/www/wwwroot/edmundo10.com.br/bot/whatsapp/auth/

3. [DESTINO] Ownership e boot do bot

chown -R www:www /www/wwwroot/edmundo10.com.br

systemctl start edmundo10-whatsapp

sleep 10

systemctl status edmundo10-whatsapp --no-pager

journalctl -u edmundo10-whatsapp -n 50 --no-pager

4. [DESTINO] Health check local

curl -sS http://127.0.0.1:3035/status -H "apikey: edm10_secret_key_2026_v1"

Esperar "ready": true / conectado

5. [LOCAL do operador] Validar sem DNS via /etc/hosts

echo 'NOVO_IP edmundo10.com.br www.edmundo10.com.br' >> /etc/hosts

Abrir https://edmundo10.com.br — testar login admin, QR (deve estar já logado), stats

6. [DNS] Só se Fase 4.5 verde: apontar registro A (e AAAA se usar IPv6) para NOVO_IP

e confirmar com dig edmundo10.com.br @1.1.1.1

7. [DESTINO] SSL definitivo

certbot --nginx -d edmundo10.com.br -d www.edmundo10.com.br --non-interactive --agree-tos -m edmundo@edmundo10.com.br

nginx -t && systemctl reload nginx

```

Fase 5: Pós-Cutover

  • [ ] Monitorar journalctl -u edmundo10-whatsapp -f por 1h
  • [ ] Monitorar /www/wwwlogs/edmundo10.com.br.error.log por 24h
  • [ ] Teste de envio autorizado: apenas para 5521999915554 e 5521999605790 (regra AGENTS.md §7)
  • [ ] VPS antigo: manter ligado com service parado por 7 dias (rollback); depois derrubar

Fase 6: Cleanup

  • Remover backups .bkp* que tenham sido trazidos por engano
  • Remover entrada /etc/hosts local de teste
  • Revogar SSH keys que não sejam mais necessárias no origem

7. RISCOS E MITIGAÇÕES

| Risco | Prob. | Impacto | Mitigação |

|-------|-------|---------|-----------|

| Sessão WhatsApp invalidada (re-scan de QR) | Média | Alto | Rsync do auth/ só com service parado; Chrome de major igual (144) no destino; se cair, ter telefone admin pronto para reescanear via /painel-novo/whatsapp_qr.php |

| Divergência WPP_API_KEY entre service e config.php | Baixa | Alto | Já batem hoje (edm10_secret_key_2026_v1); replicar service file igual |

| Chrome com major diferente não reabre perfil | Média | Alto | Pin no v144 no destino; se upgrade ocorrer, hold via apt-mark hold google-chrome-stable até o cutover |

| UID/GID diferentes quebrarem ownership do auth/ | Média | Médio | useradd -u 1000 -g 1000 www antes de qualquer rsync |

| SSL do Certbot falhar no primeiro renew | Baixa | Médio | DNS propagar antes (TTL 300); certbot --dry-run após cutover |

| SQLite corrompido por cópia em andamento | Baixa | Alto | Service parado antes do rsync final do data/; backup runtime.sqlite.predump |

| runtime.sqlite recebendo escrita durante pré-sync | N/A | — | Pré-sync é só para acelerar; sync final com service parado é autoritativo |

| Puppeteer/libs faltando no destino | Baixa | Médio | Stack §2.3 inclui fonts-liberation, libnss3, libatk1.0-0, libxshmfence1, libgbm1 |

| Hostinger bloquear SSH root entre VPS | Baixa | Médio | Testar ssh root@NOVO_IP antes do cutover; usar rsync -e "ssh -p 22" com chave |


8. SPECS DO VPS DESTINO (esperado — Hostinger idêntico)

| Item | Valor |

|------|-------|

| OS | Ubuntu 24.04 LTS (idêntico) |

| CPU | 4 vCPU (EPYC ou equivalente) |

| RAM | 16 GiB (o atual tem 15 + 8 de swap; novo só para o edmundo é folga grande) |

| Disco | ≥ 50 GiB (projeto total ~1GB; sobra para logs/chrome cache) |

| IPv6 | Desejável (ter AAAA) |

| Snapshot automático | Habilitar na Hostinger |

Uso esperado em produção (1 projeto isolado):

  • RAM em uso: ~2 GB (Node + Chrome headless + PHP-FPM + Nginx)
  • CPU: <5% médio
  • Disco: <2 GB ativo (maior parte em auth/session e logs)

9. ROLLBACK

  1. [DESTINO] systemctl stop edmundo10-whatsapp
  2. [ORIGEM] systemctl start edmundo10-whatsapp
  3. [DNS] reverter registro A (e AAAA) para IP antigo
  4. TTL baixo (300s) faz propagar em minutos
  5. Investigar causa com logs do destino (journalctl -u edmundo10-whatsapp, error_log do nginx)

VPS antigo fica ligado por 7 dias após cutover antes de ser desligado/destruído.


10. CHECKLIST FINAL DE EXECUÇÃO

Pré-cutover

  • [ ] Snapshot Hostinger do VPS antigo
  • [ ] VPS destino provisionado + stack Fase 1 instalada
  • [ ] Chrome v144 confirmado no destino (apt-mark hold opcional)
  • [ ] User www UID=1000/GID=1000 criado no destino
  • [ ] Git clone + npm ci concluídos no destino
  • [ ] Pré-sync de data/ e storage/ executado
  • [ ] Vhost nginx ativo (respondendo em http://NOVO_IP)
  • [ ] Systemd service copiado (ainda parado)
  • [ ] TTL do DNS em 300s há ≥ 24h
  • [ ] Teste /etc/hosts local: painel abre no destino com dados pré-syncados

Cutover

  • [ ] systemctl stop edmundo10-whatsapp no origem
  • [ ] Rsync final data/, storage/, auth/
  • [ ] chown -R www:www no destino
  • [ ] systemctl start edmundo10-whatsapp no destino
  • [ ] journalctl -u edmundo10-whatsapp -f sem erros
  • [ ] curl em /status responde ready: true
  • [ ] Login admin OK via /etc/hosts
  • [ ] QR: bot já logado (sem pedir scan)
  • [ ] Envio de teste para número autorizado OK
  • [ ] DNS apontando para NOVO_IP
  • [ ] Certbot emite certificado novo
  • [ ] HTTPS respondendo no novo IP

Pós-cutover

  • [ ] Monitor 1h
  • [ ] Monitor 24h
  • [ ] VPS antigo com service parado mas VPS ligada
  • [ ] D+7: destruir VPS antigo (após confirmação explícita)

11. NOTAS

  • BT-Panel é opcional no destino. Recomendo instalar nginx/php/node nativos e não depender do painel — simplifica auditoria e atualizações.
  • O watchdog.sh é mantido por segurança histórica, mas com Restart=always no systemd ele raramente dispara. Não remover.
  • O package.json diz "rnt-whatsapp-service" por herança de clone do Rio no Teatro; ignorar esse label — o código já divergiu e é específico do edmundo10.
  • Regras operacionais em AGENTS.md continuam valendo no destino — especialmente a §7 sobre testes somente em números autorizados.

Documento criado: 2026-04-22

Revisão: 2026-04-22 (verificações resolvidas, inventário corrigido)