Notas de venta

Cobros puntuales con link de pago o cargo automático: crea, finaliza, envía y cobra notas de venta.

Notas de venta

Una nota de venta (Invoice) es un documento de cobro. Existe en dos sabores:

  1. Generada por una suscripción — una por ciclo, automática. No las creas ni las editas tú; las lees para conciliar (Ciclo de vida).
  2. Creada por ti — un cobro puntual a un cliente: una cuota, un servicio único, un saldo pendiente. El cliente la paga a través de su link de pago, o Venti la carga automáticamente a un medio de pago inscrito.

Esta página cubre el segundo sabor.

📘

La nota de venta es un documento de cobro de Venti, no un documento tributario: no reemplaza tu boleta o factura.

El flujo

draft ──(finalize)──→ open ──(pago o cargo automático)──→ paid
  │                    │ └──(void)──→ void
  └──(void)──→ void    └──(mark_uncollectible)──→ uncollectible

1. Crear (estado draft)

curl https://api.ventipay.com/v1/invoices \
  -u sk_live_xxx: \
  -H "Content-Type: application/json" \
  -d '{
    "currency": "clp",
    "customer_email": "[email protected]",
    "description": "Servicio de instalación",
    "lines": [
      { "name": "Instalación a domicilio", "price": 45000, "quantity": 1 }
    ],
    "tax_amounts": [
      { "name": "IVA", "percentage": 19, "inclusive": true }
    ],
    "due_at": "2026-08-01"
  }'
{
  "id": "inv_Rw5xPq7KvL2mT9nJ4sZcY8fH",
  "object": "invoice",
  "status": "draft",
  "paid": false,
  "currency": "clp",
  "amount": 45000,
  "subtotal": 45000,
  "tax": 8550,
  "tax_amounts": [
    { "name": "IVA", "percentage": 19, "inclusive": true, "amount": 8550 }
  ],
  "lines": [
    { "name": "Instalación a domicilio", "price": 45000, "quantity": 1, "total": 45000 }
  ],
  "collection_method": "send_invoice",
  "customer_id": "cus_WBRjn77K2eFdAoU7gKibtkb3",
  "due_at": "2026-08-01T00:00:00.000Z",
  "url": "https://pay.ventipay.com/invoice/inv_Rw5xPq7KvL2mT9nJ4sZcY8fH"
}

Cómo se calcula el total, siempre en unidades menores:

  • subtotal = suma de price × quantity de las lines.
  • discount = cupones aplicables + promoción, si los hay.
  • tax_amounts con inclusive: true solo se desglosan; con inclusive: false se suman al total.
  • amount = subtotal − discount + impuestos exclusivos. Es lo que paga el cliente.
🚧

Los impuestos de una nota de venta viajan en tax_amounts (nombre, porcentaje, inclusivo) — usa los datos de tus TaxRate. El campo default_tax_rates (IDs) solo asocia los impuestos como referencia y no afecta el total.

En draft puedes editar todo con PUT /invoices/{id}: líneas, impuestos, cliente, período, medio de pago, forma de cobro. Después de finalizarla, solo los campos descriptivos (description, due_at, note, metadata) y el cliente/medio de pago.

2. Finalizar (estado open)

curl -X POST https://api.ventipay.com/v1/invoices/inv_Rw5xPq7KvL2mT9nJ4sZcY8fH/finalize \
  -u sk_live_xxx:

La nota de venta queda open: cobrable e inmutable en sus montos.

3. Cobrar

Tienes tres caminos, combinables:

a) El cliente paga por el link. Comparte la url (o envíala por email con POST /invoices/{id}/send, que requiere un cliente con email). El cliente paga en la página alojada de Venti con cualquier medio de pago disponible, como en un checkout normal.

b) Cargo a un medio de pago inscrito.

curl -X POST https://api.ventipay.com/v1/invoices/inv_Rw5xPq7KvL2mT9nJ4sZcY8fH/authorize \
  -u sk_live_xxx: \
  -H "Content-Type: application/json" \
  -d '{ "payment_method_id": "pm_Kc9rXw2LqN7vT4mJ8sZhP3fY" }'

También disponible como POST /invoices/{id}/pay. Sin payment_method_id, usa el default_payment_method_id de la nota de venta. Para inscribir tarjetas sin cobrar, usa un Setup Intent.

c) Cobro automático programado. Crea la nota de venta con collection_method: automatic, un default_payment_method_id y una fecha due_at: a partir del vencimiento, Venti intenta el cargo automáticamente de forma periódica mientras siga open.

¿Te pagaron por fuera (efectivo, transferencia directa)? Márcala pagada sin mover dinero:

curl -X POST https://api.ventipay.com/v1/invoices/inv_Rw5xPq7KvL2mT9nJ4sZcY8fH/authorize \
  -u sk_live_xxx: \
  -H "Content-Type: application/json" \
  -d '{ "paid_out_of_band": true }'

4. Pagada

Al pagarse, la nota de venta queda paid con paid_at y successful_payment_id — un Payment normal que abona a tu balance menos las comisiones estándar. Si fue paid_out_of_band, no hay pago asociado ni movimiento de dinero.

Para reembolsar, reembolsa el pago asociado (POST /payments/{successful_payment_id}/refund). Las notas de venta marcadas paid_out_of_band no son reembolsables por Venti.

Cerrar sin cobrar

  • POST /invoices/{id}/voidanula la nota de venta (error de emisión, cobro improcedente). No se puede pagar ni reabrir.
  • POST /invoices/{id}/mark_uncollectible — la marca incobrable (el cliente no pagará). Es un estado contable final; no aplica a notas de venta paid o void.

Notas de venta de suscripción

Las notas de venta con subscription_id las genera y cobra el motor de renovación:

  • Nacen directamente open y con collection_method: automatic.
  • Su period_starts_at / period_ends_at es el ciclo que cubren, y hay exactamente una por período — reintentos y reprocesos nunca duplican el cobro.
  • proration indica si el período fue parcial y cuánto se descontó.
  • Si cambias el medio de pago de la suscripción, sus notas de venta pendientes se actualizan solas.

Filtra por suscripción con GET /invoices?subscription_id=sub_... o por estado con GET /invoices?status[]=open.