Pular para conteúdo

0006 — Observabilidade remota e kill-switch do GlitchTip

Status: Aprovado · Responsável: Gustavo Madruga · Atualizado em: 2026-09-21 · Decidido em: 2026-09-21

Contexto

O programa roda na máquina do cliente, sem acesso remoto. Diagnosticar exigia pedir o arquivo de log para a equipe do cliente, um a um: o que foi escrito no dXpEnvio, o que voltou no dXpRetorno, os avisos e a configuração do processo só existiam lá.

Ao mesmo tempo, o GlitchTip que já existia não tinha desligamento. O DSN vem do app.json embarcado no jar e o Sentry.init o passava explícito, então nenhuma variável de ambiente o desligava e --debug só trocava a tag. Em 15/09/2026 a rodada local do e2e-maxsul-pied abriu três incidentes com environment=production no projeto 18 — chaves E2E-REMESSA-INC, E2E-FILHO-1XX e E2E-RESOLV-MAN, todos com "Rejeitado pelo fake" no texto. Não corrompeu dado, mas queimou o sinal: alerta de remessa travada em produção ficou indistinguível de incidente real de cliente. A suíte contornou com um app.json de override antes do jar no classpath — paliativo que depende da ordem do classpath.

Decisão

  1. A variável de ambiente SENTRY_DSN vence o app.json sempre que estiver definida — inclusive vazia, que desliga o envio. É o mesmo desligamento dos apps Micronaut da casa, e dispensa o truque de classpath no e2e.
  2. O DSN continua versionado no app.json. O desenho de injetar o DSN no deploy é dos apps que o Coolify provisiona; este é on-premise, distribuído como jar, sem ninguém injetando env na máquina do cliente. Tirá-lo do repo moveria o problema para o empacotamento de cada cliente sem ganho: DSN de ingest é público por desenho.
  3. Um caminho só para o WARN: o SentryAppender do Logback (minimumEventLevel=WARN, minimumBreadcrumbLevel=INFO) é quem leva evento ao GlitchTip. As chamadas explícitas a Sentry.captureMessage de nível WARNING saíram; a curadoria que elas faziam (dedup por causa nos avisos da coleta, filtro de conflito no dRels3) passou a decidir o nível do log.
  4. Dois loggers ficam fora do appender, por filtro no logback.xml: o do eco (…integradorclient.eco) e o do operador (…integradorclient.operador, para configuração quebrada e JVM de 32 bits).
  5. O eco do dXp vai cru, 100%, como breadcrumb, em blocos de até 25 linhas ou 4 000 caracteres, com o teto de breadcrumbs em 200.
  6. setSendDefaultPii(true) (padrão da casa) e o hook de encerramento do SDK ligado, com flushTimeoutMillis explícito — o programa captura e chama System.exit na linha seguinte.

Consequências

  • Uma rodada de e2e ou de desenvolvimento com SENTRY_DSN='' não cria issue nenhuma; o paliativo do classpath pode sair da suíte.
  • As linhas cruas carregam CPF/CNPJ, nome e fantasia (cgc_cpf, nome_prop, fantasia no layout do pAbast). É decisão consciente do dono: o GlitchTip é auto-hospedado na infraestrutura da X-Adm, não em SaaS de terceiro, e a retenção medida no serviço é de 90 dias (GLITCHTIP_RETENTION_DAYS no default, sem env). Quem lê o projeto já tem acesso ao GlitchTip da casa.
  • Degradação repetitiva vira evento por ciclo (ex.: pAbast falhou … volta a pendente enquanto o ERP está fora). O GlitchTip agrupa por template numa issue só, mas o consumo de cota é real — vale olhar o painel na primeira semana.
  • O eco no evento depende de o ciclo ser mono-thread. O escopo do Sentry é por thread e a thread nova recebe um clone do hub; hoje o daemon roda tudo numa thread só (Agendador.rodarParaSempre). Paralelizar o ciclo faria o eco sumir dos incidentes sem erro nenhum — quem mexer nisso reabre esta decisão.
  • O SDK fica preso em 6.34.0 (core e sentry-logback): a 7.x exige Java 11 e o alvo aqui é bytecode 8 (decisão 0001). Há teste que exercita o par sentry-logback × logback-classic 1.3.14 de verdade.

Alternativas deliberadas

  • --debug desligar o envio. Simples, mas deixaria o e2e refém de lembrar a flag e não alinharia com o resto da casa, que desliga por SENTRY_DSN.
  • Appender em ERROR, como a norma de engenharia fixa para os apps Micronaut. Recusada: aqui WARN é justamente a degradação que o suporte precisa ver de longe (pAbast falhou, retorno sem handshake). A divergência é declarada, não silenciosa.
  • Uma breadcrumb por linha do eco. Um lote cheio são ~1 998 linhas: encheria a janela do SDK antes de o erro acontecer e o incidente chegaria com o fim do log, sem a cabeça.
  • Anexo (Attachment) com o arquivo inteiro. O GlitchTip não suporta anexo — verificado no banco dele, sem tabela de anexo.