Skip to content

Credential portability: take/push provider creds between client and hub over SSH #782

Description

@aarontrowbridge

Important

Problem

Provider credentials live only where opencode first resolved them — normally the hub. A machine that has only ever been a fleet client has none locally, so Go Standalone lands on a providerless chat. This is exactly what happened on 2026-09-03 (baseten key existed hub-side only; fixed by a manual copy).

Approach

A pair of commands — "take my credentials to go" and "push my credentials to the hub" — that copy opencode's provider-auth files between client and hub over the existing SSH tunnel path, gated by a confirmation that names exactly which providers will move. Keys transit only over SSH; they never pass through chat, the HTTP API, or any agent-visible channel.

Approaches Considered

  • SSH-tunnel file copy, human-gated (chosen) — uses infrastructure the fleet already trusts; explicit, inspectable, bidirectional.
  • Env-based key injection into the standalone spawn from a hub-fetched secret — avoids files at rest on the client but needs a live hub to leave, and Go Standalone must work when the hub is down.
  • Agent-mediated copy (paste keys in chat) — rejected outright: keys must never be agent-visible.

Scope

In: pull (hub → client) and push (client → hub) directions; a provider manifest shown for confirmation; merge semantics for the destination auth files (add/refresh providers, never silently drop existing ones); a clear "already present, skipped" report.
Out: rotating or generating keys; storing keys anywhere new beyond opencode's own config locations; the onboarding credential scanner's behavior; syncing arbitrary env/config beyond provider auth.

Assumptions / Open Qs

  • Assumed the SSH path used by the managed tunnels is reusable for a file transfer by the extension (same host, same key) — verify during implementation; if the tunnel is forward-only, fall back to the same SSH config's native transport.
  • Open: whether the hub copy should happen while the hub server is running (file-consistency question) — dev to pick a safe moment (e.g. copy is read-only hub-side, so running is fine).

Acceptance Criteria

  1. On a fleet client with tunnel up, "take my credentials to go" copies the hub's provider-auth entries into the client's opencode config locations and reports which providers moved.
  2. After the pull, a freshly spawned standalone server resolves those providers (chat works without a hub).
  3. "Push my credentials to the hub" does the reverse for a machine that onboarded standalone.
  4. Every transfer requires an explicit confirmation naming the providers before anything is written.
  5. Destination-side providers not part of the transfer are preserved; the command never deletes or overwrites unrelated entries.
  6. No provider key material is ever logged, cached in chat, or exposed through any agent-visible surface.

Key Decisions

  • Files move opencode-config-location → opencode-config-location, unchanged in format; the command is a courier, not a transformer.
  • Merge = add or refresh the transferred providers' entries only.
  • The confirmation card lists provider ids/sources, never key contents.

Constraints & Invariants

  • Keys transit only over SSH (or the tunnel). Never through HTTP request/response bodies, chat messages, or logs.
  • The command fails loudly and changes nothing when the transport or either side's config is unreadable.
Prior Art / Patterns - The extension deliberately treats opencode as the secret owner and only queries a live server's provider signal — this command extends that posture with an explicit, user-gated courier step. - The onboarding credential scanner's provider-source vocabulary (env, auth files, account files) is the pattern for the manifest. - Vault: `sessions/session-20260903-fleet-improvements-brainstorm.md` §6 row D carries the code anchors.

Source

  • Durable record: vault-aaron/sessions/session-20260903-fleet-improvements-brainstorm.md §3.4 + §6
  • Evidence: vault-aaron/sessions/session-20260903-hub-wedge-forensics.md §1 (row 10, the manual copy)

Notes

  • Part of the 2026-09-03 handoff bundle (D of E). Small UX command; sequence after B.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Labels

No labels
No labels

Type

No type

Projects

No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions