Capítulo 17a Conformidade, armazenamento & operação Admin: #/protect/overview

Backup & Recovery (nextxch Protect): exportação de evidências, configuração, dados, restauração e troca de provedor

O nextxch Protect reúne no admin, em Backup & Recovery, tudo o que você precisa para evidências, backup e recuperação: exportação EML com valor probatório e manifesto assinado com Ed25519, backup da configuração com versões, backup de dados incremental e criptografado (diretório, compartilhamento SMB ou S3 com Object Lock), restauração na caixa de correio a partir do arquivo GoBD, dos itens excluídos ou de um backup de dados, recuperação bare-metal na primeira inicialização e implantação por pipeline com restauração e sincronização ao vivo para uma troca de provedor. Tudo está integrado ao servidor, sem produto adicional e sem serviço externo.

Dica operacional & nota de arquitetura

Ordem para começar: primeiro configure a chave de backup em Backup & Recovery > Configuração (uma frase secreta de pelo menos 12 caracteres ou uma chave de recuperação, somente como administrador do servidor com login) e guarde-a fora do servidor. Backup da configuração e backup de dados usam a mesma chave; o servidor armazena apenas a parte pública e pode gravar backups, mas nunca lê-los. Licença: backup da configuração, verificação de exportações de evidências, autoatendimento no Webmail, restauração na primeira inicialização e restauração por pipeline da configuração estão incluídos em todas as edições; backup de dados, exportação de evidências, tarefas de restauração, a parte de dados da restauração por pipeline e a sincronização ao vivo a partir do Business.

1. Início rápido: chave, destino, primeiro backup e verificação

Destinos e agendamentos são configurados em Backup & Recovery > Agendamentos e destinos (somente administradores do servidor). O nextxch-cli faz login com uma chave de API ou um login de administrador.

Referência / configuração
# 1. Admin > Backup & Recovery > Configuration: set up the backup key
#    (passphrase of 12+ characters or recovery key, keep it safe outside the server)
# 2. Schedules & targets: add a target (directory, SMB share \\nas\backup\nextxch or S3) and "Test"
# 3. Back up the configuration (every tier) and take it along as a file:
nextxch-cli config backup --label "before migration" -o nextxch-config.zip

# 4. Data backup (Business): full first, then incremental by schedule
nextxch-cli backup run --target nas --full
nextxch-cli backup list --target nas

# 5. Verify, with the passphrase including decryption of the sample
export NEXTXCH_BACKUP_PASSPHRASE='...'
nextxch-cli backup verify --target nas --passphrase-env NEXTXCH_BACKUP_PASSPHRASE --limit 200

2. Exportação com valor probatório: ZIP, manifesto, assinatura e verificação

As mensagens entram no ZIP byte a byte como .eml. manifest.json lista cada arquivo com SHA-256, tamanho, hash de arquivamento, estado de integridade, retenção e retenção legal (legal hold); manifest.json.sig é uma assinatura Ed25519 sobre os bytes exatos do manifesto, derivada do segredo do servidor e idêntica em todos os nós do cluster. GET /api/compliance/exports/public-key retorna a chave pública sem login. A opção de descriptografia remove apenas a criptografia em repouso (somente ServerAdmin e ComplianceAuditor; caso contrário, 403 DECRYPT_NOT_ALLOWED); não é uma descriptografia geral de S/MIME ou OpenPGP. O download individual GET /api/compliance/messages/{id}/raw retorna os hashes como cabeçalhos HTTP X-Nextxch-Sha256, X-Nextxch-Stored-Sha256, X-Nextxch-Integrity e Repr-Digest. Exportação a partir do Business, verificação em todas as edições.

Referência / configuração
nextxch-evidence-20261111-0930-1a2b3c4d.zip
  messages/000001-<archiveId>.eml     original message, byte for byte
  messages/000002-<archiveId>.eml
  SHA256SUMS.txt                      verifiable with sha256sum -c
  manifest.json                       format nextxch-evidence-export/1, scope (incl. caseReference), items[]
  manifest.json.sig                   Ed25519: algorithm, keyId, publicKey, signedSha256, signature
  README.txt

# Start an export (202, status under GET /api/compliance/exports/{id}):
curl -X POST https://mail.company.com/api/compliance/exports -H "X-Api-Key: $KEY" \
  -H "Content-Type: application/json" \
  -d '{"scope":"mailbox","account":"anna@company.com","sinceUtc":"2026-01-01T00:00:00Z","caseReference":"Case 2026-0815"}'

# Verify offline, without access to the server (exit code 0 valid, 1 invalid/tampered, 2 usage error):
curl -s https://mail.company.com/api/compliance/exports/public-key > nextxch-evidence-key.json
nextxch-cli export verify nextxch-evidence-20261111-0930-1a2b3c4d.zip --public-key <publicKey from the file>
unzip -d export nextxch-evidence-20261111-0930-1a2b3c4d.zip && cd export && sha256sum -c SHA256SUMS.txt

3. Backup da configuração: conteúdo, criptografia, diff e restauração parcial

Um pacote contém a configuração como código (config/*.yaml), arquivos de estado sem segredos (server/*), regras Sieve e os segredos criptografados em secrets.enc (AES-256-GCM, chave de dados envolvida para a chave de backup; um backup manual pode receber adicionalmente sua própria frase secreta). Seções: config:<area>, dkim, passwords, tls-certificates, api-keys, sieve, server-files, licence; licence, passwords e api-keys só são restaurados quando nomeados explicitamente. Por padrão, a restauração é uma simulação (dry run) com pré-visualização. Em todas as edições; REST em /api/v1/config/backups.

Referência / configuração
nextxch-cli config list                                   # versions (reason: manual, pre-update, after-change, pre-restore, import)
nextxch-cli config diff 20261101T020000Z-a1b2c3 current             # difference between two versions or to the current state
nextxch-cli config backup --label "before update" --passphrase-env BACKUP_PW -o nextxch-config.zip
nextxch-cli config import -f nextxch-config.zip           # take over a package of another server

# Partial restore: preview first, then apply
nextxch-cli config restore 20261101T020000Z-a1b2c3 --sections dkim,config:domains --domain company.com --dry-run
nextxch-cli config restore 20261101T020000Z-a1b2c3 --sections dkim,config:domains --domain company.com --yes

# REST: POST /api/v1/config/backups/{id}/restore
# {"sections":["dkim","config:domains"],"domain":"company.com","prune":false,"dryRun":true}

4. Backup de dados: destinos, formato e catálogo

Cada execução gera uma versão autônoma: snapshot do banco de dados por tabela (independente do provedor, permitindo inclusive SQLite para PostgreSQL), arquivos de estado, o manifesto do arquivo GoBD e todos os blobs referenciados. Os blobs são endereçados por SHA-256 e transferidos apenas uma vez; uma execução incremental envia somente hashes novos. Tudo é armazenado criptografado no formato NXB1 (AES-256-GCM em blocos, vinculado ao nome do objeto). Catálogo e índice de blobs são JSON legível sem segredos; o catálogo é assinado com a chave Ed25519 da exportação de evidências. O formato completo está no repositório em docs/protect/backup-format.md. A partir do Business; REST em /api/admin/protect/backups (administradores do servidor).

Referência / configuração
<target>/                                 directory, SMB share or s3://bucket/nextxch-backup/
  nextxch-backup.json                       target marker
  keys/backup-key-<keyId>.json              public key + sealed private key
  keys/dk-<dataKeyId>.json                  data key of one run (ECDH wrapped)
  blobs/ab/cd/<sha256>.nxb                  one mail or file content, immutable
  versions/20261111T023000Z-a1b2c3/
    catalog.json  catalog.json.sig          catalog (written last = version complete) + signature
    blobs.ndjson.gz                         blob index of the version
    db/<table>.ndjson.gz.nxb                database snapshot, one file per table
    files/<path>.nxb                        state files of the data directory
    archive-manifest.json.gz.nxb            retention, legal hold, integrity chain

# Settings via REST (PUT /api/admin/protect/backups/settings):
{"verifyEveryHours":24,"verifySampleSize":50,"alertOnFailure":true,"uploadParallelism":4}

# Back up a domain or single mailboxes:
nextxch-cli backup run --target s3-fsn1 --scope domains:company.com,company.at
nextxch-cli backup run --target s3-fsn1 --scope mailboxes:anna@company.com --no-wait

5. Restaurar na caixa de correio: origem, ponto no tempo, destino

Origens: archive (arquivo GoBD), recoverable (itens excluídos) e backup (backup de dados). Escolha o ponto no tempo com --point (id do snapshot, day:yyyy-MM-dd ou latest) ou --as-of. Destinos: original (pasta original), restored (padrão, pasta "Wiederhergestellt yyyy-MM-dd", nome via --label) ou account (outra caixa de correio do mesmo locatário, por exemplo uma caixa de correio de sucessor). Duplicatas são ignoradas por SHA-256, Message-ID e UID; as origens permanecem inalteradas. Permitido para TenantAdmin e ServerAdmin, até 250.000 itens por tarefa; tarefas a partir do Business, política e autoatendimento no Webmail em todas as edições.

Referência / configuração
nextxch-cli restore points  --account anna@company.com --source backup
nextxch-cli restore browse  --account anna@company.com --source backup --point latest --folder INBOX --filter "invoice"
nextxch-cli restore preview --account anna@company.com --source archive --as-of 2026-10-31T23:59:59Z --folder "Projects/Plant"
nextxch-cli restore start   --account anna@company.com --source archive --as-of 2026-10-31T23:59:59Z \
  --folder "Projects/Plant" --target restored --label "Plant (restored)"

# Whole mailbox into a successor mailbox:
nextxch-cli restore start --account ben@company.com --source backup --point day:2026-11-01 \
  --target account --target-account successor@company.com --passphrase-env NEXTXCH_BACKUP_PASSPHRASE
nextxch-cli restore jobs --account ben@company.com

# REST: /api/compliance/restore (sources, points, browse, preview, jobs, policy)
# Webmail: GET /api/mail/self-restore, POST /api/mail/self-restore {"ids":[...]}

6. Recuperação bare-metal: nova instalação mais backup devolvem o servidor antigo

Em uma instalação nova (MSI, Docker ou Linux, no máximo um locatário, um domínio, uma conta e ainda nenhum login de administrador), /setup/ mostra "Restaurar a partir de backup" abaixo do login: enviar o pacote, frase secreta, pré-visualização, restauração, opcionalmente o backup de dados, concluir e reiniciar. Acesso somente com o token de configuração de uso único que a primeira inicialização grava no log e em {DataDirectory}/first-run/setup-token.txt (cabeçalho X-Nextxch-Setup-Token), ou a partir do próprio servidor com Setup:TrustLoopback=true. O primeiro login de administrador ou Concluir fecha o assistente definitivamente. A chave de backup do servidor antigo não é transferida e precisa ser configurada novamente depois. O índice de texto completo do SQLite não faz parte do backup: a pesquisa encontra os e-mails restaurados após uma reindexação.

Referência / configuração
# Headless via CLI (same API /api/setup):
export NEXTXCH_SETUP_TOKEN="$(cat /var/lib/nextxch/first-run/setup-token.txt)"
export NEXTXCH_BACKUP_PASSPHRASE='...'
nextxch-cli setup restore --config nextxch-config.zip --data s3://dr-bucket/nextxch/ --prune --dry-run
nextxch-cli setup restore --config nextxch-config.zip --data s3://dr-bucket/nextxch/ --prune --yes

# Unattended on first start (Docker Compose, Kubernetes, MSI):
environment:
  NEXTXCH_RESTORE_FROM: s3://dr-bucket/nextxch/          # .zip, directory, s3://, https:// or config-backup:<id>
  NEXTXCH_RESTORE_PASSPHRASE: ${BACKUP_PASSPHRASE}       # without: configuration without secrets
  NEXTXCH_RESTORE_DATA_FROM: s3://dr-bucket/nextxch/     # optional, location of the data backup
  NEXTXCH_RESTORE_PRUNE: "true"                          # remove bootstrap objects
  NEXTXCH_RESTORE_WITH_CREDENTIALS: "true"               # passwords, API keys, licence (default true)
  NEXTXCH_RESTORE_S3_ENDPOINT: https://fsn1.your-objectstorage.com
  NEXTXCH_RESTORE_S3_ACCESS_KEY: ${S3_KEY}
  NEXTXCH_RESTORE_S3_SECRET_KEY: ${S3_SECRET}
# Result: {DataDirectory}/pipeline-restore/first-start.json ("ok": true = variable is ignored afterwards)
# Helm: restore.from, restore.scope, restore.mapping, restore.passphrase, restore.s3.* (replicaCount: 1)

7. Implantação por pipeline com restauração (nextxch-cli deploy --restore)

Um comando ou uma etapa de pipeline reconstrói um servidor a partir de um backup: aplicar a configuração, restaurar os dados, executar verificações (amostra de hashes, integridade, e-mail de teste somente para o Mailpit ou uma caixa de correio local) e, opcionalmente, instruções para a alteração de DNS/MX; o DNS nunca é alterado automaticamente. Cada execução é idempotente e, após uma interrupção, retoma na última etapa concluída. O arquivo de mapeamento (kind RestoreMapping, esquema em GET /api/v1/deploy/mapping-schema) reescreve nomes de host, endereços IP e caminhos, define de onde vêm os certificados (backup, acme, files) e descreve o banco de dados e o armazenamento do novo host; domínios de e-mail nunca são renomeados. Login com uma chave de integração com escopo deploy.restore. Configuração em todas as edições, parte de dados a partir do Business (exceto na primeira inicialização de uma instalação nova); a parte de dados abrange o escopo all.

Referência / configuração
# mapping.yaml
apiVersion: nextxch/v1
kind: RestoreMapping
hostnames:
  mail.old-provider.example: mail.company.com
ips:
  203.0.113.10: 198.51.100.20
paths:
  "C:\\Data\\NextxchData": /var/lib/nextxch
certificates:
  mode: acme                      # backup | acme | files
  acme: {contactEmail: hostmaster@company.com}
database:
  provider: Postgres              # must match the new host (Storage__Provider)
  connectionStringEnv: NEXTXCH_PG_CONNECTION
storage:
  blobBackend: S3
  s3: {endpoint: https://fsn1.your-objectstorage.com, bucket: nextxch-mail}

# Plan (dry run, shows every replacement), then restore with checks:
nextxch-cli deploy --restore ./nextxch-config.zip --scope config --map mapping.yaml --dry-run
nextxch-cli deploy --restore s3://dr-bucket/nextxch/ --map mapping.yaml --test-mail mailpit --dns-instructions --yes

# REST: POST /api/v1/deploy/restore (dryRun defaults to true)
# {"source":"s3://dr-bucket/nextxch/","scope":"all","mapping":"...","dryRun":false,"testMail":"mailpit","hashSample":20}
# Local package: POST /api/v1/deploy/restore/upload (application/zip) -> source "upload:<sha256>"
# Runs: GET /api/v1/deploy/restore/runs

8. Modelos de CI: GitHub Actions, GitLab CI, Azure DevOps e Ansible

Os modelos estão no repositório em deploy/ci: restauração com etapa de planejamento e aprovação no ambiente de produção, além de um teste noturno de DR que restaura em um ambiente descartável e grava um relatório com duração (RTO) e estado (RPO). Segredos devem ficar em variáveis de CI mascaradas e protegidas; e-mails de teste vão para um contêiner Mailpit ao lado do job e nunca saem dele.

Referência / configuração
deploy/ci/github-actions/nextxch-restore.yml        plan on a throwaway instance, container with restore on first start, checks, DNS step
deploy/ci/github-actions/nextxch-dr-probe.yml       nightly DR probe with RTO/RPO report
deploy/ci/gitlab/.gitlab-ci.yml                     restore (RESTORE_SOURCE, RESTORE_SCOPE, PLAN_ONLY ...) + DR probe (NEXTXCH_PIPELINE=dr-probe)
deploy/ci/azure-devops/azure-pipelines.yml          restore with parameters, deployment job on environment production
deploy/ci/azure-devops/azure-pipelines-dr-probe.yml nightly DR probe, report in the run summary
deploy/ci/ansible/playbook-restore.yml              role nextxch_restore: container (Linux) or MSI (Windows)
deploy/ci/mapping.example.yaml, mapping.schema.json example and JSON Schema of the mapping file

9. Sincronização ao vivo para uma troca de provedor: um congelamento curto em vez de uma longa interrupção

Após a restauração completa, o novo servidor acompanha o antigo com execuções delta: o servidor antigo continua gravando seu backup de dados (por exemplo, a cada hora no S3), e cada execução transfere apenas blobs, linhas de tabela e arquivos de estado alterados desde a última versão transferida. O progresso fica em {DataDirectory}/pipeline-restore/live-sync.json; executar o mesmo comando novamente não altera nada ou retoma. Para a migração final, o servidor antigo é congelado manualmente (bloquear as portas de e-mail e de clientes no firewall dele, manter o serviço em execução, último backup com nextxch-cli backup run --full); em seguida, --cutover --source-frozen transfere esse backup com uma comparação completa das linhas. Depois, reinicie o novo servidor e altere o DNS. A partir do Business; REST: POST /api/v1/deploy/live-sync, POST /api/v1/deploy/live-sync/cutover, GET /api/v1/deploy/live-sync.

Referência / configuração
nextxch-cli deploy --restore s3://dr-bucket/nextxch/ --scope all --yes                          # 1. full restore (baseline)
nextxch-cli deploy --restore s3://dr-bucket/nextxch/ --live-sync --dry-run                      # remaining delta, changes nothing
nextxch-cli deploy --restore s3://dr-bucket/nextxch/ --live-sync --interval 5m --until-cutover  # 2. follow the old server
nextxch-cli deploy --restore s3://dr-bucket/nextxch/ --cutover                                  # 3. instructions for the freeze
# old server: block ports, then  nextxch-cli backup run --full
nextxch-cli deploy --restore s3://dr-bucket/nextxch/ --cutover --source-frozen                  # 4. last backup, last run

Configurações, valores padrão e boas práticas

Configuração / local Descrição Valor padrão Boa prática para produção
Konfigurationssicherung: Versionen (#/protect/config) Versões automáticas antes de cada atualização (AutoBeforeUpdate) e após alterações (AutoAfterChanges, agrupadas após DebounceMinutes), além de versões manuais, importações e um snapshot de segurança antes de cada restauração. KeepLast 30 · KeepDailyDays 90 · Debounce 10 min Antes de alterações maiores, crie uma versão manual com rótulo e guarde o .zip fora do servidor.
Sicherungsschlüssel (Passphrase / Wiederherstellungsschlüssel) ECDH P-256; a parte privada existe apenas selada (PBKDF2-SHA256 com 600.000 iterações, AES-256-GCM) e viaja dentro de cada pacote. Sem chave e sem frase secreta, um backup da configuração não contém segredos. nicht eingerichtet · Passphrase ab 12 Zeichen Imprima a chave de recuperação e guarde-a separada do servidor; sem ela, os backups de dados não podem ser lidos.
Datensicherung: Aufbewahrung je Ziel As KeepLast versões mais recentes, mais a versão mais recente de cada uma das últimas KeepHourly horas, KeepDaily dias, KeepWeekly semanas ISO e KeepMonthly meses (UTC). 3 / 24 / 7 / 4 / 12 Mantenha pelo menos duas versões durante uma sincronização ao vivo; caso contrário, o delta não pode ser calculado (BASELINE_GONE).
S3 Object Lock (ObjectLockMode, ObjectLockDays) Os objetos são gravados com o modo Governance ou Compliance e uma data retain-until; blobs reutilizados recebem uma data estendida (agora mais 1,5 vez os dias de bloqueio), para que nenhuma versão aponte para um objeto que se torne excluível cedo demais. Normal · 30 Tage Para proteção contra ransomware, use o modo Compliance em um bucket dedicado com versionamento; objetos bloqueados só são removidos por uma execução posterior, após a data deles.
Zeitpläne (Frequency, Type, Scope) A cada hora, diariamente ou semanalmente, incremental ou completo, por destino e escopo (servidor, domínios, caixas de correio); horário no fuso local do servidor, sem expressão cron. Täglich 02:30 inkr. · Sonntag 03:30 voll Os agendamentos preparados não têm destino no início: atribua um destino e ative-os; caso contrário, nenhum backup será executado.
Automatische Prüfung (VerifyEveryHours, VerifySampleSize) Verifica hashes armazenados, cabeçalhos de envelope, arquivos de chave, a assinatura do catálogo e a legibilidade do catálogo e do índice de blobs sem a chave; com a frase secreta, a amostra e todos os arquivos de tabela também são descriptografados. alle 24 h · 50 Objekte Mantenha AlertOnFailure ativado para que backups e verificações com falha cheguem aos destinos de alerta.
Parallele Uploads je Sicherung (UploadParallelism) Número de uploads simultâneos para destinos S3 e de diretório. 4 (1 bis 32) Para S3 em conexões rápidas, 8 a 16; para um NAS em SMB lento, de preferência 2 a 4.
SQL Server: ALLOW_SNAPSHOT_ISOLATION O nextxch tenta ativar o snapshot isolation na inicialização. Se estiver desativado, as tabelas são exportadas uma a uma com READ COMMITTED (consistency read-committed) e a execução emite um aviso. an, wenn erlaubt A visão geral mostra a instrução SQL para copiar; com snapshot isolation, o snapshot do banco de dados é transacionalmente consistente.
RecoverableItemsDays (restore-policy.json) Por quanto tempo compromissos, contatos, tarefas e notas excluídos mantêm seu conteúdo; depois, resta apenas um marcador vazio (tombstone) para a sincronização. E-mails excluídos de forma reversível permanecem até serem expurgados. 14 Tage (nach Upgrade 30) Registre isso na documentação de procedimentos: sem um backup de dados, itens de groupware excluídos perdem seu conteúdo após esse período.
Selbstbedienung im Webmail (SelfServiceEnabled, SelfServiceDays) Os usuários recuperam por conta própria e-mails e itens de groupware excluídos em Restaurar itens excluídos (até 500 por execução). Ajustável para todo o servidor ou por domínio; 0 dias significa nenhuma janela própria. an · 0 Tage Para domínios com regras rígidas, defina ali uma janela ou desative o autoatendimento.
Beweisexport: Rollen, Umfang, Download ComplianceAuditor, TenantAdmin (somente o próprio locatário) e ServerAdmin podem exportar; escopo search, mailbox, range ou legalHold, até 100.000 mensagens (no máximo 250.000). O link de download é válido por 24 horas. includeSoftDeleted true · 24 h Sempre informe uma referência de caso (caseReference): ela consta no manifesto assinado e no log de auditoria.
Setup:TrustLoopback Permite requisições do próprio servidor (loopback) ao assistente de configuração sem o token de configuração. Por padrão, toda requisição precisa do token de first-run/setup-token.txt. false Defina somente em hosts sem outros usuários locais; caso contrário, passe o token via NEXTXCH_SETUP_TOKEN.
Audit-Log & GoBD Cada etapa consta no log de auditoria: config.backup*, data.backup.*, Compliance.EvidenceExport*, Protect.Restore*, Protect.SelfRestore, Protect.RestorePolicy, setup.* e config.restore; visível em Backup & Recovery > Log. O arquivo GoBD permanece inalterado em qualquer restauração. aktiv O backup de dados contém o manifesto do arquivo com retenção e retenção legal (legal hold); após uma restauração, cada hash arquivado é verificado e os bloqueios são definidos novamente.