explain

Agent vs SSH (when each path is used)

When grain uses the guest agent, when it falls back to SSH, and why both exist.

Roles

PathStrengthsWeaknesses
Guest agentStructured API, streaming exec, fs/cp, health probes, PTY shellMust be present (baked or deployed); Linux guest binary
SSHUniversal, interactive muscle memory, bootstrap agent deployHost-key noise, scp quirks, harder to automate cleanly

Default CLI behavior

CommandPrefersOverride
grain xAgent streaming exec--ssh / --agent
grain shAgent WebSocket PTY--ssh / --agent
grain cpAgent Put/Get--ssh / --agent
grain fsAgent only
Create deploySSH used to install agent when missingGolden images skip deploy when healthy

Create wait modes

ModeReady when
autoAgent if image HasAgent, else SSH
sshSSH accepts; agent soft-deployed
agentAgent health required (hard fail)
userdataAgent + userdata marker

Transport

Host → agent:

  1. TCP hostfwd to guest :7475 (always available with QEMU user net)
  2. virtio-vsock when agent_transport allows and /dev/vhost-vsock exists (typically Linux)

Practical guidance

  • Day-to-day automation: agent (x, cp, fs, API exec)
  • Debugging a broken agent: grain sh --ssh and grain logs
  • Images: prefer grain-ubuntu so agent is already present
  • Security-sensitive tokens: prefer egress proxy over writing secrets into the guest when possible