DEILE
03 — Segurança

Defesa em profundidade. Por arquitetura, não confiança.

Defesa em profundidade, por arquitetura. Cada camada tem código auditável e comportamento verificável.

Pilha de defesa

Oito camadas, todas por design.

A segurança do DEILE não é configuração. É arquitetura. Cada camada existe no código e pode ser auditada — e cada gap conhecido está documentado nas decisões e referenciado adiante na página.

L1

Permission Manager

Regras com prioridade resource → tool → level. Default leitura, escrita exige regra explícita. Mudanças em configuração sensível emitem evento de policy change tipado.

L2

Approval System

Gate por nível de risco (low / moderate / high / critical) antes de ações irreversíveis. Mensagens diretas, menções de cargo, comandos potencialmente destrutivos passam por aqui.

L3

Audit Logger

Eventos tipados via enum. Toda execução de ferramenta, todo policy change, todo bloqueio do loop guard vira linha JSON estruturada — nunca formato livre.

L4

Secrets Scanner

Detecta padrões de GitHub (ghp_/gho_/ghu_/ghs_/ghr_/github_pat_) e GitLab (glpat-/gldt-/glptt-/glsoat-), além de chaves AWS, tokens Discord/Slack e chaves de provedores LLM. Redação automática no session store.

L5

Loop Guard

Aborta turnos em runaway por 4 regras simultâneas (teto, repetição idêntica, janela móvel, sem progresso). Emite evento SUSPICIOUS_ACTIVITY auditado.

L6

Pod Security Standard restricted

Cada pod roda como usuário não-root, sistema de arquivos raiz somente leitura, todas as capacidades do Linux dropadas, seccomp default. Imagem baked (COPY no Dockerfile, nada montado).

L7

NetworkPolicy default-deny

Tudo bloqueado por padrão. Ingress restrito por label de pod. Egress permite DNS e HTTPS 443 (não RFC1918), mitigando pivot lateral — o controle por host é aplicado em camada de aplicação.

L8

Credenciais como arquivos

Secrets do Kubernetes são montadas em /run/secrets, modo 0600, nunca como variáveis de ambiente — o que impede leitura via /proc/<pid>/environ por processos vizinhos.

Loop guard

Quatro regras para detectar runaway. Uma para abortar.

O guarda fica entre o agente e cada chamada de tool. Quando detecta padrão de runaway, aborta o turno e emite um evento auditado. Vale para o tool-loop interativo e para os três provedores não-streaming.

Teto absoluto

Toda sessão tem um número máximo de tool calls. Ultrapassou, aborta.

3 idênticas consecutivas

Mesma tool com mesmos argumentos por 3 turnos seguidos — sinal claro de loop. Aborta.

3 de 5 em janela móvel

Repetição alta em janela curta detecta loops parciais. Aborta.

6 sem progresso

Sequência longa de tools retornando vazio ou erro indica thrashing. Aborta.

Approval system

Ações irreversíveis passam por um gate explícito.

Mandar uma mensagem direta para alguém, mencionar um cargo no Discord, executar uma operação destrutiva — antes de qualquer uma dessas, o pipeline pede aprovação classificada por nível de risco.

tool dangerous
   │
   ▼
approval_system.request_approval(risk_level)
   │
   ├─ LOW      → auto-aprovado em auto bypass (configurável)
   ├─ MODERATE → aprovação humana esperada
   ├─      → aprovação obrigatória + log de motivação
   └─  → aprovação obrigatória + segunda confirmação
                                │
                                ▼
                       executar     ou     
Como os segredos viajam

Arquivos no disco. Nunca em /proc/<pid>/environ.

Kubernetes Secret
   │
   ▼  volumeMounts (defaultMode 0600)
/run/secrets/<role>/<name>
   │
   ▼  wrapper lê o arquivo no boot
processo do wrapper recebe o valor em variável local
   │
   ├─ wrapper popula os.environ APENAS o tempo necessário p/ bootstrap dos providers
   │
   ▼  bootstrap_providers() consome
processo do agente roda SEM o valor no environ
   │
   └─ exceção controlada: tokens de SDK que exigem permanência (ex.: cliente Discord)
       continuam em variável de processo, NÃO em arquivo
por que importa

Variáveis de ambiente são visíveis por qualquer processo do mesmo usuário via /proc. Mantê-las em arquivos com modo restrito impede leitura por processos vizinhos no mesmo namespace.

limite honesto

O processo do agente ainda PODE ler o arquivo (ele tem permissão por desenho — precisa carregar a credencial). A defesa é contra processos laterais e contra exposição via core dumps.

Whitelist por superfície

O mesmo binário, três políticas distintas.

Cada pod traduz a sua origem de entrada em uma whitelist diferente. Não confiamos no input do Discord do mesmo jeito que no operador rodando kubectl. A whitelist é aplicada antes do tool-loop, e cada bloqueio gera evento auditado.

deilebot (canal Discord)

Entrada vinda de fora do cluster. Toolset reduzido para mensageria + um único gancho de despacho controlado. Sem acesso a shell, escrita de arquivos ou git.

tools permitidas
discord_* · dispatch_deile_task · vision · cron_*

deile-worker (alvo do pipeline)

Roda code real. Toolset completo (bash, edição, git, testes), exceto mensageria — para não permitir que um brief malicioso peça DM. Ingress restrita ao pipeline com Bearer.

tools permitidas
tudo, exceto messaging + dispatch_deile_task

deile-shell (REPL interativo)

Acessível somente via kubectl exec por um operador autenticado no cluster. Toolset completo. Sem ingress de rede. Prompt vem do humano.

tools permitidas
all (operado por humano)
Hardening dos containers

Cada pod nasce mínimo. Nada além do que precisa.

A imagem do DEILE é uma só (deile-stack:local) usada por todos os pods. O que muda é o entrypoint do wrapper e a whitelist de ferramentas. Os controles abaixo são aplicados a TODOS.

Controle Valor
runAsNonRoot true (uid 10001)
readOnlyRootFilesystem true
allowPrivilegeEscalation false
capabilities.drop [ALL]
seccompProfile RuntimeDefault
PodSecurity enforce restricted (1.29+)
secrets mount mode 0600 — file, não env var
imagePullPolicy Never (image baked, não pull em runtime)