SIGN IN SIGN UP

agentHost: give every remote connection one owner and one reconnect path

Remote agent host connections were established in six different places, and reconnection was
implemented five times over. Only WebSocket connections could use the protocol client's soft
reconnect, so SSH, WSL, tunnel and Dev Container connections were torn down and rebuilt on every
transport drop: a new clientId, no action replay, and pending tool calls cancelled by the host.
This moves connection ownership into RemoteAgentHostService and gives every kind the same
reconnect behaviour.

- Adds ReconnectingTransport, which re-establishes an inner transport through an owner-supplied
  callback. Relay-backed kinds now supply a transport factory, so they get the protocol client's
  backoff, clientId preservation, server-side action replay and outbox draining.
- Adds a reconnect policy per connection kind, replacing five hand-written backoff loops. The
  protocol client now honours a maximum attempt count instead of retrying forever, and reports
  terminal failure upward rather than running its own recovery.
- Adds a `reconnecting` connection status, distinct from `connecting`. Recovery loops no longer
  replace a protocol client that is already restoring itself, and a send during a drop waits for
  the connection instead of failing.
- Adds IRemoteAgentHostConnectionFactory. A factory builds an unconnected client and exposes the
  entries of its kind; the service performs the handshake, classifies the result, sets the status
  and owns retries. WebSocket and SSH use this path.
- Moves entry persistence to the owning producer. The service reads entries and never writes them,
  so an address that moves between stores cannot be resurrected.
- Moves malformed-frame protection into RelayTransport, where it now closes the transport instead
  of the connection, so a corrupted stream recovers through soft reconnect. SSH and WSL did not
  have this protection before.
- Opens the SSH configuration file, instead of a setting that cannot contain the host, for an SSH
  host defined by an ~/.ssh/config alias.

WSL, tunnel, cloud sandbox and Dev Container connections still register through
addManagedConnection. Later changes move them to connection factories, after which
addManagedConnection and the dialableByService flag can both be removed.

(Commit message generated by Copilot)

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
C
Connor Peet committed
0e7afd7c636ec2e0f426fa48a1ff0d37c8b2f3a5
Parent: d5ceefb