> ## Documentation Index
> Fetch the complete documentation index at: https://developers.readyforcommerce.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Changelog

> Every change to the Ready for Commerce API, newest first.

**2026-11-14**

A restore leaves out a taken slug and keeps the variants when none of the version's is left

### Restore a version

[Restore a version](https://developers.readyforcommerce.com/api-reference/core-restore-version.md) · `POST /api/v1/orgs/{orgId}/core/history/{versionId}/restore`

* A slug another product holds now no longer refuses the restore with `409`: the product keeps its own slug, the rest is restored, and `notRestored` answers it as `catalog.slug_taken` with its `slug`.
* A version none of whose variants the product still holds no longer refuses the restore with `422`: the product keeps its options and variants, the rest is restored, and `notRestored` answers each of the version's variants as `catalog.variant_deleted` with its `variantId`.

**2026-11-14**

A cost above the MAP or the MSRP is warned once

### Create a product

[Create a product](https://developers.readyforcommerce.com/api-reference/catalog-create-product.md) · `POST /api/v1/orgs/{orgId}/catalog/products`

* Its `warnings` no longer hold `catalog.map_below_cost` or `catalog.msrp_below_cost`: a cost above the MAP or the MSRP is warned once, as `catalog.cost_above_map` or `catalog.cost_above_msrp`.

### Update a product

[Update a product](https://developers.readyforcommerce.com/api-reference/catalog-update-product.md) · `PATCH /api/v1/orgs/{orgId}/catalog/products/{productId}`

* Its `warnings` no longer hold `catalog.map_below_cost` or `catalog.msrp_below_cost`: a cost above the MAP or the MSRP is warned once, as `catalog.cost_above_map` or `catalog.cost_above_msrp`.

### Update a product's prices

[Update a product's prices](https://developers.readyforcommerce.com/api-reference/catalog-update-product-prices.md) · `PATCH /api/v1/orgs/{orgId}/catalog/products/{productId}/prices`

* Its `warnings` no longer hold `catalog.map_below_cost` or `catalog.msrp_below_cost`: a cost above the MAP or the MSRP is warned once, as `catalog.cost_above_map` or `catalog.cost_above_msrp`.

### Set a product's status

[Set a product's status](https://developers.readyforcommerce.com/api-reference/catalog-set-product-status.md) · `PUT /api/v1/orgs/{orgId}/catalog/products/{productId}/status`

* Its `warnings` no longer hold `catalog.map_below_cost` or `catalog.msrp_below_cost`: a cost above the MAP or the MSRP is warned once, as `catalog.cost_above_map` or `catalog.cost_above_msrp`.

**2026-11-14**

Duplicate a product

### Duplicate a product

[Duplicate a product](https://developers.readyforcommerce.com/api-reference/catalog-duplicate-product.md) · `POST /api/v1/orgs/{orgId}/catalog/products/{productId}/duplicate`

* Copies a product as a new draft titled with (Copy), then (Copy 2) and so on, with its description, options and variants with their prices, costs, measures and stock settings, and answers `201` with the copy.
* The copy's variants hold no identifiers: no SKU, GTIN, ISBN, part number or custom code.
* Needs the permission to duplicate products, and honors an `Idempotency-Key`.

**2026-11-14**

Restore a product to an earlier version

### List a record's versions

[List a record's versions](https://developers.readyforcommerce.com/api-reference/core-list-versions.md) · `GET /api/v1/orgs/{orgId}/core/history`

* Lists a product's versions with `type=catalog.product` and the product's id: one when it is created, and one for each save of its content, prices or status that changes something, kept 30 days and up to 200.

### Restore a version

[Restore a version](https://developers.readyforcommerce.com/api-reference/core-restore-version.md) · `POST /api/v1/orgs/{orgId}/core/history/{versionId}/restore`

* Restores a product to one of its versions, with the `expectedVersion` it was read at, as one save of its content, prices, status, codes, measures, customs data and stock tracking; its on-hand and supplier stock stay as they are.
* Restoring other prices also needs the permission to edit prices, another status the one to set a product's status, and removing a variant added since the one to delete variants.
* Answers in `notRestored` what it leaves out: a variant deleted since, as `catalog.variant_deleted` with its `variantId`, and a SKU, GTIN or ISBN another product holds now, as `catalog.identifier_taken` with its `type` and `value`.

**2026-11-14**

Delete a product

### Delete a product

[Delete a product](https://developers.readyforcommerce.com/api-reference/catalog-delete-product.md) · `DELETE /api/v1/orgs/{orgId}/catalog/products/{productId}`

* Deletes a product for good with all its variants and answers `204`; its listings in every store are released, and it cannot be undone.
* Needs the permission to delete products.

**2026-11-14**

Set a product's status

### Set a product's status

[Set a product's status](https://developers.readyforcommerce.com/api-reference/catalog-set-product-status.md) · `PUT /api/v1/orgs/{orgId}/catalog/products/{productId}/status`

* Sets a product to `draft`, `active`, `unlisted` or `archived`, from any other, with the `expectedVersion` it was read at; a product saved since then answers `core.version_conflict`, and the status it already has changes nothing.
* Needs the permission to set a product's status, apart from the one to edit products.

**2026-11-14**

Set a product's description in HTML

### Create a product

[Create a product](https://developers.readyforcommerce.com/api-reference/catalog-create-product.md) · `POST /api/v1/orgs/{orgId}/catalog/products`

* Takes the product's `descriptionHtml`, its description in HTML. It keeps paragraphs, headings, lists and task lists, quotes, code blocks, images, tables, rules, line breaks, links, text styles, colour, highlight, alignment, and YouTube, Vimeo or video embeds; anything else, such as a script, an event attribute or another site's frame, is removed and its text kept, and a description left with nothing is saved as none.

### Update a product

[Update a product](https://developers.readyforcommerce.com/api-reference/catalog-update-product.md) · `PATCH /api/v1/orgs/{orgId}/catalog/products/{productId}`

* Takes the same `descriptionHtml`, kept when left out and cleared by `null`.

### Get a product

[Get a product](https://developers.readyforcommerce.com/api-reference/catalog-get-product.md) · `GET /api/v1/orgs/{orgId}/catalog/products/{productId}`

* Holds the product's `descriptionHtml` as it was saved, `null` when it has none.

### Update a product's prices

[Update a product's prices](https://developers.readyforcommerce.com/api-reference/catalog-update-product-prices.md) · `PATCH /api/v1/orgs/{orgId}/catalog/products/{productId}/prices`

* The answer holds the product's `descriptionHtml`, as getting a product reads it.

**2026-11-14**

Set a variant's weights, dimensions, customs data and stock tracking

### Create a product

[Create a product](https://developers.readyforcommerce.com/api-reference/catalog-create-product.md) · `POST /api/v1/orgs/{orgId}/catalog/products`

* Each variant takes its `productWeight`, `productLength`, `productWidth`, `productHeight`, `shippingWeight`, `shippingLength`, `shippingWidth` and `shippingHeight`, each a `value` with its `unit` (`g`, `kg`, `oz`, `lb` or `ct` for a weight, `mm`, `cm`, `in` or `yd` for a dimension); a `value` of 0 is saved as none, and one too small or too large to keep answers `422 catalog.measure_out_of_range`.
* Each variant takes its `countryOfOrigin`, a two-letter code in any case such as `mx`, saved as `MX` (`422 catalog.country_invalid` otherwise), and its `hsCode`, kept as its digits alone, such as `HS 8544.49.30-80` saved as `8544493080`, which must be 6 to 13 digits from 0 to 9 (`422 catalog.hs_code_invalid` otherwise).
* Each variant takes `trackInventory` and, when tracked, its `fallbackStock`, 0 when left out; a `fallbackStock` for an untracked variant answers `422 catalog.stock_untracked`.

### Update a product

[Update a product](https://developers.readyforcommerce.com/api-reference/catalog-update-product.md) · `PATCH /api/v1/orgs/{orgId}/catalog/products/{productId}`

* Each variant takes the same fields, each kept when left out and cleared by `null`, `trackInventory` aside, with the same four new codes; a variant no longer tracked has none of its three stocks.

### Get a product

[Get a product](https://developers.readyforcommerce.com/api-reference/catalog-get-product.md) · `GET /api/v1/orgs/{orgId}/catalog/products/{productId}`

* Each variant holds its eight measures in the unit each was given in, `null` where it has none, its `countryOfOrigin`, its `hsCode`, its `trackInventory` and its `onHandStock`, `supplierStock` and `fallbackStock`.

### Update a product's prices

[Update a product's prices](https://developers.readyforcommerce.com/api-reference/catalog-update-product-prices.md) · `PATCH /api/v1/orgs/{orgId}/catalog/products/{productId}/prices`

* Each variant of the answer holds its eight measures, its `countryOfOrigin`, its `hsCode`, its `trackInventory` and its three stocks, as getting a product reads them.

**2026-11-14**

Set a variant's prices and costs, checked by the price rules

### Update a product's prices

[Update a product's prices](https://developers.readyforcommerce.com/api-reference/catalog-update-product-prices.md) · `PATCH /api/v1/orgs/{orgId}/catalog/products/{productId}/prices`

* Changes the `price`, `compareAt`, `map`, `msrp`, `onHandCost`, `supplierCost` and `fallbackCost` of the variants it names by `id`, each a decimal string in the variant's currency such as `"19.99"`, `null` clearing it; a variant left out keeps its money. It needs the permission to edit prices, apart from the one to change a product's content, and the `expectedVersion` the product was read at.
* Refuses a compare-at price below the price (`422 catalog.compare_below_price`), a price below the cost, the on-hand cost or else the supplier's (`422 catalog.price_below_cost`), and a MAP above the MSRP (`422 catalog.map_above_msrp`), each only when the update changes one of its prices. Answers `422 catalog.price_invalid` for an amount that is no number or has more decimals than its currency, and `422 catalog.price_out_of_range` for one below 0 or too large.
* Answers `ProductSaved`, whose `warnings` name each other price rule the update leaves broken, such as `catalog.price_below_map`, and a price below a cost the update raised (`catalog.price_below_cost`).

### Create a product

[Create a product](https://developers.readyforcommerce.com/api-reference/catalog-create-product.md) · `POST /api/v1/orgs/{orgId}/catalog/products`

* Each variant takes the same seven amounts, which need the permission to edit prices (`403 core.forbidden` without it), and every price rule is checked: five new codes, and the price warnings.

### Update a product

[Update a product](https://developers.readyforcommerce.com/api-reference/catalog-update-product.md) · `PATCH /api/v1/orgs/{orgId}/catalog/products/{productId}`

* Each variant of the answer holds its `currency` and its seven amounts as decimal strings in it, `null` where it has none.

### Get a product

[Get a product](https://developers.readyforcommerce.com/api-reference/catalog-get-product.md) · `GET /api/v1/orgs/{orgId}/catalog/products/{productId}`

* Each variant holds its `currency` and its seven amounts as decimal strings in it, `null` where it has none.

**2026-11-14**

Get a SKU no variant of your organization holds

### Get a free SKU

[Get a free SKU](https://developers.readyforcommerce.com/api-reference/catalog-get-free-sku.md) · `GET /api/v1/orgs/{orgId}/catalog/products/free-sku`

* Answers `{ sku }`, a SKU no variant of the organization holds, three letters, three digits and three letters such as `KMT-472-BXR`, without the letters I, L and O or the digits 0 and 1. It is not reserved: give it to a variant when creating or updating a product, which answers `409 catalog.identifier_taken` if another variant took it first.

**2026-11-14**

Give each variant its SKU, GTIN, ISBN, part number and custom codes

### Create a product

[Create a product](https://developers.readyforcommerce.com/api-reference/catalog-create-product.md) · `POST /api/v1/orgs/{orgId}/catalog/products`

* Each variant takes `identifiers`, a list in order of `{ type, value }`, `type` one of `sku`, `gtin`, `isbn`, `mpn` (the part number) or `custom`, and a `label` for a custom code alone. Spaces are trimmed and collapsed; a GTIN or an ISBN is stored without spaces or hyphens, its check digit verified.
* Answers `ProductSaved`: the product, and `warnings`, a list of `{ code, params }`. `catalog.part_number_similar` warns when another product holds a part number that differs only in punctuation, such as hyphens or spaces, and never stops the save.
* Answers `422 catalog.identifier_invalid` with the variant, the code's place, its type and the reason; `422 catalog.identifier_repeated` for a variant's second SKU, a repeated code or a repeated custom label; and `409 catalog.identifier_taken` when another variant of the organization holds the SKU, GTIN or ISBN: three new codes.

### Update a product

[Update a product](https://developers.readyforcommerce.com/api-reference/catalog-update-product.md) · `PATCH /api/v1/orgs/{orgId}/catalog/products/{productId}`

* Each variant of `variants` takes `identifiers`, which replace its codes whole (`[]` removes them all); a variant that leaves them out keeps its own. A code moved from one variant to another in the same update passes.
* Answers `ProductSaved`, with the same `warnings`, and the same three new codes as creating a product.

### Get a product

[Get a product](https://developers.readyforcommerce.com/api-reference/catalog-get-product.md) · `GET /api/v1/orgs/{orgId}/catalog/products/{productId}`

* Each variant holds `identifiers`, each with its `type`, its stored `value` and its `label` (`null` but for a custom code), in their order.

**2026-11-14**

Add, rename and remove a product's options and variants when you update it

### Update a product

[Update a product](https://developers.readyforcommerce.com/api-reference/catalog-update-product.md) · `PATCH /api/v1/orgs/{orgId}/catalog/products/{productId}`

* Takes `options` and `variants`, each the whole list: send the ones you keep with their `id`, new ones without, and leave out the ones to remove. With `options` sent and `variants` left out, a variant holding a value you removed goes with it.
* Removing a variant also needs the permission to delete variants, `catalog.product.delete_variant`: without it the update answers `403 core.forbidden`.
* Answers `422 catalog.option_unknown` and `422 catalog.variant_unknown`, two new codes, when an `id` is not one of the product's, the same `422` codes as creating a product when the options and variants break its rules, and `403 core.usage_limit_reached` when new variants pass your plan's limit.

**2026-11-14**

Change a product's details, refused when someone saved it since you read it

### Update a product

[Update a product](https://developers.readyforcommerce.com/api-reference/catalog-update-product.md) · `PATCH /api/v1/orgs/{orgId}/catalog/products/{productId}`

* Changes a product's title, slug, condition, product type, meta title or meta description: a field left out stays as it is, and `null` clears the product type, the meta title or the meta description.
* Takes the `expectedVersion` the product was read at, and answers the product with its new `version`.
* Answers `409 core.version_conflict`, a new code, when the product was saved after you read it, and `409 catalog.slug_taken` when another product already uses the slug.

**2026-11-14**

List products, searched by title and filtered by status

### List products

[List products](https://developers.readyforcommerce.com/api-reference/catalog-list-products.md) · `GET /api/v1/orgs/{orgId}/catalog/products`

* Lists the organization's products page by page, the most recently changed first or by title, with each one's title, slug, status and number of variants.
* Searches the title and filters by status.

**2026-11-13**

Create a product with its variants and read it back

### Get a product

[Get a product](https://developers.readyforcommerce.com/api-reference/catalog-get-product.md) · `GET /api/v1/orgs/{orgId}/catalog/products/{productId}`

* Reads one product with its options, their values and its variants.

### Create a product

[Create a product](https://developers.readyforcommerce.com/api-reference/catalog-create-product.md) · `POST /api/v1/orgs/{orgId}/catalog/products`

* Creates a product with its options and its variants, each variant one combination of the option values.
* Refuses a product with no variant, a repeated option, value or combination, or more than 10 options, 250 values in an option or 2,000 variants, each with its own `422` code.
* Answers `409 catalog.slug_taken` when another product already uses the slug, and `403 core.usage_limit_reached` when the variants would pass the organization's free allowance.

**2026-11-13**

Two more 403 codes in every operation's errors

Each operation's error response now also lists `403 core.module_not_enabled`, when the organization
has not activated the module the operation belongs to, and `403 core.module_read_only`, when that
module is read-only for the organization, with `params.module` naming it. These operations could
already answer both codes.

Both codes join the error response of:

* [Get the calling credential](https://developers.readyforcommerce.com/api-reference/core-get-credential.md) · `GET /api/v1/credential`
* [Get the organization](https://developers.readyforcommerce.com/api-reference/core-get-org.md) · `GET /api/v1/orgs/{orgId}/core/org`
* [Update the organization](https://developers.readyforcommerce.com/api-reference/core-update-org.md) · `PATCH /api/v1/orgs/{orgId}/core/org`
* [Get the billing summary](https://developers.readyforcommerce.com/api-reference/core-get-billing.md) · `GET /api/v1/orgs/{orgId}/core/billing`
* [Get this month's usage](https://developers.readyforcommerce.com/api-reference/core-get-billing-usage.md) · `GET /api/v1/orgs/{orgId}/core/billing/usage`
* [List record types](https://developers.readyforcommerce.com/api-reference/core-list-dataio-adapters.md) · `GET /api/v1/orgs/{orgId}/core/dataio/adapters`
* [Get a record type](https://developers.readyforcommerce.com/api-reference/core-get-dataio-adapter.md) · `GET /api/v1/orgs/{orgId}/core/dataio/adapters/{entity}`
* [List imports](https://developers.readyforcommerce.com/api-reference/core-list-imports.md) · `GET /api/v1/orgs/{orgId}/core/imports`
* [Complete an upload](https://developers.readyforcommerce.com/api-reference/core-complete-import-upload.md) · `POST /api/v1/orgs/{orgId}/core/imports/uploads/{fileId}/complete`
* [Write an import's results](https://developers.readyforcommerce.com/api-reference/core-start-import-results.md) · `POST /api/v1/orgs/{orgId}/core/imports/{jobId}/results`
* [Get a file's status](https://developers.readyforcommerce.com/api-reference/core-get-file.md) · `GET /api/v1/orgs/{orgId}/core/files/{fileId}`
* [List exports](https://developers.readyforcommerce.com/api-reference/core-list-exports.md) · `GET /api/v1/orgs/{orgId}/core/exports`
* [Rename an export](https://developers.readyforcommerce.com/api-reference/core-rename-export.md) · `PATCH /api/v1/orgs/{orgId}/core/exports/{jobId}`
* [List export templates](https://developers.readyforcommerce.com/api-reference/core-list-export-templates.md) · `GET /api/v1/orgs/{orgId}/core/exports/templates`
* [Create an export template](https://developers.readyforcommerce.com/api-reference/core-create-export-template.md) · `POST /api/v1/orgs/{orgId}/core/exports/templates`
* [Update an export template](https://developers.readyforcommerce.com/api-reference/core-update-export-template.md) · `PATCH /api/v1/orgs/{orgId}/core/exports/templates/{templateId}`
* [Delete an export template](https://developers.readyforcommerce.com/api-reference/core-delete-export-template.md) · `DELETE /api/v1/orgs/{orgId}/core/exports/templates/{templateId}`
* [Get a job](https://developers.readyforcommerce.com/api-reference/core-get-job.md) · `GET /api/v1/orgs/{orgId}/core/jobs/{jobId}`
* [List a job's messages](https://developers.readyforcommerce.com/api-reference/core-list-job-messages.md) · `GET /api/v1/orgs/{orgId}/core/jobs/{jobId}/messages`
* [Get a job's file link](https://developers.readyforcommerce.com/api-reference/core-get-job-file.md) · `GET /api/v1/orgs/{orgId}/core/jobs/{jobId}/files/{file}`
* [Cancel a job](https://developers.readyforcommerce.com/api-reference/core-cancel-job.md) · `POST /api/v1/orgs/{orgId}/core/jobs/{jobId}/cancel`
* [Search records](https://developers.readyforcommerce.com/api-reference/core-search.md) · `GET /api/v1/orgs/{orgId}/core/search`
* [List a record's versions](https://developers.readyforcommerce.com/api-reference/core-list-versions.md) · `GET /api/v1/orgs/{orgId}/core/history`
* [Compare a version](https://developers.readyforcommerce.com/api-reference/core-get-version.md) · `GET /api/v1/orgs/{orgId}/core/history/{versionId}`
* [Restore a version](https://developers.readyforcommerce.com/api-reference/core-restore-version.md) · `POST /api/v1/orgs/{orgId}/core/history/{versionId}/restore`
* [List incidents](https://developers.readyforcommerce.com/api-reference/core-list-incidents.md) · `GET /api/v1/orgs/{orgId}/core/incidents`
* [Mark an incident read or unread](https://developers.readyforcommerce.com/api-reference/core-mark-incident.md) · `PUT /api/v1/orgs/{orgId}/core/incidents/{incidentId}/read`
* [Resolve an incident](https://developers.readyforcommerce.com/api-reference/core-resolve-incident.md) · `POST /api/v1/orgs/{orgId}/core/incidents/{incidentId}/resolve`
* [List notifications](https://developers.readyforcommerce.com/api-reference/core-list-notifications.md) · `GET /api/v1/orgs/{orgId}/core/notifications`
* [Mark a notification read or unread](https://developers.readyforcommerce.com/api-reference/core-mark-notification.md) · `PUT /api/v1/orgs/{orgId}/core/notifications/{notificationId}/read`
* [Mark all read](https://developers.readyforcommerce.com/api-reference/core-mark-all-notifications-read.md) · `POST /api/v1/orgs/{orgId}/core/notifications/read`
* [List saved views](https://developers.readyforcommerce.com/api-reference/core-list-views.md) · `GET /api/v1/orgs/{orgId}/core/views`
* [Create a saved view](https://developers.readyforcommerce.com/api-reference/core-create-view.md) · `POST /api/v1/orgs/{orgId}/core/views`
* [Set a table's default view](https://developers.readyforcommerce.com/api-reference/core-set-default-view.md) · `PUT /api/v1/orgs/{orgId}/core/views/default`
* [Update a saved view](https://developers.readyforcommerce.com/api-reference/core-update-view.md) · `PATCH /api/v1/orgs/{orgId}/core/views/{viewId}`
* [Delete a saved view](https://developers.readyforcommerce.com/api-reference/core-delete-view.md) · `DELETE /api/v1/orgs/{orgId}/core/views/{viewId}`
* [List store connections](https://developers.readyforcommerce.com/api-reference/integrations-list-connections.md) · `GET /api/v1/orgs/{orgId}/integrations/connections`
* [Connect a store](https://developers.readyforcommerce.com/api-reference/integrations-connect-store.md) · `POST /api/v1/orgs/{orgId}/integrations/connections`
* [Reconnect a store](https://developers.readyforcommerce.com/api-reference/integrations-reconnect-store.md) · `PUT /api/v1/orgs/{orgId}/integrations/connections/{connectionId}/credentials`
* [Disconnect a store](https://developers.readyforcommerce.com/api-reference/integrations-disconnect-store.md) · `DELETE /api/v1/orgs/{orgId}/integrations/connections/{connectionId}`

`core.module_read_only` joins the error response of this operation, which already listed
`core.module_not_enabled`:

* [Start an export](https://developers.readyforcommerce.com/api-reference/core-start-export.md) · `POST /api/v1/orgs/{orgId}/core/exports`

**2026-11-13**

The developer site opens

The developer site opens with the [API reference](https://developers.readyforcommerce.com/api-reference/introduction.md) and this changelog,
in English and Spanish. Every operation is in beta until launch, so it may still change: each
change is listed here, with the operations it touches.


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.