Skip to content

Agentic API — Example Calls

Three minimal flows for the Cash Runway agentic surface: curl, TypeScript, and Python. Each example assumes the API key is provisioned under Settings → API keys and carries the READ_BANK + READ_FORECAST scopes.

The same bearer header works for every endpoint:

http
Authorization: Bearer cr_live_<prefixId>_<secret>

Full spec: /api/agent/openapi.json.

curl

1. Session bootstrap (/status)

bash
curl -sS https://app.cashrunway.ai/api/agent/status \
  -H "Authorization: Bearer $CASHRUNWAY_API_KEY" | jq

2. Latest cash position

bash
curl -sS https://app.cashrunway.ai/api/agent/cash-position \
  -H "Authorization: Bearer $CASHRUNWAY_API_KEY" \
  -D - | jq

Note the -D - flag — the X-Cash Runway-* headers carry subscription + quota state and are worth reading on every call.

3. 13-week forecast

bash
curl -sS "https://app.cashrunway.ai/api/agent/forecast?scenarioId=scn_abc" \
  -H "Authorization: Bearer $CASHRUNWAY_API_KEY" | jq '.weeks[] | {weekStart, closing, net}'

TypeScript (fetch)

ts
const BASE = 'https://app.cashrunway.ai/api/agent';
const KEY = process.env.CASHRUNWAY_API_KEY!;

async function agentGet<T>(path: string): Promise<T> {
  const res = await fetch(`${BASE}${path}`, {
    headers: { Authorization: `Bearer ${KEY}` },
  });
  if (!res.ok) throw new Error(`${res.status} ${await res.text()}`);
  return res.json() as Promise<T>;
}

// 1. Session bootstrap
const status = await agentGet<{
  subscription: { status: string; plan: string; trialDaysRemaining?: number };
  quota: { used: number; remaining: number };
}>('/status');
console.log(`${status.subscription.plan} — ${status.quota.remaining} queries remaining`);

// 2. Cash position with agent notes
const cash = await agentGet<{
  startingCash: string;
  accounts: Array<{ id: string; name: string; balance: string }>;
  notesForAgent: Array<{ kind: string; severity: string; text: string }>;
  billingAlert?: { severity: 'warn' | 'critical'; message: string };
}>('/cash-position');
if (cash.billingAlert) console.warn('Billing alert:', cash.billingAlert.message);
console.log('Opening cash:', cash.startingCash);

// 3. Forecast
const forecast = await agentGet<{
  weeks: Array<{ weekStart: string; closing: string; net: string }>;
}>('/forecast');
for (const w of forecast.weeks) {
  console.log(`${w.weekStart}: closing=${w.closing} net=${w.net}`);
}

Python

python
import os, requests

BASE = "https://app.cashrunway.ai/api/agent"
KEY = os.environ["CASHRUNWAY_API_KEY"]

def agent_get(path: str) -> dict:
    r = requests.get(f"{BASE}{path}", headers={"Authorization": f"Bearer {KEY}"})
    r.raise_for_status()
    return r.json()

# 1. Session bootstrap
status = agent_get("/status")
print(f"{status['subscription']['plan']}{status['quota']['remaining']} remaining")

# 2. Cash position
cash = agent_get("/cash-position")
if alert := cash.get("billingAlert"):
    print(f"[{alert['severity']}] {alert['message']}")
print("Opening cash:", cash["startingCash"])

# 3. Forecast
fc = agent_get("/forecast")
for w in fc["weeks"]:
    print(f"{w['weekStart']}: closing={w['closing']} net={w['net']}")

Headers to watch

Every successful response carries billing + query-credit context in headers, so you don't have to parse the body to decide whether to pace yourself:

HeaderValue
X-CashRunway-Subscriptiontrialing / active / past_due / canceled / trial_ended
X-CashRunway-PlanSubscription display name (legacy — read the usage block for the query-credit plan)
X-CashRunway-Trial-Days-Remaininginteger, only when trialing
X-CashRunway-Reset-Minutesinteger — minutes until the next query credit frees up
X-CashRunway-Quota-Remaininginteger — legacy daily bucket (prefer the usage block)
X-CashRunway-Quota-ResetISO timestamp — legacy daily bucket (prefer usage.windowResetAt)

When something needs action, a billingAlert field also appears in the JSON body. Its absence on a healthy call is itself the positive signal.

Last updated:

Released under a proprietary license.