Mix de produtos
Cria, lista, lê, altera e apaga mixes, pacotes de produtos com preço fechado que o cliente pode montar escolhendo entre componentes.
Um mix de produtos é um pacote com preço fechado (bundle_price_centavos) formado por vários produtos, os componentes. Quando o cliente o adiciona ao carrinho, a plataforma o separa em linhas normais, uma por componente, e reparte o preço do pacote entre elas proporcionalmente. O frete e os impostos continuam funcionando como em qualquer carrinho.
Um mix pode ser fixo (leva tudo) ou montável: com allow_customer_pick ligado, o cliente escolhe entre min_components e max_components e pode trocar um componente por outro do mesmo swap_group. Quem enxerga o mix na vitrine depende da visibility e das atribuições a clientes e grupos.
Todas as rotas exigem o módulo mix-products ligado e o privilégio manage_mix_products ou manage_catalog. Um mix recém-criado fica desativado (D) até você mudar o status para A.
Listar mixes
/api/v1/admin/mix-productsAdminListar mixes de todos os sellers
A lista traz os dados do mix, sem os componentes (leia um mix para vê-los). Ordem: o mais novo primeiro.
Parâmetros de consulta
pageintegerpadrão: 1per_pageintegerpadrão: 25statusstringADHvendor_iduuidsearchstringsku e na descrição.curl "$BASE_URL/api/v1/admin/mix-products?status=A&per_page=10" \
-H "Authorization: Bearer $TOKEN"{
"mixes": [
{
"id": "c4a76056-c671-4631-bbcb-65223ff3322b",
"vendor_id": "94bd7e9a-fdad-4d01-8fc2-ba9d677d8b36",
"name": "Kit Verão",
"description": "",
"sku": "MIX-001",
"status": "A",
"bundle_price_centavos": 19990,
"currency": "BRL",
"visibility": "public",
"min_components": 1,
"max_components": 5,
"allow_customer_pick": false,
"image_url": "",
"created_at": "2026-07-19T13:08:54.861669Z",
"updated_at": "2026-07-20T14:54:44.873099Z"
}
],
"total": 2,
"page": 1,
"per_page": 10,
"total_pages": 1
}Criar um mix
/api/v1/admin/mix-productsAdminCriar um mix
Cria o mix com seus componentes e atribuições de uma vez, numa transação, e devolve o mix completo.
Corpo da requisição
namestringobrigatóriocomponentsarrayobrigatórioComponentes. Ao menos um.
product_iduuidobrigatórioquantityintegerpadrão: 1sort_orderintegeris_requiredbooleanallow_swapbooleanswap_groupstringbundle_price_centavosintegerdescriptionstringskustringstatusstringpadrão: DADHA ativo, D desativado, H oculto. Vazio vira D.currencystringpadrão: BRLvisibilitystringpadrão: privatepublicprivatecustomer-listmin_componentsintegerpadrão: 0max_componentsintegerpadrão: 00 significa sem máximo. Se informado, min_components não pode ser maior.allow_customer_pickbooleanpadrão: falseimage_urlstringvendor_iduuidassignmentsarrayPara quem o mix é liberado.
customer_iduuidusergroup_iduuidcustomer_id ou usergroup_id.curl -X POST "$BASE_URL/api/v1/admin/mix-products" \
-H "Authorization: Bearer $TOKEN" \
-H "Content-Type: application/json" \
-d '{
"name": "Kit Verão",
"bundle_price_centavos": 19990,
"status": "A",
"visibility": "public",
"components": [
{"product_id": "ab3f1a07-2ae2-45b7-a4be-bcb67314d601", "quantity": 2, "is_required": true}
]
}'Ler um mix
/api/v1/admin/mix-products/{id}AdminLer um mix com componentes e atribuições
Devolve o mix completo: além dos campos da lista, components e assignments, e os totais calculados quando há componentes.
Parâmetros de caminho
iduuidobrigatóriocurl "$BASE_URL/api/v1/admin/mix-products/050363eb-f63c-4c3c-abb6-30581638e91a" \
-H "Authorization: Bearer $TOKEN"Resposta (criar, ler e alterar)
A criação responde 201 com o mesmo corpo.
{
"id": "050363eb-f63c-4c3c-abb6-30581638e91a",
"name": "Kit Verão",
"description": "",
"sku": "MIX-005",
"status": "A",
"bundle_price_centavos": 19990,
"currency": "BRL",
"visibility": "public",
"min_components": 0,
"max_components": 0,
"allow_customer_pick": false,
"image_url": "",
"created_at": "2026-07-04T18:33:35.649004Z",
"updated_at": "2026-07-04T18:33:35.649004Z",
"components": [
{
"id": "bde899cc-65d0-459a-838f-b9cc85af6b60",
"mix_id": "050363eb-f63c-4c3c-abb6-30581638e91a",
"product_id": "ab3f1a07-2ae2-45b7-a4be-bcb67314d601",
"quantity": 2,
"sort_order": 0,
"is_required": true,
"allow_swap": false,
"product_name": "Camiseta Básica",
"product_sku": "CAM-001",
"product_price_centavos": 8990
}
],
"component_subtotal_centavos": 17980,
"savings_centavos": 0
}Campos da resposta
iduuidvendor_iduuidnamestringdescriptionstringskustringstatusstringADHbundle_price_centavosintegercurrencystringvisibilitystringpublicprivatecustomer-listmin_componentsintegermax_componentsintegerallow_customer_pickbooleanimage_urlstringcomponentsarrayid, mix_id, product_id, quantity, sort_order, is_required, allow_swap, swap_group e, do produto, product_name, product_sku, product_price_centavos, product_image.assignmentsarrayid, mix_id, customer_id ou usergroup_id, created_at e, para exibição, customer_email ou usergroup_name.component_subtotal_centavosintegersavings_centavosintegercreated_atstringupdated_atstringAlterar um mix
/api/v1/admin/mix-products/{id}AdminAlterar um mix
Atualização parcial dos campos do mix. As listas têm regra própria: se você enviar components, todos os componentes são substituídos pela lista nova; se enviar assignments, todas as atribuições são substituídas. Omitir a lista a mantém. Devolve o mix completo.
Parâmetros de caminho
iduuidobrigatórioCorpo da requisição
namestringdescriptionstringskustringstatusstringADHbundle_price_centavosintegercurrencystringvisibilitystringpublicprivatecustomer-listmin_componentsintegermax_componentsintegerallow_customer_pickbooleanimage_urlstringcomponentsarrayassignmentsarraycurl -X PUT "$BASE_URL/api/v1/admin/mix-products/050363eb-f63c-4c3c-abb6-30581638e91a" \
-H "Authorization: Bearer $TOKEN" \
-H "Content-Type: application/json" \
-d '{"status":"A","bundle_price_centavos":17990}'Apagar um mix
/api/v1/admin/mix-products/{id}AdminApagar um mix
Remove o mix e, com ele, seus componentes e atribuições. Responde 204 sem corpo.
Parâmetros de caminho
iduuidobrigatóriocurl -X DELETE "$BASE_URL/api/v1/admin/mix-products/050363eb-f63c-4c3c-abb6-30581638e91a" \
-H "Authorization: Bearer $TOKEN"Sem corpo.
Erros
Esta área devolve erros no formato {"error": "<código>", "message": "<texto>"}, diferente do formato {"error", "detail"} de outras áreas.
| Status | Quando | Corpo de exemplo |
|---|---|---|
| 400 | Corpo que não é JSON. | {"error":"invalid_body","message":"..."} |
| 400 | Dados inválidos: sem name, sem componentes, status ou visibility fora da lista, preço negativo, min maior que max, componente sem product_id, atribuição sem cliente nem grupo. | {"error":"invalid_input","message":"mix-products: invalid input: at least one component is required"} |
| 401 | Sem token ou token expirado. | {"error":"invalid or expired token"} |
| 403 | Módulo desligado. | {"error":"module_disabled","module":"mix-products"} |
| 403 | Sem o privilégio. | {"error":"insufficient privileges","privilege_required_any":["manage_mix_products","manage_catalog"]} |
| 404 | GET de um mix que não existe. | {"error":"not_found","message":"mix not found"} |
| 500 | {id} que não é UUID; DELETE de mix que não existe. | {"error":"internal_error","message":"..."} |