Beta

The Partner Trading API v1 is in beta — endpoints and response shapes may still change.

Developers
Cru World Wine
API v1 · REST & MCP
Your offers

Change an offer

Change the asking price or quantity of one listed line of your portfolio, or of a whole listing. A repriced line comes back with a new portfolio_id.

PATCH/offers/{code}LIVE
Required scopeoffers:writeAuthentication required

How this write runs

offer.update
Partner credentialCLIENT-KEY · CLIENT-SECRET Executes at once and answers 200. The body must carry a reference: send the identical request again after a timeout and Cru replays the first outcome instead of acting twice.
Connected appAuthorization: Bearer Answers 202 with a confirmation code and does nothing else. It runs only when the app calls POST /confirmations/{code} within 15 minutes, after the customer agrees.

Writes & confirmations, in full →

Path parameter

REQUIRED
codestringA listed line’s portfolio_id, from GET /offers, GET /portfolio or the offer a write answered with, to act on just that line’s units. A listing’s LISTING- code also works, for the whole listing. URL-encode it as a single path segment.

Request body

APPLICATION/JSON
FIELDDESCRIPTION
referencestring · 1–50 chars · partners: requiredYour idempotency key: letters and digits, then . _ : or - allowed. Required on a partner credential’s write and kept for good, so a retry with it can never act twice. Ignored for connected apps.
pricenumber · > 0 · optionalNew price per unit, in the market’s currency, as GET /offers and GET /portfolio quote it: pricing.listing_price. A supplier offer’s is converted into your offer feed’s currency.
quantityinteger · 1–1000 · optionalNew quantity. Send price, quantity or both.

Any other field is refused with VALIDATION_UNKNOWN_PARAMETER / 400.

Changed: offer is the wine, as GET /offers gives it

The offer a write answers with is no longer a listing: it is now the wine as GET /offers/{code} gives it, with only the lines the units written are on now. Each line has its portfolio_id, stock_type, pricing and warehouse in place of the listing’s code, held, price, proceeds and holding_ids. A write’s answer no longer carries a listing’s code — only a connected app’s PATCH preview names the listing it changes — so give a line’s portfolio_id to PATCH or DELETE /offers/{code} to change or remove its units.

Changed: a listing in another currency is relisted in yours

A listing priced in another currency is no longer refused with TRADE_REFUSED. Wine stored with Cru or held outside it is relisted in the market’s currency, as the Cru website does, even when only its quantity changes, at the price you read here. A connected app’s preview then says so, as in “It is listed in SGD now and will be listed in GBP.” A supplier offer stays in your offer feed’s currency: the price you send is converted into it, and a change of quantity alone keeps the feed’s price.

What a change does depends on where the wine is

Held outside Cru (external): a lower quantity deletes units, a higher one creates them. Stored with Cru: units come off or go on sale, up to what you hold in that warehouse. Supplier offers take a lasting override. BPO stock cannot be changed.

Change one line, or a whole listing

Given a listed line’s portfolio_id, only that line’s units change: the preview’s before and after quantities are the line’s, and its code the listing’s. A lower quantity takes units off that line alone. Repriced, the line gets a new portfolio_id, which the offer in the answer carries. Given a listing’s code, every line of the listing changes.

Response fields

200 OK · 202 Accepted

The wine as it now is, with only the lines the changed units are on — under a new portfolio_id if the price changed.

Executed 200

actionstring

The action that ran, such as bid.place.

statusstring

completed.

offerobject | null

The wine as GET /offers/{code} gives it, with only the lines the changed units are on now: a repriced line under its new portfolio_id.

Staged 202

confirmation.codestring

cnf_ and 43 more characters. A secret: the only handle on the instruction, valid for 15 minutes, once.

confirmation.actionstring

The action staged, such as bid.place.

confirmation.statusstring

pending.

confirmation.expires_atdatetime

RFC 3339 UTC.

confirmation.previewobject

summary, code (the listing’s LISTING- code), lwin18, wine_name, before and after — each price and quantity — and currency.

Errors

A body with neither price nor quantity returns VALIDATION_REQUIRED_FIELD / 422, naming price. A listing code that is not one of yours returns OFFER_NOT_FOUND / 404. A listing of BPO stock is TRADE_REFUSED / 422, with the message “BPO stock cannot be changed through the API.” So is a quantity below a supplier offer’s minimum, or, for wine stored with Cru, above what you have in that warehouse to list. If some of its units sell before the change is carried out, as between a connected app’s preview and its confirmation, the answer is PRICE_CHANGED / 409. A portfolio_id of a line that is not listed returns TRADE_REFUSED / 422, with the message “This portfolio line is not listed for sale.”, and one that is not yours or is out of date OFFER_NOT_FOUND / 404. Missing or invalid credentials return AUTH_INVALID_CREDENTIALS / 401. A credential without offers:write gets AUTH_INSUFFICIENT_SCOPE / 403. View all error codes →

UP NEXT Remove an offer

API credentials

Enter the client key and secret issued by Cru. They are kept for this browser tab’s session — a reload keeps them, closing the tab or clearing them ends them.

Credentials are never included in copied examples, and are redacted from anything the console prints back.

Request API access

Tell us who you are and what you want to build. Cru issues a client key and secret for your organisation, scoped to what you need.

Markets you trade in (choose one or more)

We use what you send here to reply about API access, and for nothing else. Cloudflare Turnstile checks the form for bots (privacy policy).