Pincture API

Send one photo, get a finished series back — for your store, BarrioX menus or ZonaFranca X catalogs. Every request spends the credits of the key's account, exactly like the app.

Authentication

Create a key in Settings → API keys and send it as a bearer token.

curl https://pincture.com/api/v1/me -H "Authorization: Bearer pk_live_…"

Create a series

mode: product (platform amazon | shopify | etsy | ebay, 7 images), menu (BarrioX dish: card + square + story, style bright | rustic | moody | tropical | marble) or catalog (photo + spec sheet). By default it generates straight away using your answers; pass "ask_questions": true to get the clarifying questions first.

curl -X POST https://pincture.com/api/v1/projects \
  -H "Authorization: Bearer pk_live_…" -H "Content-Type: application/json" \
  -d '{
    "mode": "product",
    "platform": "amazon",
    "image_url": "https://example.com/photos/vase.jpg",
    "locale": "en",
    "answers": { "height": "28 cm", "material": "Ceramic", "benefit": "Handmade" },
    "external_ref": "sku-TV-028",
    "webhook_url": "https://your-app.com/hooks/pincture"
  }'

→ 201 { "id": "upsybits0p4acal5", "status": "analyzing" }

Get the result

Poll, or wait for the webhook. Image URLs are signed and valid for 90 days.

curl https://pincture.com/api/v1/projects/upsybits0p4acal5 -H "Authorization: Bearer pk_live_…"

{
  "id": "upsybits0p4acal5", "status": "done", "mode": "product", "platform": "amazon",
  "external_ref": "sku-TV-028",
  "cards": [
    { "scene": "main", "format": "main", "width": 2000, "height": 2000,
      "url": "https://pincture.com/f/…", "compliance": { "passed": true, "checks": [ … ] } },
    …
  ]
}

Status flow: analyzing → questions → generating → done (or failed). If you created it with ask_questions, answer with POST /api/v1/projects/:id and {"answers": {…}}.

Catalogs (ZonaFranca X)

Create the catalog in the app, then push up to 100 products per call. Wholesale fields go straight onto the spec sheet, the PDF and the Excel export.

curl -X POST https://pincture.com/api/v1/catalogs/CATALOG_ID/items \
  -H "Authorization: Bearer pk_live_…" -H "Content-Type: application/json" \
  -d '{
    "items": [{
      "image_url": "https://…/TV-028.jpg",
      "sku": "TV-028", "name": "Terracotta vase 28 cm",
      "unitPrice": "4.80", "currency": "USD", "moq": "200 pcs",
      "incoterms": "FOB Colón", "origin": "Panama", "hsCode": "6913.90",
      "unitsPerBox": "12", "boxDims": "60×40×35 cm", "boxWeight": "14 kg"
    }],
    "webhook_url": "https://zonafrancax.com/hooks/pincture"
  }'

Webhooks

When a series finishes we POST {"event":"project.completed","project":{…}} to your webhook_url. The body is signed with HMAC-SHA256 (base64url) in the X-Pincture-Signature header using your WEBHOOK_SECRET. Failed deliveries are retried with back-off.

import { createHmac } from "node:crypto";
const ok = createHmac("sha256", process.env.WEBHOOK_SECRET).update(rawBody).digest("base64url") === req.headers["x-pincture-signature"];

Server-wide integrations: set BARRIOX_WEBHOOK_URL to receive every finished menu dish, and ZONAFRANCAX_WEBHOOK_URL to receive items of published catalogs.

Errors

JSON {"error": "code"}: 401 unauthorized, 402 insufficient_credits (with needed and balance), 403 locked (feature needs the Studio pack), 404 not_found, 400 bad_request.