PuntoAyuda

Buscar

Buscar en la ayuda

Desarrolladores · versión 1.0.0

API de integraciones de Punto

Con esta API, el sistema de tu comercio (una tienda online, un ERP, una app de pedidos) le manda a Punto cada pedido y Punto hace el resto: da de alta al comprador, descuenta stock, calcula los impuestos, numera el comprobante, emite la factura electrónica cuando corresponde y lo suma a los reportes, igual que si la venta se hubiera hecho en el mostrador.

Hay dos entradas: ventas (un pedido ya cobrado, que se factura en el acto) y órdenes (un pedido para preparar y entregar, que se factura después).

Dirección base de la API

export PUNTO_API="https://api.punto.la"
export PUNTO_KEY="<tu key de integración>"

Antes de empezar

Para conectar tu sistema hacen falta tres cosas, y las prepara el comercio desde el panel de Punto:

  1. El complemento API de integraciones activo. Se contrata desde el panel, en Mi plan. Sin él, todas las llamadas responden 403 con reason: addon_api_required.
  2. Una caja para el canal. Cada pedido nombra la caja de Punto contra la que se registra (registerId). Se crea como cualquier otra caja, en Configuración › Sucursales, y es la que decide todo lo fiscal: si tiene timbrado y punto de expedición cargados, las ventas salen con factura; si no, se registran sin emitir. Usá una caja dedicada, sin ningún dispositivo conectado: si en esa caja también vende una persona, los dos numeran comprobantes de la misma serie.
  3. Una key de integración. Ver Autenticación.

El identificador de la caja se ve en la dirección del navegador al abrirla en Configuración.

Autenticación

Cada llamada lleva la key en el encabezado Authorization:

Authorization: Bearer <tu key>

La key se emite en Configuración › Keys de integración → Nueva key, eligiendo en Qué puede hacer la opción Integración de ventas. Se muestra una sola vez: guardala en el servidor de tu sistema, nunca en el navegador ni en una app que se distribuye.

Alcance de una key. Cada key se emite con un alcance fijo, que no se puede cambiar después (se emite una nueva y se revoca la anterior):

AlcancePara qué sirve
read (Lectura)Consultar datos del comercio: catálogo, reportes. Es el que usa el conector MCP.
write (Lectura y configuración)Lo usa Punto AI para configurar el comercio. No sirve para esta API.
integration (Integración de ventas)Esta API: registrar ventas y órdenes, y además leer el catálogo.

Los alcances no se incluyen entre sí: una key write no registra ventas y una integration no configura nada.

Una key no puede más que su dueño. Hereda los permisos y las sucursales del usuario que la emitió: emitila con un usuario que tenga permiso para vender y acceso a la sucursal de la caja del canal.

Cortar el acceso. Revocar la key en el panel la deja sin efecto en el acto, sin tocar lo que ya se registró. Si se da de baja el complemento, todas las keys dejan de responder solas.

Límites de uso

Cada key tiene dos límites, que se cuentan por key (no por comercio ni por IP):

  • 60 llamadas por minuto.
  • 5.000 llamadas por día.

Al pasarte, la llamada responde 429 y no se procesa. Esperá un minuto antes de reintentar y espaciá los reintentos (por ejemplo, 1, 2, 4 y 8 segundos entre intentos). Para consultar el estado fiscal de un pedido no hace falta más de una consulta cada 30 segundos.

Errores

Toda respuesta tiene la misma forma. Si salió bien:

{ "ok": true, "data": { ... } }

Si no:

{
  "ok": false,
  "error": {
    "message": "El total del pedido no coincide con lo que suman sus líneas...",
    "code": 422,
    "details": { "reason": "total_mismatch", "declared": 19000, "computed": 22000 }
  }
}

Programá contra error.details.reason, no contra el texto: el texto es para la persona que lee el registro y puede cambiar. Qué significa cada status:

StatusQué hacer
401Falta la key o es inválida.
403La key no puede hacer esto: complemento inactivo, alcance equivocado, usuario sin permiso o cuenta del comercio bloqueada. Reintentar no lo arregla.
404El pedido consultado no existe en este comercio.
409El estado del comercio impide registrarlo (por ejemplo, se agotó la numeración de la caja). No reintentes igual: hace falta que alguien lo resuelva en Punto.
422El pedido tiene un dato que corregir. Arreglalo y volvé a mandarlo.
429Límite de uso. Esperá y reintentá.
5xxFalla del servidor. Reintentá con el MISMO orderId: es seguro (ver Idempotencia).

Los reason de cada operación están en su sección.

Idempotencia

Cada pedido viaja con orderId: el identificador del pedido en tu sistema (letras, números, punto, guion y guion bajo, hasta 45 caracteres). Es lo que garantiza que un pedido no se registre dos veces.

  • Si mandás el mismo orderId otra vez —porque se cortó la conexión y no viste la respuesta—, Punto devuelve lo que ya había registrado, con duplicated: true y status 200. Un alta nueva responde 201 con duplicated: false.
  • Si llegan dos llamadas del mismo pedido a la vez, se registra una sola y las dos reciben el mismo resultado.
  • El reintento devuelve lo registrado aunque el catálogo haya cambiado desde entonces: nunca te va a decir que un pedido ya facturado falló.

Ventas y órdenes tienen cada una su espacio de orderId: el mismo pedido puede entrar primero como orden y después como venta con el mismo identificador.

Precios, impuestos y totales

Cada línea nombra un artículo del catálogo de Punto (por itemId o por sku), la cantidad y el precio unitario que cobró tu sistema. Punto compara ese precio con el de su lista (la del cliente, la de la sucursal o la del catálogo, en ese orden):

  • Por debajo de la lista, la diferencia queda registrada como descuento de la línea. Así el margen y el reporte de productos siguen siendo reales.
  • Por encima de la lista, se acepta como precio modificado, igual que cuando el cajero cambia un precio a mano.
  • Agregados (addons): se nombran por optionId y cantidad; el recargo lo pone el catálogo. El unitPrice de la línea es el precio con los agregados incluidos.
  • Envíos y recargos van en charges, como línea propia con su descripción. Nunca sumados al precio de un producto.

Los impuestos los calcula Punto con las mismas reglas que una venta del mostrador: tu sistema no manda IVA ni totales por tasa, y si los manda se ignoran. Tampoco manda el número de comprobante: la numeración es de Punto.

El total se compara. Mandás en total lo que cobraste (o vas a cobrar) al comprador, y Punto lo compara con lo que suman las líneas. Si la diferencia es mayor al redondeo (una unidad de la moneda por línea), el pedido no se registra y responde 422 con reason: total_mismatch, declared y computed. Nunca se factura algo distinto de lo que vio el comprador.

Factura electrónica y KuDE

Si la caja del canal tiene facturación electrónica configurada, cada venta emite su documento electrónico. En Paraguay (SIFEN) el documento se envía a validar en segundo plano, así que la respuesta del alta todavía no trae el veredicto: se consulta después.

Cómo seguirlo. Consultá GET /v1/integrations/sales?orderId=<id> (o el de la orden, si la facturaste desde una orden) hasta que einvoice.sifenVerdict deje de ser pending. Una consulta cada 30 segundos alcanza; la mayoría se resuelven en pocos minutos.

einvoiceQué significa
status: nullLa caja no emite factura electrónica. La venta está registrada igual.
sifenVerdict: pendingEnviada, esperando validación.
sifenVerdict: approved (issued: true)Aprobada. cdc y documentNumber son los datos del documento.
sifenVerdict: rejectedRechazada; sifenReason dice por qué. La corrige el comercio desde el panel: no reenvíes el pedido, porque ya está registrado.

Dónde recibe el comprador su factura. El KuDE (la representación imprimible del documento) queda disponible en el portal de Punto: einvoice.portalUrl es el link que tu tienda le muestra al comprador, por ejemplo en la confirmación del pedido o en el email que le mandás. Esta API no devuelve el PDF.

issued: true significa que el documento fue aprobado, no solo enviado: un documento puede haberse enviado y ser rechazado después.

Órdenes: del pedido a la factura

Una orden es un pedido para preparar y entregar: entra a la cola de la cocina y a la pantalla de pedidos del local como cualquier otra, con origen tienda online. No se factura al crearla.

Se factura de dos maneras:

  1. Desde la caja, como cualquier orden (por ejemplo, un delivery que se cobra al volver el repartidor). Consultando GET /v1/integrations/orders vas a ver la venta cuando se cobre.
  2. Desde tu sistema, con POST /v1/integrations/sales y fromOrderId: Punto registra la venta, la vincula a la orden y la cierra, como hace la caja al cobrarla. La venta toma al comprador de la orden si no mandás otro.

Una orden con scheduledFor en otro día no aparece en la cocina hasta ese día. Una orden con envío (fulfillment: delivery) necesita al comprador y la dirección: la dirección queda guardada en su ficha y la orden conserva una copia, así el pedido sigue diciendo a dónde fue aunque el cliente la cambie después.

Ventas

Pedidos ya cobrados, que se registran como venta y se facturan en el acto.

Consultar una venta

GET/v1/integrations/sales

Devuelve la venta registrada para un pedido y el estado de su factura electrónica. Consultala hasta que einvoice.sifenVerdict deje de ser pending (ver Factura electrónica y KuDE).

Parámetros

CampoTipoDescripción
orderIdobligatorio
stringEl identificador del pedido en tu sistema, el mismo que mandaste al registrarlo.

Ejemplo

Estado fiscal

curl "$PUNTO_API/v1/integrations/sales?orderId=WEB-10245" \
  -H "Authorization: Bearer $PUNTO_KEY"

Respuesta (dentro de data)

CampoTipoDescripción
orderId
string
uid
stringIdentificador interno de la venta (ecom: + tu orderId).
transactionId
string (uuid)
duplicated
booleanSolo en el alta: true si el pedido ya estaba registrado.
document
object | null
document.number
string | nullNúmero de comprobante con su prefijo, listo para mostrar.
document.invoiceNo
integer | null
document.prefix
string | nullEstablecimiento y punto de expedición.
document.serie
string | null
document.timbrado
string | null
document.date
string | null
document.total
number | null
einvoice
objectEstado de la factura electrónica. Ver Factura electrónica y KuDE.
einvoice.issued
booleantrue solo si fue aprobada.
einvoice.status
string | nullEstado del envío. null: la caja no emite factura electrónica. Valores: pending, sending, issued, error, cancelled, skipped.
einvoice.sifenVerdict
string | nullValores: pending, approved, rejected.
einvoice.sifenReason
string | nullMotivo del rechazo.
einvoice.cdc
string | nullCódigo de control del documento.
einvoice.documentNumber
string | null
einvoice.portalUrl
string (uri) | nullLink del portal donde el comprador descarga su KuDE.
order
objectSolo con fromOrderId: la orden facturada, ya cerrada.
order.orderId
stringTu identificador del pedido.
order.id
string (uuid)Identificador de la orden en Punto.
order.number
integer | nullNúmero de la orden en la sucursal (el que ve la cocina).
order.status
stringsent: en cola; in_progress: preparándose; ready: lista; out_for_delivery: en camino; delivered: entregada; closed: facturada; cancelled: cancelada. Valores: open, sent, in_progress, ready, out_for_delivery, delivered, closed, cancelled.
order.fulfillment
stringValores: delivery, takeaway, dine_in.
order.scheduledFor
string | null
order.createdAt
string
order.registerId
string (uuid) | null
order.customerId
string (uuid) | null
order.delivery
object | nullLa dirección con la que se registró la orden.
order.delivery.address
string | null
order.delivery.reference
string | null
order.delivery.lat
number | null
order.delivery.lng
number | null
order.total
numberTotal de la orden según sus líneas.

Códigos de respuesta

200La venta y su estado fiscal (sin duplicated).
401Falta la key o es inválida.
403La key no puede hacer esto. reason: addon_api_required (complemento inactivo), api_key_scope_missing (alcance equivocado), account_blocked, account_suspended, account_inactive (cuenta del comercio). Un usuario sin permiso para vender responde 403 sin reason.
404No hay nada registrado con ese orderId en este comercio.
422El pedido tiene un dato que corregir. Ver reason.
429Límite de uso de la key (60 por minuto, 5.000 por día). Esperá un minuto.

Registrar una venta

POST/v1/integrations/sales

Registra un pedido ya cobrado como venta: descuenta stock, calcula impuestos, numera el comprobante y, si la caja lo tiene configurado, emite la factura electrónica.

Con fromOrderId, factura una orden que entró antes por POST /v1/integrations/orders y la cierra.

Motivos de rechazo (error.details.reason): register_unavailable, item_unavailable, addons_invalid, price_below_addons, total_mismatch, tax_unavailable, payment_method_unknown, payment_method_cash, credit_requires_customer, credit_not_enabled, order_not_found, order_outlet_mismatch (422); order_cancelled, order_already_invoiced, invoice_range_exhausted, invoice_number_taken (409). Un timbrado vencido responde 422 con details.code: invoice_auth_expired.

Cuerpo de la petición

CampoTipoDescripción
orderIdobligatorio
stringIdentificador del pedido en tu sistema. Ver Idempotencia. Hasta 45 caracteres.
registerIdobligatorio
string (uuid)La caja de Punto contra la que se registra.
itemsobligatorio
array<object>Hasta 200 elementos.
items[].itemId
string (uuid)Identificador del artículo en Punto.
items[].sku
stringCódigo del artículo, si no mandás itemId. Hasta 120 caracteres.
items[].quantityobligatorio
number
items[].unitPriceobligatorio
numberPrecio por unidad que cobró tu sistema, con los agregados incluidos.
items[].note
stringNota de la línea (llega a la cocina en una orden). Hasta 200 caracteres.
items[].addons
array<object>Agregados del artículo (opciones de sus grupos). El recargo lo pone el catálogo. Hasta 50 elementos.
items[].addons[].optionIdobligatorio
string (uuid)
items[].addons[].quantity
integerPor defecto: 1.
charges
array<object>Hasta 200 elementos.
charges[].descriptionobligatorio
stringHasta 120 caracteres.
charges[].amountobligatorio
number
charges[].taxId
string (uuid)Impuesto del cargo. Sin él, el impuesto predeterminado del comercio.
totalobligatorio
numberLo que cobraste al comprador. Se compara con lo que suman las líneas.
payment
objectObligatorio al contado; prohibido con credit: true.
payment.methodobligatorio
stringMedio de pago configurado en Punto: su identificador, código o nombre. El efectivo se rechaza (payment_method_cash): esa plata no entró al cajón del comercio. Hasta 120 caracteres.
payment.reference
stringReferencia de la pasarela, para conciliar. Hasta 120 caracteres.
customer
objectEl comprador. Se busca por documento; si no existe, se crea (hace falta name o fiscalName). Sin comprador, la venta sale a consumidor final.
customer.document
stringDocumento del comprador (identificador fiscal o personal).
customer.documentType
stringSi el documento es el fiscal o el personal. Sin él, Punto lo deduce. Valores: ruc, ci.
customer.name
string
customer.fiscalName
stringRazón social para la factura.
customer.email
string (email)
customer.phone
stringCon código de país, formato E.164 (por ejemplo +595981000111).
note
stringHasta 500 caracteres.
credit
booleanVenta a crédito: sin payment, con dueDate y un comprador con crédito habilitado en Punto. Por defecto: false.
dueDate
string (date)Vencimiento de una venta a crédito.
issuedAt
string (date-time)Momento de la venta. Sin él, el de la llamada.
fromOrderId
stringorderId de una orden registrada con POST /v1/integrations/orders que esta venta factura. La orden tiene que ser de la misma sucursal que la caja. Hasta 45 caracteres.

Ejemplo

Venta cobrada con envío

curl -X POST "$PUNTO_API/v1/integrations/sales" \
  -H "Authorization: Bearer $PUNTO_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "orderId": "WEB-10245",
    "registerId": "81c541da-640e-4891-a1a0-b32841e64c75",
    "items": [
      { "sku": "CAFE-250", "quantity": 2, "unitPrice": 45000 }
    ],
    "charges": [
      { "description": "Envío a domicilio", "amount": 15000 }
    ],
    "total": 105000,
    "payment": { "method": "Tarjeta de crédito", "reference": "psp_7f3a91" },
    "customer": { "document": "4567890", "name": "Ana Gómez", "email": "[email protected]" }
  }'

Facturar una orden

curl -X POST "$PUNTO_API/v1/integrations/sales" \
  -H "Authorization: Bearer $PUNTO_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "orderId": "WEB-10246",
    "fromOrderId": "WEB-10246",
    "registerId": "81c541da-640e-4891-a1a0-b32841e64c75",
    "items": [
      { "sku": "CAFE-250", "quantity": 1, "unitPrice": 45000 }
    ],
    "total": 45000,
    "payment": { "method": "Transferencia" }
  }'

Respuesta (dentro de data)

CampoTipoDescripción
orderId
string
uid
stringIdentificador interno de la venta (ecom: + tu orderId).
transactionId
string (uuid)
duplicated
booleanSolo en el alta: true si el pedido ya estaba registrado.
document
object | null
document.number
string | nullNúmero de comprobante con su prefijo, listo para mostrar.
document.invoiceNo
integer | null
document.prefix
string | nullEstablecimiento y punto de expedición.
document.serie
string | null
document.timbrado
string | null
document.date
string | null
document.total
number | null
einvoice
objectEstado de la factura electrónica. Ver Factura electrónica y KuDE.
einvoice.issued
booleantrue solo si fue aprobada.
einvoice.status
string | nullEstado del envío. null: la caja no emite factura electrónica. Valores: pending, sending, issued, error, cancelled, skipped.
einvoice.sifenVerdict
string | nullValores: pending, approved, rejected.
einvoice.sifenReason
string | nullMotivo del rechazo.
einvoice.cdc
string | nullCódigo de control del documento.
einvoice.documentNumber
string | null
einvoice.portalUrl
string (uri) | nullLink del portal donde el comprador descarga su KuDE.
order
objectSolo con fromOrderId: la orden facturada, ya cerrada.
order.orderId
stringTu identificador del pedido.
order.id
string (uuid)Identificador de la orden en Punto.
order.number
integer | nullNúmero de la orden en la sucursal (el que ve la cocina).
order.status
stringsent: en cola; in_progress: preparándose; ready: lista; out_for_delivery: en camino; delivered: entregada; closed: facturada; cancelled: cancelada. Valores: open, sent, in_progress, ready, out_for_delivery, delivered, closed, cancelled.
order.fulfillment
stringValores: delivery, takeaway, dine_in.
order.scheduledFor
string | null
order.createdAt
string
order.registerId
string (uuid) | null
order.customerId
string (uuid) | null
order.delivery
object | nullLa dirección con la que se registró la orden.
order.delivery.address
string | null
order.delivery.reference
string | null
order.delivery.lat
number | null
order.delivery.lng
number | null
order.total
numberTotal de la orden según sus líneas.

Códigos de respuesta

200El pedido ya estaba registrado (duplicated: true): es la venta original.
201Venta registrada.
401Falta la key o es inválida.
403La key no puede hacer esto. reason: addon_api_required (complemento inactivo), api_key_scope_missing (alcance equivocado), account_blocked, account_suspended, account_inactive (cuenta del comercio). Un usuario sin permiso para vender responde 403 sin reason.
409El estado del comercio impide registrarlo. No reintentes igual.
422El pedido tiene un dato que corregir. Ver reason.
429Límite de uso de la key (60 por minuto, 5.000 por día). Esperá un minuto.

Órdenes

Pedidos para preparar y entregar, que se facturan después.

Consultar una orden

GET/v1/integrations/orders

En qué punto está la orden (status) y, si ya se facturó —por esta API o en la caja—, la venta con su estado fiscal en sale.

Parámetros

CampoTipoDescripción
orderIdobligatorio
stringEl identificador del pedido en tu sistema, el mismo que mandaste al registrarlo.

Ejemplo

Estado de la orden

curl "$PUNTO_API/v1/integrations/orders?orderId=WEB-10246" \
  -H "Authorization: Bearer $PUNTO_KEY"

Respuesta (dentro de data)

CampoTipoDescripción
orderId
stringTu identificador del pedido.
id
string (uuid)Identificador de la orden en Punto.
number
integer | nullNúmero de la orden en la sucursal (el que ve la cocina).
status
stringsent: en cola; in_progress: preparándose; ready: lista; out_for_delivery: en camino; delivered: entregada; closed: facturada; cancelled: cancelada. Valores: open, sent, in_progress, ready, out_for_delivery, delivered, closed, cancelled.
fulfillment
stringValores: delivery, takeaway, dine_in.
scheduledFor
string | null
createdAt
string
registerId
string (uuid) | null
customerId
string (uuid) | null
delivery
object | nullLa dirección con la que se registró la orden.
delivery.address
string | null
delivery.reference
string | null
delivery.lat
number | null
delivery.lng
number | null
total
numberTotal de la orden según sus líneas.
duplicated
booleanSolo en el alta: true si la orden ya estaba registrada.
invoiced
booleanSi ya tiene una venta.
sale
object | nullLa venta que la facturó, con su estado fiscal.
sale.transactionId
string (uuid)
sale.uid
string
sale.document
object | null
sale.document.number
string | nullNúmero de comprobante con su prefijo, listo para mostrar.
sale.document.invoiceNo
integer | null
sale.document.prefix
string | nullEstablecimiento y punto de expedición.
sale.document.serie
string | null
sale.document.timbrado
string | null
sale.document.date
string | null
sale.document.total
number | null
sale.einvoice
objectEstado de la factura electrónica. Ver Factura electrónica y KuDE.
sale.einvoice.issued
booleantrue solo si fue aprobada.
sale.einvoice.status
string | nullEstado del envío. null: la caja no emite factura electrónica. Valores: pending, sending, issued, error, cancelled, skipped.
sale.einvoice.sifenVerdict
string | nullValores: pending, approved, rejected.
sale.einvoice.sifenReason
string | nullMotivo del rechazo.
sale.einvoice.cdc
string | nullCódigo de control del documento.
sale.einvoice.documentNumber
string | null
sale.einvoice.portalUrl
string (uri) | nullLink del portal donde el comprador descarga su KuDE.

Códigos de respuesta

200La orden (sin duplicated).
401Falta la key o es inválida.
403La key no puede hacer esto. reason: addon_api_required (complemento inactivo), api_key_scope_missing (alcance equivocado), account_blocked, account_suspended, account_inactive (cuenta del comercio). Un usuario sin permiso para vender responde 403 sin reason.
404No hay nada registrado con ese orderId en este comercio.
422El pedido tiene un dato que corregir. Ver reason.
429Límite de uso de la key (60 por minuto, 5.000 por día). Esperá un minuto.

Registrar una orden

POST/v1/integrations/orders

Registra un pedido para preparar y entregar. Entra directo a la cocina y a la pantalla de pedidos del local, con origen tienda online. No se factura: se factura después desde la caja o con POST /v1/integrations/sales y fromOrderId.

Motivos de rechazo (error.details.reason, todos 422): register_unavailable, item_unavailable, addons_invalid, price_below_addons, total_mismatch, tax_unavailable, delivery_requires_customer, delivery_address_required, order_invalid.

Cuerpo de la petición

CampoTipoDescripción
orderIdobligatorio
stringIdentificador del pedido en tu sistema. Ver Idempotencia. Hasta 45 caracteres.
registerIdobligatorio
string (uuid)La caja de Punto; la orden queda en su sucursal.
fulfillmentobligatorio
stringCómo llega al comprador: se envía, lo retira o se consume en el local. Valores: delivery, takeaway, dine_in.
itemsobligatorio
array<object>Hasta 200 elementos.
items[].itemId
string (uuid)Identificador del artículo en Punto.
items[].sku
stringCódigo del artículo, si no mandás itemId. Hasta 120 caracteres.
items[].quantityobligatorio
number
items[].unitPriceobligatorio
numberPrecio por unidad que cobró tu sistema, con los agregados incluidos.
items[].note
stringNota de la línea (llega a la cocina en una orden). Hasta 200 caracteres.
items[].addons
array<object>Agregados del artículo (opciones de sus grupos). El recargo lo pone el catálogo. Hasta 50 elementos.
items[].addons[].optionIdobligatorio
string (uuid)
items[].addons[].quantity
integerPor defecto: 1.
charges
array<object>Hasta 200 elementos.
charges[].descriptionobligatorio
stringHasta 120 caracteres.
charges[].amountobligatorio
number
charges[].taxId
string (uuid)Impuesto del cargo. Sin él, el impuesto predeterminado del comercio.
totalobligatorio
numberLo que el comprador aprobó. Se compara con lo que suman las líneas.
customer
objectObligatorio con fulfillment: delivery.
customer.document
stringDocumento del comprador (identificador fiscal o personal).
customer.documentType
stringSi el documento es el fiscal o el personal. Sin él, Punto lo deduce. Valores: ruc, ci.
customer.name
string
customer.fiscalName
stringRazón social para la factura.
customer.email
string (email)
customer.phone
stringCon código de país, formato E.164 (por ejemplo +595981000111).
delivery
objectObligatorio con fulfillment: delivery.
delivery.addressobligatorio
stringHasta 250 caracteres.
delivery.reference
stringCómo encontrar el lugar. Hasta 250 caracteres.
delivery.lat
numberVan juntas con lng, o ninguna. Entre -90 y 90.
delivery.lng
numberEntre -180 y 180.
delivery.name
stringNombre de la dirección en la ficha del comprador (por ejemplo, Casa). Hasta 80 caracteres.
delivery.city
stringHasta 80 caracteres.
scheduledFor
stringPara cuándo es: fecha (AAAA-MM-DD) o fecha y hora ISO 8601. Sin él, es para ahora.
note
stringHasta 500 caracteres.

Ejemplo

Orden con envío

curl -X POST "$PUNTO_API/v1/integrations/orders" \
  -H "Authorization: Bearer $PUNTO_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "orderId": "WEB-10246",
    "registerId": "81c541da-640e-4891-a1a0-b32841e64c75",
    "fulfillment": "delivery",
    "items": [
      {
        "sku": "HAMB-CLASICA",
        "quantity": 1,
        "unitPrice": 42000,
        "note": "Sin cebolla",
        "addons": [ { "optionId": "c1a2b3c4-d5e6-4f70-8a91-b2c3d4e5f604", "quantity": 1 } ]
      }
    ],
    "charges": [ { "description": "Envío a domicilio", "amount": 10000 } ],
    "total": 52000,
    "customer": { "document": "4567890", "name": "Ana Gómez", "phone": "+595981000111" },
    "delivery": {
      "address": "Av. España 1234",
      "reference": "Portón negro",
      "lat": -25.2867,
      "lng": -57.647
    }
  }'

Respuesta (dentro de data)

CampoTipoDescripción
orderId
stringTu identificador del pedido.
id
string (uuid)Identificador de la orden en Punto.
number
integer | nullNúmero de la orden en la sucursal (el que ve la cocina).
status
stringsent: en cola; in_progress: preparándose; ready: lista; out_for_delivery: en camino; delivered: entregada; closed: facturada; cancelled: cancelada. Valores: open, sent, in_progress, ready, out_for_delivery, delivered, closed, cancelled.
fulfillment
stringValores: delivery, takeaway, dine_in.
scheduledFor
string | null
createdAt
string
registerId
string (uuid) | null
customerId
string (uuid) | null
delivery
object | nullLa dirección con la que se registró la orden.
delivery.address
string | null
delivery.reference
string | null
delivery.lat
number | null
delivery.lng
number | null
total
numberTotal de la orden según sus líneas.
duplicated
booleanSolo en el alta: true si la orden ya estaba registrada.
invoiced
booleanSi ya tiene una venta.
sale
object | nullLa venta que la facturó, con su estado fiscal.
sale.transactionId
string (uuid)
sale.uid
string
sale.document
object | null
sale.document.number
string | nullNúmero de comprobante con su prefijo, listo para mostrar.
sale.document.invoiceNo
integer | null
sale.document.prefix
string | nullEstablecimiento y punto de expedición.
sale.document.serie
string | null
sale.document.timbrado
string | null
sale.document.date
string | null
sale.document.total
number | null
sale.einvoice
objectEstado de la factura electrónica. Ver Factura electrónica y KuDE.
sale.einvoice.issued
booleantrue solo si fue aprobada.
sale.einvoice.status
string | nullEstado del envío. null: la caja no emite factura electrónica. Valores: pending, sending, issued, error, cancelled, skipped.
sale.einvoice.sifenVerdict
string | nullValores: pending, approved, rejected.
sale.einvoice.sifenReason
string | nullMotivo del rechazo.
sale.einvoice.cdc
string | nullCódigo de control del documento.
sale.einvoice.documentNumber
string | null
sale.einvoice.portalUrl
string (uri) | nullLink del portal donde el comprador descarga su KuDE.

Códigos de respuesta

200La orden ya estaba registrada (duplicated: true).
201Orden registrada y enviada a preparar.
401Falta la key o es inválida.
403La key no puede hacer esto. reason: addon_api_required (complemento inactivo), api_key_scope_missing (alcance equivocado), account_blocked, account_suspended, account_inactive (cuenta del comercio). Un usuario sin permiso para vender responde 403 sin reason.
422El pedido tiene un dato que corregir. Ver reason.
429Límite de uso de la key (60 por minuto, 5.000 por día). Esperá un minuto.