@luanpdd/kit-mcp 1.34.0 → 1.36.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (118) hide show
  1. package/README.md +1 -1
  2. package/bin/cli.js +2 -2
  3. package/bin/mcp.js +6 -6
  4. package/bin/ui.js +74 -74
  5. package/gates/ai-prompt-stability.md +120 -120
  6. package/gates/budget-description.md +68 -68
  7. package/gates/confidence.md +29 -29
  8. package/gates/dependency-check.md +33 -33
  9. package/gates/dept-cycle-prevention.md +179 -179
  10. package/gates/golden-signals-coverage.md +133 -133
  11. package/gates/legacy-refactor-safety.md +178 -178
  12. package/gates/multi-tenant-rls-coverage.md +102 -102
  13. package/gates/no-personal-uuid.md +72 -72
  14. package/gates/obs-agents-mcp-supabase.md +86 -86
  15. package/gates/obs-skills-frontmatter.md +76 -76
  16. package/gates/observability-coverage.md +151 -151
  17. package/gates/omm-no-regression.md +83 -83
  18. package/gates/postmortem-template-required.md +127 -127
  19. package/gates/prr-checklist-coverage.md +128 -128
  20. package/gates/regression.md +32 -32
  21. package/gates/release-pipeline-policy.md +132 -132
  22. package/gates/secrets-scan.md +33 -33
  23. package/gates/service-role-not-in-user-facing.md +113 -113
  24. package/gates/skill-must-include.md +71 -71
  25. package/gates/sync-idempotent.md +62 -62
  26. package/gates/verify-phase-goal.md +34 -34
  27. package/kit/agents/designer-ui.md +216 -216
  28. package/kit/agents/workflow-generator.md +537 -0
  29. package/kit/commands/adicionar-backlog.md +1 -1
  30. package/kit/commands/adicionar-fase.md +1 -1
  31. package/kit/commands/adicionar-tarefa.md +1 -1
  32. package/kit/commands/auditar-observabilidade.md +103 -103
  33. package/kit/commands/auditar-toil.md +129 -129
  34. package/kit/commands/caracterizar-prompt.md +195 -195
  35. package/kit/commands/criar-workflow.md +158 -0
  36. package/kit/commands/definir-perfil.md +1 -1
  37. package/kit/commands/definir-slo.md +108 -108
  38. package/kit/commands/fio.md +1 -1
  39. package/kit/commands/golden-signals.md +142 -142
  40. package/kit/commands/instrumentar-fase.md +200 -200
  41. package/kit/commands/investigar-producao.md +162 -162
  42. package/kit/commands/observabilidade.md +118 -118
  43. package/kit/commands/postmortem.md +179 -179
  44. package/kit/commands/prr.md +205 -205
  45. package/kit/commands/publicar-rapido.md +207 -207
  46. package/kit/commands/risk-budget.md +220 -220
  47. package/kit/commands/sre.md +230 -230
  48. package/kit/file-manifest.json +5 -2
  49. package/kit/framework/references/output-style.md +22 -22
  50. package/kit/hooks/post-apply-migration.js +199 -199
  51. package/kit/hooks/sidecar-tool-publisher.js +210 -210
  52. package/kit/skills/_shared-dados-distribuidos/glossary.md +224 -224
  53. package/kit/skills/_shared-legacy/glossary.md +389 -389
  54. package/kit/skills/_shared-multi-tenant/glossary.md +186 -186
  55. package/kit/skills/_shared-observability/glossary.md +396 -396
  56. package/kit/skills/_shared-sre/glossary.md +712 -712
  57. package/kit/skills/_shared-supabase/glossary.md +234 -234
  58. package/kit/skills/blameless-postmortems/SKILL.md +340 -340
  59. package/kit/skills/burn-rate-alerting/SKILL.md +258 -258
  60. package/kit/skills/cascading-failures/SKILL.md +311 -311
  61. package/kit/skills/core-analysis-loop/SKILL.md +352 -352
  62. package/kit/skills/distributed-tracing/SKILL.md +362 -362
  63. package/kit/skills/dynamic-workflow-authoring/SKILL.md +327 -0
  64. package/kit/skills/eliminating-toil/SKILL.md +243 -243
  65. package/kit/skills/event-based-slos/SKILL.md +296 -296
  66. package/kit/skills/four-golden-signals/SKILL.md +314 -314
  67. package/kit/skills/hermetic-builds/SKILL.md +323 -323
  68. package/kit/skills/legacy-monster-methods/SKILL.md +444 -444
  69. package/kit/skills/llm-as-dependency/SKILL.md +436 -436
  70. package/kit/skills/load-shedding-graceful-degradation/SKILL.md +396 -396
  71. package/kit/skills/observability-driven-development/SKILL.md +315 -315
  72. package/kit/skills/observability-maturity-model/SKILL.md +222 -222
  73. package/kit/skills/opentelemetry-standard/SKILL.md +351 -351
  74. package/kit/skills/production-readiness-review/SKILL.md +305 -305
  75. package/kit/skills/release-engineering/SKILL.md +367 -367
  76. package/kit/skills/retry-strategies/SKILL.md +372 -372
  77. package/kit/skills/sre-risk-management/SKILL.md +221 -221
  78. package/kit/skills/structured-events/SKILL.md +265 -265
  79. package/kit/skills/supabase-cron-queues/SKILL.md +275 -275
  80. package/kit/skills/supabase-database-functions/SKILL.md +332 -332
  81. package/kit/skills/supabase-declarative-schema/SKILL.md +183 -183
  82. package/kit/skills/supabase-pgvector-rag/SKILL.md +253 -253
  83. package/kit/skills/supabase-postgres-style/SKILL.md +138 -138
  84. package/kit/skills/supabase-storage/SKILL.md +234 -234
  85. package/kit/skills/telemetry-pipelines/SKILL.md +259 -259
  86. package/kit/skills/telemetry-sampling/SKILL.md +256 -256
  87. package/kit/skills/ui-anti-padroes-ia/SKILL.md +261 -261
  88. package/kit/skills/ui-contexto-produto/SKILL.md +248 -248
  89. package/kit/skills/ui-cor-estrategia/SKILL.md +213 -213
  90. package/kit/skills/ui-critica-auditoria/SKILL.md +260 -260
  91. package/kit/skills/ui-motion-funcional/SKILL.md +264 -264
  92. package/kit/skills/ui-ritmo-espacial/SKILL.md +259 -259
  93. package/kit/skills/ui-tipografia/SKILL.md +211 -211
  94. package/package.json +1 -1
  95. package/src/cli/index.js +1114 -1114
  96. package/src/cli/render.js +194 -194
  97. package/src/cli/upgrade-check.js +135 -135
  98. package/src/core/error-redaction.js +76 -76
  99. package/src/core/failures.js +153 -153
  100. package/src/core/gate-runner.js +205 -205
  101. package/src/core/gates.js +82 -82
  102. package/src/core/logger.js +170 -170
  103. package/src/core/manifest-verify.js +174 -174
  104. package/src/core/metrics.js +268 -268
  105. package/src/core/notify.js +60 -60
  106. package/src/core/path-safety.js +141 -141
  107. package/src/core/replays.js +120 -120
  108. package/src/core/ui.js +185 -185
  109. package/src/mcp-server/install.js +149 -149
  110. package/src/mcp-server/roots.js +124 -124
  111. package/src/ui/auto-spawn.js +113 -113
  112. package/src/ui/browser.js +78 -78
  113. package/src/ui/client.js +130 -130
  114. package/src/ui/events.js +65 -65
  115. package/src/ui/lockfile.js +191 -191
  116. package/src/ui/port.js +67 -67
  117. package/src/ui/server.js +547 -547
  118. package/src/ui/wrapper.js +129 -129
@@ -1,311 +1,311 @@
1
- ---
2
- name: cascading-failures
3
- description: Use ao desenhar/auditar serviços com deps externas — cap 22 livro Google SRE. Triggers de cascade, loops de feedback, prevenção via timeout/jitter/deadline/circuit breaker, immediate response.
4
- ---
5
-
6
- # SRE — Addressing Cascading Failures
7
-
8
- ## Quando usar
9
-
10
- LLM carrega esta skill ao analisar serviço com risco de cascade, ou durante incident em progresso onde failure se amplifica. Trigger phrases:
11
-
12
- - "cascading failure", "falha em cascata"
13
- - "retry storm", "thundering herd"
14
- - "outage propagando", "serviço caindo um após outro"
15
- - "como prevenir cascade?", "circuit breaker"
16
- - "cap 22 Google SRE"
17
- - "deadline propagation", "load shedding"
18
-
19
- ## Regras absolutas
20
-
21
- - **Cascade tem 5 triggers canônicos:** server overload, resource exhaustion, service unavailability, latency spike sem timeout, retry sem jitter. Memorize-os.
22
- - **Prevenção custa 1×, recuperação custa 100×.** Toda dep crítica DEVE ter timeout + retry com jitter + circuit breaker + deadline propagation. Sem isso, cascade é questão de tempo.
23
- - **Saturation (cap 6 v1.10) é early warning de cascade.** Quando saturation > 80%, ainda há tempo. Quando hit 100%, já está em cascade.
24
- - **Retry SEMPRE com jitter.** Full jitter por default (`delay = random(0, base × 2^attempt)`). Sem jitter = thundering herd garantido.
25
- - **Retry SEMPRE com deadline.** Retry sem timeout amplifica cascade — call de 30s vira 90s vira 270s. Deadline propagation evita work zumbi.
26
- - **Circuit breaker DEFAULT em qualquer dep externa.** Estados closed/open/half-open. Open dispara após N failures consecutivas; half-open permite 1 probe; closed após probe verde.
27
- - **Load shedding > 503 graceful > queue overflow.** Server saturated DEVE retornar 503 com Retry-After ANTES de aceitar request que vai falhar. Aceitar e cair = pior que rejeitar.
28
- - **Slow start em recovery.** Após outage, ramp-up gradual (10% → 25% → 50% → 100%). Full blast em recovery = falha de novo (caches frios, conn pools).
29
-
30
- ## Patterns canônicos
31
-
32
- ### Pattern 1: 5 triggers canônicos de cascade (cap 22)
33
-
34
- ```text
35
- 1. SERVER OVERLOAD
36
- Sintoma: load > capacity → latency p99 sobe 10× → errors 5xx → crashes
37
- Trigger upstream: traffic spike, outage de cache, batch job rodou em horário ruim
38
- Detect: Saturation gauge (cap 6) > 80% por > 5 min
39
- Resposta: load shedding + escalação manual
40
-
41
- 2. RESOURCE EXHAUSTION
42
- Tipos: CPU, memory, file descriptors, threads, connection pool
43
- Sintoma específico:
44
- CPU 100% → latency sobe; FDs esgotados → "too many open files"
45
- Memory OOM → process kill; threads → deadlock; conn pool empty → wait
46
- Detect: monitor por recurso específico; alarmes em 80% de cada
47
- Resposta: configure limits; circuit breaker; rate limit caller
48
-
49
- 3. SERVICE UNAVAILABILITY (DEP DOWN)
50
- Sintoma: dep externa retorna 5xx ou timeout. Sem circuit breaker:
51
- N clients × M retries × T deadline = explosão de calls
52
- Detect: error rate de dep > 50% por 1 min; latency dep > p99 normal × 5
53
- Resposta: circuit breaker abre; fallback (cache, default value, degraded mode)
54
-
55
- 4. LATENCY SPIKE SEM TIMEOUT
56
- Sintoma: dep responde lento mas não falha. Caller fica esperando.
57
- Conn pool de caller esgota; novos requests também ficam pendurados.
58
- Detect: dep latency p99 > baseline × 5
59
- Resposta: timeout AGRESSIVO (ex: p99.9 baseline + 50%); circuit breaker
60
-
61
- 5. RETRY SEM JITTER
62
- Sintoma: 1000 clients retentam ao mesmo tempo após dep recovery.
63
- Server recém-recuperado é matado pelo wake-up.
64
- Detect: traffic spike no momento exato de recovery
65
- Resposta: full jitter; retry budget global; slow start
66
- ```
67
-
68
- ### Pattern 2: Defesa em camadas (cap 22)
69
-
70
- Cada chamada externa precisa de **5 camadas de defesa**:
71
-
72
- ```ts
73
- // Camada 1: Timeout agressivo
74
- const TIMEOUT_MS = 2000 // p99.9 baseline + 50%
75
-
76
- // Camada 2: Retry com jitter + deadline
77
- async function callDep(input: Input, deadline: number): Promise<Output> {
78
- const startMs = performance.now()
79
- let attempt = 0
80
- let lastError: Error | undefined
81
-
82
- while (true) {
83
- const remaining = deadline - performance.now()
84
- if (remaining <= 0) throw new DeadlineExceededError(lastError)
85
-
86
- const callTimeoutMs = Math.min(TIMEOUT_MS, remaining)
87
-
88
- try {
89
- // Camada 3: Circuit breaker
90
- if (circuitBreaker.isOpen()) throw new CircuitOpenError()
91
-
92
- const result = await withTimeout(
93
- depClient.call(input),
94
- callTimeoutMs
95
- )
96
- circuitBreaker.recordSuccess()
97
- return result
98
- } catch (e) {
99
- lastError = e as Error
100
- circuitBreaker.recordFailure()
101
-
102
- // Camada 4: Não retentar erros não-retentáveis
103
- if (!isRetryable(e)) throw e
104
-
105
- // Camada 5: Retry budget global
106
- if (!retryBudget.tryAcquire()) throw new RetryBudgetExhaustedError(e)
107
-
108
- attempt++
109
- if (attempt >= MAX_RETRIES) throw e
110
-
111
- // Full jitter
112
- const baseMs = 100 * Math.pow(2, attempt - 1)
113
- const jitterMs = Math.random() * baseMs * 2
114
- await sleep(Math.min(jitterMs, remaining))
115
- }
116
- }
117
- }
118
-
119
- function isRetryable(e: any): boolean {
120
- // 4xx (validation, auth, not_found) → não retry
121
- // 5xx, timeout, connection reset → retry
122
- if (e.statusCode >= 400 && e.statusCode < 500) return false
123
- if (e.statusCode === 429) return true // rate limited — retry com backoff
124
- return true
125
- }
126
- ```
127
-
128
- ### Pattern 3: Circuit breaker — estados canônicos
129
-
130
- ```text
131
- ┌────────────────────┐
132
- │ CLOSED (normal) │
133
- │ request flows OK │
134
- └─────────┬──────────┘
135
- │ N consecutive failures
136
-
137
- ┌────────────────────┐
138
- │ OPEN │
139
- │ fail fast for T │
140
- │ no calls to dep │
141
- └─────────┬──────────┘
142
- │ T elapsed
143
-
144
- ┌────────────────────┐
145
- │ HALF-OPEN │
146
- │ allow 1-N probes │
147
- └────┬───────────┬───┘
148
- success │ │ failure
149
- ▼ ▼
150
- CLOSED OPEN
151
-
152
- Configuração canônica:
153
- N (failures-to-open): 5-10 consecutive
154
- T (open duration): 30-60s
155
- half-open probe count: 1-5
156
- failure detection window: 30-60s rolling
157
- ```
158
-
159
- ### Pattern 4: Deadline propagation across hops
160
-
161
- ```text
162
- Client → Service A (deadline=30s) → Service B (deadline=?) → Service C (deadline=?)
163
-
164
- WRONG (cascade amplification):
165
- A: receives deadline=30s, calls B with timeout=30s
166
- B: receives no deadline, default 30s, calls C with timeout=30s
167
- C: takes 30s
168
- Total: 30s in C, plus parent overhead. Client gone at 30s, A-B-C still working.
169
-
170
- RIGHT (deadline propagation):
171
- A: receives TTL=30s; takes 100ms processing; calls B with TTL=29.9s
172
- B: receives TTL=29.9s; takes 50ms; calls C with TTL=29.85s
173
- C: receives TTL=29.85s; works until that limit, no more
174
- When TTL hits 0, ALL hops fail fast. No zombie work.
175
-
176
- Implementação:
177
- - HTTP: header `Deadline-Ms` ou similar (custom)
178
- - gRPC: built-in `grpc-timeout` header
179
- - JS/TS: AbortSignal.timeout(remainingMs)
180
- - Each hop: deadline = received_deadline - elapsed_local; abort se ≤ 0
181
- ```
182
-
183
- ### Pattern 5: Defesas server-side
184
-
185
- Server protege a si próprio (não confia em clientes):
186
-
187
- | Defesa | Técnica | Exemplo |
188
- |---|---|---|
189
- | **Rate limit per-client** | Token bucket no proxy/gateway | Kong/Envoy rate limit; 100 req/s/client |
190
- | **Concurrency limit** | Semaphore no handler | Máx 1000 in-flight; reject 503 if cheio |
191
- | **Queue depth limit** | Bound + drop policy | Queue máx 10k msgs; drop oldest > 5k |
192
- | **Resource budget** | Cgroups / container limits | CPU 4 cores, memory 8GB hard cap |
193
- | **Slow start na recovery** | Gradual ramp | Aceita 10% → 25% → 50% → 100% por 5 min |
194
-
195
- ### Pattern 6: Testing for cascading failures
196
-
197
- Antes de prod, exercitar cascade scenarios:
198
-
199
- ```text
200
- 1. Game day exercise
201
- - Cap 1 dep crítica em 50% errors via fault injection
202
- - Observar: caller circuit breakers abrem? Latency caller estável?
203
- - Métrica: zero impacto a clientes (degraded mode kicks in)
204
-
205
- 2. Load test até saturação
206
- - Ramp traffic até 1.5× expected peak
207
- - Confirmar: load shedding ativa antes de crash
208
- - Métrica: error rate sob 1% mesmo em 1.5× load
209
-
210
- 3. Chaos engineering
211
- - Random kill de instâncias (Chaos Monkey)
212
- - Confirmar: retries com jitter espalham wake-up
213
- - Métrica: SLO mantido durante 10 kills/hour
214
- ```
215
-
216
- ## Anti-patterns
217
-
218
- ### ANTI: timeout otimista
219
-
220
- ```text
221
- ANTI: timeout = p99 baseline. "Maioria das requests fica abaixo".
222
-
223
- PROBLEMA: tail latency (1%) sempre estoura. Cada 100 requests, 1
224
- consome timeout inteiro. Conn pool acumula slow requests.
225
-
226
- CERTO: timeout = p99.9 baseline + 50% margem. Aceita que 0.1% será
227
- cancelado. Tail é problema de dep, não cliente.
228
- ```
229
-
230
- ### ANTI: retry infinito com backoff "razoável"
231
-
232
- ```text
233
- ANTI: retry até sucesso, com 1s/2s/4s/8s/... exponencial sem cap.
234
-
235
- PROBLEMA: durante outage de 30 min, último retry seria após 30 min
236
- esperando. Conn fica pendurada. Memory leak.
237
-
238
- CERTO: max retries = 3-5; max backoff = 30s; deadline global
239
- (request terminada após T segundos não importa quantos
240
- retries). Após max, fallback ou error final.
241
- ```
242
-
243
- ### ANTI: circuit breaker per-instance (não compartilhado)
244
-
245
- ```text
246
- ANTI: cada instância de service A tem seu próprio circuit breaker
247
- pra dep B. Quando B fica lenta, instância 1 abre circuito,
248
- mas instâncias 2-100 ainda pingam B até abrirem.
249
-
250
- PROBLEMA: 100× mais carga em B doente. B nunca recupera.
251
-
252
- CERTO: circuit breaker compartilhado (e.g., via Redis/Memcached para
253
- state) OR lib que detecta failure rate cross-instance via
254
- gossip/coordination. Open = cluster all stop.
255
- ```
256
-
257
- ### ANTI: load shedding via reject ao invés de 503 + Retry-After
258
-
259
- ```text
260
- ANTI: server saturated → drop conn TCP-level (RST).
261
-
262
- PROBLEMA: client não sabe que precisa esperar. Retry imediato.
263
- Mais carga. Retry storm.
264
-
265
- CERTO: 503 Service Unavailable + Retry-After: 30 (segundos).
266
- Client aware retry com delay. Backoff respeitado.
267
- ```
268
-
269
- ### ANTI: graceful degradation só em prod
270
-
271
- ```text
272
- ANTI: degraded mode só liga durante incident; nunca exercitado.
273
-
274
- PROBLEMA: quando precisa, descobre bug no degraded mode. Outage
275
- piora.
276
-
277
- CERTO: degraded mode é PATH PRINCIPAL em alguma fração de tráfego
278
- (1%) por padrão. Sempre exercitado. Quando dep cai, ramp pra
279
- 100% degraded é tested transition.
280
- ```
281
-
282
- ## Verificação
283
-
284
- Antes de aceitar serviço em prod:
285
-
286
- 1. Toda chamada a dep externa tem timeout < p99.9 baseline + 50%
287
- 2. Toda retry tem jitter (full jitter default)
288
- 3. Toda chamada respeita deadline propagation
289
- 4. Circuit breaker ativo em deps críticas (estados closed/open/half-open)
290
- 5. Server-side: rate limit + concurrency limit + queue depth bound
291
- 6. Slow start configurado em deploy/recovery
292
- 7. Game day exercise rodado nos últimos 90 dias
293
- 8. Saturation gauge (cap 6) instrumentado e alertado em 80%
294
-
295
- ---
296
-
297
- ## Clock Skew como Failure Mode (v1.22+)
298
-
299
- > Além dos triggers canônicos do cap 22 (sem timeout, retry sem jitter, sem circuit breaker), clock skew é failure mode adicional em sistemas distribuídos: nó com relógio adiantado pode marcar lease expirada antes do tempo real, disparando reeleição desnecessária e cascading failure. Padrão de mitigação (fencing token + nunca usar `clock_timestamp()` em lógica de expiração) em [`armadilhas-sistemas-distribuidos`](../armadilhas-sistemas-distribuidos/SKILL.md) (v1.22 — DDIA Ch 8).
300
-
301
- ## Ver também
302
-
303
- - [`_shared-sre/glossary.md`](../_shared-sre/glossary.md) — vocabulário cap 22 (cascading failure, retry storm, etc.)
304
- - [`retry-strategies`](../retry-strategies/SKILL.md) (v1.11) — detalhes de jitter + deadline propagation
305
- - [`load-shedding-graceful-degradation`](../load-shedding-graceful-degradation/SKILL.md) (v1.11) — defesas server-side
306
- - [`four-golden-signals`](../four-golden-signals/SKILL.md) (v1.10) — Saturation como early warning de cascade
307
- - [`production-readiness-review`](../production-readiness-review/SKILL.md) (v1.10) — PRR Axe 4 verifica defesas
308
- - [`omm-auditor`](../../agents/omm-auditor.md) (v1.9) — Capacidade 1 (Resilience) consume cascading-failures-auditor
309
- - [`cascading-failures-auditor`](../../agents/cascading-failures-auditor.md) (v1.11) — agent que detecta gaps automaticamente
310
-
311
- *Material-fonte: Site Reliability Engineering — Beyer/Jones/Petoff/Murphy (Google/O'Reilly, 2016) — Cap 22: "Addressing Cascading Failures".*
1
+ ---
2
+ name: cascading-failures
3
+ description: Use ao desenhar/auditar serviços com deps externas — cap 22 livro Google SRE. Triggers de cascade, loops de feedback, prevenção via timeout/jitter/deadline/circuit breaker, immediate response.
4
+ ---
5
+
6
+ # SRE — Addressing Cascading Failures
7
+
8
+ ## Quando usar
9
+
10
+ LLM carrega esta skill ao analisar serviço com risco de cascade, ou durante incident em progresso onde failure se amplifica. Trigger phrases:
11
+
12
+ - "cascading failure", "falha em cascata"
13
+ - "retry storm", "thundering herd"
14
+ - "outage propagando", "serviço caindo um após outro"
15
+ - "como prevenir cascade?", "circuit breaker"
16
+ - "cap 22 Google SRE"
17
+ - "deadline propagation", "load shedding"
18
+
19
+ ## Regras absolutas
20
+
21
+ - **Cascade tem 5 triggers canônicos:** server overload, resource exhaustion, service unavailability, latency spike sem timeout, retry sem jitter. Memorize-os.
22
+ - **Prevenção custa 1×, recuperação custa 100×.** Toda dep crítica DEVE ter timeout + retry com jitter + circuit breaker + deadline propagation. Sem isso, cascade é questão de tempo.
23
+ - **Saturation (cap 6 v1.10) é early warning de cascade.** Quando saturation > 80%, ainda há tempo. Quando hit 100%, já está em cascade.
24
+ - **Retry SEMPRE com jitter.** Full jitter por default (`delay = random(0, base × 2^attempt)`). Sem jitter = thundering herd garantido.
25
+ - **Retry SEMPRE com deadline.** Retry sem timeout amplifica cascade — call de 30s vira 90s vira 270s. Deadline propagation evita work zumbi.
26
+ - **Circuit breaker DEFAULT em qualquer dep externa.** Estados closed/open/half-open. Open dispara após N failures consecutivas; half-open permite 1 probe; closed após probe verde.
27
+ - **Load shedding > 503 graceful > queue overflow.** Server saturated DEVE retornar 503 com Retry-After ANTES de aceitar request que vai falhar. Aceitar e cair = pior que rejeitar.
28
+ - **Slow start em recovery.** Após outage, ramp-up gradual (10% → 25% → 50% → 100%). Full blast em recovery = falha de novo (caches frios, conn pools).
29
+
30
+ ## Patterns canônicos
31
+
32
+ ### Pattern 1: 5 triggers canônicos de cascade (cap 22)
33
+
34
+ ```text
35
+ 1. SERVER OVERLOAD
36
+ Sintoma: load > capacity → latency p99 sobe 10× → errors 5xx → crashes
37
+ Trigger upstream: traffic spike, outage de cache, batch job rodou em horário ruim
38
+ Detect: Saturation gauge (cap 6) > 80% por > 5 min
39
+ Resposta: load shedding + escalação manual
40
+
41
+ 2. RESOURCE EXHAUSTION
42
+ Tipos: CPU, memory, file descriptors, threads, connection pool
43
+ Sintoma específico:
44
+ CPU 100% → latency sobe; FDs esgotados → "too many open files"
45
+ Memory OOM → process kill; threads → deadlock; conn pool empty → wait
46
+ Detect: monitor por recurso específico; alarmes em 80% de cada
47
+ Resposta: configure limits; circuit breaker; rate limit caller
48
+
49
+ 3. SERVICE UNAVAILABILITY (DEP DOWN)
50
+ Sintoma: dep externa retorna 5xx ou timeout. Sem circuit breaker:
51
+ N clients × M retries × T deadline = explosão de calls
52
+ Detect: error rate de dep > 50% por 1 min; latency dep > p99 normal × 5
53
+ Resposta: circuit breaker abre; fallback (cache, default value, degraded mode)
54
+
55
+ 4. LATENCY SPIKE SEM TIMEOUT
56
+ Sintoma: dep responde lento mas não falha. Caller fica esperando.
57
+ Conn pool de caller esgota; novos requests também ficam pendurados.
58
+ Detect: dep latency p99 > baseline × 5
59
+ Resposta: timeout AGRESSIVO (ex: p99.9 baseline + 50%); circuit breaker
60
+
61
+ 5. RETRY SEM JITTER
62
+ Sintoma: 1000 clients retentam ao mesmo tempo após dep recovery.
63
+ Server recém-recuperado é matado pelo wake-up.
64
+ Detect: traffic spike no momento exato de recovery
65
+ Resposta: full jitter; retry budget global; slow start
66
+ ```
67
+
68
+ ### Pattern 2: Defesa em camadas (cap 22)
69
+
70
+ Cada chamada externa precisa de **5 camadas de defesa**:
71
+
72
+ ```ts
73
+ // Camada 1: Timeout agressivo
74
+ const TIMEOUT_MS = 2000 // p99.9 baseline + 50%
75
+
76
+ // Camada 2: Retry com jitter + deadline
77
+ async function callDep(input: Input, deadline: number): Promise<Output> {
78
+ const startMs = performance.now()
79
+ let attempt = 0
80
+ let lastError: Error | undefined
81
+
82
+ while (true) {
83
+ const remaining = deadline - performance.now()
84
+ if (remaining <= 0) throw new DeadlineExceededError(lastError)
85
+
86
+ const callTimeoutMs = Math.min(TIMEOUT_MS, remaining)
87
+
88
+ try {
89
+ // Camada 3: Circuit breaker
90
+ if (circuitBreaker.isOpen()) throw new CircuitOpenError()
91
+
92
+ const result = await withTimeout(
93
+ depClient.call(input),
94
+ callTimeoutMs
95
+ )
96
+ circuitBreaker.recordSuccess()
97
+ return result
98
+ } catch (e) {
99
+ lastError = e as Error
100
+ circuitBreaker.recordFailure()
101
+
102
+ // Camada 4: Não retentar erros não-retentáveis
103
+ if (!isRetryable(e)) throw e
104
+
105
+ // Camada 5: Retry budget global
106
+ if (!retryBudget.tryAcquire()) throw new RetryBudgetExhaustedError(e)
107
+
108
+ attempt++
109
+ if (attempt >= MAX_RETRIES) throw e
110
+
111
+ // Full jitter
112
+ const baseMs = 100 * Math.pow(2, attempt - 1)
113
+ const jitterMs = Math.random() * baseMs * 2
114
+ await sleep(Math.min(jitterMs, remaining))
115
+ }
116
+ }
117
+ }
118
+
119
+ function isRetryable(e: any): boolean {
120
+ // 4xx (validation, auth, not_found) → não retry
121
+ // 5xx, timeout, connection reset → retry
122
+ if (e.statusCode >= 400 && e.statusCode < 500) return false
123
+ if (e.statusCode === 429) return true // rate limited — retry com backoff
124
+ return true
125
+ }
126
+ ```
127
+
128
+ ### Pattern 3: Circuit breaker — estados canônicos
129
+
130
+ ```text
131
+ ┌────────────────────┐
132
+ │ CLOSED (normal) │
133
+ │ request flows OK │
134
+ └─────────┬──────────┘
135
+ │ N consecutive failures
136
+
137
+ ┌────────────────────┐
138
+ │ OPEN │
139
+ │ fail fast for T │
140
+ │ no calls to dep │
141
+ └─────────┬──────────┘
142
+ │ T elapsed
143
+
144
+ ┌────────────────────┐
145
+ │ HALF-OPEN │
146
+ │ allow 1-N probes │
147
+ └────┬───────────┬───┘
148
+ success │ │ failure
149
+ ▼ ▼
150
+ CLOSED OPEN
151
+
152
+ Configuração canônica:
153
+ N (failures-to-open): 5-10 consecutive
154
+ T (open duration): 30-60s
155
+ half-open probe count: 1-5
156
+ failure detection window: 30-60s rolling
157
+ ```
158
+
159
+ ### Pattern 4: Deadline propagation across hops
160
+
161
+ ```text
162
+ Client → Service A (deadline=30s) → Service B (deadline=?) → Service C (deadline=?)
163
+
164
+ WRONG (cascade amplification):
165
+ A: receives deadline=30s, calls B with timeout=30s
166
+ B: receives no deadline, default 30s, calls C with timeout=30s
167
+ C: takes 30s
168
+ Total: 30s in C, plus parent overhead. Client gone at 30s, A-B-C still working.
169
+
170
+ RIGHT (deadline propagation):
171
+ A: receives TTL=30s; takes 100ms processing; calls B with TTL=29.9s
172
+ B: receives TTL=29.9s; takes 50ms; calls C with TTL=29.85s
173
+ C: receives TTL=29.85s; works until that limit, no more
174
+ When TTL hits 0, ALL hops fail fast. No zombie work.
175
+
176
+ Implementação:
177
+ - HTTP: header `Deadline-Ms` ou similar (custom)
178
+ - gRPC: built-in `grpc-timeout` header
179
+ - JS/TS: AbortSignal.timeout(remainingMs)
180
+ - Each hop: deadline = received_deadline - elapsed_local; abort se ≤ 0
181
+ ```
182
+
183
+ ### Pattern 5: Defesas server-side
184
+
185
+ Server protege a si próprio (não confia em clientes):
186
+
187
+ | Defesa | Técnica | Exemplo |
188
+ |---|---|---|
189
+ | **Rate limit per-client** | Token bucket no proxy/gateway | Kong/Envoy rate limit; 100 req/s/client |
190
+ | **Concurrency limit** | Semaphore no handler | Máx 1000 in-flight; reject 503 if cheio |
191
+ | **Queue depth limit** | Bound + drop policy | Queue máx 10k msgs; drop oldest > 5k |
192
+ | **Resource budget** | Cgroups / container limits | CPU 4 cores, memory 8GB hard cap |
193
+ | **Slow start na recovery** | Gradual ramp | Aceita 10% → 25% → 50% → 100% por 5 min |
194
+
195
+ ### Pattern 6: Testing for cascading failures
196
+
197
+ Antes de prod, exercitar cascade scenarios:
198
+
199
+ ```text
200
+ 1. Game day exercise
201
+ - Cap 1 dep crítica em 50% errors via fault injection
202
+ - Observar: caller circuit breakers abrem? Latency caller estável?
203
+ - Métrica: zero impacto a clientes (degraded mode kicks in)
204
+
205
+ 2. Load test até saturação
206
+ - Ramp traffic até 1.5× expected peak
207
+ - Confirmar: load shedding ativa antes de crash
208
+ - Métrica: error rate sob 1% mesmo em 1.5× load
209
+
210
+ 3. Chaos engineering
211
+ - Random kill de instâncias (Chaos Monkey)
212
+ - Confirmar: retries com jitter espalham wake-up
213
+ - Métrica: SLO mantido durante 10 kills/hour
214
+ ```
215
+
216
+ ## Anti-patterns
217
+
218
+ ### ANTI: timeout otimista
219
+
220
+ ```text
221
+ ANTI: timeout = p99 baseline. "Maioria das requests fica abaixo".
222
+
223
+ PROBLEMA: tail latency (1%) sempre estoura. Cada 100 requests, 1
224
+ consome timeout inteiro. Conn pool acumula slow requests.
225
+
226
+ CERTO: timeout = p99.9 baseline + 50% margem. Aceita que 0.1% será
227
+ cancelado. Tail é problema de dep, não cliente.
228
+ ```
229
+
230
+ ### ANTI: retry infinito com backoff "razoável"
231
+
232
+ ```text
233
+ ANTI: retry até sucesso, com 1s/2s/4s/8s/... exponencial sem cap.
234
+
235
+ PROBLEMA: durante outage de 30 min, último retry seria após 30 min
236
+ esperando. Conn fica pendurada. Memory leak.
237
+
238
+ CERTO: max retries = 3-5; max backoff = 30s; deadline global
239
+ (request terminada após T segundos não importa quantos
240
+ retries). Após max, fallback ou error final.
241
+ ```
242
+
243
+ ### ANTI: circuit breaker per-instance (não compartilhado)
244
+
245
+ ```text
246
+ ANTI: cada instância de service A tem seu próprio circuit breaker
247
+ pra dep B. Quando B fica lenta, instância 1 abre circuito,
248
+ mas instâncias 2-100 ainda pingam B até abrirem.
249
+
250
+ PROBLEMA: 100× mais carga em B doente. B nunca recupera.
251
+
252
+ CERTO: circuit breaker compartilhado (e.g., via Redis/Memcached para
253
+ state) OR lib que detecta failure rate cross-instance via
254
+ gossip/coordination. Open = cluster all stop.
255
+ ```
256
+
257
+ ### ANTI: load shedding via reject ao invés de 503 + Retry-After
258
+
259
+ ```text
260
+ ANTI: server saturated → drop conn TCP-level (RST).
261
+
262
+ PROBLEMA: client não sabe que precisa esperar. Retry imediato.
263
+ Mais carga. Retry storm.
264
+
265
+ CERTO: 503 Service Unavailable + Retry-After: 30 (segundos).
266
+ Client aware retry com delay. Backoff respeitado.
267
+ ```
268
+
269
+ ### ANTI: graceful degradation só em prod
270
+
271
+ ```text
272
+ ANTI: degraded mode só liga durante incident; nunca exercitado.
273
+
274
+ PROBLEMA: quando precisa, descobre bug no degraded mode. Outage
275
+ piora.
276
+
277
+ CERTO: degraded mode é PATH PRINCIPAL em alguma fração de tráfego
278
+ (1%) por padrão. Sempre exercitado. Quando dep cai, ramp pra
279
+ 100% degraded é tested transition.
280
+ ```
281
+
282
+ ## Verificação
283
+
284
+ Antes de aceitar serviço em prod:
285
+
286
+ 1. Toda chamada a dep externa tem timeout < p99.9 baseline + 50%
287
+ 2. Toda retry tem jitter (full jitter default)
288
+ 3. Toda chamada respeita deadline propagation
289
+ 4. Circuit breaker ativo em deps críticas (estados closed/open/half-open)
290
+ 5. Server-side: rate limit + concurrency limit + queue depth bound
291
+ 6. Slow start configurado em deploy/recovery
292
+ 7. Game day exercise rodado nos últimos 90 dias
293
+ 8. Saturation gauge (cap 6) instrumentado e alertado em 80%
294
+
295
+ ---
296
+
297
+ ## Clock Skew como Failure Mode (v1.22+)
298
+
299
+ > Além dos triggers canônicos do cap 22 (sem timeout, retry sem jitter, sem circuit breaker), clock skew é failure mode adicional em sistemas distribuídos: nó com relógio adiantado pode marcar lease expirada antes do tempo real, disparando reeleição desnecessária e cascading failure. Padrão de mitigação (fencing token + nunca usar `clock_timestamp()` em lógica de expiração) em [`armadilhas-sistemas-distribuidos`](../armadilhas-sistemas-distribuidos/SKILL.md) (v1.22 — DDIA Ch 8).
300
+
301
+ ## Ver também
302
+
303
+ - [`_shared-sre/glossary.md`](../_shared-sre/glossary.md) — vocabulário cap 22 (cascading failure, retry storm, etc.)
304
+ - [`retry-strategies`](../retry-strategies/SKILL.md) (v1.11) — detalhes de jitter + deadline propagation
305
+ - [`load-shedding-graceful-degradation`](../load-shedding-graceful-degradation/SKILL.md) (v1.11) — defesas server-side
306
+ - [`four-golden-signals`](../four-golden-signals/SKILL.md) (v1.10) — Saturation como early warning de cascade
307
+ - [`production-readiness-review`](../production-readiness-review/SKILL.md) (v1.10) — PRR Axe 4 verifica defesas
308
+ - [`omm-auditor`](../../agents/omm-auditor.md) (v1.9) — Capacidade 1 (Resilience) consume cascading-failures-auditor
309
+ - [`cascading-failures-auditor`](../../agents/cascading-failures-auditor.md) (v1.11) — agent que detecta gaps automaticamente
310
+
311
+ *Material-fonte: Site Reliability Engineering — Beyer/Jones/Petoff/Murphy (Google/O'Reilly, 2016) — Cap 22: "Addressing Cascading Failures".*