Skip to content
OpenSmartRoute
Documentation
Hosted platformREST API reference

Public endpoints

No API key required: deployment information, the model catalogue with live statistics, rankings and self-serve signup.

Hosted platformAPI version 2.1.0

get/api/v1/blog

Posts

Published blog posts, newest first (summary only; GET /blog/{slug} carries the body). archive=true lists the archived posts instead (published more than the archive window ago).

No authentication

Parameters

NameInTypeDefaultDescription
limitqueryinteger20
offsetqueryinteger0
tagquerystring | null
categoryquerystring | null
qquerystring | null
archivequerybooleanfalse

Responses

200Successful Response
422Validation ErrorHTTPValidationError
Requestbash
curl -s "$OSR_URL/api/v1/blog?limit=20&offset=0"

get/api/v1/blog/{slug}

Post

One public post (published or archived) with its Markdown body, image, keywords, source and related posts.

No authentication

Parameters

NameInTypeDefaultDescription
slug(required)pathstring

Responses

200Successful Response
422Validation ErrorHTTPValidationError
Requestbash
curl -s "$OSR_URL/api/v1/blog/<slug>"

get/api/v1/blog/{slug}/image

Post Image

The post's own picture: the stored copy (long-lived cache, ETag), or a redirect to its source while no copy exists yet. 404 for a post without a picture of its own (the site then draws its cover).

No authentication

Parameters

NameInTypeDefaultDescription
slug(required)pathstring

Responses

200Successful Response
422Validation ErrorHTTPValidationError
Requestbash
curl -s "$OSR_URL/api/v1/blog/<slug>/image"

get/api/v1/catalogue

Catalogue

No authentication

Responses

200Successful Response
Requestbash
curl -s "$OSR_URL/api/v1/catalogue"

post/api/v1/estimate

Estimate Public

Quote a request before sending it: tokens, cost per candidate and the recommended pick. Works without a key (rate limited per client, no tenant rules) and with one (metered as estimate, workspace tenants and plan applied). monthly_requests adds a monthly projection.

Requires an API key

Parameters

NameInTypeDefaultDescription
x-osr-tenantheaderstring | null

Request bodyEstimateIn

FieldTypeDefaultDescription
constraintsobject
contextobject
executebooleanfalse
historyobject[]
kindsstring[] | null
monthly_requestsinteger | null
objectiveobject<number>
output_tokensinteger | null
planbooleanfalse
plan_modestring | null
profileobject
promptPromptRef | null
text(required)string
top_kinteger3

Responses

200Successful Response
422Validation ErrorHTTPValidationError
401Missing, invalid or revoked API key
Requestbash
curl -s -X POST "$OSR_URL/api/v1/estimate" \
  -H "Authorization: Bearer $OSR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{ "constraints": {}, "context": {}, "history": [], "kinds": [], "monthly_requests": 1, "objective": {}, "output_tokens": 1, "plan_mode": "string" }'
Bodyjson
{
  "constraints": {},
  "context": {},
  "history": [],
  "kinds": [],
  "monthly_requests": 1,
  "objective": {},
  "output_tokens": 1,
  "plan_mode": "string"
}

get/api/v1/facts

Public Facts

The public numbers of this deployment, each in its own class, so no page mixes them up. version (the release this deployment runs and its build), catalogue (the reference model index - indexed, not necessarily executable here), storefront (models sold by the token through this deployment's providers), deployment (targets that execute here, the providers behind them, whether the routing SLM and the autopilot run), activity (what was actually routed: requests, workspaces, the measured saving) and marketplace (listings published here against those indexed from public registries and repositories). classes spells out what each class means. Cached for a minute.

No authentication

Responses

200Successful Response
Requestbash
curl -s "$OSR_URL/api/v1/facts"

get/api/v1/growth/indexnow-key

Indexnow Key

The IndexNow key of this deployment as text/plain (404 when IndexNow is off).

No authentication

Responses

200Successful Response
Requestbash
curl -s "$OSR_URL/api/v1/growth/indexnow-key"

get/api/v1/growth/linkedin/callback

Linkedin Callback

Where LinkedIn sends the operator's browser after consent (the app's registered redirect URL). Exchanges the code, stores the connection and returns to the console growth page with ?linkedin=connected or ?linkedin=error&reason=.

No authentication

Parameters

NameInTypeDefaultDescription
codequerystring | null
statequerystring | null
errorquerystring | null
error_descriptionquerystring | null

Responses

303Successful Response
422Validation ErrorHTTPValidationError
Requestbash
curl -s "$OSR_URL/api/v1/growth/linkedin/callback"

get/api/v1/info

Info

What a visitor may know about this deployment: brand, versions, edition, plans, sign-up and sign-in options. Where state lives, the service topology and the mail transport are operator facts and stay on GET /api/v1/admin/overview and GET /api/v1/admin/services.

No authentication

Responses

200Successful Response
Requestbash
curl -s "$OSR_URL/api/v1/info"

post/api/v1/journey

Record

Report what an anonymous visitor did on the site: page views, calls to action, the signup form's progress. Up to 25 events per call; the visitor id is stored hashed, paths lose their query string but a few harmless keys, referrers keep their origin only. Nothing identifies a person.

No authentication

Request bodyJourneyIn

FieldTypeDefaultDescription
events(required)JourneyEventIn[]
visitor(required)string

Responses

204Successful Response
422Validation ErrorHTTPValidationError
Requestbash
curl -s -X POST "$OSR_URL/api/v1/journey" \
  -H "Content-Type: application/json" \
  -d '{ "events": [], "visitor": "string" }'
Bodyjson
{
  "events": [],
  "visitor": "string"
}

post/api/v1/journey/answer

Answer

One answer to "What is holding you back?" (a visitor on the site or the signup page) or "What is in your way?" (a signed-in workspace stuck before its first request): a reason from the stage's list and an optional line of text. The onboarding stage needs the workspace's session or key; one answer per workspace is kept (a new one replaces it).

Requires an API key

Request bodyAnswerIn

FieldTypeDefaultDescription
pathstring | null
reason(required)string
stage(required)string
textstring | null
visitorstring | null

Responses

201Successful Response
422Validation ErrorHTTPValidationError
401Missing, invalid or revoked API key
Requestbash
curl -s -X POST "$OSR_URL/api/v1/journey/answer" \
  -H "Authorization: Bearer $OSR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{ "reason": "string", "stage": "string" }'
Bodyjson
{
  "reason": "string",
  "stage": "string"
}

get/api/v1/journey/blocker

Blocker

The calling workspace's answer to "What is in your way?", or null when it has not answered.

Requires an API key

Parameters

NameInTypeDefaultDescription
x-goog-api-keyheaderstring | null

Responses

200Successful Response
422Validation ErrorHTTPValidationError
401Missing, invalid or revoked API key
Requestbash
curl -s "$OSR_URL/api/v1/journey/blocker" \
  -H "Authorization: Bearer $OSR_API_KEY"

get/api/v1/journey/reasons

Reasons

The reasons each stage of the survey offers, with their labels (what the forms render).

No authentication

Responses

200Successful Response
Requestbash
curl -s "$OSR_URL/api/v1/journey/reasons"

get/api/v1/llms

Llms

The reference LLM catalogue: real vendors, prices per million tokens, context windows, modalities. Independent of what this deployment routes to; routed_by lists the routing targets that resolve to each model. Sorted by newest (default), name, price, price-desc, context or intelligence.

No authentication

Parameters

NameInTypeDefaultDescription
qquerystring""
vendorquerystring | null
modalityquerystring | null
toolsqueryboolean | null
reasoningqueryboolean | null
open_weightsqueryboolean | null
freequeryboolean | null
sortquerystring"newest"
limitqueryinteger500
offsetqueryinteger0

Responses

200Successful Response
422Validation ErrorHTTPValidationError
Requestbash
curl -s "$OSR_URL/api/v1/llms?q=&sort=newest"

get/api/v1/llms/{vendor}/{model}

Llm

One reference model with the routing targets that resolve to it and its vendor siblings.

No authentication

Parameters

NameInTypeDefaultDescription
vendor(required)pathstring
model(required)pathstring

Responses

200Successful Response
422Validation ErrorHTTPValidationError
Requestbash
curl -s "$OSR_URL/api/v1/llms/<vendor>/<model>"

get/api/v1/maintenance

Maintenance

No authentication

Responses

200Successful Response
Requestbash
curl -s "$OSR_URL/api/v1/maintenance"

get/api/v1/models

Models

No authentication

Parameters

NameInTypeDefaultDescription
daysqueryinteger7

Responses

200Successful Response
422Validation ErrorHTTPValidationError
Requestbash
curl -s "$OSR_URL/api/v1/models?days=7"

get/api/v1/models/{model_id}

Model

No authentication

Parameters

NameInTypeDefaultDescription
model_id(required)pathstring
daysqueryinteger30

Responses

200Successful Response
422Validation ErrorHTTPValidationError
Requestbash
curl -s "$OSR_URL/api/v1/models/<model_id>?days=30"

post/api/v1/newsletter/confirm

Confirm

Confirm with the token from the email; 404 when it is unknown or older than three days. The address receives the branded welcome with its unsubscribe link. The moment, the address the click came from and the statement agreed to are kept as the consent record (GET /api/v1/newsletter/preferences shows it).

No authentication

Request bodyTokenIn

FieldTypeDefaultDescription
token(required)string

Responses

200Successful Response
422Validation ErrorHTTPValidationError
Requestbash
curl -s -X POST "$OSR_URL/api/v1/newsletter/confirm" \
  -H "Content-Type: application/json" \
  -d '{ "token": "string" }'
Bodyjson
{
  "token": "string"
}

get/api/v1/newsletter/issues/{issue_id}

Issue Page

One sent issue as the website shows it behind the *view this issue in your browser* link: subject, day, opener and the posts it carried (public blog data only). 404 for an unknown issue or one not sent yet.

No authentication

Parameters

NameInTypeDefaultDescription
issue_id(required)pathstring

Responses

200Successful Response
422Validation ErrorHTTPValidationError
Requestbash
curl -s "$OSR_URL/api/v1/newsletter/issues/<issue_id>"

get/api/v1/newsletter/preferences

Reader Preferences

The reader's page behind the *Newsletter preferences* link of every issue: the address, status, daily or weekly, time zone, the topics followed, the consent record and everything else stored about them. No sign-in; the token from the footer is the credential.

No authentication

Parameters

NameInTypeDefaultDescription
token(required)querystring

Responses

200Successful Response
422Validation ErrorHTTPValidationError
Requestbash
curl -s "$OSR_URL/api/v1/newsletter/preferences"

put/api/v1/newsletter/preferences

Set Reader Preferences

Switch between the daily issue and the weekly digest (weekly_day in the reader's zone), set the time zone the issue is timed by, and choose the topics (categories) to receive - an empty list, or every category, means all of them; an issue with nothing in the reader's topics is not sent to them.

No authentication

Parameters

NameInTypeDefaultDescription
token(required)querystring

Request bodyReaderPreferencesIn

FieldTypeDefaultDescription
frequencystring | null
timezonestring | null
topicsstring[] | null

Responses

200Successful Response
422Validation ErrorHTTPValidationError
Requestbash
curl -s -X PUT "$OSR_URL/api/v1/newsletter/preferences" \
  -H "Content-Type: application/json" \
  -d '{ "frequency": "string", "timezone": "string", "topics": [] }'
Bodyjson
{
  "frequency": "string",
  "timezone": "string",
  "topics": []
}

delete/api/v1/newsletter/preferences

Erase Reader

Erase everything held about the reader - the subscription row with its consent record and the hashed engagement rows. Irreversible; a later signup starts from nothing.

No authentication

Parameters

NameInTypeDefaultDescription
token(required)querystring

Responses

200Successful Response
422Validation ErrorHTTPValidationError
Requestbash
curl -s -X DELETE "$OSR_URL/api/v1/newsletter/preferences"

post/api/v1/newsletter/subscribe

Subscribe

Start a subscription: the address receives a confirmation link (three days). Always 202; an already confirmed address is not told apart. 5 per IP per minute.

No authentication

Request bodySubscribeIn

FieldTypeDefaultDescription
email(required)string
sourcestring"web"
timezonestring | null
topicsstring[][]

Responses

202Successful Response
422Validation ErrorHTTPValidationError
Requestbash
curl -s -X POST "$OSR_URL/api/v1/newsletter/subscribe" \
  -H "Content-Type: application/json" \
  -d '{ "email": "ada@example.com" }'
Bodyjson
{
  "email": "ada@example.com"
}

post/api/v1/newsletter/unsubscribe

Unsubscribe

One-click unsubscribe with the token from an issue's footer - as JSON {"token"} from the web page or as the ?token= query a mail client's *List-Unsubscribe* POST carries (RFC 8058). Campaign tokens keep working.

No authentication

Parameters

NameInTypeDefaultDescription
tokenquerystring | null

Responses

200Successful Response
422Validation ErrorHTTPValidationError
Requestbash
curl -s -X POST "$OSR_URL/api/v1/newsletter/unsubscribe" \
  -H "Content-Type: application/json" \
  -d '{ "token": "string" }'
Bodyjson
{
  "token": "string"
}

get/api/v1/rankings

Rankings

No authentication

Parameters

NameInTypeDefaultDescription
daysqueryinteger7
domainquerystring | null

Responses

200Successful Response
422Validation ErrorHTTPValidationError
Requestbash
curl -s "$OSR_URL/api/v1/rankings?days=7"

get/api/v1/rankings/listings

Listings Board

The marketplace board: published listings of one kind (or all) by installs (default), rating (Bayesian average - the mean shrunk towards rating_prior.mean by rating_prior.weight virtual ratings) or newest. Each row is the public card with rank, reviews and bayesian_rating; publishers appear by display name only.

No authentication

Parameters

NameInTypeDefaultDescription
kindquerystring | null
sortquerystring"installs"
limitqueryinteger50

Responses

200Successful Response
422Validation ErrorHTTPValidationError
Requestbash
curl -s "$OSR_URL/api/v1/rankings/listings?sort=installs&limit=50"

get/api/v1/rankings/listings/kinds

Listings Kinds

Every marketplace kind with its published listings, installs and reviews.

No authentication

Responses

200Successful Response
Requestbash
curl -s "$OSR_URL/api/v1/rankings/listings/kinds"

get/api/v1/rankings/models

Models

Models ranked by published benchmarks - the composite osr_index by default (Artificial Analysis intelligence index, Open LLM Leaderboard average and Chatbot Arena score, weighted, with osr_coverage telling how many of the three the model publishes), or one metric (sort: intelligence_index, coding_index, agentic_index, hf_leaderboard_avg, arena_score, hub_downloads, hub_likes, price, newest). movement is the change in rank since the previous day. Refreshed automatically every interval_s seconds (default: three times a day).

No authentication

Parameters

NameInTypeDefaultDescription
sortquerystring"osr_index"
vendorquerystring | null
open_weightsqueryboolean | null
qquerystring""
limitqueryinteger50
offsetqueryinteger0

Responses

200Successful Response
422Validation ErrorHTTPValidationError
Requestbash
curl -s "$OSR_URL/api/v1/rankings/models?sort=osr_index&q="

get/api/v1/rankings/models/{vendor}/{model}

Model

One model's board entry with its rank history (days back, one point per refresh day).

No authentication

Parameters

NameInTypeDefaultDescription
vendor(required)pathstring
model(required)pathstring
daysqueryinteger30

Responses

200Successful Response
422Validation ErrorHTTPValidationError
Requestbash
curl -s "$OSR_URL/api/v1/rankings/models/<vendor>/<model>?days=30"

get/api/v1/rankings/targets

Targets Board

Targets ranked by reported outcomes across every workspace, optionally one kind (llm, agent, skill, tool, persona, workflow, human) within one task domain (see /rankings/targets/domains) over window_days (default 30). score is the Wilson lower bound of the reported success rate; rows with fewer than min_samples outcomes are provisional and listed last. share is the target's part of the routed requests in that domain; p50_latency_ms is read off a 10 ms histogram. Anonymised: no workspace, request or prompt data.

No authentication

Parameters

NameInTypeDefaultDescription
kindquerystring | null
domainquerystring | null
window_daysqueryinteger30
limitqueryinteger50

Responses

200Successful Response
422Validation ErrorHTTPValidationError
Requestbash
curl -s "$OSR_URL/api/v1/rankings/targets?window_days=30&limit=50"

get/api/v1/rankings/targets/domains

Targets Domains

The task domains routed in the window with their request counts (domains thinner than min_samples requests are left out); the values /rankings/targets?domain= accepts.

No authentication

Parameters

NameInTypeDefaultDescription
window_daysqueryinteger30

Responses

200Successful Response
422Validation ErrorHTTPValidationError
Requestbash
curl -s "$OSR_URL/api/v1/rankings/targets/domains?window_days=30"

post/api/v1/sales/inquiries

Open Inquiry

Ask to talk to sales about a plan (the enterprise plan is sold this way). No key needed; a signed-in caller's workspace is attached so the agreement can be applied to it. Answers with the inquiry and its reference; the requester is e-mailed the same, the operators are told. Five per address and day.

Requires an API key

Request bodyInquiryIn

FieldTypeDefaultDescription
companystring""
email(required)string
intereststring"hosted"
messagestring""
namestring""
planstring"enterprise"
volumestring""
websitestring""

Responses

201Successful Response
422Validation ErrorHTTPValidationError
401Missing, invalid or revoked API key
Requestbash
curl -s -X POST "$OSR_URL/api/v1/sales/inquiries" \
  -H "Authorization: Bearer $OSR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{ "email": "ada@example.com" }'
Bodyjson
{
  "email": "ada@example.com"
}

get/api/v1/services

Services

Everything the platform runs as a service, with its status on this deployment. Each item: status (live works now, limited runs with a stated restriction, off not here), detail (the reason), endpoint (METHOD /path), access (public / key / operator), plan (the cheapest plan that includes it), docs and page on the site, and facts - small live figures from the same stores the dashboards read. Cached for a minute.

No authentication

Responses

200Successful Response
Requestbash
curl -s "$OSR_URL/api/v1/services"

get/api/v1/showcase

Read Showcase

The product pages' walk-through drafts with the answer the router wrote for each and what it cost (target, model, tokens, price, latency). answer is null for a draft the platform has not answered yet; stale says whether a refresh is due.

No authentication

Responses

200Successful Response
Requestbash
curl -s "$OSR_URL/api/v1/showcase"

post/api/v1/signup

Signup

No authentication

Request bodySignupIn

FieldTypeDefaultDescription
accept_termsbooleanfalse
attributionany
captcha_tokenstring | null
email(required)string
namestring""
passwordstring | null
timezonestring | null
websitestring | null

Responses

201Successful Response
422Validation ErrorHTTPValidationError
Requestbash
curl -s -X POST "$OSR_URL/api/v1/signup" \
  -H "Content-Type: application/json" \
  -d '{ "email": "ada@example.com" }'
Bodyjson
{
  "email": "ada@example.com"
}

get/api/v1/site/photos

Manifest

The photographs an operator replaced or re-captioned, by key: caption, crop focus, credit and - when the picture itself was replaced - its size and a content version. The site merges this over the photographs it ships; a key that is not here shows the shipped picture.

No authentication

Responses

200Successful Response
Requestbash
curl -s "$OSR_URL/api/v1/site/photos"

get/api/v1/site/photos/{key}

Picture

The replaced picture: a redirect to its address in object storage when it lives there, else the bytes (WebP, long-lived cache, ETag); 404 when the key keeps the shipped one.

No authentication

Parameters

NameInTypeDefaultDescription
key(required)pathstring

Responses

200Successful Response
422Validation ErrorHTTPValidationError
Requestbash
curl -s "$OSR_URL/api/v1/site/photos/<key>"

get/api/v1/stats/public

Stats Public

No authentication

Responses

200Successful Response
Requestbash
curl -s "$OSR_URL/api/v1/stats/public"

get/api/v1/status

Status

Readiness checks, uptime and the observability controls of this deployment (no key needed). The same checks as GET /readyz with the edition, versions and tracing state added; the status code is 503 while a check fails so status pages can poll it directly.

No authentication

Responses

200Successful Response
Requestbash
curl -s "$OSR_URL/api/v1/status"

get/api/v1/status/board

Status Board

Everything the status page shows: overall state, every component with its last check and 90 days of uptime, open and recent incidents, and what the platform served per day (requests, platform failures).

No authentication

Responses

200Successful Response
Requestbash
curl -s "$OSR_URL/api/v1/status/board"

get/api/v1/status/incidents

List Incidents

Incidents opened or active in the last days days, newest first, each with its updates.

No authentication

Parameters

NameInTypeDefaultDescription
daysqueryinteger90
limitqueryinteger50

Responses

200Successful Response
422Validation ErrorHTTPValidationError
Requestbash
curl -s "$OSR_URL/api/v1/status/incidents?days=90&limit=50"

get/api/v1/status/incidents/{incident_id}

One Incident

No authentication

Parameters

NameInTypeDefaultDescription
incident_id(required)pathstring

Responses

200Successful Response
422Validation ErrorHTTPValidationError
Requestbash
curl -s "$OSR_URL/api/v1/status/incidents/<incident_id>"

Something wrong or out of date on this page? Tell us - the page is named for you, so a one-line note is enough.