Send an offer
Resolves the audience (explicit contacts, a static list's members, and/or ad-hoc emails), snapshots each work's price, mints a per-recipient tokenized link, enqueues the sends, and flips the offer to `sending`. The dispatch worker delivers each email asynchronously.
Resolves the audience (explicit contacts, a static list's members, and/or ad-hoc emails), snapshots each work's price, mints a per-recipient tokenized link, enqueues the sends, and flips the offer to sending. The dispatch worker delivers each email asynchronously.
Authorization
bearerAuth offers:update, contacts:read, contacts:create, artworks:read, sales:read, gallery:readA gallery API key, sent as Authorization: Bearer gpk_… (or the x-api-key header).
In: header
Scope: offers:update, contacts:read, contacts:create, artworks:read, sales:read, gallery:read
Path Parameters
The offer id.
Query Parameters
Preview this operation without committing it. When true, the request is authenticated, scoped, and validated, but no side effect runs — no write, no idempotency claim, no audit event, no outbound delivery. The response is HTTP 200 with an X-Dry-Run: true header and a body of { "dry_run": true }, plus an effect object describing what the real call would change when this operation can resolve one.
Header Parameters
Optional. Send a unique key per logical operation to make retries safe: a retry with the same key replays the stored success for 14 days instead of re-running the write. Reusing a key with a different body returns 400.
Request Body
application/json
TypeScript Definitions
Use the request body type in TypeScript.
Resolve recipients and start sending an offer.
Response Body
application/json
application/json
application/problem+json
application/problem+json
application/problem+json
application/problem+json
application/problem+json
application/problem+json
{ "dry_run": true, "effect": { "summary": "string", "count": 0, "targets": [ { "type": "string", "id": "string", "label": "string" } ], "amount": { "minor": -9007199254740991, "currency": "str" }, "details": { "property1": "string", "property2": "string" }, "irreversible": true }}{ "id": "string", "title": "string", "subject": "string", "intro": "string", "template_id": "string", "status": "draft", "track_engagement": true, "scheduled_at": "string", "sent_at": "string", "cc_emails": [ "string" ], "bcc_emails": [ "string" ], "created_by": "string", "metadata": { "property1": "string", "property2": "string" }, "created_at": "string", "updated_at": "string", "items": [ { "offer_id": "string", "artwork_id": "string", "position": -9007199254740991, "caption_override": "string", "price_shown_cents": -9007199254740991, "currency": "string", "price_visible": true, "created_at": "string" } ], "recipients": [ { "id": "string", "offer_id": "string", "contact_id": "string", "email": "string", "expires_at": "string", "delivery_status": "pending", "sent_at": "string", "first_opened_at": "string", "last_activity_at": "string", "open_count": -9007199254740991, "click_count": -9007199254740991, "created_at": "string" } ]}{ "type": "../dictionary", "title": "string", "status": 0, "detail": "string", "code": "invalid_request", "retry": "permanent", "details": null}{ "type": "../dictionary", "title": "string", "status": 0, "detail": "string", "code": "invalid_request", "retry": "permanent", "details": null}{ "type": "../dictionary", "title": "string", "status": 0, "detail": "string", "code": "invalid_request", "retry": "permanent", "details": null}{ "type": "../dictionary", "title": "string", "status": 0, "detail": "string", "code": "invalid_request", "retry": "permanent", "details": null}{ "type": "../dictionary", "title": "string", "status": 0, "detail": "string", "code": "invalid_request", "retry": "permanent", "details": null}{ "type": "../dictionary", "title": "string", "status": 0, "detail": "string", "code": "invalid_request", "retry": "permanent", "details": null}List an offer's recommended recipients GET
Returns the contacts the recommendation engine would add to this offer: anyone whose stored match on one of the offer's works clears the visible floor, best first, with the works they matched and the strongest evidence item. Contacts already on the offer are omitted. Empty until the engine has judged the offer's works.
Suggest an offer subject line POST
Suggests an email subject line for an offer from its title, work count, and the gallery name. Read-shaped: it returns a suggestion and writes nothing (the sender edits it before saving). The model loop is server-only (the key never reaches the browser) with a deterministic template fallback; requires a first-party session.