ILO · PARTNER API · V1

Sell ilo from
your own platform.

Issue license keys for Ilo Raw, Color Tools, Retouch and Animation from your store, marketplace or app — and look them up, revoke them and hand out the installers, all over one secure API.

Get started

The partner API is for companies that sell ilo products or build them into their own service. To get access, write to us at support@ilo.tools with your company and what you plan to build. You get a partner account with the plans you may sell, your partner prices, a monthly license quota and API keys.

Base URL: https://ilo-site.vercel.app/api/v1 — HTTPS only, JSON in and out. Start with a sandbox key (ilo_test_…): it works exactly like a live key but issues test keys that are never billed and never activate.

Authentication

Send your key in the Authorization header on every request:

Authorization: Bearer ilo_live_k1a2b3c4d5e6_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
  • Live keys start with ilo_live_, sandbox keys with ilo_test_. We show a key once, when it is created, and keep only a fingerprint of it — we can never show it again.
  • Call the API from your server only. Never put a key in a web page, a mobile app or a public repository; the API refuses browser requests from other sites.
  • Each key has permissions (scopes): catalog:read, licenses:issue, licenses:read, licenses:revoke, downloads:read, usage:read. Ask for the ones you need.
  • Your account can be limited to your servers' addresses. Keys can expire; we can rotate or revoke one at any time.

Quick start

Check your key:

curl https://ilo-site.vercel.app/api/v1/ping \
  -H "Authorization: Bearer $ILO_KEY"

See what you can sell, at your price:

curl https://ilo-site.vercel.app/api/v1/catalog \
  -H "Authorization: Bearer $ILO_KEY"

Issue a license after your customer pays (the reference is your own order id):

curl https://ilo-site.vercel.app/api/v1/licenses \
  -H "Authorization: Bearer $ILO_KEY" \
  -H "Content-Type: application/json" \
  -d '{ "plan": "an-1y", "email": "customer@example.com", "name": "Dana Levi", "reference": "ORDER-10045" }'
{
  "license": {
    "id": "lic_9Qx…", "reference": "ORDER-10045", "mode": "live",
    "plan": "an-1y", "product": "animation", "email": "customer@example.com",
    "price": 149, "currency": "usd",
    "keys": [ { "product": "Ilo Animation", "key": "ANI-…", "type": "1 year", "expires": "2027-10-07" } ],
    "status": "active", "createdAt": "2026-10-07T10:12:03.000Z", "revokedAt": null
  }
}

Give the customer the key and the installer link (from /downloads). They paste the key in the app the first time they open it.

Endpoints

CallScopeWhat it does
GET/ping—Your account, the key's mode and scopes, your limits.
GET/catalogcatalog:readThe products and plans you may sell, with the retail price and your partner price.
POST/licenseslicenses:issueIssue license keys: { plan, email, name?, reference }. Answers 201, or 200 with "idempotent": true when the reference was already issued.
GET/licenseslicenses:readYour licenses, newest first. Filters: ?reference=, ?email=, ?limit= (1–200), ?before= (the next value of the previous page).
GET/licenses/{id}licenses:readOne license, with its live state on the license servers (activations, expiry, revoked).
POST/licenses/{id}/revokelicenses:revokeStop the keys (refund, chargeback, cancelled order). Optional { reason }.
POST/licenses/{id}/restorelicenses:revokeAllow revoked keys again.
GET/downloadsdownloads:readThe current installers for macOS and Windows, per product.
GET/usageusage:readThis month's calls, licenses, revoked licenses and amount, and your remaining quota. ?month=2026-10 for another month.

Issuing licenses

  • Plans: raw-1m, raw-6m, raw-1y, ct-… (Color Tools), rt-… (Retouch), an-… (Animation), b-… (Raw + Color Tools) and all-… (all four) — for 1 month, 6 months or 1 year. A bundle returns one key per product.
  • One reference, one license. Send the same reference again (a retry after a timeout, a double click) and you get the same license back — never a second one. The same reference with a different plan or email is refused with 409.
  • Keys work on two computers each and expire at the end of the plan. Your customer activates them in the app; you can watch activations with GET /licenses/{id}.
  • Billing: each live license is billed at your partner price; revoked licenses are not billed. We send a monthly statement.

Errors

Errors have an HTTP status and a JSON body: { "error": { "code": "…", "message": "…", "requestId": "req_…" } }. Every answer has an X-Request-Id header — send it to us when something looks wrong.

StatusCodeMeaning
400invalid_jsonThe body is not a JSON object.
401unauthorized · key_revoked · key_expiredNo key, a wrong key, or a key that no longer works.
403insufficient_scope · plan_not_allowed · ip_not_allowed · account_suspendedThe key or the account may not do this.
404not_foundNo such endpoint, or no such license on your account.
409reference_conflictThe reference was already used for a different license.
413 · 415body_too_large · unsupported_media_typeBodies are JSON, up to 32 KB.
422unknown_plan · invalid_email · invalid_referenceA field is missing or wrong.
429rate_limited · quota_exceeded · too_many_failuresSlow down (see Retry-After), or your monthly quota is used up.
5xxserver_error · unavailableOur side — retry with the same reference; it is always safe.

Limits

Each account has a number of requests per minute (60 unless agreed otherwise) and, optionally, a number of licenses per month. Every answer tells you where you stand:

X-RateLimit-Limit: 60
X-RateLimit-Remaining: 57
X-RateLimit-Reset: 1791370800

When you hit the limit you get 429 with Retry-After in seconds. Back off and retry — with the same reference for a license, so nothing is ever issued twice.

Sandbox

With an ilo_test_ key everything works the same, but licenses get keys like TEST-4F2A1-… that never activate, are never sent to the license servers and are never billed. Sandbox and live licenses are kept apart: a sandbox key never sees live licenses, and the other way round. Build and test with the sandbox, then switch the key.

Security

  • Keys are stored only as keyed fingerprints; a stolen database would not reveal them. Keep yours in your server's secret store and rotate them.
  • Repeated failed sign-ins from one address are blocked for ten minutes. Every call is written to an audit log (time, key, call, answer — never keys or customer details).
  • Lost a key, or think it leaked? Tell us — we revoke it at once and give you a new one.
  • Customer emails are used only to issue and look up their licenses, as in our privacy policy.