VendorProducts
Update Product
Update Product — vendor REST API endpoint.
PATCH
/vendor/products/:idVendor bearer token requiredUpdate Product
Update an existing product.
What this means in plain English
Partially update a product. All body fields are optional. Requires OWNER, ADMIN, or EDITOR role.
When to use this
- Updating pricing or inventory on an existing SKU.
- Changing catalog metadata without touching images.
Path parameters
| Name | Type | Required | Description |
|---|---|---|---|
| id | string (UUID) | Yes | Product ID. |
Request body
| Name | Type | Required | Description |
|---|---|---|---|
| name | string | No | Updated name (3–255 characters). |
| sku | string | No | Updated SKU. |
| slug | string | No | URL slug (3–255 characters). |
| shortDescription | string | No | Short product description. |
| description | string | No | Full product description. |
| brand | string | No | Brand name (max 255 characters). |
| countryOfOrigin | string | No | Country of origin (max 255 characters). |
| manufacturer | string | No | Manufacturer name (max 255 characters). |
| leadTime | integer | No | Lead time in days (min 0). |
| unspc | string | No | UNSPSC code — 8 or 10 digits. |
| commodityCode | string | No | Commodity / HS-style code (max 28 characters). |
| eccn | string | No | Export Control Classification Number (max 255 characters). |
| freeShipping | boolean | No | Free shipping flag. |
| abilityOne | boolean | No | AbilityOne flag. |
| madeInUsa | boolean | No | Made in USA flag. |
| greenProduct | boolean | No | Green product flag. |
| keyFeatures | string[] | No | Key features (max 6 items, 255 characters each). |
| accountCode | string | No | Account code (max 255 characters). |
| programCode | string | No | Department Code (max 255 characters). |
| resourceCode | string | No | Resource code (max 255 characters). |
| categoryIds | string[] (UUID) | No | Category UUIDs to assign. Use [List Categories](/docs/v1/vendor/categories/list) to look up valid UUIDs. |
| collectionIds | string[] (UUID) | No | Collection UUIDs to assign. |
| tagIds | string[] (UUID) | No | Tag UUIDs to assign. |
| facetValueIds | string[] (UUID) | No | Facet value UUIDs to assign. |
| variants[].id | string (UUID) | No | Existing variant ID to update (must belong to this product). |
| variants[].sku | string | No | Variant SKU (required when creating a new variant). |
| variants[].name | string | No | Variant name (required when creating a new variant). |
| variants[].vendorPrice | number | No | Vendor/cost price. Supplying it recomputes the customer retail price as `vendorPrice × (1 + your commission %)`. Required when creating a new variant. Omit to leave the existing price/cost unchanged. |
| variants[].listPrice | number | No | List price (MSRP). Shown as a strikethrough compare-at price when higher than the retail price; never charged at checkout. |
| variants[].upc | string | No | UPC (max 255 characters). |
| variants[].unitOfMeasure | string | No | Unit of measure (max 50 characters). |
| variants[].partNumber | string | No | Manufacturer part number (max 255 characters). |
| variants[].weight | number | No | Weight (min 0). |
| variants[].initialInventory | integer | No | Initial stock when creating a new variant (min 0). |
| variants[].attributes | object | No | Arbitrary key/value variant attributes. |
| variants[].isActive | boolean | No | Active flag. |
| variantStock[].variantId | string (UUID) | Yes | Variant to update. |
| variantStock[].quantity | integer | Yes | Target on-hand quantity (min 0). |
Request example
curl -X PATCH 'https://api.next.gcommerce.glass/api/v1/vendor/products/a0000000-0000-4000-8000-000000000050' \
-H 'Content-Type: application/json' \
-d '{
"variantStock": [
{
"variantId": "550e8400-e29b-41d4-a716-446655440021",
"quantity": 250
}
]
}'Response examples
200Success
{
"id": "550e8400-e29b-41d4-a716-446655440020",
"name": "Widget Pro",
"slug": "widget-pro",
"sku": "WIDGET-001",
"shortDescription": "Premium widget",
"warranty": "1 year limited",
"description": "High-quality widget for industrial use.",
"pageTitle": "Widget Pro | Jane's Store",
"pageDescription": "Shop the Widget Pro — durable, lightweight, made in USA.",
"brand": "Acme",
"countryOfOrigin": "US",
"manufacturer": "Acme Corp",
"leadTime": 3,
"unspc": "53120000",
"commodityCode": "12345678",
"eccn": "EAR99",
"freeShipping": false,
"abilityOne": false,
"madeInUsa": true,
"greenProduct": false,
"keyFeatures": ["Durable", "Lightweight"],
"videos": null,
"accountCode": "ACC-001",
"programCode": "PROG-001",
"resourceCode": "RES-001",
"status": "PUBLISHED",
"pendingRevision": {
"name": "Widget Pro v2",
"shortDescription": "Updated short description",
"description": "Updated long description pending review",
"images": [
{
"base64Image": "data:image/png;base64,iVBORw0KGgo...",
"alt": "Widget Pro v2 front view",
"sortOrder": 0,
"isPrimary": true
}
]
},
"pendingRevisionSubmittedAt": "2026-07-10T14:30:00.000Z",
"bulkImportJobId": null,
"createdAt": "2026-01-15T12:00:00.000Z",
"updatedAt": "2026-03-01T08:30:00.000Z",
"variants": [
{
"id": "550e8400-e29b-41d4-a716-446655440021",
"productId": "550e8400-e29b-41d4-a716-446655440020",
"sku": "WIDGET-001",
"upc": "012345678905",
"unitOfMeasure": "EA",
"partNumber": "MPN-001",
"name": "Default",
"price": "29.99",
"listPrice": "39.99",
"vendorPrice": "19.99",
"weight": "1.50",
"initialInventory": 100,
"attributes": { "color": "red" },
"isActive": true,
"createdAt": "2026-01-15T12:00:00.000Z",
"updatedAt": "2026-03-01T08:30:00.000Z"
}
],
"images": [
{
"id": "550e8400-e29b-41d4-a716-446655440022",
"productId": "550e8400-e29b-41d4-a716-446655440020",
"variantId": null,
"url": "https://api.next.gcommerce.glass/assets/products/images/550e8400-e29b-41d4-a716-446655440022",
"alt": "Widget Pro front view",
"sortOrder": 0,
"isPrimary": true
}
],
"documents": [
{
"id": "550e8400-e29b-41d4-a716-446655440023",
"productId": "550e8400-e29b-41d4-a716-446655440020",
"title": "Spec sheet",
"type": "spec",
"url": "https://example.com/spec.pdf",
"document": "https://api.next.gcommerce.glass/assets/products/widget-pro/docs/spec.pdf",
"size": "245.50",
"sortOrder": 0,
"createdAt": "2026-01-15T12:00:00.000Z",
"updatedAt": "2026-01-15T12:00:00.000Z"
}
],
"categories": [
{
"id": "550e8400-e29b-41d4-a716-446655440070",
"name": "Industrial Supplies",
"slug": "industrial-supplies"
}
],
"collections": [],
"tags": [],
"facetValues": [],
"reviews": [],
"averageRating": 4.5,
"totalReviews": 12
}Status codes
200
OK
Request succeeded.
401
Unauthorized
Missing or invalid bearer token.
403
Forbidden
Insufficient permissions for this action.
400
Bad Request
Validation failed or invalid parameters.
404
Not Found
Resource not found.
429
Too Many Requests
Global rate limit exceeded (10,000 requests per 10 minutes per IP).
500
Internal Server Error
Unexpected server error.
403
Forbidden
No vendor membership, or insufficient vendor role (requires OWNER, ADMIN, or EDITOR for write operations).
**Admin approval:** New products are created as `PENDING_APPROVAL` and are not visible on storefronts until a platform admin approves them.
**Live product edits:** On `PUBLISHED` or `HIDDEN` products, changes to `name`, `shortDescription`, `description`, or `images` are staged in `pendingRevision` — the product stays `PUBLISHED` and the storefront keeps showing the current live data until an admin approves.
**Immediate updates:** Vendor price (cost) and MSRP, stock, slug, categories, variants, SEO fields, bulk-update fields, and other non-moderated fields apply immediately on live products without re-approval. The customer retail price (derived from vendor price × commission) also updates immediately.
Do not send a `status` field — it is rejected on vendor REST create/update and managed by the platform.
Poll `GET /vendor/products/:id` and inspect `pendingRevision` (non-null with staged fields). List filters: `?status=PENDING_APPROVAL` (never published), `?hasPendingRevision=true` (live products with staged edits), or `?needsModeration=true` (either case).
Do not send `status` — it is server-managed.
**Live products (`PUBLISHED` / `HIDDEN`):** `name`, `shortDescription`, and `description` require admin approval and are staged in `pendingRevision`. Image changes use the multipart image endpoints (also staged on live products).
**Non-live products (`PENDING_APPROVAL` / `DRAFT`):** Moderated text fields apply directly to the product row; status remains unchanged unless the product was never published (`PENDING_APPROVAL` stays until admin approves).
Response `status` stays `PUBLISHED` when staging on a live product — do not expect `PENDING_APPROVAL` for live-product content edits.
Stock-only updates via `variantStock`, or variant cost changes alone, apply immediately and do not trigger staging.
You can only change `vendorPrice` (cost) and `listPrice` (MSRP). The customer retail price is always derived from `vendorPrice × (1 + your commission %)`; any `price` you send is ignored. Sending a `vendorPrice` recomputes the retail price; omitting it leaves the existing price untouched.
Only include fields you want to change — omitted fields are left unchanged.
`variants[]` with `id` updates an existing variant; without `id` creates a new one (a new variant must include `vendorPrice`).
Do not send images in this PATCH body. Use [Add Product Image](/docs/v1/vendor/products/add-image) or [Replace Product Images](/docs/v1/vendor/products/replace-images).
Use `variantStock` to set absolute inventory per variant without replacing the full variants array.
Categories are read-only for vendors. Pass existing UUIDs in `categoryIds`; invalid or unknown IDs are rejected.
Try it
Uses your saved session from login. Edit values and send a live request, or copy the cURL command.