API reference
Everything you do in the console is a call away. Browse listings, register a key, rent a GPU, and watch the meter, all over one JSON API and a single bearer token.
The API drives the whole platform. You list price-sorted GPUs, push an SSH public key, rent a box, poll it until your connection string appears, then tear it down. There is no provider account, no quota dance, and no second credential to manage. Authenticate every request with one token and you are in.
Base URL
Every endpoint lives under /api/v1 on the IPX origin. There is one version and it is v1.
https://gpu.ipxtechholding.com/api/v1
In the examples below we keep the origin in a shell variable so you can copy a request and run it as-is.
$ export IPX_BASE="https://gpu.ipxtechholding.com" $ curl "$IPX_BASE/api/v1/listings"
Authentication
The API uses named bearer tokens, created under Settings → API access. Each token starts with ipx_, is shown once at creation, and can be revoked individually at any time. We store only a SHA-256 digest, so if you lose one you create a new one rather than recover it.
Send it in the Authorization header on every authenticated request, prefixed with Bearer. We document it below as the shell variable $IPX_TOKEN.
# store your token once, then reuse it $ export IPX_TOKEN="ipx_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" # send it on every authenticated call $ curl "$IPX_BASE/api/v1/credits" \\ -H "Authorization: Bearer $IPX_TOKEN"
Workspaces and roles
Every token belongs to one workspace: your personal workspace or a team you are a member of. Requests act inside that workspace and carry your live role there, exactly like the console.
- Developer: rent and terminate boxes, manage SSH keys, read the balance.
- Admin and owner: everything above, plus opening credit top-ups.
The role is checked on every request, not stamped into the token. Leave a team and its tokens stop working immediately; get promoted and your existing token gains the new powers. A token whose action exceeds your role returns 403 Forbidden.
Treat tokens like passwords. They can rent hardware and spend the workspace balance. Never commit them or paste them into client-side code. If one leaks, revoke it in Settings; revocation is immediate. For CI and short-lived automation, create tokens with a 30 or 90 day expiry.
Which endpoints need a token
Listings are public, so you can browse prices before you sign in. Everything that touches a workspace, its keys, or its money requires a valid bearer token.
- Public:
GET /api/v1/listings - Authenticated: SSH keys, rentals, and credits
Authentication errors
If the Authorization header is missing, malformed, expired, revoked, or no longer matches a workspace membership, the request is rejected with 401 Unauthorized and a JSON error body. No partial work is done. A valid token used beyond its role returns 403.
// a missing, invalid, expired, or revoked token, on any authenticated endpoint
{
"error": "unauthorized"
}
Rate limits
Authenticated calls are limited to 120 requests per minute per token. Past the limit you get 429 Too Many Requests; back off briefly and retry. Registration and other credential endpoints have tighter limits.
Conventions
JSON in, JSON out
Requests and responses are JSON. Send parameters as query string or form body, and you always get a JSON object back, including on errors. There is no XML and no envelope to unwrap. Collection endpoints return a named array, for example { "listings": [ ... ] }.
Money is micro-USD
All amounts are integers in micro-USD, where 1 USD = 1,000,000 micro. Integers keep money exact, with no floating-point drift. Convert by dividing or multiplying by one million.
680000is $0.685000000is a $5.00 spend cap1000000is $1.00
Listings expose both forms for convenience. price_micro_usd_per_hour is the exact integer you should compute against, and price_usd_per_hour is a rounded decimal for display only. Everywhere else, the field name carries the unit, for example accumulated_cost_micro_usd, max_cost_micro_usd, and balance_micro_usd.
One exception: when you top up credits, Stripe works in cents, so the credit endpoint takes amount_cents rather than micro-USD. The credits page covers that in full.
Status codes
We use standard HTTP status codes. A 2xx means it worked, a 4xx means the request was wrong, and a 5xx or 502 means something failed upstream. Error bodies are always { "error": "message" }.
GET /api/v1/rentals/:id and by a termination.Authorization header.// every non-2xx carries the same minimal shape
{
"error": "insufficient credit to start this rental"
}
The rental lifecycle
Renting is asynchronous. A successful POST /api/v1/rentals returns 201 immediately with a state of provisioning_requested, then the box boots and dials home. Poll GET /api/v1/rentals/:id until the state reaches active_connected, at which point a connection_string appears.
provisioning_requested -> booting_instance -> awaiting_tunnel
|
v
terminated <- terminating <- active_connected
The connection_string field is null until the tunnel is live, then becomes a ready-to-run command like ssh -p 20137 root@gpu.ipxtechholding.com. Poll on a short interval and stop as soon as it is non-null. The rentals page has a complete poll loop.
A first call
Listings are public, so this works before you even hold a token. It confirms your base URL is right and shows the money fields in context.
$ curl "https://gpu.ipxtechholding.com/api/v1/listings?limit=1"
{
"listings": [
{
"id": 4812,
"gpu_name": "RTX 4090",
"vram_gb": 24,
"num_gpus": 1,
"region": "us-east",
"interruptible": false,
"price_micro_usd_per_hour": 680000,
"price_usd_per_hour": 0.68
}
]
}
Resources
Four resources cover the whole platform. Start with SSH keys and listings, then rentals, then credits when you need to top up.