curl --request GET \
--url https://www.closient.com/retailers/api/v1/retailers/{retailer_id}/listings/{listing_id} \
--header 'X-API-Key: <api-key>'import requests
url = "https://www.closient.com/retailers/api/v1/retailers/{retailer_id}/listings/{listing_id}"
headers = {"X-API-Key": "<api-key>"}
response = requests.get(url, headers=headers)
print(response.text)const options = {method: 'GET', headers: {'X-API-Key': '<api-key>'}};
fetch('https://www.closient.com/retailers/api/v1/retailers/{retailer_id}/listings/{listing_id}', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));<?php
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_URL => "https://www.closient.com/retailers/api/v1/retailers/{retailer_id}/listings/{listing_id}",
CURLOPT_RETURNTRANSFER => true,
CURLOPT_ENCODING => "",
CURLOPT_MAXREDIRS => 10,
CURLOPT_TIMEOUT => 30,
CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
CURLOPT_CUSTOMREQUEST => "GET",
CURLOPT_HTTPHEADER => [
"X-API-Key: <api-key>"
],
]);
$response = curl_exec($curl);
$err = curl_error($curl);
curl_close($curl);
if ($err) {
echo "cURL Error #:" . $err;
} else {
echo $response;
}package main
import (
"fmt"
"net/http"
"io"
)
func main() {
url := "https://www.closient.com/retailers/api/v1/retailers/{retailer_id}/listings/{listing_id}"
req, _ := http.NewRequest("GET", url, nil)
req.Header.Add("X-API-Key", "<api-key>")
res, _ := http.DefaultClient.Do(req)
defer res.Body.Close()
body, _ := io.ReadAll(res.Body)
fmt.Println(string(body))
}HttpResponse<String> response = Unirest.get("https://www.closient.com/retailers/api/v1/retailers/{retailer_id}/listings/{listing_id}")
.header("X-API-Key", "<api-key>")
.asString();require 'uri'
require 'net/http'
url = URI("https://www.closient.com/retailers/api/v1/retailers/{retailer_id}/listings/{listing_id}")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Get.new(url)
request["X-API-Key"] = '<api-key>'
response = http.request(request)
puts response.read_body{
"attributes": {
"categoryIds": [
"cat130042"
],
"sephoraDescription": "A lightweight serum."
},
"badges": [
{
"is_active": true,
"label": "Clean at Sephora",
"slug": "clean-at-sephora"
}
],
"created": "2026-01-15T10:00:00Z",
"gtin": "00812345678901",
"id": "b2c3d4e5f60718293a4b5c6d7e",
"is_active": true,
"modified": "2026-02-01T09:30:00Z",
"product_id": "9a8b7c6d5e4f30211a2b3c4d5e",
"retailer_id": "f47ac10b58cc4372a5670e02b2",
"sku": "SEPH-2311456",
"source_reference": "P442501",
"urls": [
{
"is_active": true,
"store_url": "https://www.sephora.ca",
"storefront_id": "c3d4e5f6789012345abcdef012",
"url": "https://www.sephora.ca/product/P442501"
}
]
}{
"detail": "The requested resource was not found.",
"error_code": "not_found",
"retryable": false,
"status": 404,
"timestamp": "2026-03-31T12:00:00+00:00",
"title": "Not Found",
"type": "https://closient.com/docs/errors/not_found"
}{
"detail": "The requested resource was not found.",
"error_code": "not_found",
"retryable": false,
"status": 404,
"timestamp": "2026-03-31T12:00:00+00:00",
"title": "Not Found",
"type": "https://closient.com/docs/errors/not_found"
}{
"detail": "The requested resource was not found.",
"error_code": "not_found",
"retryable": false,
"status": 404,
"timestamp": "2026-03-31T12:00:00+00:00",
"title": "Not Found",
"type": "https://closient.com/docs/errors/not_found"
}{
"detail": "The requested resource was not found.",
"error_code": "not_found",
"retryable": false,
"status": 404,
"timestamp": "2026-03-31T12:00:00+00:00",
"title": "Not Found",
"type": "https://closient.com/docs/errors/not_found"
}{
"detail": "The requested resource was not found.",
"error_code": "not_found",
"retryable": false,
"status": 404,
"timestamp": "2026-03-31T12:00:00+00:00",
"title": "Not Found",
"type": "https://closient.com/docs/errors/not_found"
}{
"detail": "The requested resource was not found.",
"error_code": "not_found",
"retryable": false,
"status": 404,
"timestamp": "2026-03-31T12:00:00+00:00",
"title": "Not Found",
"type": "https://closient.com/docs/errors/not_found"
}{
"detail": "The requested resource was not found.",
"error_code": "not_found",
"retryable": false,
"status": 404,
"timestamp": "2026-03-31T12:00:00+00:00",
"title": "Not Found",
"type": "https://closient.com/docs/errors/not_found"
}Get one retailer product listing
One listing of one retailer, with its badges and per-property URLs resolved.
The lookup is scoped to retailer_id, so a listing id belonging to a different retailer is 404 rather than a cross-retailer read.
Reading a canonical (Closient-curated) retailer’s listings needs only an authenticated caller. An organization-private retailer requires view access on the organization that owns it, and a credential scoped to a different organization gets 404 rather than 403, so the API never confirms that another organization’s retailer exists.
curl --request GET \
--url https://www.closient.com/retailers/api/v1/retailers/{retailer_id}/listings/{listing_id} \
--header 'X-API-Key: <api-key>'import requests
url = "https://www.closient.com/retailers/api/v1/retailers/{retailer_id}/listings/{listing_id}"
headers = {"X-API-Key": "<api-key>"}
response = requests.get(url, headers=headers)
print(response.text)const options = {method: 'GET', headers: {'X-API-Key': '<api-key>'}};
fetch('https://www.closient.com/retailers/api/v1/retailers/{retailer_id}/listings/{listing_id}', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));<?php
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_URL => "https://www.closient.com/retailers/api/v1/retailers/{retailer_id}/listings/{listing_id}",
CURLOPT_RETURNTRANSFER => true,
CURLOPT_ENCODING => "",
CURLOPT_MAXREDIRS => 10,
CURLOPT_TIMEOUT => 30,
CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
CURLOPT_CUSTOMREQUEST => "GET",
CURLOPT_HTTPHEADER => [
"X-API-Key: <api-key>"
],
]);
$response = curl_exec($curl);
$err = curl_error($curl);
curl_close($curl);
if ($err) {
echo "cURL Error #:" . $err;
} else {
echo $response;
}package main
import (
"fmt"
"net/http"
"io"
)
func main() {
url := "https://www.closient.com/retailers/api/v1/retailers/{retailer_id}/listings/{listing_id}"
req, _ := http.NewRequest("GET", url, nil)
req.Header.Add("X-API-Key", "<api-key>")
res, _ := http.DefaultClient.Do(req)
defer res.Body.Close()
body, _ := io.ReadAll(res.Body)
fmt.Println(string(body))
}HttpResponse<String> response = Unirest.get("https://www.closient.com/retailers/api/v1/retailers/{retailer_id}/listings/{listing_id}")
.header("X-API-Key", "<api-key>")
.asString();require 'uri'
require 'net/http'
url = URI("https://www.closient.com/retailers/api/v1/retailers/{retailer_id}/listings/{listing_id}")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Get.new(url)
request["X-API-Key"] = '<api-key>'
response = http.request(request)
puts response.read_body{
"attributes": {
"categoryIds": [
"cat130042"
],
"sephoraDescription": "A lightweight serum."
},
"badges": [
{
"is_active": true,
"label": "Clean at Sephora",
"slug": "clean-at-sephora"
}
],
"created": "2026-01-15T10:00:00Z",
"gtin": "00812345678901",
"id": "b2c3d4e5f60718293a4b5c6d7e",
"is_active": true,
"modified": "2026-02-01T09:30:00Z",
"product_id": "9a8b7c6d5e4f30211a2b3c4d5e",
"retailer_id": "f47ac10b58cc4372a5670e02b2",
"sku": "SEPH-2311456",
"source_reference": "P442501",
"urls": [
{
"is_active": true,
"store_url": "https://www.sephora.ca",
"storefront_id": "c3d4e5f6789012345abcdef012",
"url": "https://www.sephora.ca/product/P442501"
}
]
}{
"detail": "The requested resource was not found.",
"error_code": "not_found",
"retryable": false,
"status": 404,
"timestamp": "2026-03-31T12:00:00+00:00",
"title": "Not Found",
"type": "https://closient.com/docs/errors/not_found"
}{
"detail": "The requested resource was not found.",
"error_code": "not_found",
"retryable": false,
"status": 404,
"timestamp": "2026-03-31T12:00:00+00:00",
"title": "Not Found",
"type": "https://closient.com/docs/errors/not_found"
}{
"detail": "The requested resource was not found.",
"error_code": "not_found",
"retryable": false,
"status": 404,
"timestamp": "2026-03-31T12:00:00+00:00",
"title": "Not Found",
"type": "https://closient.com/docs/errors/not_found"
}{
"detail": "The requested resource was not found.",
"error_code": "not_found",
"retryable": false,
"status": 404,
"timestamp": "2026-03-31T12:00:00+00:00",
"title": "Not Found",
"type": "https://closient.com/docs/errors/not_found"
}{
"detail": "The requested resource was not found.",
"error_code": "not_found",
"retryable": false,
"status": 404,
"timestamp": "2026-03-31T12:00:00+00:00",
"title": "Not Found",
"type": "https://closient.com/docs/errors/not_found"
}{
"detail": "The requested resource was not found.",
"error_code": "not_found",
"retryable": false,
"status": 404,
"timestamp": "2026-03-31T12:00:00+00:00",
"title": "Not Found",
"type": "https://closient.com/docs/errors/not_found"
}{
"detail": "The requested resource was not found.",
"error_code": "not_found",
"retryable": false,
"status": 404,
"timestamp": "2026-03-31T12:00:00+00:00",
"title": "Not Found",
"type": "https://closient.com/docs/errors/not_found"
}Authorizations
Path Parameters
Unique identifier of the retailer this listing belongs to.
22^[23456789ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz]{22}$Unique identifier of the listing.
22^[23456789ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz]{22}$Response
OK
One retailer product listing as the catalog holds it.
URL-safe 22-character shortuuid encoding of the row's UUID primary key. Stable across the row's lifetime; suitable for sharing in URLs, log lines, and external SDK clients. Accepted on input as either the shortuuid form or the canonical UUID form (xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx).
22^[23456789ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz]{22}$URL-safe 22-character shortuuid encoding of the row's UUID primary key. Stable across the row's lifetime; suitable for sharing in URLs, log lines, and external SDK clients. Accepted on input as either the shortuuid form or the canonical UUID form (xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx).
22^[23456789ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz]{22}$Identifier of the shared product this listing points at.
22^[23456789ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz]{22}$GTIN of the listed product. The key the listing upsert accepts, echoed here so a caller can reconcile this row against its own feed without a second lookup.
The retailer's own SKU for this product across its whole catalog. Distinct from an offer's SKU, which is the SKU at one specific store or storefront.
False once the retailer drops the product from its catalog. DELETE clears this flag rather than removing the row.
When this listing row was first written.
When this listing row last changed.
Retailer-scoped facts that have no typed column yet — a staging area, not a permanent home. A key that proves useful is promoted to a real column.
The retailer's own product identifier in the source feed (e.g. a Sephora productId).
Designations this retailer applies to this product. Change them through POST /retailers/{retailer_id}/listings, which syncs the whole set.
Show child attributes
Show child attributes
One product URL per retailer web property. Change them through POST /retailers/{retailer_id}/listings, which syncs the whole set.
Show child attributes
Show child attributes