diff --git a/data/sbx_cli/sbx.yaml b/data/sbx_cli/sbx.yaml index aaeb00d5d5bf..bffd7ef2ef87 100644 --- a/data/sbx_cli/sbx.yaml +++ b/data/sbx_cli/sbx.yaml @@ -25,6 +25,7 @@ see_also: - sbx login - Sign in to Docker - sbx logout - Stop all running sandboxes and sign out of Docker - sbx ls - List sandboxes + - sbx mcp - Manage MCP servers - sbx policy - Manage sandbox policies - sbx ports - Manage sandbox port publishing - sbx reset - Reset all sandboxes and clean up state @@ -32,6 +33,7 @@ see_also: - sbx run - Run an agent in a sandbox - sbx secret - Manage stored secrets - sbx setup - (Experimental) Detect host configuration and prepare Docker Sandboxes + - sbx skills - (Experimental) Manage skills shared across sandboxes - sbx stop - Stop one or more sandboxes without removing them - sbx template - Manage sandbox templates - sbx tui - Open the interactive TUI dashboard diff --git a/data/sbx_cli/sbx_create.yaml b/data/sbx_cli/sbx_create.yaml index b4aeeeb1cfc3..981108256c9e 100644 --- a/data/sbx_cli/sbx_create.yaml +++ b/data/sbx_cli/sbx_create.yaml @@ -14,6 +14,10 @@ options: default_value: "0" usage: | Number of CPUs to allocate to the sandbox (0 = auto: all host CPUs) + - name: deny-network + default_value: '[]' + usage: | + Add a per-sandbox network deny rule at creation time. Can be specified multiple times. The rule applies only to the new sandbox and can be listed or removed later with `sbx policy ls ` / `sbx policy rm network --sandbox --resource `. Safe under centralized governance because a local deny can only narrow, never widen, egress. - name: help shorthand: h default_value: "false" @@ -30,6 +34,11 @@ options: - name: name usage: | Name for the sandbox (default: -, letters, numbers, hyphens, periods, plus signs and minus signs only) + - name: publish + shorthand: p + default_value: '[]' + usage: | + Publish a sandbox port to the host (can be repeated): [[HOST_IP:]HOST_PORT:]SANDBOX_PORT[/PROTOCOL] - name: quiet shorthand: q default_value: "false" diff --git a/data/sbx_cli/sbx_create_claude.yaml b/data/sbx_cli/sbx_create_claude.yaml index 2ffde54ce9e0..33123b7a14dd 100644 --- a/data/sbx_cli/sbx_create_claude.yaml +++ b/data/sbx_cli/sbx_create_claude.yaml @@ -27,6 +27,10 @@ inherited_options: shorthand: D default_value: "false" usage: Enable debug logging + - name: deny-network + default_value: '[]' + usage: | + Add a per-sandbox network deny rule at creation time. Can be specified multiple times. The rule applies only to the new sandbox and can be listed or removed later with `sbx policy ls ` / `sbx policy rm network --sandbox --resource `. Safe under centralized governance because a local deny can only narrow, never widen, egress. - name: kit default_value: '[]' experimental: true @@ -39,6 +43,11 @@ inherited_options: - name: name usage: | Name for the sandbox (default: -, letters, numbers, hyphens, periods, plus signs and minus signs only) + - name: publish + shorthand: p + default_value: '[]' + usage: | + Publish a sandbox port to the host (can be repeated): [[HOST_IP:]HOST_PORT:]SANDBOX_PORT[/PROTOCOL] - name: quiet shorthand: q default_value: "false" diff --git a/data/sbx_cli/sbx_create_codex.yaml b/data/sbx_cli/sbx_create_codex.yaml index a14e03c2b75c..d6fa02e323c4 100644 --- a/data/sbx_cli/sbx_create_codex.yaml +++ b/data/sbx_cli/sbx_create_codex.yaml @@ -27,6 +27,10 @@ inherited_options: shorthand: D default_value: "false" usage: Enable debug logging + - name: deny-network + default_value: '[]' + usage: | + Add a per-sandbox network deny rule at creation time. Can be specified multiple times. The rule applies only to the new sandbox and can be listed or removed later with `sbx policy ls ` / `sbx policy rm network --sandbox --resource `. Safe under centralized governance because a local deny can only narrow, never widen, egress. - name: kit default_value: '[]' experimental: true @@ -39,6 +43,11 @@ inherited_options: - name: name usage: | Name for the sandbox (default: -, letters, numbers, hyphens, periods, plus signs and minus signs only) + - name: publish + shorthand: p + default_value: '[]' + usage: | + Publish a sandbox port to the host (can be repeated): [[HOST_IP:]HOST_PORT:]SANDBOX_PORT[/PROTOCOL] - name: quiet shorthand: q default_value: "false" diff --git a/data/sbx_cli/sbx_create_copilot.yaml b/data/sbx_cli/sbx_create_copilot.yaml index 4224e34e4ea9..21fb6f94ca08 100644 --- a/data/sbx_cli/sbx_create_copilot.yaml +++ b/data/sbx_cli/sbx_create_copilot.yaml @@ -27,6 +27,10 @@ inherited_options: shorthand: D default_value: "false" usage: Enable debug logging + - name: deny-network + default_value: '[]' + usage: | + Add a per-sandbox network deny rule at creation time. Can be specified multiple times. The rule applies only to the new sandbox and can be listed or removed later with `sbx policy ls ` / `sbx policy rm network --sandbox --resource `. Safe under centralized governance because a local deny can only narrow, never widen, egress. - name: kit default_value: '[]' experimental: true @@ -39,6 +43,11 @@ inherited_options: - name: name usage: | Name for the sandbox (default: -, letters, numbers, hyphens, periods, plus signs and minus signs only) + - name: publish + shorthand: p + default_value: '[]' + usage: | + Publish a sandbox port to the host (can be repeated): [[HOST_IP:]HOST_PORT:]SANDBOX_PORT[/PROTOCOL] - name: quiet shorthand: q default_value: "false" diff --git a/data/sbx_cli/sbx_create_cursor.yaml b/data/sbx_cli/sbx_create_cursor.yaml index ba8a42a2547a..e5c1cc91d403 100644 --- a/data/sbx_cli/sbx_create_cursor.yaml +++ b/data/sbx_cli/sbx_create_cursor.yaml @@ -27,6 +27,10 @@ inherited_options: shorthand: D default_value: "false" usage: Enable debug logging + - name: deny-network + default_value: '[]' + usage: | + Add a per-sandbox network deny rule at creation time. Can be specified multiple times. The rule applies only to the new sandbox and can be listed or removed later with `sbx policy ls ` / `sbx policy rm network --sandbox --resource `. Safe under centralized governance because a local deny can only narrow, never widen, egress. - name: kit default_value: '[]' experimental: true @@ -39,6 +43,11 @@ inherited_options: - name: name usage: | Name for the sandbox (default: -, letters, numbers, hyphens, periods, plus signs and minus signs only) + - name: publish + shorthand: p + default_value: '[]' + usage: | + Publish a sandbox port to the host (can be repeated): [[HOST_IP:]HOST_PORT:]SANDBOX_PORT[/PROTOCOL] - name: quiet shorthand: q default_value: "false" diff --git a/data/sbx_cli/sbx_create_docker-agent.yaml b/data/sbx_cli/sbx_create_docker-agent.yaml index b04a541e2dc2..1421def0a064 100644 --- a/data/sbx_cli/sbx_create_docker-agent.yaml +++ b/data/sbx_cli/sbx_create_docker-agent.yaml @@ -27,6 +27,10 @@ inherited_options: shorthand: D default_value: "false" usage: Enable debug logging + - name: deny-network + default_value: '[]' + usage: | + Add a per-sandbox network deny rule at creation time. Can be specified multiple times. The rule applies only to the new sandbox and can be listed or removed later with `sbx policy ls ` / `sbx policy rm network --sandbox --resource `. Safe under centralized governance because a local deny can only narrow, never widen, egress. - name: kit default_value: '[]' experimental: true @@ -39,6 +43,11 @@ inherited_options: - name: name usage: | Name for the sandbox (default: -, letters, numbers, hyphens, periods, plus signs and minus signs only) + - name: publish + shorthand: p + default_value: '[]' + usage: | + Publish a sandbox port to the host (can be repeated): [[HOST_IP:]HOST_PORT:]SANDBOX_PORT[/PROTOCOL] - name: quiet shorthand: q default_value: "false" diff --git a/data/sbx_cli/sbx_create_droid.yaml b/data/sbx_cli/sbx_create_droid.yaml index 237a68b2864a..a6da121023b2 100644 --- a/data/sbx_cli/sbx_create_droid.yaml +++ b/data/sbx_cli/sbx_create_droid.yaml @@ -27,6 +27,10 @@ inherited_options: shorthand: D default_value: "false" usage: Enable debug logging + - name: deny-network + default_value: '[]' + usage: | + Add a per-sandbox network deny rule at creation time. Can be specified multiple times. The rule applies only to the new sandbox and can be listed or removed later with `sbx policy ls ` / `sbx policy rm network --sandbox --resource `. Safe under centralized governance because a local deny can only narrow, never widen, egress. - name: kit default_value: '[]' experimental: true @@ -39,6 +43,11 @@ inherited_options: - name: name usage: | Name for the sandbox (default: -, letters, numbers, hyphens, periods, plus signs and minus signs only) + - name: publish + shorthand: p + default_value: '[]' + usage: | + Publish a sandbox port to the host (can be repeated): [[HOST_IP:]HOST_PORT:]SANDBOX_PORT[/PROTOCOL] - name: quiet shorthand: q default_value: "false" diff --git a/data/sbx_cli/sbx_create_gemini.yaml b/data/sbx_cli/sbx_create_gemini.yaml index 5a94084deb6d..2fc2765b0a61 100644 --- a/data/sbx_cli/sbx_create_gemini.yaml +++ b/data/sbx_cli/sbx_create_gemini.yaml @@ -27,6 +27,10 @@ inherited_options: shorthand: D default_value: "false" usage: Enable debug logging + - name: deny-network + default_value: '[]' + usage: | + Add a per-sandbox network deny rule at creation time. Can be specified multiple times. The rule applies only to the new sandbox and can be listed or removed later with `sbx policy ls ` / `sbx policy rm network --sandbox --resource `. Safe under centralized governance because a local deny can only narrow, never widen, egress. - name: kit default_value: '[]' experimental: true @@ -39,6 +43,11 @@ inherited_options: - name: name usage: | Name for the sandbox (default: -, letters, numbers, hyphens, periods, plus signs and minus signs only) + - name: publish + shorthand: p + default_value: '[]' + usage: | + Publish a sandbox port to the host (can be repeated): [[HOST_IP:]HOST_PORT:]SANDBOX_PORT[/PROTOCOL] - name: quiet shorthand: q default_value: "false" diff --git a/data/sbx_cli/sbx_create_kiro.yaml b/data/sbx_cli/sbx_create_kiro.yaml index 9734a1b2fd3a..3f7180c1932b 100644 --- a/data/sbx_cli/sbx_create_kiro.yaml +++ b/data/sbx_cli/sbx_create_kiro.yaml @@ -27,6 +27,10 @@ inherited_options: shorthand: D default_value: "false" usage: Enable debug logging + - name: deny-network + default_value: '[]' + usage: | + Add a per-sandbox network deny rule at creation time. Can be specified multiple times. The rule applies only to the new sandbox and can be listed or removed later with `sbx policy ls ` / `sbx policy rm network --sandbox --resource `. Safe under centralized governance because a local deny can only narrow, never widen, egress. - name: kit default_value: '[]' experimental: true @@ -39,6 +43,11 @@ inherited_options: - name: name usage: | Name for the sandbox (default: -, letters, numbers, hyphens, periods, plus signs and minus signs only) + - name: publish + shorthand: p + default_value: '[]' + usage: | + Publish a sandbox port to the host (can be repeated): [[HOST_IP:]HOST_PORT:]SANDBOX_PORT[/PROTOCOL] - name: quiet shorthand: q default_value: "false" diff --git a/data/sbx_cli/sbx_create_opencode.yaml b/data/sbx_cli/sbx_create_opencode.yaml index 765031ce6620..0a383c92cbd5 100644 --- a/data/sbx_cli/sbx_create_opencode.yaml +++ b/data/sbx_cli/sbx_create_opencode.yaml @@ -27,6 +27,10 @@ inherited_options: shorthand: D default_value: "false" usage: Enable debug logging + - name: deny-network + default_value: '[]' + usage: | + Add a per-sandbox network deny rule at creation time. Can be specified multiple times. The rule applies only to the new sandbox and can be listed or removed later with `sbx policy ls ` / `sbx policy rm network --sandbox --resource `. Safe under centralized governance because a local deny can only narrow, never widen, egress. - name: kit default_value: '[]' experimental: true @@ -39,6 +43,11 @@ inherited_options: - name: name usage: | Name for the sandbox (default: -, letters, numbers, hyphens, periods, plus signs and minus signs only) + - name: publish + shorthand: p + default_value: '[]' + usage: | + Publish a sandbox port to the host (can be repeated): [[HOST_IP:]HOST_PORT:]SANDBOX_PORT[/PROTOCOL] - name: quiet shorthand: q default_value: "false" diff --git a/data/sbx_cli/sbx_create_shell.yaml b/data/sbx_cli/sbx_create_shell.yaml index 957b35099960..29dff3922ddc 100644 --- a/data/sbx_cli/sbx_create_shell.yaml +++ b/data/sbx_cli/sbx_create_shell.yaml @@ -27,6 +27,10 @@ inherited_options: shorthand: D default_value: "false" usage: Enable debug logging + - name: deny-network + default_value: '[]' + usage: | + Add a per-sandbox network deny rule at creation time. Can be specified multiple times. The rule applies only to the new sandbox and can be listed or removed later with `sbx policy ls ` / `sbx policy rm network --sandbox --resource `. Safe under centralized governance because a local deny can only narrow, never widen, egress. - name: kit default_value: '[]' experimental: true @@ -39,6 +43,11 @@ inherited_options: - name: name usage: | Name for the sandbox (default: -, letters, numbers, hyphens, periods, plus signs and minus signs only) + - name: publish + shorthand: p + default_value: '[]' + usage: | + Publish a sandbox port to the host (can be repeated): [[HOST_IP:]HOST_PORT:]SANDBOX_PORT[/PROTOCOL] - name: quiet shorthand: q default_value: "false" diff --git a/data/sbx_cli/sbx_daemon.yaml b/data/sbx_cli/sbx_daemon.yaml index aa860aa43592..c8959a703f8c 100644 --- a/data/sbx_cli/sbx_daemon.yaml +++ b/data/sbx_cli/sbx_daemon.yaml @@ -13,6 +13,7 @@ inherited_options: see_also: - sbx - Manage AI coding agent sandboxes. - sbx daemon log-level - Inspect or change sandboxd's per-category log levels + - sbx daemon restart - Restart the sandboxd daemon - sbx daemon start - Start the sandboxd daemon - sbx daemon status - Check sandboxd daemon status - sbx daemon stop - Stop the sandboxd daemon diff --git a/data/sbx_cli/sbx_daemon_restart.yaml b/data/sbx_cli/sbx_daemon_restart.yaml new file mode 100644 index 000000000000..d7bea6d0f156 --- /dev/null +++ b/data/sbx_cli/sbx_daemon_restart.yaml @@ -0,0 +1,15 @@ +name: sbx daemon restart +synopsis: Restart the sandboxd daemon +usage: sbx daemon restart [flags] +options: + - name: help + shorthand: h + default_value: "false" + usage: help for restart +inherited_options: + - name: debug + shorthand: D + default_value: "false" + usage: Enable debug logging +see_also: + - sbx daemon - Manage sandboxd daemon diff --git a/data/sbx_cli/sbx_mcp.yaml b/data/sbx_cli/sbx_mcp.yaml new file mode 100644 index 000000000000..dbeaf7878fb2 --- /dev/null +++ b/data/sbx_cli/sbx_mcp.yaml @@ -0,0 +1,22 @@ +name: sbx mcp +synopsis: Manage MCP servers +description: | + Register and manage MCP servers for use with sandbox sessions. +options: + - name: help + shorthand: h + default_value: "false" + usage: help for mcp +inherited_options: + - name: debug + shorthand: D + default_value: "false" + usage: Enable debug logging +see_also: + - sbx - Manage AI coding agent sandboxes. + - sbx mcp add - Register an MCP server + - sbx mcp auth - Authorize MCP servers + - sbx mcp inspect - Show MCP server details + - sbx mcp load - Load an already-registered MCP server into a running sandbox + - sbx mcp ls - List registered MCP servers + - sbx mcp rm - Remove a registered MCP server diff --git a/data/sbx_cli/sbx_mcp_add.yaml b/data/sbx_cli/sbx_mcp_add.yaml new file mode 100644 index 000000000000..d6778577d711 --- /dev/null +++ b/data/sbx_cli/sbx_mcp_add.yaml @@ -0,0 +1,199 @@ +name: sbx mcp add +synopsis: Register an MCP server +description: |- + Register an MCP server by name. The server is validated and its + specification is stored for use with sbx create/run --static-mcp. + + This command only registers the server. To attach an already-registered + server to a running sandbox, use 'sbx mcp load'. + + The --url flag accepts four input formats; the type is auto-detected: + + - Remote MCP endpoint URL (https://host/mcp — talks MCP at the URL; + OAuth metadata is discovered via RFC 9728/8414). + - MCP community-registry URL (https://registry.modelcontextprotocol.io/v0/servers/...) + — fetches the registry envelope and resolves the OCI image. + - Server-manifest URL (any URL returning a server.json or server.yaml + body shaped like the MCP community-registry schema — GitHub raw URLs, + internal HTTP servers, ad-hoc CDN links all work). + - Docker Hardened Images (DHI) image ref (dhi.io/: or + dhi.io/@sha256:... — the server.json manifest is extracted + from the image's in-toto attestation via the OCI Referrers API). + + Other image refs (inputs without "://" that are not dhi.io, e.g. + docker.io/foo:tag) are no longer accepted. Use a server manifest instead. + + SSRF guard and --skip-ssrf-check: + A --url whose host resolves to a private/RFC1918, loopback, link-local, + or cloud-metadata address is rejected by the SSRF guard (this protects + against manifest URLs that reach internal services, cloud metadata, or + DNS-rebinding targets). Some legitimate servers live on private networks + (split-horizon DNS, internal load balancers, VPN-only endpoints, + PrivateLink), so their public hostname resolves to a private address. + Pass --skip-ssrf-check to opt out of the guard for a single add when you + trust the host. This also disables DNS-rebinding/redirect re-checks, so + use it only for URLs you control. + + OAuth for remote endpoints (--oauth-authorization-server / --client-id): + Two related options configure OAuth for a remote --url server (both are + only valid with --url): + + --oauth-authorization-server hand-supplies the authorization-server + metadata for a server that publishes no well-known RFC 9728/8414 metadata + (e.g. Gmail). It is a local file path or an http(s) URL to a JSON document + conforming to the RFC 8414 oauth-authorization-server shape + (authorization_endpoint and token_endpoint are required). In this CLI it + must be accompanied by --client-id. + + --client-id supplies a PRE-REGISTERED OAuth client. It may be given WITHOUT + --oauth-authorization-server: the server's authorization metadata is then + discovered normally and the supplied client is attached to it. This is the + right mode for a server whose discoverable metadata exposes no + registration_endpoint (so Dynamic Client Registration is impossible) but + which accepts a client id the operator registered ahead of time. + + Client secrets (confidential clients): + There is no --client-secret flag. The secret for a confidential client + lives in the encrypted secret store in the global scope under the + service name "mcp:.client_secret", and is read from there + whenever the server is used: + + sbx secret set mcp:.client_secret + + Run it with no -t so the value is read from stdin instead of landing in + your shell history. The secret is never written to the MCP registration + on disk. Remove it later with 'sbx secret rm mcp:.client_secret'. + + The stored secret is bound to the OAuth identity (client id, issuer and + token endpoint) that first used it. Re-registering the same server name + against a different client or authorization server therefore does NOT + reuse it — store the secret again for the new client. To let a new + identity claim the existing secret, drop the recorded binding with + 'sbx secret rm mcp:.client_secret.identity'. + + Two rules apply on the discovered path (they do not affect a server that + advertises a registration_endpoint, the hand-supplied + --oauth-authorization-server path, or --command servers): + + - If the discovered authorization metadata has NO registration_endpoint, + Dynamic Client Registration is impossible, so --client-id is REQUIRED; + the add fails without it. This is the Slack shape (discoverable metadata, + no DCR, a pre-registered client). + - A stored client secret is REQUIRED when the server's advertised + token_endpoint_auth_methods_supported (RFC 8414) does NOT include "none" + — i.e. it accepts only confidential clients (client_secret_basic / + client_secret_post). Registration still succeeds without one, but the + add-time authorization is skipped; store the secret and run + 'sbx mcp auth ' to finish. When the list includes "none" a + public/PKCE client is allowed and --client-id alone is enough. If the + server advertises no token_endpoint_auth_methods_supported at all (the + field is optional in RFC 8414), the requirement cannot be determined and + the add proceeds as usual. + + Default OAuth scopes (--scope): + --scope records the DEFAULT set of scopes to request at consent time for a + remote --url OAuth server (repeatable). These are requested by 'sbx mcp auth' + when it is run with no --scope of its own. Scopes are validated only when the + authorization server advertises a supported set (RFC 8414 scopes_supported): + then every scope must be a member or the add fails naming the offending + scope(s). If the server advertises no supported set (the field is optional in + RFC 8414), the requested scopes are accepted as given. --scope applies both to + a hand-supplied override and to a plain --url server whose OAuth metadata is + discovered. + + Alternative input — local stdio command (--command + --args): + The command runs as a subprocess on the HOST, outside the sandbox. + + WARNING: Local servers are for ad-hoc development only. They have + no identity, no verifiable supply chain, and no sandboxing. The + process runs with your host user's full permissions — it can read + your filesystem, access your network, and call any API your user + can. Do not use --command with untrusted executables. +usage: sbx mcp add (--url | --command ) [flags] +options: + - name: args + default_value: '[]' + usage: Command-line arguments for the command + - name: client-id + usage: | + OAuth client id for a pre-registered client (with --url; may be used with or without --oauth-authorization-server). A confidential client's secret comes from 'sbx secret set mcp:.client_secret' + - name: command + usage: Executable to run for a local stdio server + - name: dir + usage: Working directory (cwd) for a --command host server + - name: help + shorthand: h + default_value: "false" + usage: help for add + - name: local + default_value: "false" + usage: Run registry OCI server locally via docker run + - name: oauth-authorization-server + usage: | + Path or http(s) URL to an RFC 8414 oauth-authorization-server metadata JSON document + - name: scope + default_value: '[]' + usage: | + Default OAuth scope to request at consent time (repeatable; must be advertised by the server's authorization metadata). Applies to --url remote OAuth servers. + - name: skip-ssrf-check + default_value: "false" + usage: | + Disable the SSRF guard for this add: allow a --url whose host resolves to a private/metadata address (operator asserts the host is trusted) + - name: skip_auth + default_value: "false" + usage: | + Register an OAuth server without starting the hosted OAuth flow + - name: url + usage: | + MCP server manifest URL, remote endpoint URL, or dhi.io image ref +inherited_options: + - name: debug + shorthand: D + default_value: "false" + usage: Enable debug logging +example: |4- + # Remote MCP endpoint (OAuth auto-detected) + sbx mcp add notion --url https://mcp.notion.com/mcp + sbx mcp add linear --url https://mcp.linear.app/mcp + + # MCP community-registry URL + sbx mcp add fetch --url https://registry.modelcontextprotocol.io/v0/servers/fetch-mcp/versions/latest + + # Plain server-manifest URL (server.json / server.yaml) + sbx mcp add opine --url https://example.com/mcp/opine/server.yaml + + # Docker Hardened Image (manifest is extracted from the image attestation) + sbx mcp add fetch --url dhi.io/fetch-mcp:latest + + # Registry URL, local mode (runs on host via docker run; stdio packages only) + sbx mcp add fetch --local --url https://registry.modelcontextprotocol.io/v0/servers/fetch-mcp/versions/latest + + # Private-network endpoint (host resolves to a private address) — opt out of the SSRF guard + sbx mcp add internal --url https://maas.prd.astra.example.com/mcp --skip-ssrf-check + + # Remote endpoint with a hand-supplied OAuth override (server publishes no + # well-known OAuth metadata): --oauth-authorization-server is a path or + # http(s) URL to an RFC 8414 metadata document, --client-id the OAuth client id + sbx mcp add acme --url https://mcp.acme.com/mcp --oauth-authorization-server ./acme-as.json --client-id my-client + + # Pre-registered client on a DISCOVERABLE server that has no registration + # endpoint — no --oauth-authorization-server needed (metadata is discovered) + sbx mcp add slack --url https://slack.example.com/mcp --client-id my-preregistered-client + + # Confidential client — store the secret first (prompted, never in argv or + # shell history), then register; the secret is read from the secret store + sbx secret set mcp:slack.client_secret + sbx mcp add slack --url https://slack.example.com/mcp --client-id my-preregistered-client + + # Record default OAuth scopes to request at consent time (must be advertised + # by the server's authorization metadata; repeat --scope for each one) + sbx mcp add acme --url https://mcp.acme.com/mcp --scope read --scope write + + # Local stdio command (runs on host — development only) + sbx mcp add github --command npx --args @modelcontextprotocol/server-github + sbx mcp add postgres --command docker --args "run,-i,--rm,mcp/postgres" + + # Local stdio command with a working directory (cwd) for the host process + sbx mcp add local-fs --command node --args server.js --dir /srv/data +see_also: + - sbx mcp - Manage MCP servers diff --git a/data/sbx_cli/sbx_mcp_auth.yaml b/data/sbx_cli/sbx_mcp_auth.yaml new file mode 100644 index 000000000000..957e588bca44 --- /dev/null +++ b/data/sbx_cli/sbx_mcp_auth.yaml @@ -0,0 +1,59 @@ +name: sbx mcp auth +synopsis: Authorize MCP servers +description: |- + Authorize registered remote MCP servers through the hosted MCP control plane. + + Commands use the Docker Hub account from 'sbx login' as the request principal. + User and tenant identity are derived by the control plane; they are not sent in + the request body. + + Running 'sbx mcp auth ' authorizes or reauthorizes one server. If the + stored credential is expired, sbx asks the control plane to refresh it first and + only falls back to interactive OAuth when refresh needs user consent. + + Use 'sbx mcp auth status' to inspect hosted credential status without starting + OAuth, and 'sbx mcp auth rm' to remove hosted credentials without removing + local MCP server registrations. + + Pass --scope (repeatable) to authorize a specific set of scopes for this run, + overriding the default recorded at 'sbx mcp add' time. Scopes are validated only + when the server advertises a supported set (RFC 8414 scopes_supported); each + scope must then be a member or the command fails. If the server advertises no + supported set, the requested scopes are accepted as given. With no --scope and + no recorded default, all advertised scopes are requested. +usage: sbx mcp auth [server-name] [flags] +options: + - name: all + default_value: "false" + usage: Apply to all registered OAuth servers + - name: format + default_value: text + usage: 'Output format: "text" or "json"' + - name: help + shorthand: h + default_value: "false" + usage: help for auth + - name: scope + default_value: '[]' + usage: | + OAuth scope to authorize for this run (repeatable; overrides the recorded default; must be advertised by the server's authorization metadata) + - name: verbose + default_value: "false" + usage: Print authorization polling progress +inherited_options: + - name: debug + shorthand: D + default_value: "false" + usage: Enable debug logging +example: |4- + sbx mcp auth status --all + sbx mcp auth status notion + sbx mcp auth rm --all + sbx mcp auth rm notion + sbx mcp auth --all + sbx mcp auth notion + sbx mcp auth notion --scope read --scope write +see_also: + - sbx mcp - Manage MCP servers + - sbx mcp auth rm - Remove MCP server OAuth credentials + - sbx mcp auth status - Show MCP server OAuth status diff --git a/data/sbx_cli/sbx_mcp_auth_rm.yaml b/data/sbx_cli/sbx_mcp_auth_rm.yaml new file mode 100644 index 000000000000..c2e351a8e3e7 --- /dev/null +++ b/data/sbx_cli/sbx_mcp_auth_rm.yaml @@ -0,0 +1,30 @@ +name: sbx mcp auth rm +synopsis: Remove MCP server OAuth credentials +description: |- + Remove hosted OAuth credentials for registered MCP servers. + + This command does not remove local MCP server registrations. Use 'sbx mcp rm' + to remove a registration. +usage: sbx mcp auth rm [server-name] [flags] +options: + - name: all + default_value: "false" + usage: Apply to all registered OAuth servers + - name: format + default_value: text + usage: 'Output format: "text" or "json"' + - name: help + shorthand: h + default_value: "false" + usage: help for rm +inherited_options: + - name: debug + shorthand: D + default_value: "false" + usage: Enable debug logging +example: |4- + sbx mcp auth rm --all + sbx mcp auth rm notion + sbx mcp auth rm notion --format=json +see_also: + - sbx mcp auth - Authorize MCP servers diff --git a/data/sbx_cli/sbx_mcp_auth_status.yaml b/data/sbx_cli/sbx_mcp_auth_status.yaml new file mode 100644 index 000000000000..f667b9454d84 --- /dev/null +++ b/data/sbx_cli/sbx_mcp_auth_status.yaml @@ -0,0 +1,29 @@ +name: sbx mcp auth status +synopsis: Show MCP server OAuth status +description: |- + Show hosted OAuth credential status for registered MCP servers. + + This command does not start OAuth or refresh expired credentials. +usage: sbx mcp auth status [server-name] [flags] +options: + - name: all + default_value: "false" + usage: Apply to all registered OAuth servers + - name: format + default_value: text + usage: 'Output format: "text" or "json"' + - name: help + shorthand: h + default_value: "false" + usage: help for status +inherited_options: + - name: debug + shorthand: D + default_value: "false" + usage: Enable debug logging +example: |4- + sbx mcp auth status --all + sbx mcp auth status notion + sbx mcp auth status --all --format=json +see_also: + - sbx mcp auth - Authorize MCP servers diff --git a/data/sbx_cli/sbx_mcp_inspect.yaml b/data/sbx_cli/sbx_mcp_inspect.yaml new file mode 100644 index 000000000000..b9490f01d089 --- /dev/null +++ b/data/sbx_cli/sbx_mcp_inspect.yaml @@ -0,0 +1,16 @@ +name: sbx mcp inspect +synopsis: Show MCP server details +usage: sbx mcp inspect [flags] +options: + - name: help + shorthand: h + default_value: "false" + usage: help for inspect +inherited_options: + - name: debug + shorthand: D + default_value: "false" + usage: Enable debug logging +example: ' sbx mcp inspect notion' +see_also: + - sbx mcp - Manage MCP servers diff --git a/data/sbx_cli/sbx_mcp_load.yaml b/data/sbx_cli/sbx_mcp_load.yaml new file mode 100644 index 000000000000..90dc46aa1d88 --- /dev/null +++ b/data/sbx_cli/sbx_mcp_load.yaml @@ -0,0 +1,32 @@ +name: sbx mcp load +synopsis: Load an already-registered MCP server into a running sandbox +description: |- + Attach a previously-registered MCP server to a running sandbox's gateway. + Connected agents see the new server's tools immediately via the standard MCP + tools/list_changed notification — no agent restart required. + + The server must already exist in the local MCP store (register first with + 'sbx mcp add'). Both remote/hosted and local-stdio servers are supported. +usage: sbx mcp load --sandbox [flags] +options: + - name: help + shorthand: h + default_value: "false" + usage: help for load + - name: sandbox + usage: Target sandbox name (required) +inherited_options: + - name: debug + shorthand: D + default_value: "false" + usage: Enable debug logging +example: |4- + # Register, then load into the running sandbox 'my-sbx'. + sbx mcp add notion --url https://mcp.notion.com/mcp + sbx mcp load notion --sandbox my-sbx + + # Local stdio server. + sbx mcp add github --command npx --args @modelcontextprotocol/server-github + sbx mcp load github --sandbox my-sbx +see_also: + - sbx mcp - Manage MCP servers diff --git a/data/sbx_cli/sbx_mcp_ls.yaml b/data/sbx_cli/sbx_mcp_ls.yaml new file mode 100644 index 000000000000..4ed1a21c10b9 --- /dev/null +++ b/data/sbx_cli/sbx_mcp_ls.yaml @@ -0,0 +1,16 @@ +name: sbx mcp ls +synopsis: List registered MCP servers +usage: sbx mcp ls [flags] +options: + - name: help + shorthand: h + default_value: "false" + usage: help for ls +inherited_options: + - name: debug + shorthand: D + default_value: "false" + usage: Enable debug logging +example: ' sbx mcp ls' +see_also: + - sbx mcp - Manage MCP servers diff --git a/data/sbx_cli/sbx_mcp_rm.yaml b/data/sbx_cli/sbx_mcp_rm.yaml new file mode 100644 index 000000000000..86c1845233e3 --- /dev/null +++ b/data/sbx_cli/sbx_mcp_rm.yaml @@ -0,0 +1,16 @@ +name: sbx mcp rm +synopsis: Remove a registered MCP server +usage: sbx mcp rm [flags] +options: + - name: help + shorthand: h + default_value: "false" + usage: help for rm +inherited_options: + - name: debug + shorthand: D + default_value: "false" + usage: Enable debug logging +example: ' sbx mcp rm notion' +see_also: + - sbx mcp - Manage MCP servers diff --git a/data/sbx_cli/sbx_policy_inspect.yaml b/data/sbx_cli/sbx_policy_inspect.yaml index 07c9cd16d3c4..16999f6dabe3 100644 --- a/data/sbx_cli/sbx_policy_inspect.yaml +++ b/data/sbx_cli/sbx_policy_inspect.yaml @@ -4,9 +4,13 @@ description: |- Inspect full detail for a selected policy or rule. The selector may be a policy ID, policy name, rule ID, or rule name. - Selecting a policy lists every resource with its decision, rule, and status; - selecting a rule shows just that rule. Use "sbx policy ls" to find policy - names and "sbx policy ls --wide" to find rule IDs and resource values. + Selecting a policy lists every resource with its decision, rule, and status, + plus a rule table showing each rule's RULE_ID, whether it is editable, and + either the exact removal command or the reason it is read-only. Selecting a + rule shows just that rule with the same editability detail. RULE_ID is the + identifier accepted by "sbx policy rm network --id" (local rules only). Use + "sbx policy ls" to find policy names and "sbx policy ls --wide" to find rule + IDs and resource values. usage: sbx policy inspect [flags] options: - name: help diff --git a/data/sbx_cli/sbx_policy_ls.yaml b/data/sbx_cli/sbx_policy_ls.yaml index ae94de08655b..6f5f4ed8639d 100644 --- a/data/sbx_cli/sbx_policy_ls.yaml +++ b/data/sbx_cli/sbx_policy_ls.yaml @@ -7,8 +7,10 @@ description: |- where it applies, and a summary of decisions by resource type. With SANDBOX, it summarizes active rules that apply to that sandbox. - Use --wide to show the detailed rule-level table with rule IDs, resources, status, - and rule metadata. Use --json for the filtered daemon response. + Use --wide to show the detailed rule-level table with separate POLICY, + POLICY_ID, RULE, and RULE_ID columns plus resources, status, and rule + metadata. RULE_ID is the identifier accepted by "sbx policy rm network --id" + (local rules only). Use --json for the filtered daemon response. When remote governance is active, inactive policy rules are hidden by default. Use --include-inactive to show inactive rules for troubleshooting. diff --git a/data/sbx_cli/sbx_policy_rm_network.yaml b/data/sbx_cli/sbx_policy_rm_network.yaml index 6fe4f009c553..bdf02c7493de 100644 --- a/data/sbx_cli/sbx_policy_rm_network.yaml +++ b/data/sbx_cli/sbx_policy_rm_network.yaml @@ -3,6 +3,11 @@ synopsis: Remove a network rule description: |- Remove a network rule by rule ID, resource, or both. + --id takes the RULE_ID value shown by "sbx policy ls --wide" and + "sbx policy inspect" — the rule's identifier, not its name. Passing a rule + name fails with an error that names the actual rule ID and, for removable + rules, the exact corrected command. + The rule is removed from the global policy by default. Use --sandbox to remove from policy "local" scoped to a single sandbox instead. diff --git a/data/sbx_cli/sbx_run.yaml b/data/sbx_cli/sbx_run.yaml index 68f2acf02f11..cf0083b8bf7e 100644 --- a/data/sbx_cli/sbx_run.yaml +++ b/data/sbx_cli/sbx_run.yaml @@ -25,6 +25,10 @@ options: default_value: "0" usage: | Number of CPUs to allocate to the sandbox (0 = auto: all host CPUs) + - name: deny-network + default_value: '[]' + usage: | + Add a per-sandbox network deny rule at creation time. Can be specified multiple times. The rule applies only to the new sandbox and can be listed or removed later with `sbx policy ls ` / `sbx policy rm network --sandbox --resource `. Safe under centralized governance because a local deny can only narrow, never widen, egress. - name: help shorthand: h default_value: "false" @@ -40,6 +44,11 @@ options: Memory limit in binary units (e.g., 1024m, 8g). Default: 50% of host memory, max 32 GiB - name: name usage: 'Name for the sandbox (default: -)' + - name: publish + shorthand: p + default_value: '[]' + usage: | + Publish a sandbox port to the host (can be repeated): [[HOST_IP:]HOST_PORT:]SANDBOX_PORT[/PROTOCOL]. Applied when the sandbox is created; ignored when re-attaching (use "sbx ports") - name: template shorthand: t usage: | diff --git a/data/sbx_cli/sbx_secret.yaml b/data/sbx_cli/sbx_secret.yaml index ca2861728b7c..f645edd996ac 100644 --- a/data/sbx_cli/sbx_secret.yaml +++ b/data/sbx_cli/sbx_secret.yaml @@ -10,9 +10,9 @@ description: |- REGISTRY SECRETS (e.g. "ghcr.io", "myregistry.azurecr.io") Used to pull private template images and kit artifacts before sandbox - creation. Host-only secrets (no -g) are not injected into sandboxes; - global secrets (-g) are injected by the proxy into the registry login of - every new sandbox (the credential never enters the sandbox filesystem). + creation. Unlike service secrets, registry credentials are host-only by + default. They are not injected into sandboxes unless --all-sandboxes or + --sandbox is set (the credential never enters the sandbox filesystem). Use "sbx secret set --registry --password-stdin" to store them. options: - name: help diff --git a/data/sbx_cli/sbx_secret_import.yaml b/data/sbx_cli/sbx_secret_import.yaml index d7223a5cea00..10b8c397c77f 100644 --- a/data/sbx_cli/sbx_secret_import.yaml +++ b/data/sbx_cli/sbx_secret_import.yaml @@ -18,7 +18,7 @@ description: |- Services that already have an OAuth token configured (e.g. anthropic after `sbx run claude … -- auth login`) are skipped: the OAuth token takes precedence at runtime so any api-key import would never be used. - Run `sbx secret rm -g ` first if you want to switch from + Run `sbx secret rm ` first if you want to switch from OAuth to api-key auth. Available services: anthropic, cursor, droid, github, google, groq, mistral, nebius, openai, openrouter, xai diff --git a/data/sbx_cli/sbx_secret_ls.yaml b/data/sbx_cli/sbx_secret_ls.yaml index 044b6c6d6a77..318720d5dbe3 100644 --- a/data/sbx_cli/sbx_secret_ls.yaml +++ b/data/sbx_cli/sbx_secret_ls.yaml @@ -1,6 +1,11 @@ name: sbx secret ls synopsis: List stored secrets -usage: sbx secret ls [SANDBOX] [flags] +description: |- + List stored secrets across global and sandbox scopes. + + With no scope flag, all stored secrets are shown. Use --global to show only + global secrets, or --sandbox to show only secrets scoped to one sandbox. +usage: sbx secret ls [flags] options: - name: global shorthand: g @@ -10,6 +15,8 @@ options: shorthand: h default_value: "false" usage: help for ls + - name: sandbox + usage: Only list secrets for one sandbox - name: service usage: Filter by secret service name inherited_options: @@ -25,7 +32,7 @@ example: |4- sbx secret ls -g # List secrets for a specific sandbox - sbx secret ls my-sandbox + sbx secret ls --sandbox my-sandbox # Filter by service sbx secret ls --service github diff --git a/data/sbx_cli/sbx_secret_rm.yaml b/data/sbx_cli/sbx_secret_rm.yaml index 5830519a0c81..cac2f449b9aa 100644 --- a/data/sbx_cli/sbx_secret_rm.yaml +++ b/data/sbx_cli/sbx_secret_rm.yaml @@ -1,21 +1,23 @@ name: sbx secret rm synopsis: Remove a secret -usage: sbx secret rm [-g | SANDBOX] [SERVICE] [flags] +usage: sbx secret rm [SERVICE] [flags] options: + - name: all-sandboxes + default_value: "false" + usage: | + Remove registry credentials injected into every sandbox (requires --registry) - name: force shorthand: f default_value: "false" usage: Delete without confirmation prompt - - name: global - shorthand: g - default_value: "false" - usage: Use global secret scope - name: help shorthand: h default_value: "false" usage: help for rm - name: registry usage: Registry hostname to remove pull credentials for + - name: sandbox + usage: 'Scope the removal to one sandbox (default: global)' inherited_options: - name: debug shorthand: D @@ -23,25 +25,25 @@ inherited_options: usage: Enable debug logging example: |4- # Remove a global secret - sbx secret rm -g github + sbx secret rm github # Remove a sandbox-scoped secret - sbx secret rm my-sandbox openai + sbx secret rm openai --sandbox my-sandbox # Remove without confirmation prompt - sbx secret rm -g github -f + sbx secret rm github -f # Remove OpenAI or Anthropic credential(s) from global scope (OAuth and/or API key) - sbx secret rm -g openai - sbx secret rm -g anthropic + sbx secret rm openai + sbx secret rm anthropic # Remove custom secret by specifying the placeholder value - sbx secret rm -g --placeholder docker-placeholder-value + sbx secret rm --placeholder docker-placeholder-value # Remove registry pull credentials (removes host-only and global entries) sbx secret rm --registry ghcr.io -f # Remove only the global (all-sandboxes) registry credential - sbx secret rm -g --registry ghcr.io -f + sbx secret rm --all-sandboxes --registry ghcr.io -f see_also: - sbx secret - Manage stored secrets diff --git a/data/sbx_cli/sbx_secret_set-custom.yaml b/data/sbx_cli/sbx_secret_set-custom.yaml index ba19028e38fd..30b7745909c3 100644 --- a/data/sbx_cli/sbx_secret_set-custom.yaml +++ b/data/sbx_cli/sbx_secret_set-custom.yaml @@ -14,15 +14,12 @@ description: |- and "**" matches any number of labels. For example "*.example.com" covers "cli.example.com" and "ide.example.com" with one entry. - Secrets can be scoped globally (shared across all sandboxes) or to a specific sandbox. -usage: sbx secret set-custom [-g | sandbox] [flags] + Custom secrets apply globally by default. Use --sandbox to scope one to a + specific sandbox. +usage: sbx secret set-custom [flags] options: - name: env usage: Set this env var in the sandbox to the placeholder value - - name: global - shorthand: g - default_value: "false" - usage: Use global secret scope - name: help shorthand: h default_value: "false" @@ -34,6 +31,8 @@ options: - name: placeholder usage: | Placeholder value; use {rand} for a random suffix (e.g. sk-{rand}) + - name: sandbox + usage: 'Scope the secret to one sandbox (default: all sandboxes)' - name: token shorthand: t usage: 'Secret value (less secure: visible in shell history)' @@ -48,18 +47,18 @@ example: |4- # Create a global custom secret. A unique placeholder is generated automatically. # The sandbox env var API_KEY is set to the placeholder value; outbound requests # to the host have the placeholder replaced with the real secret. - sbx secret set-custom -g --host api.example.com --env API_KEY --value secret123 + sbx secret set-custom --host api.example.com --env API_KEY --value secret123 # Use a wildcard host to cover multiple subdomains that share one key. - sbx secret set-custom -g --host '*.coderabbit.ai' --env CODERABBIT_API_KEY --value secret123 + sbx secret set-custom --host '*.coderabbit.ai' --env CODERABBIT_API_KEY --value secret123 # Use multiple --host flags to cover unrelated domains with the same key. - sbx secret set-custom -g --host api.example.com --host api.other.io --env API_KEY --value secret123 + sbx secret set-custom --host api.example.com --host api.other.io --env API_KEY --value secret123 # Scope to a specific sandbox instead of globally. - sbx secret set-custom my-sandbox --host api.example.com --env API_KEY --value secret123 + sbx secret set-custom --sandbox my-sandbox --host api.example.com --env API_KEY --value secret123 # Custom placeholder with {rand} suffix; the CLI prints the generated value. - sbx secret set-custom -g --host api.example.com --placeholder sk-{rand} --value secret123 + sbx secret set-custom --host api.example.com --placeholder sk-{rand} --value secret123 see_also: - sbx secret - Manage stored secrets diff --git a/data/sbx_cli/sbx_secret_set.yaml b/data/sbx_cli/sbx_secret_set.yaml index d9468c2f438a..0b1bd332a9ed 100644 --- a/data/sbx_cli/sbx_secret_set.yaml +++ b/data/sbx_cli/sbx_secret_set.yaml @@ -5,27 +5,27 @@ description: |- Available services: anthropic, cursor, droid, github, google, groq, mistral, nebius, openai, openrouter, xai - When no arguments are provided, an interactive prompt guides you through - scope and service selection. + Service secrets apply globally by default. Use --sandbox to scope a secret to + one sandbox. When SERVICE is omitted, an interactive prompt selects it. - Use --registry to store pull credentials for a container registry. Where the - credential applies depends on the scope: - - Default (no -g): host-only. Used for template and kit pulls on the host; + Unlike service secrets, registry credentials are host-only by default. Use + --registry to store pull credentials for a container registry: + - Default: host-only. Used for template and kit pulls on the host; never injected into a sandbox. - - With -g: global. Used for host pulls, and injected by the proxy into the - registry login of every new sandbox. The credential itself never enters + - With --all-sandboxes: used for host pulls and injected by the proxy into + every new sandbox's registry login. The credential itself never enters the sandbox. - - With a SANDBOX argument: injected into that one sandbox only. -usage: sbx secret set [-g | SANDBOX] [SERVICE] [flags] + - With --sandbox: injected into that one sandbox only. +usage: sbx secret set [SERVICE] [flags] options: + - name: all-sandboxes + default_value: "false" + usage: | + Inject registry credentials into every sandbox (requires --registry) - name: force shorthand: f default_value: "false" usage: Overwrite an existing secret when --token is used - - name: global - shorthand: g - default_value: "false" - usage: Use global secret scope - name: help shorthand: h default_value: "false" @@ -39,6 +39,8 @@ options: Read registry password or token from stdin (use with --registry) - name: registry usage: Registry hostname for pull credentials (e.g. ghcr.io) + - name: sandbox + usage: Scope the secret to one sandbox instead of its default scope - name: token shorthand: t usage: 'Secret value (less secure: visible in shell history)' @@ -52,24 +54,24 @@ inherited_options: usage: Enable debug logging example: |4- # Store a GitHub token globally (available to all sandboxes) - sbx secret set -g github + sbx secret set github # Store an OpenAI key for a specific sandbox - sbx secret set my-sandbox openai + sbx secret set openai --sandbox my-sandbox # Non-interactive via stdin (e.g., from a secret manager or env var) - echo "$ANTHROPIC_API_KEY" | sbx secret set -g anthropic + echo "$ANTHROPIC_API_KEY" | sbx secret set anthropic # Start OpenAI OAuth flow and store global OAuth tokens - sbx secret set -g openai --oauth + sbx secret set openai --oauth # Registry: host-only (template/kit pulls, not injected into sandboxes) gh auth token | sbx secret set --registry ghcr.io --password-stdin - # Registry: global (host pulls + injected into every new sandbox) - gh auth token | sbx secret set -g --registry ghcr.io --password-stdin + # Registry: host pulls + injected into every new sandbox + gh auth token | sbx secret set --all-sandboxes --registry ghcr.io --password-stdin # Registry: specific sandbox only - gh auth token | sbx secret set my-sandbox --registry ghcr.io --password-stdin + gh auth token | sbx secret set --sandbox my-sandbox --registry ghcr.io --password-stdin see_also: - sbx secret - Manage stored secrets diff --git a/data/sbx_cli/sbx_setup.yaml b/data/sbx_cli/sbx_setup.yaml index 077e87641a40..cd8e4e7f8fda 100644 --- a/data/sbx_cli/sbx_setup.yaml +++ b/data/sbx_cli/sbx_setup.yaml @@ -7,14 +7,7 @@ description: |- Agent secrets are detected from the built-in agent kit specs and the env vars set on this host, and accepted secrets are imported into the global - secrets store (the same store as "sbx secret set -g"). - - [g] Get help with Gordon using the detected setup context - [T] toggle the detailed review table on/off - ↑/↓ move between rows - TAB toggle import / skip for the selected row - [enter] accept and import - [q]/esc quit without importing + secrets store (the same store as "sbx secret set"). usage: sbx setup options: - name: help @@ -28,3 +21,4 @@ inherited_options: usage: Enable debug logging see_also: - sbx - Manage AI coding agent sandboxes. + - sbx setup ssh - Set up SSH client config for the sandbox endpoint diff --git a/data/sbx_cli/sbx_setup_ssh.yaml b/data/sbx_cli/sbx_setup_ssh.yaml new file mode 100644 index 000000000000..8d24c6db9e30 --- /dev/null +++ b/data/sbx_cli/sbx_setup_ssh.yaml @@ -0,0 +1,29 @@ +name: sbx setup ssh +synopsis: Set up SSH client config for the sandbox endpoint +experimental: true +description: |- + Write an ~/.ssh/config block + known_hosts so "ssh .sbx" connects + to a sandbox with no prompts. Re-run any time; it's idempotent. + + No SSH client key is needed — authentication is handled by the daemon's Unix + socket (OS user boundary) combined with an active Docker login. Sign in first + (sbx login). +usage: sbx setup ssh [flags] +options: + - name: alias + default_value: '*.sbx' + usage: ssh_config Host pattern to write + - name: help + shorthand: h + default_value: "false" + usage: help for ssh +inherited_options: + - name: debug + shorthand: D + default_value: "false" + usage: Enable debug logging +example: |4- + sbx setup ssh + ssh my-sandbox.sbx -- echo hello +see_also: + - sbx setup - (Experimental) Detect host configuration and prepare Docker Sandboxes diff --git a/data/sbx_cli/sbx_skills.yaml b/data/sbx_cli/sbx_skills.yaml new file mode 100644 index 000000000000..9831ff7b26af --- /dev/null +++ b/data/sbx_cli/sbx_skills.yaml @@ -0,0 +1,24 @@ +name: sbx skills +synopsis: Manage skills shared across sandboxes +experimental: true +description: |- + Manage the persistent agent skills store shared across sandboxes. + + Copy skills from supported agent directories on the host into the store with: + sbx skills import + + Sandboxes with skills sharing enabled mount the store read-write. Use + --no-share-skills when creating a sandbox to opt out. +options: + - name: help + shorthand: h + default_value: "false" + usage: help for skills +inherited_options: + - name: debug + shorthand: D + default_value: "false" + usage: Enable debug logging +see_also: + - sbx - Manage AI coding agent sandboxes. + - sbx skills import - Import skills from supported agent directories diff --git a/data/sbx_cli/sbx_skills_import.yaml b/data/sbx_cli/sbx_skills_import.yaml new file mode 100644 index 000000000000..25e727b4aea7 --- /dev/null +++ b/data/sbx_cli/sbx_skills_import.yaml @@ -0,0 +1,48 @@ +name: sbx skills import +synopsis: Import skills from supported agent directories +experimental: true +description: |- + Copy skills from supported agent directories on the host into the + persistent store shared by sandboxes. + + Sources are scanned in this order (alphabetical; first wins on conflict): + ~/.agents/skills + ~/.claude/skills + ~/.copilot/skills + ~/.cursor/skills + ~/.factory/skills + + If two sources contain a skill with the same name, the later source is skipped + with a warning — the first source's version is kept. + + Each imported skill folder replaces any store folder of the same name (the + existing folder is backed up first, then the new copy is installed) so stale + files from a previous version cannot linger. You will be prompted before any + existing skill is overwritten; use --force to skip all prompts. + + Symlinks at the top level are followed if they point to a directory. Symlinks + within skill folders and loose files at the top level are skipped. + + The store lives under the sandbox state directory and is cleared by + 'sbx reset'. Supported by Claude, Codex, Copilot, Cursor, and Droid agents. +usage: sbx skills import [flags] +options: + - name: dry-run + default_value: "false" + usage: | + Preview which skills would be imported without copying anything + - name: force + shorthand: f + default_value: "false" + usage: Overwrite existing skills without prompting + - name: help + shorthand: h + default_value: "false" + usage: help for import +inherited_options: + - name: debug + shorthand: D + default_value: "false" + usage: Enable debug logging +see_also: + - sbx skills - (Experimental) Manage skills shared across sandboxes