Vizit Public APIAPI
Product Details

Submit a PDP by Amazon ASIN

Trigger Vizit's scrape-and-score pipeline for an Amazon ASIN.

PUT/v1/pdps/asin/{asin}

Submitting an ASIN runs Vizit's standard Amazon scrape-and-score pipeline server-side: ASIN lookup and validation, category inference with ICP check, retailer scrape, image ingest, and scoring. Unlike Submit a PDP by GTIN, the caller does not supply images or a category — both are derived from the scrape.

Upsert semantics. If a PDP already exists for this ASIN in your organization (and region), this call refreshes it — same behavior as the in-product "refresh" action. The previous scores remain visible alongside status: processing until the new scores land.

The response returns immediately with status: processing and a score_url. Use Retrieve PDP scores by ASIN (with the same region) to watch the scores come in. Score availability is bounded by the scrape and scoring pipeline — expect tens of seconds for typical Amazon ASINs.

Common errors. INVALID_ASIN if the path parameter is not 10 uppercase alphanumeric characters; ASIN_NOT_FOUND_AT_RETAILER if Amazon does not return the listing; CATEGORY_NOT_IN_ORG_ICP if the scraped category is outside your organization's ICP; NO_VALID_CATEGORY if the retailer returned no usable category data.

Authorization

bearerAuth
Authorization<token>

Short-lived access token issued by Create a token. Send it on every request as Authorization: Bearer <token>.

In: header

Path Parameters

asin*string

Amazon Standard Identification Number — 10 characters, uppercase letters and digits only. Validated at the router; a mismatch returns 400 INVALID_ASIN before any retailer call is made.

Match^[A-Z0-9]{10}$

Request Body

application/json

TypeScript Definitions

Use the request body type in TypeScript.

region?string

Amazon storefront region (e.g., us, uk, de, ca). Combined with amazon server-side to resolve the storefront. Unknown values return 400 INVALID_REGION.

Default"us"

Response Body

application/json

application/json

application/json

application/json

application/json

curl -X PUT "https://ext.vizit.com/v1/pdps/asin/B07XVTRJKX" \  -H "Content-Type: application/json" \  -d '{}'
{  "asin": "B07XVTRJKX",  "region": "us",  "pdp_id": "2ed2d86b-85b6-49b8-bfaf-11ce19f11301",  "status": "processing",  "score_url": "/v1/pdps/asin/B07XVTRJKX?region=us"}
{  "detail": "string",  "status_code": 0,  "error_code": "INVALID_GTIN",  "request_id": "266ea41d-adf5-480b-af50-15b940c2b846",  "extra": {    "failed_urls": [      {        "url": "https://cdn.example.com/broken.jpg",        "reason": "IMAGE_DOWNLOAD_TIMEOUT"      },      {        "url": "https://cdn.example.com/icon.svg",        "reason": "UNSUPPORTED_IMAGE_FORMAT"      }    ]  },  "timestamp": "2019-08-24T14:15:22Z"}
Empty
{  "detail": "string",  "status_code": 0,  "error_code": "INVALID_GTIN",  "request_id": "266ea41d-adf5-480b-af50-15b940c2b846",  "extra": {    "failed_urls": [      {        "url": "https://cdn.example.com/broken.jpg",        "reason": "IMAGE_DOWNLOAD_TIMEOUT"      },      {        "url": "https://cdn.example.com/icon.svg",        "reason": "UNSUPPORTED_IMAGE_FORMAT"      }    ]  },  "timestamp": "2019-08-24T14:15:22Z"}
Empty
{  "detail": "string",  "status_code": 0,  "error_code": "INVALID_GTIN",  "request_id": "266ea41d-adf5-480b-af50-15b940c2b846",  "extra": {    "failed_urls": [      {        "url": "https://cdn.example.com/broken.jpg",        "reason": "IMAGE_DOWNLOAD_TIMEOUT"      },      {        "url": "https://cdn.example.com/icon.svg",        "reason": "UNSUPPORTED_IMAGE_FORMAT"      }    ]  },  "timestamp": "2019-08-24T14:15:22Z"}
{  "detail": "string",  "status_code": 0,  "error_code": "INVALID_GTIN",  "request_id": "266ea41d-adf5-480b-af50-15b940c2b846",  "extra": {    "failed_urls": [      {        "url": "https://cdn.example.com/broken.jpg",        "reason": "IMAGE_DOWNLOAD_TIMEOUT"      },      {        "url": "https://cdn.example.com/icon.svg",        "reason": "UNSUPPORTED_IMAGE_FORMAT"      }    ]  },  "timestamp": "2019-08-24T14:15:22Z"}

GETRetrieve PDP scores by ASIN

Returns the current scores and processing state for a PDP submitted via [Submit a PDP by ASIN](/api/product-details/upsertPdpByAsin). Poll until `status` moves from `processing` to `scored`. During a refresh, previously computed scores remain visible alongside `status: processing` and the prior `scored_at` timestamp, so clients can keep showing the last known result while a new one is computed. Use the optional `region` query parameter to disambiguate between regional storefronts when the same ASIN has been ingested under multiple regions in your organization. The `score_url` returned by the PUT response already includes this parameter.

POSTCreate a bulk export job

Queues an asynchronous bulk export for the caller's organization. The response returns immediately with `status: PENDING` and a `status_url` pointing at [Retrieve an export](/api/exports/getExport); poll there until `status` reaches `COMPLETED` to obtain the short-lived presigned download URL. Org scope is enforced by the access token; the optional `filters` block narrows within the org. Each caller is limited to one in-flight `PENDING`/`PROCESSING` export at a time — additional submissions return `409 EXPORT_CONCURRENCY_LIMIT`. ## CSV format Exports are CSV in v1 (JSONL and Parquet deferred to v2). The header row is fixed per `subject`; carousel rows in `subject=images` exports emit empty values for hero-only columns so partners can rely on a stable column set. ### `subject=pdps` column set | Column | Type | Notes | | --- | --- | --- | | `pdp_id` | uuid | PDP identifier; stable across refreshes | | `portfolio_id` | uuid | Owning portfolio | | `retailer_region` | string | e.g. `amazon_us`, `walmart_us` | | `item_id` | string | ASIN or GTIN, depending on retailer | | `name` | string \| null | PDP display name | | `brand` | string \| null | | | `category_id` | uuid \| null | Vizit category identifier | | `category` | string \| null | Category display name | | `listing_score` | int \| null | 0–100, resolved per org | | `raw_listing_score` | float \| null | Pre-blend, pre-penalty | | `listing_score_blended` | int \| null | 0–100, pre-penalty | | `score_penalty` | bool \| null | True if any penalty applied | | `image_count_penalty` | float \| null | | | `image_mix_penalty` | float \| null | | | `image_order_penalty` | float \| null | | | `high_scoring_asset_count` | int \| null | | | `is_ideal_content_mix` | bool \| null | | | `images_matching_ideal_mix` | int \| null | | | `score_status` | string | `CREATED`, `PROCESSING`, `SCORED`, or `CATEGORY_NOT_FOUND` | | `created_at` | date-time | | | `updated_at` | date-time | | | `last_refreshed` | date-time \| null | Last successful scrape + score | ### `subject=images` column set Hero-score and mobile-readiness columns are populated only for hero rows; carousel rows emit empty values in those columns. | Column | Type | Notes | | --- | --- | --- | | `image_id` | uuid | | | `pdp_id` | uuid | Parent PDP | | `portfolio_id` | uuid | Denormalized from PDP for row-standalone exports | | `retailer_region` | string | | | `item_id` | string | ASIN or GTIN of the parent PDP | | `image_type` | string | `hero` or `carousel` | | `image_url` | string | | | `position` | int | 1-based position within the PDP (matches `CarouselImageResponse.position`) | | `source` | string \| null | e.g. `scraped` | | `vizit_score` | int \| null | 0–100, resolved per org | | `raw_score` | float \| null | | | `hero_score` | int \| null | 0–100; null for carousel rows. The `hero_score_breakdown` sub-scores (heroism, category_edge, technical_integrity, local_support) are intentionally omitted from v1 — the hero formula is in flight | | `mobile_ready` | bool \| null | All five clarity scores ≥ 80. Null for carousel | | `mobile_brand_clarity` | float \| null | Null for carousel | | `mobile_product_type_clarity` | float \| null | Null for carousel | | `mobile_variant_clarity` | float \| null | Null for carousel | | `mobile_count_clarity` | float \| null | Null for carousel | | `mobile_size_clarity` | float \| null | Null for carousel | | `mobile_scored_model` | string \| null | Null for carousel | | `classification` | string \| null | e.g. `Lifestyle`, `Packshot` | | `classification_confidence` | float \| null | 0–1 | | `classification_high_confidence` | bool \| null | | | `created_at` | date-time | | | `updated_at` | date-time | | | `scored_at` | date-time \| null | Last successful score |