curl -X POST "https://app.runtm.com/api/v2/sessions/86e11104-.../connect?port=3000" \
-H "Authorization: Bearer runtm_xxx"
import requests
response = requests.post(
"https://app.runtm.com/api/v2/sessions/86e11104-.../connect",
headers={"Authorization": "Bearer runtm_xxx"},
params={"port": 3000},
)
data = response.json()
print(f"Preview at {data['preview_url']}")
const response = await fetch(
"https://app.runtm.com/api/v2/sessions/86e11104-.../connect?port=3000",
{ method: "POST", headers: { "Authorization": "Bearer runtm_xxx" } }
);
const { preview_url, port } = await response.json();
console.log(`Preview at ${preview_url} (port ${port})`);
{
"preview_url": "https://3000-sb-xyz.dev.runtm.com",
"port": 3000
}
Get Preview URL for a Service (v2)
Resolve a preview URL for a specific port on the sandbox
POST
/
api
/
v2
/
sessions
/
{session_id}
/
connect
curl -X POST "https://app.runtm.com/api/v2/sessions/86e11104-.../connect?port=3000" \
-H "Authorization: Bearer runtm_xxx"
import requests
response = requests.post(
"https://app.runtm.com/api/v2/sessions/86e11104-.../connect",
headers={"Authorization": "Bearer runtm_xxx"},
params={"port": 3000},
)
data = response.json()
print(f"Preview at {data['preview_url']}")
const response = await fetch(
"https://app.runtm.com/api/v2/sessions/86e11104-.../connect?port=3000",
{ method: "POST", headers: { "Authorization": "Bearer runtm_xxx" } }
);
const { preview_url, port } = await response.json();
console.log(`Preview at ${preview_url} (port ${port})`);
{
"preview_url": "https://3000-sb-xyz.dev.runtm.com",
"port": 3000
}
Returns a preview URL backed by a running service on the sandbox at the requested port. This powers multi-port preview tabs in the workspace UI.
The endpoint is idempotent and self-healing:
- Reconciles the DB state with the sandbox provider (handles raw-URL auto-resume).
- Resumes the sandbox if the provider reports it as paused.
- Starts or verifies the dev server (no-ops if already responding).
- Persists
session.preview_urland cached project metadata so Slack/agent callbacks can reuse the verified URL.
services field (e.g. { "frontend": 3000, "postgres": 5432 }).
Required scope: sessions:write
Path Parameters
string
required
The session ID.
Query Parameters
integer
required
The port number to expose. Must match a port the sandbox process is actually listening on.
Headers
string
required
Bearer token. Example:
Bearer runtm_xxxstring
Required when the session belongs to an organization.
Response
string
Public preview URL pointing at the sandbox port.
integer
The port that was resolved.
Errors
| Status | Meaning |
|---|---|
404 | Session not found |
410 | Sandbox has expired or is in an invalid state |
502 | Could not resolve preview (port not listening, dev-server failed to start within 120s) |
curl -X POST "https://app.runtm.com/api/v2/sessions/86e11104-.../connect?port=3000" \
-H "Authorization: Bearer runtm_xxx"
import requests
response = requests.post(
"https://app.runtm.com/api/v2/sessions/86e11104-.../connect",
headers={"Authorization": "Bearer runtm_xxx"},
params={"port": 3000},
)
data = response.json()
print(f"Preview at {data['preview_url']}")
const response = await fetch(
"https://app.runtm.com/api/v2/sessions/86e11104-.../connect?port=3000",
{ method: "POST", headers: { "Authorization": "Bearer runtm_xxx" } }
);
const { preview_url, port } = await response.json();
console.log(`Preview at ${preview_url} (port ${port})`);
{
"preview_url": "https://3000-sb-xyz.dev.runtm.com",
"port": 3000
}