API docs

Send an image, get a vector file back. One endpoint does the work; the rest manage keys, credits and billing.

Quickstart

Create an API key on your account page; new accounts start with 5 free credits. Then post an image to /v1/vectorize. The response body is the file.

curl https://svgmill.com/v1/vectorize \
  -H "Authorization: Bearer $SVGMILL_KEY" \
  -F image=@logo.png \
  -F format=svg \
  -D headers.txt -o logo.svg

# Same trace as a DXF, free: use the token from headers.txt
curl https://svgmill.com/v1/download \
  -H "Authorization: Bearer $SVGMILL_KEY" \
  -H "Content-Type: application/json" \
  -d '{"token":"img_…","format":"dxf"}' -o logo.dxf

Every successful conversion returns three headers: X-Image-Token (use it to download other formats for free), X-Credits-Charged and X-Credits-Remaining.

Authentication

Send your key as a Bearer token: Authorization: Bearer svgmill_live_…. Live keys spend credits; test keys (svgmill_test_…) never do. Keys are shown once when you create them and stored only as a hash, so keep them somewhere safe and revoke any you think have leaked.

The website uses a browser session instead of a key. Both spend from the same balance.

Options and formats

FieldValuesWhat it does
imagefilePNG, JPG, WebP, GIF (first frame), BMP or TIFF, up to 30 MB and 16 megapixels. Or send image_url or image_base64 in a JSON body.
formatsvg pdf eps dxf pngThe file you get back. Default svg.
presetlogo bwColor logo and art (default), or one-color black and white.
colors2–64Caps the palette. Fewer colors give simpler shapes.
modeproduction preview testProduction costs 1 credit. Preview is free and returns a watermarked PNG. Test needs a test key.
tokenstringIn a JSON body, re-traces an earlier image with new options instead of uploading it again.

Test mode

Build your integration without spending credits. Create a test key on your account page and call the API as usual: conversions are free and the result carries a “SVGMILL TEST” watermark. Test mode returns SVG, or PNG with format=png. Downloads need a live key.

Without any key, mode=preview returns a free watermarked PNG and a token you can download later for 1 credit. Anonymous previews are limited to 20 an hour per IP address.

Errors

Errors always have the same shape, and a request that ends in an error uses no credit.

{ "error": { "code": "insufficient_credits", "message": "You have no credits left. Buy a pack or a plan to continue." } }
CodeStatusMeaning
invalid_request400A field is missing or out of range. The message says which.
unauthorized401No key or session, or the key was revoked.
insufficient_credits402No credits left.
forbidden403The key can’t do this, for example test mode with a live key.
account_frozen403The plan is frozen after a failed payment and there are no pack credits.
not_found404Unknown token, or its files are past the 30 days we keep them.
decode422The file isn’t a readable image.
too_large422Over 30 MB or 16 megapixels.
rate_limited429Too many requests. Wait for Retry-After seconds.
internal500Something failed on our side. Retry with the same Idempotency-Key.
timeout504The trace ran past its time limit. Try a smaller image or fewer colors.
out_of_memory507The image needs more memory than one job allows. Try a smaller image.

Rate limits

Each API key can make 60 requests a minute. Every response carries X-RateLimit-Limit, X-RateLimit-Remaining and X-RateLimit-Reset (Unix seconds). A 429 adds Retry-After.

Idempotency

Every POST accepts an Idempotency-Key header. Repeat a request with the same key within 24 hours and you get the stored response instead of a second charge. Use it whenever you retry after a timeout or network error.

Endpoint reference

Base URL https://svgmill.com. Generated from openapi.json (OpenAPI 3.1.0).

Vectorize

POST /v1/vectorize Optional: API key or browser session

Convert an image to a vector. production (default) costs 1 credit and returns the file. preview is free, works anonymously and returns a watermarked PNG whose token can be downloaded later for 1 credit. test is free, needs a test key and returns a watermarked result. A failed trace is never charged. Send a JSON token to re-trace an earlier image with new options (1 credit).

Multipart body

FieldTypeNotes
image requiredfile
modeproduction | preview | testDefault production.
presetlogo | bwDefault logo.
colorsinteger2–64.
formatsvg | pdf | eps | dxf | pngDefault svg.

JSON body

FieldTypeNotes
image_urlstring (uri)
image_base64stringRaw base64 or a data: URL.
tokenstringRe-trace an earlier image.
modeproduction | preview | testDefault production.
presetlogo | bwDefault logo.
colorsinteger2–64.
formatsvg | pdf | eps | dxf | pngDefault svg.

Responses

  • 200 The vector file (or the preview PNG). See X-Image-Token, X-Credits-Charged, X-Credits-Remaining.
  • 402 No credits
  • 403 Frozen plan and no pack credits, or test mode without a test key
  • 422 Not a readable image, or too large
  • 429 Rate limited

Accepts an Idempotency-Key header.

POST /v1/download API key or browser session

Download a format of an earlier trace. The first paid download of a preview token costs 1 credit. Every other format, and any later download of a paid token, is free.

JSON body

FieldTypeNotes
token requiredstring
formatsvg | pdf | eps | dxf | pngDefault svg.

Responses

  • 200 The file
  • 401 Not signed in
  • 402 No credits
  • 404 Unknown or expired token
  • 429 Rate limited

Accepts an Idempotency-Key header.

GET /v1/conversions API key or browser session

Conversion history. Newest first. Files are removed after 30 days; rows stay.

Parameters

NameInNotes
cursorquerynext_cursor from the previous page.
limitquery1–100, default 50.

Responses

  • 200 A page of conversions
  • 401 Not signed in
  • 429 Rate limited

Account

POST /v1/register No auth

Create an account. Sends a verification link. A known email gets a sign-in link instead. Always 202, so the response does not reveal which emails exist. Disposable domains get 422.

JSON body

FieldTypeNotes
email requiredstring (email)
return_tostringSame-origin page to return to after the link (web app).

Responses

  • 202 Link sent
  • 422 Disposable email domain
  • 429 Rate limited

Accepts an Idempotency-Key header.

GET /v1/verify No auth

Open an email link. Verifies the email, grants 5 signup credits on the first verification only, and starts a session. With a return_to from registration it redirects there (web app); otherwise it shows the first live API key once (JSON with Accept: application/json).

Parameters

NameInNotes
token requiredqueryThe token from the email link.

Responses

  • 200 Key page (HTML) or JSON
  • 302 Redirect to return_to (web app)
  • 400 Expired or used link
  • 429 Rate limited

POST /v1/login No auth

Send a sign-in link. Same flow as register. Existing accounts get no credits.

JSON body

FieldTypeNotes
email requiredstring (email)
return_tostringSame-origin page to return to after the link (web app).

Responses

  • 202 Link sent
  • 429 Rate limited

Accepts an Idempotency-Key header.

POST /v1/logout browser session

End the browser session.

Responses

  • 200 Signed out
  • 401 Not signed in
  • 429 Rate limited

Accepts an Idempotency-Key header.

GET /v1/account API key or browser session

Balance, grants, plan and usage.

Responses

  • 200 Account
  • 401 Not signed in
  • 429 Rate limited

DELETE /v1/account API key or browser session

Delete the account. Deletes the user, keys, sessions and stored files, and cancels any plan. Ledger rows are anonymised.

Responses

  • 200 Deleted
  • 401 Not signed in
  • 429 Rate limited

Keys

GET /v1/keys API key or browser session

List API keys.

Responses

  • 200 Active keys
  • 401 Not signed in
  • 429 Rate limited

POST /v1/keys API key or browser session

Create an API key. The secret is returned once and stored only as a SHA-256 hash.

JSON body

FieldTypeNotes
labelstring
testbooleanDefault false.

Responses

  • 201 The new key, with its secret
  • 401 Not signed in
  • 429 Rate limited

Accepts an Idempotency-Key header.

DELETE /v1/keys/{id} API key or browser session

Revoke an API key.

Parameters

NameInNotes
id requiredpath

Responses

  • 200 Revoked
  • 401 Not signed in
  • 429 Rate limited

Billing

GET /v1/plans No auth

Packs and plans.

Responses

  • 200 The catalogue
  • 429 Rate limited

POST /v1/checkout API key or browser session

Start a Stripe Checkout. Packs use a one-off payment, plans a subscription. Tax is calculated by Stripe.

JSON body

FieldTypeNotes
item requiredstring

Responses

  • 200 Checkout URL
  • 401 Not signed in
  • 409 Already on a plan (use /v1/subscription)
  • 429 Rate limited

Accepts an Idempotency-Key header.

GET /v1/purchases API key or browser session

Packs bought and invoices paid.

Responses

  • 200 Purchases
  • 401 Not signed in
  • 429 Rate limited

GET /v1/subscription API key or browser session

Current plan.

Responses

  • 200 Plan or null
  • 401 Not signed in
  • 429 Rate limited

POST /v1/subscription API key or browser session

Cancel, resume, change or reactivate the plan. cancel takes effect at the period end. change {item}: upgrades are immediate, billed pro rata, and the extra credits for the rest of this month are granted now; downgrades take effect at the period end. reactivate works only from inactive: it pays the outstanding invoice first, then returns a Checkout URL for a new subscription.

JSON body

FieldTypeNotes
action requiredcancel | resume | change | reactivate
itemstring

Responses

  • 200 Updated plan, or a URL to continue
  • 401 Not signed in
  • 402 Upgrade payment failed
  • 429 Rate limited

Accepts an Idempotency-Key header.

POST /v1/billing-portal API key or browser session

Stripe Customer Portal link.

Responses

  • 200 Portal URL
  • 401 Not signed in
  • 429 Rate limited

Accepts an Idempotency-Key header.