Mapa da aula
Aula 22 publicada. Mapa, exemplo, EX064.
flowchart TD
N0["22.1 Configuração como código"]
N1["22.2 Planejar, depois agir"]
N2["22.3 Correção automática segura versus ticket"]
N3["22.5 Automação é código: trate-a assim"]
N4["22.7 Atividade prática: plano de deriva"]
N5["Síntese do capítulo"]
N0 --> N1 --> N2 --> N3 --> N4 --> N5
N5 --> EX["Exemplo resolvido"]
EX --> Q["Exercício EX064"]
Desenho lógico
flowchart LR
N0["22.1 Configuração como código"]
N1["22.2 Planejar, depois agir"]
N2["22.3 Correção automática segura versus ticket"]
N3["22.5 Automação é código: trate-a assim"]
N4["22.7 Atividade prática: plano de deriva"]
N5["Síntese do capítulo"]
N0 --> N1 --> N2 --> N3 --> N4 --> N5 --> Q["EX064"]
[22.1 Configuração como código]
|
v
[22.2 Planejar, depois agir]
|
v
[22.3 Correção automática segura versus ticket]
|
v
[22.5 Automação é código: trate-a assim]
|
v
[22.7 Atividade prática: plano de deriva]
|
v
[Síntese do capítulo]
|
v
[Exemplo resolvido] --> [Exercício EX064]
Objetivos de aprendizagem e conexão
Depois deste capítulo, você deve ser capaz de:
- expressar a configuração desejada como código e compará-la automaticamente com o estado real;
- projetar uma automação que planeja antes de agir, separa as correções automáticas seguras das mudanças que precisam de aprovação e limita o seu próprio raio de impacto;
- reconhecer quando a própria fonte da verdade pode estar errada, e parar;
- manter a automação dentro do controle de mudanças e produzir evidências a partir dela.
Os Capítulos 6 e 14 descreveram linhas de base e verificações de integridade feitas à mão. Com três relays e um parque crescente, a verificação manual deixa de acontecer. A automação torna confiáveis as verificações de rotina — e torna os erros rápidos e amplos. Este capítulo trata de obter o primeiro sem o segundo.
22.1 Configuração como código
Escreva o estado desejado de cada classe de host como dados sob controle de versões: configurações do SSH, endereços de escuta, servidores de hora, encaminhamento de logs, versões de pacotes. Um coletor lê o estado real de cada host (somente leitura), e uma comparação produz a deriva: as chaves cujo valor real difere do desejado. O guia do NIST de gestão de configuração descreve o monitoramento das configurações contra linhas de base como uma atividade central (NIST SP 800-128); o framework do NIST de desenvolvimento seguro de software aplica disciplinas semelhantes — controle de versões, revisão, pipelines de build protegidos — ao código que o implementa (NIST SP 800-218).
22.2 Planejar, depois agir
Uma boa automação separa o planejar do aplicar. O plano lista toda mudança pretendida: host, configuração, valor atual, valor desejado e modo. A etapa de aplicação executa um plano aprovado, e não um cálculo novo. Isso dá a uma pessoa a chance de ver o que vai acontecer, dá ao registro de mudança algo específico para aprovar e produz evidências depois.
O plano do Laboratório 22 para o RLY-02 lista duas mudanças, SSH com senha e servidores de hora públicos, com os valores atuais e desejados.
O listener de depuração do RLY-03 aparece no plano como um ticket, e não como uma ação, porque removê-lo poderia destruir a evidência de quem o habilitou.
22.3 Correção automática segura versus ticket
Alguma deriva é segura para corrigir automaticamente: configurações de baixo risco, reversíveis e bem compreendidas (desabilitar de novo a autenticação por senha do SSH; restaurar os servidores de hora aprovados; restaurar o encaminhamento de logs). Outra deriva precisa passar pelo controle de mudanças: qualquer coisa que possa mudar o comportamento do serviço (uma versão de pacote), qualquer coisa que possa ser evidência (um listener de depuração inesperado — que pode ser de um atacante ou de um engenheiro, e deve ser preservado antes da remoção, Capítulo 20) e qualquer coisa que afete o processo físico. Escreva a lista de correções automáticas de forma explícita e mantenha-a curta.
22.4 Limites do raio de impacto
A automação precisa se proteger contra os seus próprios erros. Limites comuns: aplicar a um host de cada vez, verificando cada um antes do próximo; parar na primeira falha; e parar e escalar se for encontrada deriva demais — se a maior parte do parque parece ter derivado, a explicação mais provável é que o estado desejado está errado (um commit ruim, um branch errado), e a correção automática espalharia o erro por toda parte. Uma grande interrupção causada por uma atualização defeituosa distribuída a muitos sistemas de uma vez — como o incidente de julho de 2024 que afetou hosts Windows rodando um produto de segurança, descrito pela Microsoft como tendo afetado cerca de 8,5 milhões de dispositivos (Microsoft, 20 de julho de 2024) — ilustra por que a implantação escalonada e as condições de parada importam para qualquer distribuição automatizada.
22.5 Automação é código: trate-a assim
O próprio código da automação e os arquivos de estado desejado têm alto valor: quem consegue mudá-los consegue mudar todos os hosts. Proteja-os com revisão antes do merge, acesso de escrita restrito, commits assinados ou branches protegidos, e logs de cada execução. As credenciais da automação para ler e mudar os hosts são contas privilegiadas (Capítulo 7).
A fusão do NTP no Capítulo 25 é o aviso: um único commit revisado mudou a hora em todos os relays.
Trate a conta que a automação usa para alcançar do RLY-01 ao RLY-03 como a vendor-kell: limitada no tempo onde possível, registrada e revisada na revisão trimestral de acessos do Capítulo 7.
22.6 Exemplo resolvido: uma execução simulada em três relays (sintético)
O Laboratório 22 compara o estado desejado com três relays. O RLY-01 está conforme. O RLY-02 tem a autenticação por senha do SSH reabilitada e servidores de hora públicos — ambos na lista de correções automáticas. O RLY-03 tem um listener de depuração em todas as interfaces, um pacote do relay mais antigo e nenhum encaminhamento de logs. Dois de três hosts derivaram, mais da metade do parque, então a salvaguarda interrompe a execução. Aqui a interrupção é, num sentido, um alarme falso — a fonte da verdade está bem —, mas a regra está certa em parar: uma pessoa confirma o estado desejado e então aprova a aplicação das três correções automáticas, host por host, enquanto o listener de depuração e a versão do pacote vão para tickets. O listener de depuração no RLY-03 é o mesmo sintoma encontrado pela verificação de integridade no RLY-01 no Capítulo 6: duas vezes é um padrão, e o método de resolução de problemas do Capítulo 20 se aplica.
Note também que a falta de encaminhamento de logs no RLY-03 significa que os seus próprios logs sobre o listener de depuração podem nunca ter chegado ao SIEM — mais um motivo para preservar as evidências locais antes de corrigir.
22.7 Atividade prática: plano de deriva
Laboratório 22 (salve como lab22.py, execute com python3 lab22.py):
# Lab 22 - automated configuration-drift check with a dry-run plan (offline, standard library only)
# Synthetic desired state (from version control) and actual state (as collected from three relay hosts).
import json
desired = {"ssh.password_auth": False, "ssh.permit_root": False, "relay.listen": "10.30.0.5:8443",
"relay.debug_listen": None, "ntp.servers": ["10.30.0.1", "10.30.0.2"], "log.forward": "siem-01:6514",
"pkg.relayd": "2.4.1"}
actual = {
"rly-01": {**desired},
"rly-02": {**desired, "ssh.password_auth": True, "ntp.servers": ["pool.example.net"]},
"rly-03": {**desired, "relay.debug_listen": "0.0.0.0:9000", "pkg.relayd": "2.3.9", "log.forward": None},
}
SAFE_AUTOFIX = {"ssh.password_auth", "ssh.permit_root", "ntp.servers", "log.forward"} # low-risk, reversible
def plan(host, state):
steps = []
for k, want in desired.items():
have = state.get(k)
if have != want:
mode = "auto" if k in SAFE_AUTOFIX else "ticket"
steps.append({"host": host, "key": k, "have": have, "want": want, "mode": mode})
return steps
all_steps = [s for h, st in actual.items() for s in plan(h, st)]
for s in all_steps:
print(f"{s['host']} {s['key']:<20} have={json.dumps(s['have']):<22} want={json.dumps(s['want']):<26} -> {s['mode']}")
print("hosts compliant:", [h for h, st in actual.items() if not plan(h, st)])
print("dry run only: %d auto-fix steps, %d need a change ticket" % (sum(s['mode'] == 'auto' for s in all_steps), sum(s['mode'] == 'ticket' for s in all_steps)))
# Guard: never auto-apply to more than one host at a time, and stop if the host count with drift exceeds half the fleet
drifted = {s['host'] for s in all_steps}
print("guard: drifted hosts %d of %d -> %s" % (len(drifted), len(actual), "HALT and escalate (possible bad source of truth)" if len(drifted) > len(actual) / 2 else "proceed one host at a time"))
Saída esperada (Python 3.13.5):
rly-02 ssh.password_auth have=true want=false -> auto
rly-02 ntp.servers have=["pool.example.net"] want=["10.30.0.1", "10.30.0.2"] -> auto
rly-03 relay.debug_listen have="0.0.0.0:9000" want=null -> ticket
rly-03 log.forward have=null want="siem-01:6514" -> auto
rly-03 pkg.relayd have="2.3.9" want="2.4.1" -> ticket
hosts compliant: ['rly-01']
dry run only: 3 auto-fix steps, 2 need a change ticket
guard: drifted hosts 2 of 3 -> HALT and escalate (possible bad source of truth)
Leia primeiro a interrupção. Dois de três relays derivaram, mais da metade do parque, então a execução parou antes de aplicar qualquer coisa. Depois leia o plano por host: a autenticação por senha e os servidores de hora públicos do RLY-02, e a falta de encaminhamento de logs do RLY-03, estão na lista de correções automáticas; o listener de depuração e o pacote do relay mais antigo do RLY-03 não estão, e viram tickets. Antes de aprovar qualquer correção no RLY-03, copie os seus logs locais, porque, sem encaminhamento, eles podem ser o único registro de quando o listener de depuração apareceu.
22.8 Erros comuns e limites
- Automação que aplica mudanças sem um plano revisável.
- Listas longas de correções automáticas, incluindo configurações que podem ser evidência ou mudar o comportamento.
- Aplicar a todos os hosts de uma vez.
- Nenhuma condição de parada para "deriva demais".
- Código e credenciais da automação menos protegidos do que os hosts que ela gerencia.
- Tratar a conformidade automatizada como prova de segurança; ela prova apenas as configurações que confere.
A interrupção do Laboratório 22 com dois de três relays derivados é o quarto item feito do jeito certo.
Uma lista de correções automáticas que incluísse o listener de depuração teria removido a evidência de quem o configurou no RLY-03.
Exercícios — capítulo 22
EX064 — Aprove o plano. Objetivo: revisar um plano de automação como aprovador de mudanças. Entradas: a saída do Laboratório 22. Restrições: aprove, modifique ou rejeite cada passo. Etapas: (1) decida para cada um dos cinco passos; (2) dê a ordem de aplicação; (3) declare a verificação depois de cada host. Evidência esperada: tabela. Rubrica: 3 = correções automáticas aprovadas host por host (RLY-02, depois RLY-03), listener de depuração preservado e depois removido sob um ticket após a investigação, atualização do pacote como mudança normal com canário (Capítulo 27), encaminhamento de logs restaurado cedo no RLY-03 para recuperar a visibilidade; verificações nomeadas; 2 = falta a ordem ou a preservação; 1 = aprovar tudo; 0 = nada.
EX065 — Ajuste a salvaguarda. Objetivo: raciocinar sobre limiares de parada. Entradas: a salvaguarda interrompe quando mais da metade do parque tem deriva. Restrições: o parque vai crescer para 12 relays. Etapas: (1) diga se "mais da metade" ainda é sensato com 12; (2) proponha uma salvaguarda melhor usando o tipo de deriva, e não apenas a contagem de hosts. Evidência esperada: parágrafo. Rubrica: 3 = reconhece que a mesma chave derivando em muitos hosts sugere uma fonte da verdade ruim, enquanto chaves diferentes em hosts diferentes sugerem mudanças locais; propõe parar quando uma chave difere em mais de uma fração definida dos hosts, ou quando há um commit recente e não revisado no estado desejado; 2 = parcial; 1 = mantém "metade"; 0 = nada.
EX066 — Proteja o pipeline. Objetivo: proteger a própria automação. Entradas: o repositório de estado desejado e a conta da automação. Restrições: cinco controles. Etapas: liste-os com evidências. Evidência esperada: tabela. Rubrica: 3 = branch protegido com revisão obrigatória, mantenedores restritos com MFA, commits ou tags assinados, conta da automação limitada aos hosts gerenciados com credenciais num cofre, logs das execuções encaminhados ao SIEM com um alerta para execuções fora do calendário; evidência para cada um; 2 = quatro; 1 = genérico; 0 = nada.
Síntese do capítulo
Expresse o estado desejado como código, colete o estado real em modo somente leitura e calcule a deriva. Planeje antes de agir; corrija automaticamente apenas uma lista curta de configurações de baixo risco e reversíveis, e mande todo o resto — especialmente qualquer coisa que possa ser evidência — para o controle de mudanças. Limite o raio de impacto: um host de cada vez, parar na falha, interromper quando a deriva parecer uma fonte da verdade ruim. Proteja a automação com o mesmo cuidado que os hosts que ela gerencia.