Productos

Crea y gestiona productos: los artículos y planes vendibles de tu catálogo de Tokeflow, agrupados en familias y con precios definidos a través de ofertas.

Un producto es algo vendible: un artículo de pago único como un curso, o un plan recurrente como un nivel de suscripción. Los productos son la capa intermedia del catálogo. Pertenecen a una familia de productos y sus precios se definen a través de una o más ofertas.

Usa los productos para modelar qué vendes. Usa las ofertas para modelar cómo se compra y se factura.

Un producto tiene un type (one_time o recurring) y un status (active o archived). Cuando un producto pertenece a una familia, su tier_order lo posiciona dentro de esa familia —un valor mayor significa un plan superior— lo que impulsa las rutas de mejora (upgrade) y degradación (downgrade) entre planes recurrentes.

Tokeflow es una plataforma de orquestación de pagos, no un procesador de pagos. El catálogo modela tus precios; la autorización, captura y liquidación reales de cualquier cargo ocurren en el proveedor de pagos conectado. Los objetos del catálogo nunca mueven dinero.

El objeto producto

{
  "id": "prd_a1b2c3d4e5",
  "merchant_id": "mrc_a1b2c3d4e5",
  "product_family_id": "pfa_a1b2c3d4e5",
  "name": "Plano Light",
  "description": "Plano com recursos essenciais",
  "type": "recurring",
  "tier_order": 1,
  "status": "active",
  "metadata": {
    "source": "dashboard"
  },
  "created_at": "2026-05-19T12:00:00.000Z",
  "updated_at": "2026-05-19T12:00:00.000Z"
}
FieldTypeDescription
idstringID único del producto, con el prefijo prd_. Opaco: nunca lo analices.
merchant_idstringEl Merchant propietario del producto (mrc_).
product_family_idstring | nullFamilia a la que pertenece este producto (pfa_), o null si es independiente.
namestringNombre legible por humanos, p. ej. "Plano Light".
descriptionstring | nullDescripción más larga opcional.
typeenumone_time o recurring.
tier_orderinteger | nullPosición dentro de la familia (mayor = plan superior). null cuando el producto no tiene familia.
statusenumactive o archived.
metadataobject | nullDatos clave/valor arbitrarios que adjuntas. Se devuelven tal cual.
created_atstringMarca de tiempo de creación en ISO 8601 UTC.
updated_atstringMarca de tiempo de la última actualización en ISO 8601 UTC.

Enumeraciones

EnumValues
typeone_time, recurring
statusactive, archived

tier_order es obligatorio siempre que se establezca product_family_id, y debe ser único dentro de la familia. Se utiliza para ordenar los planes en mejoras (upgrades) y degradaciones (downgrades). Para un producto independiente (sin familia), déjalo sin establecer.


Crear un producto

POST/api/v1/products

Auth: clave de Organization (con merchant_id) o clave de Merchant. Ámbito: products:write.

Crea un producto bajo un Merchant. Combina esta creación con una clave de idempotencia cuando sean posibles los reintentos.

Parámetros del cuerpo

FieldTypeRequiredDescription
namestringSíNombre del producto.
typeenumSíone_time o recurring.
statusenumSíactive o archived.
product_family_idstringNoFamilia bajo la cual agrupar el producto (pfa_). Obligatorio para productos recurrentes que participan en flujos de mejora/degradación.
tier_orderintegerCondicionalPosición dentro de la familia (mín. 0, mayor = superior). Obligatorio cuando se establece product_family_id.
descriptionstringNoDescripción opcional.
metadataobjectNoMetadatos arbitrarios a adjuntar.

Con una clave de Organization, incluye merchant_id en el cuerpo de la solicitud para dirigirte a un Merchant. Con una clave de Merchant, el Merchant se infiere a partir de la clave: omítelo.

curl -X POST https://api.tokeflow.com/api/v1/products \
  -H "Authorization: Bearer sk_live_mer_…" \
  -H "Content-Type: application/json" \
  -H "Idempotency-Key: 9b1f7e0a-2c3d-4e5f-8a9b-0c1d2e3f4a5b" \
  -d '{
    "name": "Plano Light",
    "type": "recurring",
    "status": "active",
    "product_family_id": "pfa_a1b2c3d4e5",
    "description": "Plano com recursos essenciais",
    "tier_order": 1,
    "metadata": { "source": "dashboard" }
  }'

Respuesta 201 Created

{
  "success": true,
  "data": {
    "id": "prd_a1b2c3d4e5",
    "merchant_id": "mrc_a1b2c3d4e5",
    "product_family_id": "pfa_a1b2c3d4e5",
    "name": "Plano Light",
    "description": "Plano com recursos essenciais",
    "type": "recurring",
    "tier_order": 1,
    "status": "active",
    "metadata": { "source": "dashboard" },
    "created_at": "2026-05-19T12:00:00.000Z",
    "updated_at": "2026-05-19T12:00:00.000Z"
  },
  "request_id": "req_8f3c…",
  "timestamp": "2026-05-19T12:00:00.000Z"
}

tier_order debe ser único dentro de una familia. Reutilizar un tier_order ya ocupado por otro producto de la misma familia devuelve 409 (conflict_error).


Listar productos

GET/api/v1/products

Auth: clave de Organization (con merchant_id) o clave de Merchant. Ámbito: products:read.

Devuelve una lista paginada de productos del Merchant, los más recientes primero. Todos los filtros son opcionales y se combinan con AND.

Parámetros de consulta

FieldTypeRequiredDescription
pageintegerNoNúmero de página, indexado desde 1. Predeterminado 1.
limitintegerNoElementos por página. Predeterminado 20, máximo 100.
typeenumNoFiltra por one_time o recurring.
statusenumNoFiltra por active o archived.
product_family_idstringNoRestringe a una sola familia (pfa_).
namestringNoCoincidencia parcial, sin distinción de mayúsculas y minúsculas, en el nombre del producto.
date_fromstringNoSolo productos creados en o después de esta marca de tiempo ISO 8601.
date_tostringNoSolo productos creados en o antes de esta marca de tiempo ISO 8601.
merchant_idstringCondicionalObligatorio con una clave de Organization para dirigirse a un Merchant.
curl "https://api.tokeflow.com/api/v1/products?page=1&limit=20&type=recurring&status=active&product_family_id=pfa_a1b2c3d4e5&name=Pro&date_from=2026-01-01T00:00:00Z&date_to=2026-12-31T23:59:59Z" \
  -H "Authorization: Bearer sk_live_mer_…"

Respuesta 200 OK

{
  "success": true,
  "data": [
    {
      "id": "prd_a1b2c3d4e5",
      "merchant_id": "mrc_a1b2c3d4e5",
      "product_family_id": "pfa_a1b2c3d4e5",
      "name": "Plano Light",
      "description": "Plano com recursos essenciais",
      "type": "recurring",
      "tier_order": 1,
      "status": "active",
      "metadata": { "source": "dashboard" },
      "created_at": "2026-05-19T12:00:00.000Z",
      "updated_at": "2026-05-19T12:00:00.000Z"
    },
    {
      "id": "prd_f6e5d4c3b2",
      "merchant_id": "mrc_a1b2c3d4e5",
      "product_family_id": "pfa_a1b2c3d4e5",
      "name": "Plano Pro",
      "description": "Plano com recursos avançados",
      "type": "recurring",
      "tier_order": 2,
      "status": "active",
      "metadata": null,
      "created_at": "2026-05-19T12:05:00.000Z",
      "updated_at": "2026-05-19T12:05:00.000Z"
    }
  ],
  "meta": {
    "pagination": {
      "page": 1,
      "limit": 20,
      "total": 2,
      "total_pages": 1,
      "has_next": false,
      "has_prev": false
    }
  },
  "request_id": "req_8f3c…",
  "timestamp": "2026-05-19T12:30:00.000Z"
}

Consulta Paginación y filtrado para conocer las convenciones compartidas.


Obtener un producto

GET/api/v1/products/:id

Auth: clave de Organization (con merchant_id) o clave de Merchant. Ámbito: products:read.

Recupera un único producto por su ID.

curl https://api.tokeflow.com/api/v1/products/prd_a1b2c3d4e5 \
  -H "Authorization: Bearer sk_live_mer_…"

Respuesta 200 OK

{
  "success": true,
  "data": {
    "id": "prd_a1b2c3d4e5",
    "merchant_id": "mrc_a1b2c3d4e5",
    "product_family_id": "pfa_a1b2c3d4e5",
    "name": "Plano Light",
    "description": "Plano com recursos essenciais",
    "type": "recurring",
    "tier_order": 1,
    "status": "active",
    "metadata": { "source": "dashboard" },
    "created_at": "2026-05-19T12:00:00.000Z",
    "updated_at": "2026-05-19T12:00:00.000Z"
  },
  "request_id": "req_8f3c…",
  "timestamp": "2026-05-19T12:30:00.000Z"
}

Un ID desconocido devuelve 404 (not_found_error).


Actualizar un producto

PATCH/api/v1/products/:id

Auth: clave de Organization (con merchant_id) o clave de Merchant. Ámbito: products:write.

Actualización parcial. Envía solo los campos que quieras cambiar; los campos omitidos se dejan intactos.

Parámetros del cuerpo

FieldTypeRequiredDescription
namestringNoNombre nuevo.
typeenumNoone_time o recurring.
statusenumNoactive o archived.
product_family_idstringNoMueve el producto a otra familia.
tier_orderintegerNoNueva posición dentro de la familia.
descriptionstringNoNueva descripción.
metadataobjectNoReemplaza el objeto de metadatos almacenado.
curl -X PATCH https://api.tokeflow.com/api/v1/products/prd_a1b2c3d4e5 \
  -H "Authorization: Bearer sk_live_mer_…" \
  -H "Content-Type: application/json" \
  -d '{
    "name": "Plano Light Plus",
    "tier_order": 2
  }'

Respuesta 200 OK

{
  "success": true,
  "data": {
    "id": "prd_a1b2c3d4e5",
    "merchant_id": "mrc_a1b2c3d4e5",
    "product_family_id": "pfa_a1b2c3d4e5",
    "name": "Plano Light Plus",
    "description": "Plano com recursos essenciais",
    "type": "recurring",
    "tier_order": 2,
    "status": "active",
    "metadata": { "source": "dashboard" },
    "created_at": "2026-05-19T12:00:00.000Z",
    "updated_at": "2026-05-19T13:00:00.000Z"
  },
  "request_id": "req_8f3c…",
  "timestamp": "2026-05-19T13:00:00.000Z"
}

metadata se reemplaza, no se combina. Para conservar las claves existentes, envía el objeto completo que quieras almacenar.


Eliminar un producto

DELETE/api/v1/products/:id

Auth: clave de Organization (con merchant_id) o clave de Merchant. Ámbito: products:write.

Elimina un producto de forma lógica (soft-delete). El registro se conserva por trazabilidad y puede recuperarse con restaurar. Un producto eliminado de forma lógica ya no aparece en los resultados de la lista.

curl -X DELETE https://api.tokeflow.com/api/v1/products/prd_a1b2c3d4e5 \
  -H "Authorization: Bearer sk_live_mer_…"

Respuesta 204 No Content

Una eliminación exitosa devuelve un cuerpo vacío con el estado 204.

La eliminación lógica (soft delete) y el archivado son diferentes. Archivar mantiene el producto en tu catálogo con status: archived (visible, no vendible). Eliminar lo quita del catálogo (recuperable mediante restauración). Usa archivar para retirar un plan al que aún quieras hacer referencia; usa eliminar para sacar un producto por completo.


Restaurar un producto

POST/api/v1/products/:id/restore

Auth: clave de Organization (con merchant_id) o clave de Merchant. Ámbito: products:write.

Restaura un producto eliminado de forma lógica, devolviéndolo al catálogo con sus atributos anteriores.

curl -X POST https://api.tokeflow.com/api/v1/products/prd_a1b2c3d4e5/restore \
  -H "Authorization: Bearer sk_live_mer_…"

Respuesta 201 Created

{
  "success": true,
  "data": {
    "id": "prd_a1b2c3d4e5",
    "merchant_id": "mrc_a1b2c3d4e5",
    "product_family_id": "pfa_a1b2c3d4e5",
    "name": "Plano Light",
    "description": "Plano com recursos essenciais",
    "type": "recurring",
    "tier_order": 1,
    "status": "active",
    "metadata": { "source": "dashboard" },
    "created_at": "2026-05-19T12:00:00.000Z",
    "updated_at": "2026-05-19T14:00:00.000Z"
  },
  "request_id": "req_8f3c…",
  "timestamp": "2026-05-19T14:00:00.000Z"
}

Archivar un producto

POST/api/v1/products/:id/archive

Auth: clave de Organization (con merchant_id) o clave de Merchant. Ámbito: products:write.

Establece status en archived. El producto permanece en tu catálogo e historial, pero ya no se ofrece para nuevas compras.

curl -X POST https://api.tokeflow.com/api/v1/products/prd_a1b2c3d4e5/archive \
  -H "Authorization: Bearer sk_live_mer_…"

Respuesta 201 Created

{
  "success": true,
  "data": {
    "id": "prd_a1b2c3d4e5",
    "merchant_id": "mrc_a1b2c3d4e5",
    "product_family_id": "pfa_a1b2c3d4e5",
    "name": "Plano Light",
    "description": "Plano com recursos essenciais",
    "type": "recurring",
    "tier_order": 1,
    "status": "archived",
    "metadata": { "source": "dashboard" },
    "created_at": "2026-05-19T12:00:00.000Z",
    "updated_at": "2026-05-19T15:00:00.000Z"
  },
  "request_id": "req_8f3c…",
  "timestamp": "2026-05-19T15:00:00.000Z"
}

Desarchivar un producto

POST/api/v1/products/:id/unarchive

Auth: clave de Organization (con merchant_id) o clave de Merchant. Ámbito: products:write.

Vuelve a establecer status en active, devolviendo un producto archivado a un estado vendible.

curl -X POST https://api.tokeflow.com/api/v1/products/prd_a1b2c3d4e5/unarchive \
  -H "Authorization: Bearer sk_live_mer_…"

Respuesta 201 Created

{
  "success": true,
  "data": {
    "id": "prd_a1b2c3d4e5",
    "merchant_id": "mrc_a1b2c3d4e5",
    "product_family_id": "pfa_a1b2c3d4e5",
    "name": "Plano Light",
    "description": "Plano com recursos essenciais",
    "type": "recurring",
    "tier_order": 1,
    "status": "active",
    "metadata": { "source": "dashboard" },
    "created_at": "2026-05-19T12:00:00.000Z",
    "updated_at": "2026-05-19T16:00:00.000Z"
  },
  "request_id": "req_8f3c…",
  "timestamp": "2026-05-19T16:00:00.000Z"
}

Obtener la oferta predeterminada

GET/api/v1/products/:id/default-offer

Auth: clave de Organization (con merchant_id) o clave de Merchant. Ámbito: products:read.

Devuelve la oferta predeterminada del producto: la que utiliza un checkout cuando no se nombra ninguna oferta específica. Responde con data: null cuando el producto no tiene una oferta predeterminada.

curl https://api.tokeflow.com/api/v1/products/prd_a1b2c3d4e5/default-offer \
  -H "Authorization: Bearer sk_live_mer_…"

Respuesta 200 OK — existe una oferta predeterminada

{
  "success": true,
  "data": {
    "id": "ofr_a1b2c3d4e5",
    "product_id": "prd_a1b2c3d4e5",
    "name": "Mensal",
    "slug": "mensal",
    "description": "Plano mensal padrão",
    "billing_cycle": "monthly",
    "custom_billing_days": null,
    "cycle_limit": 12,
    "free_trial": false,
    "trial_days": null,
    "setup_charge": false,
    "renew_after_cycle_limit": false,
    "renewal_offer_id": null,
    "is_default": true,
    "status": "active",
    "created_at": "2026-05-19T12:00:00.000Z",
    "updated_at": "2026-05-19T12:00:00.000Z",
    "prices": [
      {
        "id": "opr_b1c2d3e4f5",
        "offer_id": "ofr_a1b2c3d4e5",
        "currency": "BRL",
        "amount": 9900,
        "first_charge_amount": null,
        "is_default": true,
        "created_at": "2026-05-19T12:00:00.000Z",
        "updated_at": "2026-05-19T12:00:00.000Z"
      }
    ]
  },
  "request_id": "req_8f3c…",
  "timestamp": "2026-05-19T12:30:00.000Z"
}

Respuesta 200 OK — sin oferta predeterminada

{
  "success": true,
  "data": null,
  "request_id": "req_8f3c…",
  "timestamp": "2026-05-19T12:30:00.000Z"
}

Los importes en los precios de las ofertas son enteros en unidades menores (centavos). 9900 con la moneda BRL es R$99.00. Consulta Ofertas y Precios de ofertas para conocer el modelo de precios completo.


Errores

Los productos utilizan el sobre de error estándar. Casos comunes:

StatustypeWhen
400validation_errorCampo faltante o inválido, p. ej. type o status desconocido.
401authentication_errorClave de API faltante o inválida.
403authorization_errorLa clave carece del ámbito products:read / products:write requerido.
404not_found_errorNo hay ningún producto con ese ID para el Merchant.
409conflict_errortier_order ya utilizado por otro producto de la familia.

Consulta el catálogo de errores completo para conocer los códigos y su manejo.

Relacionado

En esta página