Before you start
You need three things, and the first request fails in a documented way if any of them is missing:1
A verified account
Sign up and verify your email address at app.uniblock.dev.
2
A workspace with credit
Credit is prepaid, so a workspace with a zero balance refuses requests
before they reach a provider. The workspace owner buys credit on the Billing
screen. See buying credit.
3
An API key
Mint one on the Keys screen. The key appears once and we keep only a hash,
so we cannot show it to you again or recover it for you. Copy it before you
leave the screen. See authentication.
Set the base URL
Point your existing OpenAI client athttps://ai.uniblock.dev and give it a
Uniblock API key. Nothing else about your code changes.
Base URL
The SDKs append the endpoint path themselves, which is why their setting carries
the
/v1 and nothing after it.
Send the request
Every request to the API carries your key in anAuthorization header using the
Bearer scheme. A missing header, a scheme other than Bearer, a key of the
wrong shape, and a key we reject are all answered with 401.
Read the response headers
Every response carries the id for that request, on two headers with the same value:Every response carries the same id on two headers:
x-uniblock-request-id,
which is ours, and x-request-id, which is the one the official OpenAI SDKs
surface on their error objects. Every error envelope repeats it as
request_id. Quote it when you ask us about a request. Without it we are
guessing at which of your requests you mean.Stream the response
Setstream: true and read the SSE stream exactly as you would from OpenAI.
Before the final data: [DONE] line, we splice in one SSE comment line carrying
the token counts. The SSE specification requires a parser to ignore comment
lines, so an OpenAI SDK skips it without being taught about it.
Annotated SSE tail
The two first-run failures
Both arrive in the OpenAI error envelope, so your existing error handling parses them. Branch ontype and code rather than on the message text: the fields are
the contract and the sentences are prose.
Every error on the API, at every status, is one JSON object with a single
top-level error key. An OpenAI client parses it with the error handling it
already has.
Error envelope
Branch on
type and code. Both are stable. message is prose and may change.
The type values are invalid_request_error, authentication_error,
permission_error, not_found_error, rate_limit_error, api_error,
insufficient_quota, and server_error.
No key, or a key we do not recognise: 401
Sending noAuthorization header at all:
401
401
"Incorrect API key provided." in the same envelope. An unknown key and a
revoked key get that one identical sentence on purpose, because confirming that
a stolen key was once real helps whoever stole it and helps nobody else.
Not enough credit: 402
A request is priced and held against your balance before it reaches a provider, so a workspace that cannot cover the hold is refused rather than served and billed. Thetype is insufficient_quota, which is the value an OpenAI client
already has a branch for, and the code is insufficient_credit:
402
Catch errors in your client
The OpenAI SDKs raise their normal status errors, so the catch you already have works. Readtype and code off the body:
Next
OpenAI compatibility
Which endpoints exist today, and what a call to one that does not returns.
Errors
Every shipped code, its status, and what to do about it.