Catalog Endpoints

Generate and download a copy of retailer's inventory

Endpoints

MethodEndpointDescription
POST/accounts/{accountId}/catalogsCreate a catalog request to generate a new catalog for Brand account
POST/accounts/{accountId}/catalogs/sellersCreate a catalog request to generate a new catalog for Seller account
POST/accounts/{accountId}/brand-catalog-exportCreate a request to export existing catalogs from a Brand account
POST/accounts/{accountId}/seller-catalog-exportCreate a request to export existing catalogs from a Seller account
GET/catalogs/{catalogId}/statusRetrieve the status of a specific catalog request.
GET/catalogs/{catalogId}/outputDownload the output of a specific catalog once it's ready.

Attributes

Catalog Creation Request Attributes

Brand accounts

Attribute

Data Type

Description

format

enum

Format of the catalog data returned.

Accepted values: json-newline
Default: json-newline
Writeable? N / Nullable? Y

brandIdFilter

list<string>

Brand ID(s) used to filter down catalog results based on specified brands.

Accepted values: list of string or int64
Writeable? N / Nullable? N

retailerIdFilter

list<string>

Retailer ID(s) used to filter catalog results based on specified retailers. If not specified, all retailers are included.

Accepted values: list of int64
Writeable? N / Nullable? Y

modifiedAfter

timestamp

Includes only SKUs modified after the specified time. Must be within the last 18 hours; otherwise, a full export is required.

Format: yyyy-mm-ddThh:mm:ss±hh:mm (ISO-8601)
Writeable? N / Nullable? Y

includeFields

list<string>

Optional fields to include in the export. If not provided, those fields will return with null values.

Accepted values: RetailerName, Description, BrandName, GoogleCategory, Category, ImageUrl
Writeable? N / Nullable? Y


Seller accounts

Attribute

Data Type

Description

sellers

list<object>

List of required seller pairs retailerId and sellerId associated with the catalog to be generated


Parameters:

  • retailerId: Retailer ID, generated internally by Criteo
  • sellerId: Seller ID in the respective retailer's catalog, used to filter down catalog products

Writeable? N / Nullable? N

modifiedAfter

timestamp

Includes only SKUs modified after the specified time. Must be within the last 18 hours; otherwise, a full export is required.


Format: yyyy-mm-ddThh:mm:ss±hh:mm (ISO-8601)
Writeable? N / Nullable? Y

includeFields

list<string>

Optional fields to include in the export. If not provided, those fields will return with null values.


Accepted values: RetailerName, Description, BrandName, GoogleCategory, Category, ImageUrl
Writeable? N / Nullable? Y


Catalog Status Response Attributes

Attribute

Data Type

Description

id

string

ID of the catalog creation request, to be used to retrieve its status and output (using other endpoints below - async)

Accepted values: string of int64
Writeable? N / Nullable? N

status

enum

Possible status of respective catalog creation

Accepted values: pending, success, failure, expired, unknown Default: pending
Writeable? N / Nullable? N

currency

enum

Currency of the products in the catalog

Accepted values: 3-chars currency code (in ISO-4217 ; e.g. USD, EUR)
Writeable? N / Nullable? Y

rowCount

integer

Number of products available in the catalog (available when reach success status)

Accepted values: int32
Writeable? N / Nullable? Y

fileSizeBytes

integer

File size of catalog, in bytes (available when reach success status)

Accepted values: int32
Writeable? N / Nullable? Y

md5Checksum

string

MD5 checksum of catalog's content (available when reach success status)

Accepted values: 32-char alpha-numeric strings
Writeable? N / Nullable? Y

createdAt

timestamp

Timestamp of catalog creation, in UTC

Accepted values: yyyy-mm-ddThh:mm:ss±hh:mm(in ISO-8601)
Writeable? N / Nullable? N

message

string

Optional informative message, for developer consumption

Accepted values: string
Writeable? N / Nullable? Y

📘

Field Definitions

  • Writeable (Y/N): Indicates if the field can be modified in requests.
  • Nullable (Y/N): Indicates if the field can accept null/empty values.
  • Primary Key: A unique, immutable identifier of the entity, generated internally by Criteo. Primary keys are typically ID fields (e.g., retailerId, campaignId, lineItemId) and are usually required in the URL path.

Catalog Output Response Attributes

Attribute

Data Type

Description

id

string

Product ID, defined by the retailer.


Accepted values: up to 500 characters
Writeable? N / Nullable? N

name

string

Product name, defined by the retailer.


Accepted values: up to 1000 characters
Writeable? N / Nullable? N

description

string

Product description, defined by the retailer.


Accepted values: up to 5000 characters
Writeable? N / Nullable? Y

category

string

Product category, defined by the retailer.


Accepted values: up to 1000 characters
Writeable? N / Nullable? Y

categoryId

string

Category ID associated with the product, derived from the retailer catalog.


Writeable? N / Nullable? Y

googleCategory

string

Category associated with the product, derived from the Google Product Taxonomy.


Writeable? N / Nullable? Y

brandId

string

Brand ID of the product.


For brand accounts, it is derived from the Universal Catalog. For retailer accounts, it is derived from the Retailer Catalog.


Writeable? N / Nullable? N

brandName

string

Brand name of the product; brands are standardized across retailers.


Accepted values: up to 120 characters
Writeable? N / Nullable? Y

sellerId

string

Seller ID(s) in the respective retailer’s catalog, used to filter down catalog items.


Writeable? N / Nullable? Y

sellerName

string

Name of the seller associated with the sellerId.


Writeable? N / Nullable? Y

retailerId

string

Retailer ID that contains the product offer.


Accepted values: string of int64
Writeable? N / Nullable? N

retailerName

string

Name of the retailer that contains the product offer.


Accepted values: up to 100 characters
Writeable? N / Nullable? N

price

decimal

Current product price in the respective retailer.


Accepted values: ≥ 0.0
Writeable? N / Nullable? Y

isInStock

boolean

Flag indicating if the product is currently in stock.


Accepted values: true, false
Writeable? N / Nullable? N

minBid

decimal

Minimum CPC (Cost-Per-Click) bid required for the product, as set by the retailer.


Any Line Item with this product must have its targetBid meet this value.
Accepted values: > 0.0
Writeable? N / Nullable? Y

gtin

string

Global Trade Item Number (GTIN), if available. Also known as EAN or UPC.


Accepted values: up to 14 digits
Writeable? N / Nullable? Y

mpn

string

Manufacturer Part Number (MPN), if available.


Accepted values: up to 70 characters
Writeable? N / Nullable? Y

imageUrl

string

HTTP URL of the product image, as provided by the retailer.


Writeable? N / Nullable? N

updatedAt

timestamp

Timestamp of the last product update, in UTC.


Format: yyyy-mm-ddThh:mm:ss±hh:mm (ISO-8601)
Writeable? N / Nullable? N

📘

Field Definitions

  • Writeable (Y/N): Indicates if the field can be modified in requests.
  • Nullable (Y/N): Indicates if the field can accept null/empty values.
  • Primary Key: A unique, immutable identifier of the entity, generated internally by Criteo. Primary keys are typically ID fields (e.g., retailerId, campaignId, lineItemId) and are usually required in the URL path.
📘

Catalog Asynchronous Workflow: Step 1 of 3

  1. Create a request for the latest catalog of the specified account using the appropriate endpoint.
  2. This action generates a catalogId that represents the account's catalog.
  3. Catalog requests are cached for 1 hour, meaning repeated requests within this timeframe will return the same catalogId and output.

Create a Catalog Request for Brand account

This endpoint creates a request for the latest available catalog for a specific account

https://api.criteo.com/{version}/retail-media/accounts/{accountId}/catalogs
💭

Best Practice Tip!

To speed up catalog downloads, you can narrow down the results by using the brandIdFilter body parameter. This allows you to filter the catalog by specific brands, helping to return results faster.

Sample Request

curl -L -X POST 'https://api.criteo.com/{version}/retail-media/accounts/18446744073709551616/catalogs' \
-H 'Content-Type: application/json' \
-H 'Accept: application/json' \
-H 'Authorization: Bearer <MY_ACCESS_TOKEN>' \
--data-raw '{
  "data": {
    "type": "RetailMediaCatalogStatus",
    "attributes": {
      "format": "json-newline",
      "brandIdFilter": [
        "40115",
        "9092"
      ]
    }
  }
}'
import requests
import json

url = "https://api.criteo.com/{version}/retail-media/accounts/18446744073709551616/catalogs"

payload = json.dumps({
  "data": {
    "type": "RetailMediaCatalogStatus",
    "attributes": {
      "format": "json-newline",
      "brandIdFilter": [
        "4768"
      ]
    }
  }
})
headers = {
  'Content-Type': 'application/json',
  'Accept': 'application/json',
  'Authorization': 'Bearer <MY_ACCESS_TOKEN>'
}

response = requests.request("POST", url, headers=headers, data=payload)

print(response.text)
OkHttpClient client = new OkHttpClient().newBuilder()
  .build();

MediaType mediaType = MediaType.parse("application/json");

RequestBody body = RequestBody.create(mediaType, "{\n  \"data\": {\n    \"type\": \"RetailMediaCatalogStatus\",\n    \"attributes\": {\n      \"format\": \"json-newline\",\n      \"brandIdFilter\": [\n        \"4768\"\n      ]\n    }\n  }\n}");

Request request = new Request.Builder()
  .url("https://api.criteo.com/{version}/retail-media/accounts/18446744073709551616/catalogs")
  .method("POST", body)
  .addHeader("Content-Type", "application/json")
  .addHeader("Accept", "application/json")
  .addHeader("Authorization", "Bearer <MY_ACCESS_TOKEN>")
  .build();

Response response = client.newCall(request).execute();
<?php
require_once 'HTTP/Request2.php';
$request = new HTTP_Request2();
$request->setUrl('https://api.criteo.com/{version}/retail-media/accounts/18446744073709551616/catalogs');
$request->setMethod(HTTP_Request2::METHOD_POST);
$request->setConfig(array(
  'follow_redirects' => TRUE
));

$request->setHeader(array(
  'Content-Type' => 'application/json',
  'Accept' => 'application/json',
  'Authorization' => 'Bearer <MY_ACCESS_TOKEN>'
));

$request->setBody('{\n  "data": {\n    "type": "RetailMediaCatalogStatus",\n    "attributes": {\n      "format": "json-newline",\n      "brandIdFilter": [\n        "4768"\n      ]\n    }\n  }\n}');
try {
  $response = $request->send();
  if ($response->getStatus() == 200) {
    echo $response->getBody();
  }
  
  else {
    echo 'Unexpected HTTP status: ' . $response->getStatus() . ' ' .
    $response->getReasonPhrase();
  }
}

catch(HTTP_Request2_Exception $e) {
  echo 'Error: ' . $e->getMessage();
}

Sample Response

{
    "data": {
        "id": "1122850670915847014",
        "type": "RetailMediaCatalogStatus",
        "attributes": {
            "status": "pending",
            "currency": null,
            "rowCount": null,
            "fileSizeBytes": null,
            "md5Checksum": null,
            "createdAt": "2024-04-06T05:11:41.351+00:00",
            "message": null
        }
    }
}
📘

Catalog Asynchronous Workflow: Step 2 of 3

After generating a catalogId, use it to poll the catalog status endpoint to check the progress. Continue polling until the catalog is successfully created and ready for download.


Create a Catalog Request for Seller account

This endpoint creates catalog for a particular Seller account:

https://api.criteo.com/{version}/retail-media/accounts/{accountId}/catalogs/sellers

Sample Request

curl --location 'https://api.criteo.com/{version}/retail-media/accounts/18446744073709551616/catalogs/sellers' \
--header 'Content-Type: application/json' \
--header 'Accept: text/plain' \
--header 'Authorization: Bearer <TOKEN>' \
--data '{
  "data": {
    "type": "RetailMediaCatalogStatus",
    "attributes": {
      "sellers": [
        {
          "retailerId": "123",
          "sellerId": "60axxxxxxxxxxxxxxxx"
        }
      ]
    }
  }
}'
import requests
import json

url = "https://api.criteo.com/{version}/retail-media/accounts/18446744073709551616/catalogs/sellers"

payload = json.dumps({
  "data": {
    "type": "RetailMediaCatalogStatus",
    "attributes": {
      "sellers": [
        {
          "retailerId": "123",
          "sellerId": "60axxxxxxxxxxxxxxxx"
        }
      ]
    }
  }
})
headers = {
  'Content-Type': 'application/json',
  'Accept': 'application/json',
  'Authorization': 'Bearer <MY_ACCESS_TOKEN>'
}

response = requests.request("POST", url, headers=headers, data=payload)

print(response.text)
OkHttpClient client = new OkHttpClient().newBuilder()
  .build();

MediaType mediaType = MediaType.parse("application/json");

RequestBody body = RequestBody.create(mediaType, "{\n  \"data\": {\n    \"type\": \"RetailMediaCatalogStatus\",\n    \"attributes\": {\n      \"sellers\": [\n        {\n          \"retailerId\": \"123\",\n          \"sellerId\": \"60axxxxxxxxxxxxxxxx\"\n        }\n      ]\n    }\n  }\n}");

Request request = new Request.Builder()
  .url("https://api.criteo.com/{version}/retail-media/accounts/18446744073709551616/catalogs/sellers")
  .method("POST", body)
  .addHeader("Content-Type", "application/json")
  .addHeader("Accept", "application/json")
  .addHeader("Authorization", "Bearer <MY_ACCESS_TOKEN>")
  .build();

Response response = client.newCall(request).execute();
<?php
require_once 'HTTP/Request2.php';
$request = new HTTP_Request2();
$request->setUrl('https://api.criteo.com/{version}/retail-media/accounts/18446744073709551616/catalogs/sellers');
$request->setMethod(HTTP_Request2::METHOD_POST);
$request->setConfig(array(
  'follow_redirects' => TRUE
));

$request->setHeader(array(
  'Content-Type' => 'application/json',
  'Accept' => 'application/json',
  'Authorization' => 'Bearer <MY_ACCESS_TOKEN>'
));

$request->setBody('{\n  "data": {\n    "type": "RetailMediaCatalogStatus",\n    "attributes": {\n      "sellers": [\n        {\n          "retailerId": "123",\n          "sellerId": "60axxxxxxxxxxxxxxxx"\n        }\n      ]\n    }\n  }\n}');
try {
  $response = $request->send();
  if ($response->getStatus() == 200) {
    echo $response->getBody();
  }
  
  else {
    echo 'Unexpected HTTP status: ' . $response->getStatus() . ' ' .
    $response->getReasonPhrase();
  }
}

catch(HTTP_Request2_Exception $e) {
  echo 'Error: ' . $e->getMessage();
}

Sample Response

{
    "data": {
        "id": "1122850670915847014",
        "type": "RetailMediaCatalogStatus",
        "attributes": {
            "status": "success",
            "currency": "USD",
            "rowCount": 369318,
            "fileSizeBytes": 216634050,
            "md5Checksum": "713f2d3c0ed718125a1acdef05224df5",
            "createdAt": "2025-01-17T22:45:11.44+00:00",
            "message": null
        }
    }
}

Get Status of a Specific Catalog

This endpoint retrieves the status of a specific catalog. Status can be pending, success, failure, or expired

https://api.criteo.com/{version}/retail-media/catalogs/{catalogId}/status

Sample Request

curl -X GET "https://api.criteo.com/{version}/retail-media/catalogs/1122850670915847014/status" \
    -H "Authorization: Bearer <MY_ACCESS_TOKEN>"
import requests

url = "https://api.criteo.com/{version}/retail-media/catalogs/357957813719011328/status"

payload={}
headers = {
  'Accept': 'application/json',
  'Authorization': 'Bearer <MY_ACCESS_TOKEN>'
}

response = requests.request("GET", url, headers=headers, data=payload)

print(response.text)
OkHttpClient client = new OkHttpClient().newBuilder()
  .build();

MediaType mediaType = MediaType.parse("text/plain");

RequestBody body = RequestBody.create(mediaType, "");

Request request = new Request.Builder()
  .url("https://api.criteo.com/{version}/retail-media/catalogs/357957813719011328/status")
  .method("GET", body)
  .addHeader("Accept", "application/json")
  .addHeader("Authorization", "Bearer <MY_ACCESS_TOKEN>")
  .build();

Response response = client.newCall(request).execute();
<?php
require_once 'HTTP/Request2.php';
$request = new HTTP_Request2();
$request->setUrl('https://api.criteo.com/{version}/retail-media/catalogs/357957813719011328/status');
$request->setMethod(HTTP_Request2::METHOD_GET);
$request->setConfig(array(
  'follow_redirects' => TRUE
));
$request->setHeader(array(
  'Accept' => 'application/json',
  'Authorization' => 'Bearer <MY_ACCESS_TOKEN>'
));

try {
  $response = $request->send();
  if ($response->getStatus() == 200) {
    echo $response->getBody();
  }
  
  else {
    echo 'Unexpected HTTP status: ' . $response->getStatus() . ' ' .
    $response->getReasonPhrase();
  }
}

catch(HTTP_Request2_Exception $e) {
  echo 'Error: ' . $e->getMessage();
}

Sample Response

{
    "data": {
        "id": "1122850670915847014",
        "type": "RetailMediaCatalogStatus",
        "attributes": {
            "status": "success",
            "currency": "USD",
            "rowCount": 1001,
            "fileSizeBytes": 353293,
            "md5Checksum": "2c15b77740028435ca476823df7fb4f8",
            "createdAt": "2020-04-06T05:11:41.351+00:00",
            "message": null
        }
    }
}
📘

Catalog Asynchronous Workflow: Step 3 of 3

Once the catalog is successfully created, use the catalog output endpoint to download the collection of catalog products. Note that catalog outputs are typically available for 72 hours before they expire, so be sure to download them within this time frame.


Download Output of a Specific Catalog

This endpoint returns the products in a specific catalog as a newline-delimited JSON byte stream

https://api.criteo.com/{version}/retail-media/catalogs/{catalogId}/output

Sample Request

curl -X GET "https://api.criteo.com/{version}/retail-media/catalogs/1122850670915847014/output" \
    -H "Authorization: Bearer <MY_ACCESS_TOKEN>"
import http.client

conn = http.client.HTTPSConnection("api.criteo.com")
payload = ''
headers = {
  'Accept': 'application/x-json-stream',
  'Authorization': 'Bearer <MY_ACCESS_TOKEN>'
}
conn.request("GET", "/{version}/retail-media/catalogs/357957813719011328/output", payload, headers)
res = conn.getresponse()
data = res.read()
print(data.decode("utf-8"))
OkHttpClient client = new OkHttpClient().newBuilder()
  .build();

MediaType mediaType = MediaType.parse("text/plain");

RequestBody body = RequestBody.create(mediaType, "");

Request request = new Request.Builder()
  .url("https://api.criteo.com/{version}/retail-media/catalogs/357957813719011328/output")
  .method("GET", body)
  .addHeader("Accept", "application/x-json-stream")
  .addHeader("Authorization", "Bearer <MY_ACCESS_TOKEN>")
  .build();

Response response = client.newCall(request).execute();
<?php
require_once 'HTTP/Request2.php';
$request = new HTTP_Request2();
$request->setUrl('https://api.criteo.com/{version}/retail-media/catalogs/357957813719011328/output');
$request->setMethod(HTTP_Request2::METHOD_GET);
$request->setConfig(array(
  'follow_redirects' => TRUE
));
$request->setHeader(array(
  'Accept' => 'application/x-json-stream',
  'Authorization' => 'Bearer <MY_ACCESS_TOKEN>'
));

try {
  $response = $request->send();
  if ($response->getStatus() == 200) {
    echo $response->getBody();
  }
  
  else {
    echo 'Unexpected HTTP status: ' . $response->getStatus() . ' ' .
    $response->getReasonPhrase();
  }
}

catch(HTTP_Request2_Exception $e) {
  echo 'Error: ' . $e->getMessage();
}

Sample Response - Brand Catalog

{ \
    "id": "sku1", \
    "name": "Product One", \
    "category": "category1", \
    "brandId": "7672171780147256541", \
    "brandName": "Brand 123", \
    "retailerId": "3239117063738827231", \
    "retailerName": "Retailer 123", \
    "price": 1.00, \
    "isInStock": true, \
    "minBid": 0.30, \
    "gtin": "abc123", \
    "mpn": "789xyz", \
    "imageUrl": "/image1.jpg", \
    "updatedAt": "2020-04-06T02:23:07Z" \
}
 
// ... newline-delimited, no comma
 
{ \
    "id": "product-1001", \
    "name": "Product One Thousand and One", \
    "category": "category2", \
    "brandId": "7672171780147256541", \
    "brandName": "Brand 123", \
    "retailerId": "18159942378514859684", \
    "retailerName": "Retailer 789", \
    "price": 5.00, \
    "isInStock": false, \
    "minBid": 0.45, \
    "gtin": "none", \
    "mpn": "none", \
    "imageUrl": "/image1001.jpg", \
    "updatedAt": "2020-04-06T01:07:23Z" \
}

Sample Response - Seller Catalog

{ \
    "id": "86833674", \
    "name": "Flat Front Short 46 x 10.5\" - Black", \
    "category": "clothing, shoes & accessories|men’s clothing|bottoms|shorts", \
    "categoryId": "3051218", \
    "brandId": "40095", \
    "brandName": "Test Brand", \
    "retailerId": "131", \
    "retailerName": "Retailer Name", \
    "price": 39.99, \
    "isInStock": true, \
    "minBid": 0.4000, \
    "gtin": "1234567890", \
    "mpn": null, \
    "imageUrl": "https://example.com/is/image/a610-881aa9a71c93", \
    "updatedAt": "2024-07-25T19:52:30Z", \
    "sellerId": "60axxxxxxxxxxxxxxxx", \
    "sellerName": "Test Seller" \
}
 
// ... newline-delimited, no comma
 
{ \
    "id": "86833235", \
    "name": "Pleated Front Short 52 x 10.5\" - String", \
    "category": "clothing, shoes & accessories|men’s clothing|bottoms|shorts", \
    "categoryId": "3051218", \
    "brandId": "40095", \
    "brandName": "Test Brand", \
    "retailerId": "131", \
    "retailerName": "Retailer Name", \
    "price": 39.99, \
    "isInStock": true, \
    "minBid": 0.4000, \
    "gtin": "1234567890", \
    "mpn": null, \
    "imageUrl": "https://example.com/is/image/a610-881aa9a71c93", \
    "updatedAt": "2024-07-25T19:52:30Z", \
    "sellerId": "60axxxxxxxxxxxxxxxx", \
    "sellerName": "Test Seller" \
}

Responses

Response

Description

🟢

200

Success

🔴

400

The indicated catalog is not available for retrieval, wait for a success status

🔴

403

API user does not have the authorization to make requests to the account ID. For an authorization request, follow the

authorization request

steps


Export Catalog of a Specific Account

Brand account

This endpoint allows you to generate the most up-to-date catalog for a specific brand account.

https://api.criteo.com/{version}/retail-media/accounts/{accountId}/brand-catalog-export
💭

Best Practice Tip!

If you wish to filter SKUs modified within the last 18 hours, you can use modifiedAfter field. The request should be formatted according to ISO 8601 standards. Although the example provided uses Eastern Standard Time (EST), you can specify any time zone.

Important: If the specified time exceeds the 18-hour limit, the request will return a 400 response, advising you to perform a full catalog export instead.

Sample Request

curl -L -X POST 'https://api.criteo.com/{version}/retail-media/accounts/4/brand-catalog-export' \
-H 'Content-Type: application/json' \
-H 'Accept: application/json' \
-H 'Authorization: Bearer <MY_ACCESS_TOKEN>' \
--data-raw '{
  "data": {
    "type": "RetailMediaCatalogStatus",
    "attributes": {
      "brandIdFilter": [
        "123"
      ],
      "retailerIdFilter": [
        "456"
      ],
      "modifiedAfter": "2025-03-21T08:00:00-5:00",
      "includeFields": ["ImageUrl","GoogleCategory", "RetailerName", "Category", "BrandName","Description"]
    }
  }
}'
import requests
import json

url = "https://api.criteo.com/{version}/retail-media/accounts/4/brand-catalog-export"

payload = json.dumps({
  "data": {
    "type": "RetailMediaCatalogStatus",
    "attributes": {
      "brandIdFilter": [
        "123"
      ],
      "retailerIdFilter": [
        "456"
      ],
      "modifiedAfter": "2025-03-21T08:00:00-5:00",
      "includeFields": ["ImageUrl","GoogleCategory", "RetailerName", "Category", "BrandName","Description"]
    }
  }
})
headers = {
  'Content-Type': 'application/json',
  'Accept': 'application/json',
  'Authorization': 'Bearer <MY_ACCESS_TOKEN>'
}

response = requests.request("POST", url, headers=headers, data=payload)

print(response.text)
OkHttpClient client = new OkHttpClient().newBuilder()
  .build();

MediaType mediaType = MediaType.parse("application/json");

RequestBody body = RequestBody.create(mediaType, "{\n  \"data\": {\n   \"type\": \"RetailMediaCatalogStatus\",\n   \"attributes\": {\n     \"brandIdFilter\": [\n       \"123\"\n     ],\n     \"retailerIdFilter\": [\n       \"456\"\n     ],\n     \"modifiedAfter\": \"2025-03-21T08:00:00-5:00\",\n     \"includeFields\": [\"ImageUrl\",\"GoogleCategory\", \"RetailerName\", \"Category\", \"BrandName\",\"Description\"]\n   }\n }\n}");

Request request = new Request.Builder()
  .url("https://api.criteo.com/{version}/retail-media/accounts/4/brand-catalog-export")
  .method("POST", body)
  .addHeader("Content-Type", "application/json")
  .addHeader("Accept", "application/json")
  .addHeader("Authorization", "Bearer <MY_ACCESS_TOKEN>")
  .build();

Response response = client.newCall(request).execute();
<?php
require_once 'HTTP/Request2.php';
$request = new HTTP_Request2();
$request->setUrl('https://api.criteo.com/{version}/retail-media/accounts/4/brand-catalog-export');
$request->setMethod(HTTP_Request2::METHOD_POST);
$request->setConfig(array(
  'follow_redirects' => TRUE
));

$request->setHeader(array(
  'Content-Type' => 'application/json',
  'Accept' => 'application/json',
  'Authorization' => 'Bearer <MY_ACCESS_TOKEN>'
));

$request->setBody('{\n  "data": {\n   "type": "RetailMediaCatalogStatus",\n   "attributes": {\n     "brandIdFilter": [\n       "123"\n     ],\n     "retailerIdFilter": [\n       "456"\n     ],\n     "modifiedAfter": "2025-03-21T08:00:00-5:00",\n     "includeFields": ["ImageUrl","GoogleCategory", "RetailerName", "Category", "BrandName","Description"]\n   }\n }\n}');
try {
  $response = $request->send();
  if ($response->getStatus() == 200) {
    echo $response->getBody();
  }
  
  else {
    echo 'Unexpected HTTP status: ' . $response->getStatus() . ' ' .
    $response->getReasonPhrase();
  }
}

catch(HTTP_Request2_Exception $e) {
  echo 'Error: ' . $e->getMessage();
}

Sample Response

{
    "data": {
        "id": "1122850670915847014",
        "type": "RetailMediaCatalogStatus",
        "attributes": {
            "status": "pending",
            "currency": null,
            "rowCount": null,
            "fileSizeBytes": null,
            "md5Checksum": null,
            "createdAt": "2025-01-22T23:10:12.21+00:00",
            "message": null
        }
    }
}

Seller account

This endpoint allows you to generate the most up-to-date catalog for a specific seller account.

https://api.criteo.com/{version}/retail-media/accounts/{accountId}/seller-catalog-export

Sample Request

curl -L -X POST 'https://api.criteo.com/{version}/retail-media/accounts/4/seller-catalog-export' \
-H 'Content-Type: application/json' \
-H 'Accept: application/json' \
-H 'Authorization: Bearer <MY_ACCESS_TOKEN>' \
--data-raw '{
  "data": {
    "type": "RetailMediaCatalogStatus",
    "attributes": {
      "sellers": [
        {
          "retailerId": "123",
          "sellerId": "5e0axxxxxxxxxx"
        }
      ],
      "modifiedAfter": "",
      "includeFields": [
        "ImageUrl",
        "Description"
      ]
    }
  }
}'
import requests
import json

url = "https://api.criteo.com/{version}/retail-media/accounts/4/seller-catalog-export"

payload = json.dumps({
  "data": {
    "type": "RetailMediaCatalogStatus",
    "attributes": {
      "sellers": [
        {
          "retailerId": "123",
          "sellerId": "5e0axxxxxxxxxx"
        }
      ],
      "modifiedAfter": "",
      "includeFields": [
        "ImageUrl",
        "Description"
      ]
    }
  }
})
headers = {
  'Content-Type': 'application/json',
  'Accept': 'application/json',
  'Authorization': 'Bearer <MY_ACCESS_TOKEN>'
}

response = requests.request("POST", url, headers=headers, data=payload)

print(response.text)
OkHttpClient client = new OkHttpClient().newBuilder()
  .build();

MediaType mediaType = MediaType.parse("application/json");

RequestBody body = RequestBody.create(mediaType, "{\n \"data\": {\n   \"type\": \"RetailMediaCatalogStatus\",\n   \"attributes\": {\n     \"sellers\": [\n       {\n         \"retailerId\": \"123\",\n         \"sellerId\": \"5e0axxxxxxxxxx\"\n       }\n     ],\n     \"modifiedAfter\": \"\",\n     \"includeFields\": [\n     \"ImageUrl\",\n     \"Description\"\n     ]\n   }\n }}");

Request request = new Request.Builder()
  .url("https://api.criteo.com/{version}/retail-media/accounts/4/seller-catalog-export")
  .method("POST", body)
  .addHeader("Content-Type", "application/json")
  .addHeader("Accept", "application/json")
  .addHeader("Authorization", "Bearer <MY_ACCESS_TOKEN>")
  .build();

Response response = client.newCall(request).execute();
<?php
require_once 'HTTP/Request2.php';
$request = new HTTP_Request2();
$request->setUrl('https://api.criteo.com/{version}/retail-media/accounts/4/seller-catalog-export');
$request->setMethod(HTTP_Request2::METHOD_POST);
$request->setConfig(array(
  'follow_redirects' => TRUE
));

$request->setHeader(array(
  'Content-Type' => 'application/json',
  'Accept' => 'application/json',
  'Authorization' => 'Bearer <MY_ACCESS_TOKEN>'
));

$request->setBody('{\n "data": {\n   "type": "RetailMediaCatalogStatus",\n   "attributes": {\n     "sellers": [\n       {\n         "retailerId": "123",\n         "sellerId": "5e0axxxxxxxxxx"\n       }\n     ],\n     "modifiedAfter": "",\n     "includeFields": [\n     "ImageUrl",\n     "Description"\n     ]\n   }\n }}');
try {
  $response = $request->send();
  if ($response->getStatus() == 200) {
    echo $response->getBody();
  }
  
  else {
    echo 'Unexpected HTTP status: ' . $response->getStatus() . ' ' .
    $response->getReasonPhrase();
  }
}

catch(HTTP_Request2_Exception $e) {
  echo 'Error: ' . $e->getMessage();
}

Sample Response

{
    "data": {
        "id": "1122850670915847014",
        "type": "RetailMediaCatalogStatus",
        "attributes": {
            "status": "pending",
            "currency": null,
            "rowCount": null,
            "fileSizeBytes": null,
            "md5Checksum": null,
            "createdAt": "2025-01-22T23:10:12.21+00:00",
            "message": null
        }
    }
}