CVS API endpoint
Returns one CVS.com OTC (over-the-counter) retail product's ingredient/label statement: active ingredients, inactive ingredients, and the vendor's full free-text ingredient paragraph (which, for OTC drug products, frequently also carries a Drug Facts-style purpose note). This is sourced from the product's own dedicated ingredients page, a separate page from the main product detail endpoint. Covers the non-prescription retail catalog only -- this does not cover prescription items, pharmacy ordering, or any patient-specific data. slug is the segment of a product page URL after "/shop/", e.g. "e-l-f-16hr-camo-concealer-prodid-2370023"; a full https://www.cvs.com/shop/... URL is also accepted. Some products (particularly non-consumable goods) may return empty ingredient fields -- this reflects upstream having no label data for that product, not an error. CVS.com is only available from US/US-territory egress; a request from an unsupported region returns an upstream error rather than an empty result.
/cvs/product-ingredients/{slug}slug is required. It is the segment of a CVS product page URL after /shop/, e.g. e-l-f-16hr-camo-concealer-prodid-2370023. A full https://www.cvs.com/shop/... URL is also accepted. The slug must end in -prodid-{numeric id} — this is exactly the shape CVS's own search and category listings link to, and the same slug /api/v1/cvs/product/{slug} accepts.
Notable response behavior:
active_ingredients and inactive_ingredients are the vendor's own structured active/inactive ingredient fields when upstream populates them separately. Many products leave these empty and only populate the combined paragraph field below — prefer paragraph as the more complete source.paragraph is the vendor's full free-text ingredient statement. For OTC drug products this frequently also carries a Drug Facts-style purpose note (e.g. "Active Ingredient (in each drop): Menthol, 1.5 mg - Purpose: Oral anesthetic ...").id/title — this reflects upstream having no label data for that product, not an error.503 upstream error rather than an empty or wrong result.slug returns a 400 invalid-parameter error before any upstream request is made. A well-formed but nonexistent product id returns a 404.| Field | In the sample | Value in the sample |
|---|---|---|
| id | Has a value | |
| title | Has a value | “e.l.f. 16hr Camo Concealer” |
| paragraph | Has a value | 1,011 characters |
| url | Has a value | cvs.com |
| Parameter | Type | Required | Default | Description | Example |
|---|---|---|---|---|---|
| slug (path) | string | Yes | CVS product page URL slug, e.g. \ | e-l-f-16hr-camo-concealer-prodid-2370023 | |
| x-api-key (header) | string | Yes | API key required |
curl -X GET "https://api.crawlora.net/api/v1/cvs/product-ingredients/e-l-f-16hr-camo-concealer-prodid-2370023" \ -H "x-api-key: $CRAWLORA_API_KEY"
{
"code": 200,
"msg": "OK",
"data": {
"id": "2370023",
"title": "e.l.f. 16hr Camo Concealer",
"paragraph": "Active Ingredients: WATER (AQUA), CYCLOPENTASILOXANE, ACRYLATES CROSSPOLYMER...Inactive Ingredients: Water, Cyclopentasiloxane, Acrylates Crosspolymer...",
"url": "https://www.cvs.com/shop/ingredients/e-l-f-16hr-camo-concealer-prodid-2370023",
"source_url": "https://www.cvs.com/shop/ingredients/e-l-f-16hr-camo-concealer-prodid-2370023",
"fetched_at": "2026-09-03T00:00:00Z"
}
}Request schema
No body schema
Response schema
#/definitions/cvs.productIngredientsResponseDoc
| Field | Type | Required | Enum | Bounds | Example | Description |
|---|---|---|---|---|---|---|
| code | integer | No | 200 | |||
| data | cvs.ProductIngredients | No | ||||
| data.active_ingredients | string | No | Menthol 1.1mg per drop | ActiveIngredients and InactiveIngredients are the vendor's own structured active/inactive ingredient fields when upstream populates them separately from Paragraph. Many products (confirmed live) leave these empty and only populate the combined Paragraph form below -- callers should prefer Paragraph as the more complete source. | ||
| data.fetched_at | string | No | ||||
| data.id | string | No | 2370023 | |||
| data.inactive_ingredients | string | No | ||||
| data.paragraph | string | No | Paragraph is the vendor's full free-text ingredient statement. For OTC drug products this frequently also carries a Drug Facts-style "Purpose" note (e.g. "Active Ingredient (in each drop): Menthol, 1.5 mg - Purpose: Oral anesthetic ..."), confirmed live. | |||
| data.source_url | string | No | ||||
| data.title | string | No | e.l.f. 16hr Camo Concealer | |||
| data.url | string | No | ||||
| msg | string | No | OK |
| Status | Description | Schema |
|---|---|---|
| 400 | Bad Request | #/definitions/app.Response |
| 404 | Not Found | #/definitions/app.Response |
| 429 | Too Many Requests | #/definitions/app.Response |
| 503 | Service Unavailable | #/definitions/app.Response |
Use environment variables for secrets and keep Crawlora API keys server-side.
curl -X GET "https://api.crawlora.net/api/v1/cvs/product-ingredients/e-l-f-16hr-camo-concealer-prodid-2370023" \
-H "x-api-key: $CRAWLORA_API_KEY"