Files
PaperClipAI/packages/adapter-utils
Priya RamanandPaperclip 8e26e17408 feat(sandbox): stream duplex run logs and bind the duplex telemetry recorder
Stream sandbox run logs on the duplex transport with the same gate and the
same log line as the file transport. The duplex path starts no file bridge
worker, so the host creates the log directory before the tail starts. The
step is best effort and never tears down a working duplex transport.

Bind the fixed duplex telemetry surface to real host sinks. The host builds
one recorder per run: the spans go to the OTel tracer, the guarded counters
go to the tool-runtime metric store, and the transport event goes to the
run-event path. Each sink runs guarded and fire-and-forget, so a telemetry
failure never breaks the request path. The server attaches the recorder to
the sandbox target next to the runner; a run with no recorder keeps the safe
no-op default. Update the telemetry README to name the counter store file.

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-08-20 17:20:28 +00:00
..

@paperclipai/adapter-utils

Shared utilities for Paperclip adapters: process spawning, environment injection, sandbox/SSH transport, workspace sync, and the round-trip helpers that move code between the local execution-workspace cwd and wherever the agent actually runs.

For the adapter-author guide see docs/adapters/creating-an-adapter.md and the in-repo notes at packages/adapters/AUTHORING.md.

No-remote-git contract

The local execution-workspace cwd is the only persistence boundary across runs. No adapter may depend on a git remote for cross-run state.

Adapters that run the agent on a different host should use the SSH round-trip helpers in src/ssh.ts:

  • prepareWorkspaceForSshExecution({ spec, localDir, remoteDir }) — bundles the local cwd (tracked files, dirty edits, untracked additions, and the git history needed to reconstruct it) to remoteDir before the run starts. Runs with no git remote configured.
  • restoreWorkspaceFromSshExecution({ spec, localDir, remoteDir, ... }) — syncs the remote cwd back into localDir after the run, including any new commits the agent created. Also runs with no git remote configured.

prepareRemoteManagedRuntime in src/remote-managed-runtime.ts wraps both calls for adapters that want a per-run remote workspace and an automatic restoreWorkspace() finally hook.

The invariant is pinned by the no-remote-git contract case in src/ssh-fixture.test.ts, which asserts that a remote-only commit propagates to the local worktree through the prepare → restore round-trip with no git remote configured at any point. Do not regress that test.