> ## Documentation Index
> Fetch the complete documentation index at: https://docs.keebai.com/llms.txt
> Use this file to discover all available pages before exploring further.

# POST /v1/ecommerce/sales

> Record a sale or an internal consumption, and issue its receipt or invoice in the same call. Deducts stock and calculates commissions.

Creates a sale in Keebai. Stock is deducted from the branch, commissions are calculated, and, if you pass `dte`, the electronic tax document is issued right after. It is also the way to issue an invoice: a free line with a net price, a known customer RUT and a payment method are enough.

Everything that can fail — receiver data, payment, credit, branch, the document type, SKUs — is checked before the sale is created.

A `type: "internal"` sale records internal consumption instead: products taken out of stock for the business's own use, with no payments and no DTE.

## Endpoint

```
POST https://api.keebai.com/v1/ecommerce/sales
```

## Required scope

`ecommerce:sales:write`

Sending `dte` also needs `ecommerce:invoicing:issue`. Without it the request fails with `403 INSUFFICIENT_SCOPE` before the sale is created.

> [!NOTE]
>
> **The invoicing scope comes from your role.** Minting a token with `ecommerce:invoicing:issue` requires the permission to issue DTE in your Keebai role, unless you are the company owner or a superuser. See [scopes](https://docs.keebai.com/dev/scopes.md#scopes-are-independent-from-role-permissions).

## Headers

| Header | Required | Value |
| - | - | - |
| `Authorization` | Yes | `Bearer kbai_pk_<token>` |
| `Content-Type` | Yes | `application/json` |
| `Idempotency-Key` | No | Your own unique key for this sale. Retrying with the same key does not create a second sale. |

## Body

| Field | Type | Required | Description |
| - | - | - | - |
| `type` | `string` | No | `sale` (default), a sale with payments, or `internal`, internal consumption: products only, no `payments`, no `dte`. |
| `branch_id` | `string` | No | Branch the sale happens in. Stock is deducted from it. Defaults to the company's only active branch; with several, the request fails with `BRANCH_REQUIRED`. |
| `items` | `object[]` | Yes | Line items: a catalog product or a free line. See below. |
| `customer` | `object` | No | `customer_id`, `name`, `email`, `phone`. |
| `seller` | `object` | No | `user_id` and `name`, both required when you send `seller`. |
| `payments` | `object[]` | No | Payments of the sale. See below. |
| `notes` | `string` | No | Free text. |
| `sold_at` | `string` | No | ISO 8601 date-time of the sale. |
| `currency` | `string` | No | Currency of the amounts. |
| `dte` | `object` | No | Issue the electronic tax document after creating the sale. See below. |

### Item

| Field | Type | Required | Description |
| - | - | - | - |
| `product_id` | `string` | No | `ObjectId` of the product. Send `product_id` or `sku` for a catalog product. Without both, the line is a free line. |
| `variant_id` | `string` | No | `ObjectId` of the variant. |
| `sku` | `string` | No | SKU or barcode. Resolves the product and variant without sending `product_id`. |
| `name` | `string` | Conditional | Line name. Defaults to the product's. Required on a free line. |
| `quantity` | `number` | Yes | Units. |
| `price` | `number` | Conditional | Unit price, VAT included. Send `price` or `net_price`, not both. Without either, a product line takes the product's, variant's, or price list's price. A free line needs one of them. |
| `net_price` | `number` | Conditional | Unit price before VAT, as you quote a business. The document shows exactly this net. |
| `discount_percentage` | `number` | No | Discount on the line, in percent. |
| `commissionee` | `object` | No | Who earns the commission of the line: `id` and `name`. |
| `exempt` | `boolean` | No | The line is exempt from VAT. |

### Payment

| Field | Type | Required | Description |
| - | - | - | - |
| `method` | `string` | Yes | Payment method. |
| `amount` | `number` | Conditional | Amount paid. With a single payment you can leave it out: the sale total is charged. With several payments each one needs its amount. |
| `reference` | `string` | No | External reference, such as a voucher number. |
| `installments` | `number` | No | Installments. |

### DTE

| Field | Type | Required | Description |
| - | - | - | - |
| `document` | `string` | Yes | `receipt` (boleta), `exempt_receipt` (boleta exenta), `invoice` (factura), or `exempt_invoice` (factura exenta). |
| `receiver` | `object` | Conditional | `rut`, `legal_name`, `activity`, `address`, `commune`, `email?`. Required for `invoice` and `exempt_invoice`. For a RUT the company invoiced before, `rut` alone is enough: the rest is filled in from the stored data, and any field you send overrides it. |
| `due_date` | `string` | No | `YYYY-MM-DD`. Due date of an invoice issued on credit, on a sale that is not fully paid. Defaults to today plus the company's credit days. Ignored when the sale is paid. |

Check which documents your company can issue today, and whether it allows credit invoices, with [`GET /v1/ecommerce/invoicing/types`](https://docs.keebai.com/dev/endpoints/ecommerce-invoicing-types).

## Example requests

```bash Sale with boleta theme={"system"}
curl -X POST https://api.keebai.com/v1/ecommerce/sales \
  -H "Authorization: Bearer kbai_pk_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" \
  -H "Content-Type: application/json" \
  -H "Idempotency-Key: pos-01-ticket-99120" \
  -d '{
    "branch_id": "br_01",
    "items": [
      { "sku": "RUN-PRO-42-NEG", "quantity": 1 },
      { "product_id": "65d3e4f5a6b7c8d9e0f1a2b9", "quantity": 2, "price": 4990, "discount_percentage": 10 }
    ],
    "customer": { "name": "Juan Pérez", "email": "juan@example.com", "phone": "56912345678" },
    "payments": [{ "method": "card", "amount": 68972, "reference": "voucher-4411" }],
    "dte": { "document": "receipt" }
  }'
```

```bash Invoice for a known customer theme={"system"}
curl -X POST https://api.keebai.com/v1/ecommerce/sales \
  -H "Authorization: Bearer kbai_pk_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" \
  -H "Content-Type: application/json" \
  -d '{
    "items": [{ "name": "Consulting hours", "quantity": 2, "net_price": 150000 }],
    "payments": [{ "method": "transfer", "reference": "TRX-8812" }],
    "dte": { "document": "invoice", "receiver": { "rut": "76123456-7" } }
  }'
```

```bash Invoice for a new customer theme={"system"}
curl -X POST https://api.keebai.com/v1/ecommerce/sales \
  -H "Authorization: Bearer kbai_pk_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" \
  -H "Content-Type: application/json" \
  -d '{
    "branch_id": "br_01",
    "items": [{ "sku": "RUN-PRO-42-NEG", "quantity": 3 }],
    "payments": [{ "method": "transfer", "amount": 179970 }],
    "dte": {
      "document": "invoice",
      "receiver": {
        "rut": "76123456-7",
        "legal_name": "Comercial Ejemplo SpA",
        "activity": "Venta al por menor",
        "address": "Av. Libertador 1234",
        "commune": "Santiago",
        "email": "facturas@ejemplo.cl"
      }
    }
  }'
```

```bash Invoice on credit with free lines theme={"system"}
curl -X POST https://api.keebai.com/v1/ecommerce/sales \
  -H "Authorization: Bearer kbai_pk_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" \
  -H "Content-Type: application/json" \
  -H "Idempotency-Key: consulting-2026-11" \
  -d '{
    "items": [
      { "name": "Consulting hours", "quantity": 2, "net_price": 150000 },
      { "name": "Filing fee", "quantity": 1, "net_price": 5000, "exempt": true }
    ],
    "dte": {
      "document": "invoice",
      "due_date": "2026-12-10",
      "receiver": { "rut": "76123456-7" }
    }
  }'
```

```bash Internal consumption theme={"system"}
curl -X POST https://api.keebai.com/v1/ecommerce/sales \
  -H "Authorization: Bearer kbai_pk_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" \
  -H "Content-Type: application/json" \
  -d '{
    "type": "internal",
    "branch_id": "br_01",
    "items": [{ "sku": "SHAMPOO-500", "quantity": 1 }],
    "notes": "Uso en lavado"
  }'
```

```js JavaScript theme={"system"}
const response = await fetch("https://api.keebai.com/v1/ecommerce/sales", {
  method: "POST",
  headers: {
    Authorization: `Bearer ${process.env.KEEBAI_API_TOKEN}`,
    "Content-Type": "application/json",
    "Idempotency-Key": ticketId,
  },
  body: JSON.stringify({
    branch_id: "br_01",
    items: [{ sku: "RUN-PRO-42-NEG", quantity: 1 }],
    payments: [{ method: "cash", amount: 59990 }],
    dte: { document: "receipt" },
  }),
});
const { sale, dte } = await response.json();
```

```python Python theme={"system"}
import os, requests

resp = requests.post(
    "https://api.keebai.com/v1/ecommerce/sales",
    headers={
        "Authorization": f"Bearer {os.environ['KEEBAI_API_TOKEN']}",
        "Idempotency-Key": ticket_id,
    },
    json={
        "branch_id": "br_01",
        "items": [{"sku": "RUN-PRO-42-NEG", "quantity": 1}],
        "payments": [{"method": "cash", "amount": 59990}],
        "dte": {"document": "receipt"},
    },
    timeout=30,
)
resp.raise_for_status()
result = resp.json()
```

## Response

### 201 Created

`sale` has the same shape as [`GET /v1/ecommerce/sales/{id}`](https://docs.keebai.com/dev/endpoints/ecommerce-sale-get). `dte` is present only when you sent `dte`.

```json theme={"system"}
{
  "sale": {
    "_id": "65e4f5a6b7c8d9e0f1a2b3c4",
    "sale_number": 1043,
    "status": "completed",
    "payment_status": "paid",
    "currency": "CLP",
    "items": [
      {
        "kind": "product",
        "name": "Zapatilla Runner Pro",
        "quantity": 1,
        "unit_price": 59990,
        "subtotal": 59990
      }
    ],
    "amounts": {
      "total": 59990
    },
    "branch_id": "br_01",
    "created_at": "2026-11-04T14:31:07.221Z"
  },
  "dte": {
    "issued": [
      {
        "sale_id": "65e4f5a6b7c8d9e0f1a2b3c4",
        "document": "receipt",
        "type": 39,
        "folio": 15422,
        "document_id": "6653e4f5a6b7c8d9e0f1a2b3",
        "status": "uploaded",
        "net": 50412,
        "exempt": 0,
        "tax": 9578,
        "total": 59990
      }
    ],
    "failed": []
  }
}
```

| Field | Type | Description |
| - | - | - |
| `sale` | `object` | The created sale. |
| `dte.issued[]` | `object[]` | Documents issued: `sale_id`, `document`, `type` (SII code), `folio`, `document_id`, `status`, `net`, `exempt`, `tax`, `total`, and `due_date` for an invoice on credit. |
| `dte.failed[]` | `object[]` | Documents that could not be issued: `sale_id`, `reason` (the error code), `message?`. The reasons are listed in [`POST /v1/ecommerce/sales/{id}/dte`](https://docs.keebai.com/dev/endpoints/ecommerce-sale-dte-issue#failure-reasons). |

### 400 Bad Request

The body does not match the schema, a field the endpoint does not accept, or one of these. Nothing is created.

| `code` | Meaning |
| - | - |
| `SALE_ITEM_CUSTOM_INCOMPLETE` | A free line (no `product_id` and no `sku`) is missing `name`, or has neither `price` nor `net_price`. |
| `SALE_ITEM_INVALID` | A line has both `price` and `net_price`. |
| `PAYMENT_AMOUNT_REQUIRED` | Several payments, and one of them has no `amount`. |
| `PAYMENT_REQUIRED` | A `receipt` or `exempt_receipt` on a sale that is not fully paid. `pending` tells you what is missing when payments were sent. |
| `DUE_DATE_INVALID` | `due_date` is not `YYYY-MM-DD` or is before today. |
| `EXEMPT_DOCUMENT_REQUIRED` | Every line is exempt: use `exempt_invoice` or `exempt_receipt`. |
| `BRANCH_REQUIRED` | No `branch_id`, and the company has no active branch or more than one. `branches` lists them. |
| `INTERNAL_SALE_PAYMENTS_NOT_ALLOWED` | A `type: "internal"` sale carried `payments`. |
| `INTERNAL_SALE_DTE_NOT_ALLOWED` | A `type: "internal"` sale carried `dte`. |
| `INTERNAL_SALE_PRODUCTS_ONLY` | A `type: "internal"` sale carried a free line. Internal consumption only takes catalog products. |

### 401 Unauthorized

Missing, invalid, revoked, or expired token.

### 403 Forbidden

`INSUFFICIENT_SCOPE` — the token does not have `ecommerce:sales:write`, or it sent `dte` without `ecommerce:invoicing:issue`. Nothing is created.

### 422 Unprocessable Entity

| `code` | Meaning |
| - | - |
| `RECEIVER_DATA_REQUIRED` | The invoice receiver is incomplete and the RUT has no stored data to fill it. `missing` lists the fields. |
| `CREDIT_NOT_ENABLED` | An `invoice` or `exempt_invoice` on a sale that is not fully paid, and the company has not enabled credit invoices. |
| `DOCUMENT_NOT_AVAILABLE` | The company cannot issue that document today. `available` lists the ones it can. |
| `SKU_NOT_FOUND` | No product has that `sku`. |
| `SKU_AMBIGUOUS` | The `sku` matches more than one product. |
| `INVALID_PAYMENT` | A payment is not valid for the company — for example a method it does not accept. |
| `STOCK_INSUFFICIENT_IN_BRANCH` | The branch does not have enough stock for one of the items. |

### 502 Bad Gateway

`ECOMMERCE_UPSTREAM_ERROR` — the ecommerce service could not answer.

## Operational notes

* **Send an `Idempotency-Key` from a point of sale.** A timeout does not tell you whether the sale was created. Retrying with the same key returns `201` with the original sale and creates nothing new; without it, a retry can double the sale and the stock deduction.
* **Errors are caught before anything is created.** Every `400` and `422` above leaves no sale and no stock movement behind.
* **A failed confirmation leaves nothing behind.** If the sale cannot be confirmed — for example `INVALID_PAYMENT` or `STOCK_INSUFFICIENT_IN_BRANCH` — the cart is discarded and the error is returned.
* **A failed DTE does not undo the sale.** The sale stays created and the failure comes back in `dte.failed`. Fix the cause and issue it later with [`POST /v1/ecommerce/sales/{id}/dte`](https://docs.keebai.com/dev/endpoints/ecommerce-sale-dte-issue).
* **A receipt needs a paid sale.** A receipt whose payments do not cover the sale fails with `PAYMENT_REQUIRED` before the sale is confirmed.
* **An invoice can go on credit.** When the company enables credit invoices in **Sales › Settings**, an `invoice` or `exempt_invoice` on a sale that is not fully paid is issued with a due date (`due_date`, or today plus the company's credit days). Otherwise it fails with `CREDIT_NOT_ENABLED` and nothing is created. Record the payment later from the Keebai portal or with the MCP tool `keebai_ecommerce_sale_payment_add`.
* **Net prices are exact.** With `net_price` the document shows exactly that net. A product line without its own price in the same sale keeps the catalog price it has at that moment.
* **`internal` never issues a DTE.** Internal consumption has no payments and no tax document; it only moves stock.
* **Lines are catalog products or free lines.** Send `product_id` (with `variant_id` when it has variants) or `sku` for a product; without `price`, `net_price` or `name`, the product's are used. A line with neither `product_id` nor `sku` is a free line, such as a service or a charge outside the catalog: it needs `name` and a price, and moves no stock.
* **Commissions are calculated on the sale.** `commissionee` on a line decides who earns it.


## OpenAPI

````yaml POST /v1/ecommerce/sales
openapi: 3.0.0
info:
  title: Keebai Public API
  description: Superficie pública REST autenticada con Personal Access Tokens (PAT).
  version: 1.0.0
  contact: {}
servers:
  - url: https://api.keebai.com
    description: Production
security: []
tags: []
paths:
  /v1/ecommerce/sales:
    post:
      tags:
        - ecommerce
      summary: Crear una venta
      description: >-
        Crea y confirma una venta y, con `dte`, emite su documento en la misma
        llamada. Cada línea es un producto (`product_id`, con `variant_id`
        opcional), un `sku`, o una línea libre con `name`. El precio va con IVA
        (`price`) o neto (`net_price`); sin él, el producto toma su precio. Sin
        `branch_id` se usa la única sucursal activa. Con un solo pago se puede
        omitir el monto. Una factura con un RUT ya facturado solo necesita
        `receiver.rut`. Todo lo que puede fallar se revisa antes de escribir.
        Con `type: "internal"` es una venta interna (solo productos, sin pagos
        ni DTE). Si la emisión falla la venta queda hecha y el error va en
        `dte.failed`.
      operationId: PublicEcommerceOperationsController_createSale
      parameters:
        - name: idempotency-key
          required: true
          in: header
          schema:
            type: string
        - name: Idempotency-Key
          in: header
          description: >-
            Identificador único de la venta para reintentos. Sin él se genera
            uno
          required: false
          schema:
            type: string
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/PublicSaleCreateDto'
      responses:
        '201':
          description: ''
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/PublicSaleCreateResponseDto'
      security:
        - PAT: []
components:
  schemas:
    PublicSaleCreateDto:
      type: object
      properties:
        type:
          type: string
          enum:
            - sale
            - internal
          default: sale
          description: >-
            `sale` venta normal con pagos; `internal` venta interna, solo
            productos, sin pagos ni DTE
        branch_id:
          type: string
          description: >-
            Sucursal de la venta. Sin ella se usa la única sucursal activa de la
            empresa
        items:
          type: array
          items:
            $ref: '#/components/schemas/PublicSaleItemDto'
        customer:
          $ref: '#/components/schemas/PublicSaleCustomerDto'
        seller:
          $ref: '#/components/schemas/PublicSaleSellerDto'
        payments:
          type: array
          items:
            $ref: '#/components/schemas/PublicSalePaymentDto'
        notes:
          type: string
          maxLength: 1000
        sold_at:
          type: string
          description: Fecha de la venta, ISO 8601
        currency:
          type: string
          default: CLP
          example: CLP
        dte:
          description: >-
            Documento tributario a emitir después de confirmar la venta. Si
            falla, la venta queda igual y el error va en `dte.failed`
          allOf:
            - $ref: '#/components/schemas/PublicSaleDteDto'
      required:
        - items
    PublicSaleCreateResponseDto:
      type: object
      properties:
        sale:
          $ref: '#/components/schemas/PublicSaleResponseDto'
        dte:
          description: Solo cuando se pidió `dte`
          allOf:
            - $ref: '#/components/schemas/PublicDteIssueResultDto'
      required:
        - sale
    PublicSaleItemDto:
      type: object
      properties:
        product_id:
          type: string
          description: ObjectId del producto
        variant_id:
          type: string
          description: ObjectId de la variante
        sku:
          type: string
          description: >-
            SKU o código de barras. Sin `product_id`, la línea se resuelve al
            producto o variante que lo tenga. Sin `product_id` ni `sku`, la
            línea es libre: lleva `name` y `price` o `net_price`, y no mueve
            stock
        name:
          type: string
          description: Nombre de la línea. Sin él, se usa el del producto
        quantity:
          type: number
          description: Cantidad
          example: 1
        price:
          type: number
          description: >-
            Precio unitario con IVA incluido. Usa `price` o `net_price`, no
            ambos. Sin ninguno, una línea de producto toma el precio del
            producto, la variante o la lista de precios
        net_price:
          type: number
          description: >-
            Precio unitario neto, sin IVA. El documento muestra exactamente ese
            neto
        discount_percentage:
          type: number
          minimum: 0
          maximum: 100
        commissionee:
          $ref: '#/components/schemas/PublicSaleCommissioneeDto'
        exempt:
          type: boolean
          description: Línea exenta de IVA
      required:
        - quantity
    PublicSaleCustomerDto:
      type: object
      properties:
        customer_id:
          type: string
          description: ObjectId del cliente del CRM
        name:
          type: string
        email:
          type: string
        phone:
          type: string
          example: '56912345678'
    PublicSaleSellerDto:
      type: object
      properties:
        user_id:
          type: string
          description: ObjectId del usuario vendedor
        name:
          type: string
          description: Nombre del vendedor
      required:
        - user_id
        - name
    PublicSalePaymentDto:
      type: object
      properties:
        method:
          type: string
          description: Código del medio de pago configurado en la empresa
          example: cash
        amount:
          type: number
          description: >-
            Monto pagado. Con un solo pago se puede omitir y se usa el total de
            la venta
          example: 15000
        reference:
          type: string
          description: Código de la transacción, cuando el medio lo pide
        installments:
          type: number
          minimum: 1
      required:
        - method
    PublicSaleDteDto:
      type: object
      properties:
        document:
          type: string
          enum:
            - invoice
            - exempt_invoice
            - receipt
            - exempt_receipt
          description: >-
            invoice (factura), exempt_invoice (factura exenta), receipt
            (boleta), exempt_receipt (boleta exenta). La factura exige
            `receiver`; con un RUT ya facturado basta `receiver.rut`
        due_date:
          type: string
          description: >-
            Vencimiento (YYYY-MM-DD) de una factura emitida a crédito, sobre una
            venta que no está pagada completa. Sin él, hoy más los días
            configurados en la empresa. Se ignora si la venta está pagada
          example: '2026-12-10'
        receiver:
          $ref: '#/components/schemas/PublicDteReceiverDto'
      required:
        - document
    PublicSaleResponseDto:
      type: object
      properties:
        _id:
          type: string
          description: ObjectId de la venta
        sale_number:
          type: number
          description: Correlativo legible de la venta
        status:
          type: string
          enum:
            - completed
            - cancelled
            - refunded
        payment_status:
          type: string
          enum:
            - pending
            - paid
            - partially_paid
            - refunded
        currency:
          type: string
        customer:
          $ref: '#/components/schemas/PublicSaleCustomerDto'
        items:
          type: array
          items:
            $ref: '#/components/schemas/PublicSaleItemDto'
        amounts:
          $ref: '#/components/schemas/PublicSaleAmountsDto'
        payment_method:
          type: string
        branch_id:
          type: string
          description: Sucursal asociada
        notes:
          type: string
        paid_at:
          type: string
          format: date-time
        cancelled_at:
          type: string
          format: date-time
        refunded_at:
          type: string
          format: date-time
        created_at:
          type: string
          format: date-time
        updated_at:
          type: string
          format: date-time
      required:
        - _id
        - sale_number
        - status
        - payment_status
        - currency
        - customer
        - items
        - amounts
        - created_at
        - updated_at
    PublicDteIssueResultDto:
      type: object
      properties:
        issued:
          type: array
          items:
            $ref: '#/components/schemas/PublicDteIssuedDto'
        failed:
          type: array
          items:
            $ref: '#/components/schemas/PublicDteFailedDto'
      required:
        - issued
        - failed
    PublicSaleCommissioneeDto:
      type: object
      properties:
        id:
          type: string
          description: Id de quien se lleva la comisión de la línea
        name:
          type: string
          description: Nombre visible del comisionado
      required:
        - id
    PublicDteReceiverDto:
      type: object
      properties:
        rut:
          type: string
          description: RUT del receptor
          example: 76123456-7
        legal_name:
          type: string
          description: >-
            Razón social. Con un RUT ya facturado antes, se completa con los
            datos guardados
          maxLength: 100
        activity:
          type: string
          description: Giro
          maxLength: 40
        address:
          type: string
          description: Dirección
          maxLength: 70
        commune:
          type: string
          description: Comuna
          maxLength: 20
        email:
          type: string
          description: Correo del receptor
          maxLength: 80
      required:
        - rut
    PublicSaleAmountsDto:
      type: object
      properties:
        service_subtotal:
          type: number
        products_subtotal:
          type: number
        custom_subtotal:
          type: number
        net_subtotal:
          type: number
        tax_amount:
          type: number
        tip:
          type: number
        total:
          type: number
      required:
        - service_subtotal
        - products_subtotal
        - custom_subtotal
        - net_subtotal
        - tax_amount
        - tip
        - total
    PublicDteIssuedDto:
      type: object
      properties:
        sale_id:
          type: string
        document:
          type: string
          enum:
            - invoice
            - exempt_invoice
            - receipt
            - exempt_receipt
            - credit_note
            - debit_note
            - purchase_invoice
            - invoice_settlement
            - dispatch_guide
        type:
          type: number
          description: Código SII del documento
        folio:
          type: number
        document_id:
          type: string
        status:
          type: string
        net:
          type: number
          description: Neto afecto, CLP
        exempt:
          type: number
          description: Monto exento, CLP
        tax:
          type: number
          description: IVA, CLP
        total:
          type: number
          description: Total, CLP
        due_date:
          type: string
          description: Vencimiento de una factura emitida a crédito (YYYY-MM-DD)
      required:
        - sale_id
        - document
        - type
        - folio
        - document_id
        - status
    PublicDteFailedDto:
      type: object
      properties:
        sale_id:
          type: string
        reason:
          type: string
          description: >-
            Motivo: dte_error, not_found, o el código del error cuando la
            emisión no llegó a hacerse
        message:
          type: string
      required:
        - sale_id
        - reason
  securitySchemes:
    PAT:
      scheme: bearer
      bearerFormat: kbai_pk_<hex>
      type: http
      description: >-
        Personal Access Token con prefijo `kbai_pk_`. Generar desde el portal
        con permiso `developer.manage_tokens`.

````

This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.