# A retomada da sessão do agente deve manter a aprovação antiga?

Uma conversa de agente retomada nunca deve herdar autoridade apenas porque herdou texto. O modelo pode continuar com o mesmo plano, o mesmo histórico de ferramentas e o mesmo tom confiante. Nada disso informa se o processo que solicita acesso é o mesmo que você aprovou, se o cofre de credenciais está disponível ou se o gateway ainda tem um registro confiável da aprovação.

Trate a retomada como uma alegação de continuidade que precisa ser verificada, não como um direito que o cliente pode declarar. Se a identidade do processo, o estado do cofre ou o estado do gateway mudou, a decisão antiga terminou. Solicite nova aprovação antes da próxima ação protegida.

Isso parece rígido até você observar como as reinicializações acontecem no trabalho real. Um agente de programação se atualiza. Um editor relança seu auxiliar depois de uma falha. O usuário encerra um processo travado e inicia outro. Um notebook entra em repouso enquanto o cofre é bloqueado. Um aplicativo da barra de menus reinicia depois de uma atualização. A conversa costuma se reconectar de forma tão suave que o usuário vê uma única sequência sem interrupções. Um código de segurança que trata essa sequência como autoridade vai juntar silenciosamente execuções diferentes em uma única aprovação.

## Uma conversa retomada não carrega autoridade

Uma conversa é evidência de contexto, enquanto uma autorização é uma decisão sobre um ator presente que tenta realizar uma ação presente. Essas coisas precisam continuar separadas.

Os sistemas de agentes costumam armazenar um identificador de conversa de longa duração, uma transcrição e talvez um histórico de chamadas de ferramentas. Isso é útil para recuperar o trabalho depois de uma desconexão. Esses dados informam o que o agente tentava fazer, quais arquivos alterou e qual solicitação de API falhou no meio. Eles não identificam o processo do sistema operacional atualmente conectado às ferramentas.

Considere uma sequência comum. Um agente prepara uma solicitação de implantação e recebe aprovação da sessão. O gateway reinicia antes que a solicitação seja enviada. O cliente do agente se reconecta, carrega a transcrição antiga e diz que está retomando a mesma execução. Se o gateway aceitar essa declaração e restaurar a aprovação anterior, a aprovação passará a cobrir um processo que o gateway não inspecionou desde que voltou.

O novo processo pode ser inofensivo. Também pode ser uma compilação recém-instalada, um executável auxiliar iniciado de outro diretório ou um segundo cliente de ferramentas que encontrou um token de retomada em cache. Não é possível distinguir esses casos lendo a conversa.

Por isso, «o usuário já aprovou esta tarefa» é o teste errado. O usuário aprova uma execução de agente identificável, sob condições definidas. A aprovação termina quando essas condições deixam de ser verdadeiras ou não podem mais ser comprovadas.

O Model Context Protocol torna essa diferença mais clara. A documentação de transporte diz que, no stdio, o cliente inicia o servidor como subprocesso e troca mensagens JSON-RPC pela entrada e saída padrão. Isso é uma relação entre processos ativos, não uma concessão duradoura armazenada em uma transcrição. O changelog do MCP também removeu as sessões no nível do protocolo do trabalho mais recente sobre Streamable HTTP e orienta servidores com estado a usar identificadores explícitos emitidos pelo servidor. Essa mudança não resolve a autorização sozinha, mas evita fingir que um identificador de sessão de transporte é uma credencial de identidade.

Mantenha os termos separados no seu projeto:

- Uma conversa é um registro da aplicação que pode sobreviver aos processos.
- Um processo é uma instância do sistema operacional com duração limitada.
- Uma aprovação de sessão é uma concessão a um processo identificado durante seu ciclo de vida.
- O uso de uma credencial é uma ação que precisa satisfazer as condições atuais do cofre e do gateway.

As equipes confundem esses termos porque uma demonstração pelo caminho feliz faz os quatro parecerem avançar juntos. As reinicializações em produção os separam.

## A identidade do processo tem mais de uma parte

Um identificador de processo isolado é fraco demais para vincular uma aprovação duradoura, porque os sistemas operacionais podem reutilizar identificadores depois que um processo termina. O caminho do processo também é fraco demais, porque o arquivo nesse caminho pode mudar. Uma assinatura de código isolada é fraca demais, porque o mesmo programa assinado pode estar em execução em vários lugares ao mesmo tempo.

Monte a identidade que você exibe e associa usando vários fatos coletados no momento da aprovação. No macOS, um bom ponto de partida é o processo em execução, a identidade do executável e a autoridade de assinatura do código. A Apple documenta os requisitos designados como o requisito de código que identifica um código assinado, geralmente construído a partir da autoridade de assinatura e do identificador incorporado quando o aplicativo não forneceu um requisito explícito. Isso oferece ao usuário algo melhor para inspecionar do que um PID bruto.

Ainda assim, não transforme uma autoridade de assinatura em uma resposta mágica. Dois processos separados com o mesmo requisito designado continuam sendo dois processos separados. Um agente assinado pode iniciar um auxiliar não assinado. Um binário de desenvolvimento compilado localmente pode ter uma assinatura ad hoc. Um invasor que controla o processo aprovado depois da aprovação não se torna seguro apenas porque a assinatura original parecia correta.

Use uma associação de processo com fatos que façam sentido em conjunto:

```text
approval_subject = {
  process_id: 48192,
  process_start_time: "2026-07-22T14:18:03Z",
  executable_file_id: "volume:.../inode:...",
  executable_hash: "sha256:...",
  signing_requirement: "anchor ... and identifier ...",
  parent_process_id: 48001,
  launch_nonce: "random-128-bit-value"
}
```

Os campos exatos variam conforme a plataforma. A regra não muda: o gateway precisa de evidências suficientes para rejeitar uma aprovação antiga quando o sujeito antigo já não existe. O nonce de inicialização importa porque vem do gateway depois que ele inspeciona o novo processo. Um cliente não pode restaurá-lo com segurança a partir de um cache local e chamar isso de continuidade.

Você não precisa mostrar todos os campos ao usuário. Na verdade, isso costuma piorar o cartão de aprovação. Mostre a autoridade de assinatura, o nome do executável e uma descrição clara do canal de ação. Mantenha a associação completa no diário para consultas posteriores.

Há um ponto difícil que vale declarar com clareza. Se o seu gateway não consegue ver nem atestar o processo que faz a solicitação, ele não pode conceder uma aprovação específica para esse processo. Ainda pode conceder uma aprovação menor, associada a outro sujeito confiável, mas não deve afirmar que verificou o processo. Chamar um nome de processo fornecido pelo cliente de «identidade» é como projetos fracos ganham rótulos com aparência oficial.

## A reinicialização do processo encerra a aprovação da sessão

Uma aprovação de sessão deve terminar quando o processo é encerrado, mesmo que o processo substituto tenha código, argumentos e histórico de conversa idênticos.

Essa regra captura casos que parecem banais até causarem problemas. Imagine um agente executado por uma extensão do editor. A extensão falha, o supervisor inicia uma substituta e o novo processo recarrega o estado da tarefa antiga. O novo processo tem o mesmo diretório do projeto e provavelmente a mesma conta de usuário. Ele não tem a autoridade concedida ao processo que falhou.

O mesmo vale quando um agente cria um processo filho. Um processo pai pode receber aprovação e depois iniciar um auxiliar para executar comandos de shell ou fazer chamadas de rede. Se a aprovação se aplica apenas ao pai, o auxiliar deve agir por meio dele, sob uma delegação controlada, ou solicitar sua própria aprovação. Passar um token bearer pela árvore de processos torna a aprovação portátil exatamente da maneira que você está tentando evitar.

Não tente corrigir isso com um prazo de expiração longo. Uma aprovação de cinco minutos que qualquer processo substituto pode retomar não é uma aprovação de sessão de cinco minutos. É uma credencial bearer de cinco minutos com um nome amigável.

Uma regra melhor é simples:

```text
if current.process_id != approved.process_id:
    deny("approval belongs to a different process")

if current.process_start_time != approved.process_start_time:
    deny("process lifetime changed")

if current.launch_nonce != approved.launch_nonce:
    deny("gateway has not bound this run")
```

O gateway deve executar essa verificação antes de decidir se uma solicitação se qualifica para a aprovação da sessão. Não faça a verificação apenas quando o agente se reconectar. Um processo pode mudar em uma arquitetura de cliente que multiplexa trabalho, e um objeto de aprovação obsoleto pode permanecer na memória por mais tempo do que o esperado.

O usuário pode reclamar que o substituto é obviamente o mesmo agente. Em geral, isso é um pedido por um cartão de aprovação mais fluido, não um motivo para apagar a fronteira. Explique que o agente foi reiniciado e mostre o novo assinante. Um clique deliberado custa menos do que investigar uma chamada de produção não intencional feita por um processo não inspecionado.

## Uma mudança no estado do cofre remove o direito de agir

O estado do cofre não é um detalhe secundário. Quando um cofre é bloqueado, qualquer decisão anterior que dependia de sua disponibilidade deve parar de conceder permissão para ações que usam credenciais.

Há duas falhas a evitar. A primeira é óbvia: o gateway continua usando uma credencial descriptografada depois que o cofre é bloqueado. A segunda é mais silenciosa: o gateway coloca uma ação com credencial em fila enquanto está bloqueado e a executa automaticamente quando o cofre é desbloqueado, porque ainda existe uma aprovação de sessão antiga. Essa segunda falha transforma um desbloqueio humano posterior em uma aprovação acidental de uma solicitação anterior.

A documentação do Keychain da Apple estabelece claramente essa fronteira. O controle de acesso pode exigir a presença do usuário quando um aplicativo tenta recuperar um item, e a Apple recomenda escolher a configuração de acessibilidade mais restritiva compatível com o aplicativo. O Secure Enclave pode controlar operações criptográficas sem expor dados biométricos subjacentes a softwares no espaço do usuário. Esses mecanismos são úteis, mas não decidem a semântica do seu gateway. A aplicação precisa decidir o que acontece com execuções de agentes já aprovadas quando essa barreira se fecha.

A resposta mais segura é manter uma época do cofre. Incremente-a sempre que o cofre for bloqueado, desbloqueado, redefinido ou perder sua sessão protegida. Associe a época a cada registro de aprovação. Uma divergência significa que o registro não pode autorizar uma ação com credencial.

```text
approved_vault_epoch = 17
current_vault_epoch = 18

if approved_vault_epoch != current_vault_epoch:
    require_new_session_approval()
```

Isso não significa que todo desbloqueio precise virar um ritual irritante. Se o agente não tiver uma sessão ativa, nada acontece. Se uma solicitação precisar de uma credencial depois do desbloqueio, o gateway pode mostrar um novo cartão explicando o motivo: o estado do cofre mudou depois da aprovação anterior. Para credenciais marcadas para aprovação em cada uso, mantenha também a verificação por chamada. Aprovação de sessão e aprovação por chamada respondem a perguntas diferentes.

A aprovação de sessão pergunta se este processo identificado pode usar este canal durante a execução atual. A aprovação por chamada pergunta se a pessoa quer este uso específico agora. Tratar a aprovação de sessão como substituta da decisão por chamada elimina o propósito de marcar uma credencial dessa forma.

## A reinicialização do gateway apaga a memória da concessão

Uma reinicialização do gateway deve invalidar as aprovações de sessão mantidas na memória, porque o gateway reiniciado não consegue provar que seu antigo registro de aprovação ainda tem uma associação completa e íntegra com o mundo real em execução.

Algumas equipes persistem tokens de aprovação e os recarregam depois da reinicialização. A motivação é compreensível: o usuário clicou uma vez, o agente continua trabalhando e uma reinicialização não deveria interromper o fluxo. Mas um token persistente frequentemente se torna uma credencial reutilizável. O cliente o envia novamente depois de se reconectar, o gateway o reconhece e a concessão antiga volta sem uma nova inspeção do processo.

Esse projeto também torna a recuperação ambígua. O gateway caiu antes de enviar a ação? Enviou a ação e caiu antes de registrar a resposta? O serviço remoto recebeu a solicitação duas vezes depois de uma repetição? Restaurar a autorização e repetir a solicitação como uma única operação mistura recuperação de identidade com recuperação de entrega. Elas precisam de controles diferentes.

Dê a cada ciclo de vida do gateway um identificador de inicialização que exista apenas na memória atual. Inclua-o em todos os registros de aprovação. Depois da reinicialização, o identificador atual será diferente, portanto nenhum registro de sessão anterior poderá corresponder.

```text
approval = {
  gateway_boot_id: "b7f9...",
  process_binding: "...",
  vault_epoch: 17,
  approved_at: "2026-07-22T14:20:11Z"
}

if approval.gateway_boot_id != gateway.current_boot_id:
    require_new_session_approval()
```

O gateway pode persistir um evento de auditoria informando que uma aprovação ocorreu. Não deve recarregar esse evento como uma concessão ativa. O histórico de auditoria explica o que aconteceu, mas não recria uma relação de autoridade em funcionamento.

O Sallyport segue esse formato ao manter o cofre no aplicativo assinado da barra de menus e negar ações enquanto o cofre estiver bloqueado. Sua autorização por sessão está associada a um novo processo do agente, e o usuário pode revogar imediatamente uma execução registrada. Essas fronteiras só são úteis se uma reinicialização ou um bloqueio não puder reconectar silenciosamente uma execução antiga a uma decisão nova.

## Associe a aprovação a evidências que o cliente não possa reproduzir

O registro de aprovação precisa de evidências atuais criadas pelo servidor. Um token de retomada fornecido pelo cliente pode ajudar o gateway a encontrar uma conversa ou exibir um rótulo útil, mas não pode ser a prova de que a autorização continua válida.

O padrão prático mais simples usa quatro valores que mudam:

1. O gateway cria um identificador de inicialização aleatório ao ser iniciado.
2. O gateway cria um nonce de execução aleatório depois de identificar um processo recém-conectado.
3. O cofre mantém uma época que muda sempre que a disponibilidade protegida muda.
4. O gateway cria um identificador de aprovação somente depois que o usuário aprova a execução identificada.

Depois, o gateway avalia cada ação em relação a todos os valores que controla. O cliente pode solicitar uma ação, mas não pode fabricar uma aprovação que corresponda a um novo identificador de inicialização ou a um novo nonce de execução.

Este é um modelo compacto de estado que as equipes podem adaptar. Ele armazena deliberadamente a referência da conversa como contexto de exibição, nunca como campo de autorização.

```json
{
  "run": {
    "conversation_ref": "worktree-cleanup-42",
    "process": {
      "pid": 48192,
      "started_at": "2026-07-22T14:18:03Z",
      "signing_requirement": "recorded-at-approval",
      "launch_nonce": "gateway-generated"
    }
  },
  "approval": {
    "id": "gateway-generated",
    "gateway_boot_id": "gateway-generated",
    "vault_epoch": 17,
    "expires_when_process_exits": true
  }
}
```

Observe o que falta: não há um sinalizador reutilizável `resume_authorized` nem um horário de expiração que possa transformar um processo morto em um sujeito ativo. Você pode manter um prazo curto como limite adicional, mas prazo não é identidade.

Quando o agente se reconectar, faça com que ele repita a inicialização e o registro do processo. O gateway deve então retornar um destes resultados:

```text
REAUTH_REQUIRED process_changed
REAUTH_REQUIRED gateway_restarted
REAUTH_REQUIRED vault_state_changed
RETRY_SAFE previous_action_not_started
STATUS_UNKNOWN inspect_activity_journal
```

A diferença entre `RETRY_SAFE` e `STATUS_UNKNOWN` importa. O gateway só pode dizer que uma ação não começou se tiver evidência durável de que ela não começou. Se perdeu energia depois de entregar uma solicitação HTTP à pilha de rede, a resposta honesta pode ser desconhecida. O agente deve consultar o destino ou o diário antes de tentar uma ação duplicada.

## Repetir uma ação é diferente de restaurar uma aprovação

Um protocolo de reconexão deve restaurar primeiro a comunicação, estabelecer uma nova autoridade em segundo lugar e decidir se deve repetir a ação em terceiro. Combinar essas etapas produz solicitações duplicadas e aprovações herdadas.

Use esta sequência para uma ação protegida que perde a conexão:

1. O agente se reconecta e inicializa uma nova relação com o gateway.
2. O gateway identifica o processo atual e o compara com qualquer registro de execução existente.
3. O gateway verifica seu identificador de inicialização e a época atual do cofre.
4. Se algum fato de autoridade mudou, o gateway solicita uma nova aprovação da sessão antes do uso da credencial.
5. O gateway informa se sabe que a ação anterior não começou, foi concluída ou tem estado desconhecido.

A ordem importa. Não peça ao agente para reenviar a solicitação original antes de estabelecer a autorização atual. Isso dá ao cliente em reconexão a chance de pressionar em torno de uma solicitação antiga: «Eu já tinha sido aprovado, apenas termine». Uma pessoa costuma ver as mesmas palavras e presumir que a solicitação é uma continuação inofensiva. O gateway deve tornar a condição alterada visível antes de apresentar a ação.

Para APIs HTTP, use uma chave de idempotência quando o destino oferecer suporte. Gere a chave para a ação comercial lógica, registre-a de forma durável antes do envio e reutilize-a somente depois de restabelecer a autorização para a repetição. Uma chave de idempotência ajuda o serviço remoto a detectar uma entrega duplicada. Ela não autoriza a repetição.

Para SSH, as repetições exigem mais cuidado, porque um comando remoto pode ter alterado parcialmente uma máquina antes que a conexão caísse. Prefira operações que escrevam um marcador explícito ou consultem o estado existente antes de modificá-lo novamente. Um comando como `mkdir` pode ficar mais seguro com uma verificação do diretório esperado. Um comando que rotacione uma credencial ou reinicie um serviço normalmente deve informar estado desconhecido depois de uma falha de transporte, até que o agente leia o estado remoto.

Não esconda essa incerteza atrás de uma linguagem otimista. Um agente que diz «a implantação foi concluída» depois de perder a resposta está fabricando confiança. O diário deve informar que o resultado da ação não foi observado, e o agente deve investigar.

## As falhas mais difíceis revelam a fronteira correta

O teste mais revelador não é uma reconexão limpa. É uma reinicialização no meio de uma ação, seguida por um agente que tenta continuar a qualquer custo.

Imagine um agente com aprovação de sessão para atualizar um rastreador de problemas por meio de uma API HTTP. Ele prepara uma solicitação, recebe aprovação e chama o gateway. O gateway injeta a credencial e começa a enviar a solicitação. Nesse momento, o aplicativo do gateway reinicia. O agente se reconecta com a referência de conversa anterior e um estado local de ferramenta armazenado em cache.

Um projeto fraco aceita a referência antiga, restaura a aprovação e repete a solicitação. O problema pode receber dois comentários. Pior, a aprovação se aplica ao processo que agora fornece o estado armazenado em cache.

Um projeto cuidadoso produz um resultado menos elegante. O gateway reiniciado cria um novo identificador de inicialização. Ele rejeita a concessão de sessão antiga. Solicita aprovação do processo conectado no momento. Verifica o diário de atividades. Se o diário registrou uma solicitação concluída, retorna o resultado. Se registrou que nenhuma solicitação saiu do gateway, permite uma nova repetição aprovada. Se a ação ultrapassou a fronteira de entrega, mas o resultado foi perdido, informa estado desconhecido. O agente lê o problema antes de decidir se outra alteração é necessária.

Isso dá mais trabalho do que confiar no token de retomada. Também é a diferença entre um sistema de ações rastreável e um sistema que esconde a ambiguidade até que o usuário encontre alterações duplicadas.

Teste pelo menos estes casos antes de considerar segura a retomada:

- Encerre o agente depois da aprovação e inicie um substituto que apresente a mesma referência de conversa.
- Reinicie o gateway enquanto um agente aprovado continua ativo e tenta outra chamada com credencial.
- Bloqueie e desbloqueie o cofre enquanto um agente aprovado espera para repetir uma ação.
- Inicie dois processos de agente assinados e idênticos e confirme que a aprovação de um não cobre o outro.
- Interrompa a resposta da rede depois que o gateway iniciar uma solicitação externa e verifique se o caminho de repetição informa a incerteza da entrega.

Esses testes capturam um erro especialmente comum: os engenheiros testam apenas se o cliente legítimo consegue se recuperar. Não testam se um cliente diferente consegue pegar emprestado o caminho de recuperação.

## Os registros devem explicar por que a autoridade terminou

Um diário de auditoria deve registrar mudanças de autoridade como eventos de primeira classe, sem obrigar o investigador a deduzi-las a partir de lacunas entre chamadas de ferramentas.

Registre a aprovação da sessão com os fatos de identidade do processo usados, o identificador de inicialização do gateway, a época do cofre e o sujeito mostrado ao usuário. Registre o encerramento com um motivo específico: processo encerrado, incompatibilidade de identidade do processo, gateway reiniciado, cofre bloqueado, revogação manual ou aprovação expirada. Registre uma ação negada separadamente de uma ação ausente. São fatos diferentes.

Uma sequência de atividades útil pode ser assim:

```text
14:20:11 session_approved run=R31 signer="Example Developer ID" boot=B8 vault=17
14:23:04 gateway_restarted previous_boot=B8 current_boot=C2
14:23:06 action_denied run=R31 reason=gateway_restarted
14:23:09 session_approved run=R32 signer="Example Developer ID" boot=C2 vault=17
14:23:12 http_action_started run=R32 request=Q44
14:23:13 http_action_result run=R32 request=Q44 status=201
```

O objetivo não é expor valores secretos ou corpos completos de solicitações em cada entrada do diário. É preservar a cadeia causal: quem solicitou, qual autoridade se aplicou, qual estado mudou e se o gateway realmente executou a ação.

A evidência contra adulteração importa porque um histórico de aprovações só é útil se alguém puder detectar alterações posteriores. O Sallyport projeta seus diários de Sessões e Atividades a partir de um diário de auditoria criptografado, encadeado por hash e sem possibilidade de gravação, e `sp audit verify` pode verificar essa cadeia offline sobre o texto cifrado, sem uma chave do cofre. Assim, um revisor pode verificar a sequência sem abrir os segredos usados nas ações.

Não faça o diário de auditoria carregar o peso da prevenção. Um registro perfeito que informa que uma aprovação antiga foi reutilizada é evidência de uma decisão ruim, não uma correção. O gateway ativo precisa negar a ação antes da injeção da credencial quando a associação deixar de corresponder.

## A reaprovação deve ser específica o bastante para justificar a interrupção

A reaprovação depois de uma mudança relevante de estado é justificável, mas um aviso vago ensina os usuários a clicar sem ler. O cartão de aprovação deve informar o que mudou e quem está solicitando agora.

Evite uma mensagem genérica como «A sessão expirou. Aprovar novamente?». Esse texto leva o usuário a tratar o evento como um simples cronômetro. Mostre a condição que rompeu a continuidade: «O gateway foi reiniciado. Aprovar este processo recém-conectado para usar a API de hospedagem Git nesta execução?». Se a identidade do processo mudou, mostre a nova autoridade de assinatura ou informe que o programa não está assinado. Se o cofre foi bloqueado, diga que desbloqueá-lo não restaurou a concessão anterior do agente.

Também é aqui que você decide se a aprovação de sessão é ampla demais para um canal. Se um agente retomado quiser fazer uma alteração SSH em produção, a aprovação por chamada pode ser a escolha sensata mesmo depois de uma nova decisão de sessão. O fato de a sessão ter passado por todas as verificações não torna todos os comandos igualmente seguros.

Não tente resolver a fadiga de aprovação tornando as aprovações transferíveis. Resolva o problema reduzindo mudanças desnecessárias, mostrando uma identidade de processo estável quando ela existir e mantendo o escopo de cada decisão compreensível. O usuário pode aprovar uma solicitação concreta. Ele não pode aprovar com segurança a promessa de que qualquer processo futuro com uma transcrição antiga poderá agir.

A regra de implementação cabe em uma nota adesiva: preserve o contexto durante uma retomada, mas reconstrua a autoridade a partir de evidências atuais. Quando o processo, o cofre ou o gateway muda, a aprovação antiga pertence à execução passada.
