# TypeScript SDK

> A typed client for Rytiv in TypeScript follows. Until it is published, the REST API is a few lines of fetch, and the MCP server gives your agent the same platform as tools.

> **Not published yet:** The TypeScript SDK is not published yet. This page will carry the install command and a quickstart once it is. Everything it will do is a plain HTTP call today, see below, and your coding agent already has the platform as [MCP tools](https://docs.rytiv.com/reference/mcp-tools.md).

## What it will do

A typed client for the same API the CLI and the MCP server use: computers, sandboxes, apps, machines, deploys, databases and buckets, with errors you can branch on (`code`). It will read your key from `RYTIV_TOKEN`, like the CLI.

## Until then: the REST API

Everything the SDK will do is a plain HTTP call today. A small helper is enough:

```ts
const API = process.env.RYTIV_ENDPOINT ?? "https://api.rytiv.app";

async function rytiv(path: string, init: RequestInit = {}) {
  const res = await fetch(`${API}/v1${path}`, {
    ...init,
    headers: {
      Authorization: `Bearer ${process.env.RYTIV_TOKEN}`,
      "Content-Type": "application/json",
      ...init.headers,
    },
  });
  const body = res.status === 204 ? null : await res.json();
  if (!res.ok) throw new Error(`${body?.code ?? res.status}: ${body?.error ?? res.statusText}`);
  return body;
}

const sandbox = await rytiv("/sandboxes", {
  method: "POST",
  body: JSON.stringify({ template: "app:web", ttlSeconds: 600 }),
});
const result = await rytiv(`/sandboxes/${sandbox.id}/exec`, {
  method: "POST",
  body: JSON.stringify({ cmd: ["node", "--version"] }),
});
console.log(result.stdout);
await rytiv(`/sandboxes/${sandbox.id}`, { method: "DELETE" });
```

The same in Python:

```python
import os, requests

API = os.environ.get("RYTIV_ENDPOINT", "https://api.rytiv.app")
HEADERS = {"Authorization": f"Bearer {os.environ['RYTIV_TOKEN']}"}

def rytiv(method, path, **kwargs):
    res = requests.request(method, f"{API}/v1{path}", headers=HEADERS, **kwargs)
    if res.status_code == 204:
        return None
    body = res.json()
    if not res.ok:
        raise RuntimeError(f"{body.get('code', res.status_code)}: {body.get('error')}")
    return body

sandbox = rytiv("POST", "/sandboxes", json={"template": "app:web", "ttlSeconds": 600})
result = rytiv("POST", f"/sandboxes/{sandbox['id']}/exec", json={"cmd": ["node", "--version"]})
print(result["stdout"])
rytiv("DELETE", f"/sandboxes/{sandbox['id']}")
```

See [REST API basics](https://docs.rytiv.com/reference/api-basics.md) for the error format, and the [API reference](https://docs.rytiv.com/reference/api.md) for every route with its fields.

## MCP

The MCP server at `https://api.rytiv.app/v1/mcp` is the SDK your coding agent uses today: eleven tools for apps, logs, secrets, Postgres and computers, each with annotations your client can use to decide what to confirm. See [MCP tools](https://docs.rytiv.com/reference/mcp-tools.md) and the [quickstart](https://docs.rytiv.com/quickstart.md).
