Runtime

How to create a read-only API key for monitoring and CI

Choose Read only when you create a key at withruntime.com/account/keys, or run runtime keys create --read-only.

On Runtime a read-only key sees the whole account, every product included, and cannot start, change or spend anything. It covers products added later without being reissued, and it lasts until revoked. A dashboard or a CI check that holds one cannot start a sandbox or touch the balance, even if the key leaks (checked 25 September 2026, security).

Create one

An owner, admin or developer of the account can create a key of either kind.

  • In the browser: at API keys, choose Read only.
  • From a terminal: the CLI asks for the key, and a person approves it in the browser after checking the code, the key's name and its access.
Terminalruntime keys create --name grafana --read-onlyruntime keys create --name pr-checks --read-only | gh secret set RUNTIME_READ_KEY

The key is printed once, alone on standard output, and Runtime keeps only a hash of it. A billing member, an agent and an existing key cannot approve a key request (keys for CI).

What it can and cannot do

A read-only key can read It cannot
Every sandbox, its state, spec and cost Create, start, stop, pause or wake anything
Images, volumes, snapshots, previews and network rules Run a command or write a file
Account notices and the balance Change a setting or a rule
Its own access and limit Spend anything
The audit log, when an owner or admin made the key See inside sandboxes: files or command output
See job runs or secrets

A request to change something is refused with 403 forbidden, raised as PermissionDeniedError in both SDKs.

Use it from code

Point the client at the key with RUNTIME_API_KEY, as with any key. This script is the kind of thing a read-only key is for: it lists what is running and what each sandbox is set up as, and touches nothing.

TypeScriptimport { Runtime } from "withruntime";const runtime = new Runtime(); // RUNTIME_API_KEY holds the read-only keyconst page = await runtime.sandboxes.list({ state: ["running"] });for await (const sbx of page) console.log(sbx.id, sbx.info.name, sbx.state);
Pythonfrom withruntime import Runtimeruntime = Runtime()  # RUNTIME_API_KEY holds the read-only keyfor sbx in runtime.sandboxes.list(state=["running"]):    print(sbx.id, sbx.info["name"], sbx.state)

A job that must be sure it holds a read-only key can check before it starts:

TypeScriptimport { PermissionDeniedError, Runtime } from "withruntime";const runtime = new Runtime();const { access } = await runtime.limits.get();if (access !== "read") throw new Error(`expected a read-only key, got ${access}`);try {  await runtime.sandboxes.create();} catch (error) {  if (error instanceof PermissionDeniedError) console.log("refused, as it should be");  else throw error;}
Pythonfrom withruntime import PermissionDeniedError, Runtimewith Runtime() as runtime:    access = runtime.limits.get()["access"]  # "full", "read" or "selected"    assert access == "read", access    try:        runtime.sandboxes.create()    except PermissionDeniedError:        print("refused, as it should be")

runtime limits prints the same from a terminal, and an agent on MCP calls runtime_limits_get. access is read for a read-only key, full for one that reaches every action, and selected for a key limited to the actions it names (API account).

Where a read-only key fits

  • Dashboards and alerting: sandbox counts, states and costs, account notices such as a paused sandbox about to expire, and the balance.
  • CI checks: a pull-request job that verifies an image tag exists or that no sandbox with a given label is left running.
  • Cost reports: runtime usage --json and GET /v1/usage give every figure in integer microdollars.
  • Audits: a read-only key made by an owner or admin reads the audit log, with who did what and from where (teams).

Mistakes to avoid

  • Giving the monitoring job the deploy key. A full key in a dashboard can start sandboxes and spend credit if it leaks. Give it its own read-only key.
  • Expecting command output. A read-only key sees a sandbox's state and cost but not what is inside it. A check that needs a file's contents needs a full key, ideally with a daily spending limit.
  • Trying to make keys with a key. No key can create, list or revoke keys; that is done by a person, in the browser.
  • Putting the key in a URL or a command line. Keep it in a secret store and pass it as RUNTIME_API_KEY.

Revoke a key from its row at API keys. Every key made, revoked or limited is in the audit log. For keys that can spend within a bound, see cap a sandbox's cost; for keeping a provider's key out of a sandbox entirely, see turn off sandbox internet.

Facts on this page were checked on 25 September 2026.