Allowances

Descripción General

La API Pública de Viáticos (Allowances) permite consultar y actualizar los viáticos asignados a una subsidiaria específica. Los viáticos siguen un flujo de estados (pending → approved → accounted → paid) y pueden incluir beneficiario, segmentos y documentos que justifican el pago.

Estados Disponibles

EstadoDescripción
pendingSolicitud creada y esperando aprobación interna.
approvedAprobada internamente y lista para ser contabilizada/pagada.
accountedContabilizada en tu sistema externo (requiereaccounted_id opcional).
paidPagada; se recomienda enviarpaid_id y paid_at.
rejectedRechazada durante el flujo interno de aprobación (solo lectura en API).

Solo es posible transicionar a través de la API desde:

  • approved → accounted
  • approved → paid
  • accounted → paid

Todas las transiciones se ejecutan mediante los métodos FSM internos (mark_as_accounted, mark_as_paid) para asegurar reglas de negocio y notificaciones.


Endpoints Disponibles

MétodoEndpointDescripción
GET/public/v1/enterprises/{enterprise_id}/subsidiaries/{subsidiary_id}/allowances/Lista de viáticos filtrables y paginados.
GET/public/v1/enterprises/{enterprise_id}/subsidiaries/{subsidiary_id}/allowances/{id}/Detalle de un viático específico.
PATCH/public/v1/enterprises/{enterprise_id}/subsidiaries/{subsidiary_id}/allowances/{id}/Actualiza estado aaccounted o paid.

1. Listar Viáticos

Endpoint

GET /public/v1/enterprises/{enterprise_id}/subsidiaries/{subsidiary_id}/allowances/

Query Params

ParámetroDescripción
pageNúmero de página (default 1).
page_sizeTamaño de página (default 100, máximo 1000).
stateFiltra por estado (pending, approved, accounted, paid, rejected).
expandCampos a expandir (ver secciónExpand).

Expand Disponibles

  • beneficiary: Devuelve objeto embebido del beneficiario (campos básicos).
  • allowance_segments: Lista de segmentos con fares, monto y días.
  • documents: Documentos asociados con URL firmada temporalmente.

Si no se solicita expand, la respuesta entrega IDs para reducir carga.

Respuesta Ejemplo

{
  "count": 2,
  "next": null,
  "previous": null,
  "status": 200,
  "error": "",
  "results": [
    {
      "id": "a24cd858-2de4-4c00-b167-02d0b60e5bf4",
      "allowance_number": 1234,
      "description": "Viaje a Santiago",
      "state": "approved",
      "beneficiary_id": "bf33075c-cb3b-44e4-9762-b21b16354e74",
      "cost_center_id": "6f14a4e4-3513-4a47-9b5f-8a9fba118db7",
      "start_date": "2025-01-10T08:00:00Z",
      "end_date": "2025-01-12T20:30:00Z",
      "days": 3,
      "amount": {
        "amount": 150000.0,
        "currency": "CLP"
      },
      "currency": "CLP",
      "converted_amount": 150000.0,
      "accounted_id": null,
      "paid_id": null,
      "paid_at": null,
      "created_at": "2025-01-05T15:30:00Z",
      "is_active": true
    }
  ]
}

2. Obtener Detalle

Endpoint

GET /public/v1/enterprises/{enterprise_id}/subsidiaries/{subsidiary_id}/allowances/{allowance_id}/

Query Params

Los mismos que en listado (expand es el más común).

Ejemplo con expand=beneficiary,allowance_segments

{
  "status": 200,
  "error": "",
  "id": "a24cd858-2de4-4c00-b167-02d0b60e5bf4",
  "allowance_number": 1234,
  "description": "Viaje a Santiago",
  "state": "approved",
  "beneficiary": {
    "id": "bf33075c-cb3b-44e4-9762-b21b16354e74",
    "first_name": "Joshua",
    "last_name": "Murphy",
    "email": "[email protected]",
    "phone": "+56912345678",
    "internal_id": "EMP-202",
    "government_id": "12345678-9"
  },
  "start_date": "2025-01-10T08:00:00Z",
  "end_date": "2025-01-12T20:30:00Z",
  "days": 3,
  "allowance_segments": [
    {
      "id": "9cb3bf44-61c9-4f74-9f68-c1e28feb11e0",
      "start_date": "2025-01-10T08:00:00Z",
      "end_date": "2025-01-11T08:00:00Z",
      "fare_id": "3c6a2a43-7ec5-456b-9417-8d4d4245b5e1",
      "fare_name": "Viático CLP Día Completo",
      "days": 1.0,
      "amount": {
        "amount": 50000.0,
        "currency": "CLP"
      },
      "converted_amount": {
        "amount": 50000.0,
        "currency": "CLP"
      }
    }
  ],
  "currency": "CLP",
  "converted_amount": 150000.0,
  "created_at": "2025-01-05T15:30:00Z",
  "is_active": true
}

3. Actualizar Estado (PATCH)

Solo permite mover el estado a accounted o paid. Cuando se actualiza el estado, se pueden almacenar identificadores externos para conciliación.

Endpoint

PATCH /public/v1/enterprises/{enterprise_id}/subsidiaries/{subsidiary_id}/allowances/{allowance_id}/

Body

CampoTipoRequeridoDescripción
statestringaccounted o paid.
accounted_idstringOpcionalID de tu sistema contable. Solo se usa cuando el estado objetivo esaccounted o paid.
paid_idstringOpcionalID del pago en tu sistema financiero. Se ignora si el estado objetivo esaccounted.
paid_atdatetimeOpcionalFecha/hora ISO8601 del pago (paid).

Validaciones Clave

  • No puedes enviar paid_id/paid_at si el estado objetivo es accounted.
  • No puedes repetir el mismo estado actual (Allowance is already in {state} state).
  • Transiciones inválidas retornan 400 con mensaje "Invalid state transition from '{current}' to '{new}'."

Ejemplo: Marcar como Contabilizado

PATCH /public/v1/enterprises/{enterprise_id}/subsidiaries/{subsidiary_id}/allowances/a24cd858-2de4-4c00-b167-02d0b60e5bf4/
Authorization: Api-Key en_sk_xxxxx
Content-Type: application/json

{
  "state": "accounted",
  "accounted_id": "ACC-2025-001"
}

Response 200 OK

{
  "id": "a24cd858-2de4-4c00-b167-02d0b60e5bf4",
  "state": "accounted",
  "accounted_id": "ACC-2025-001",
  "paid_id": null,
  "paid_at": null,
  "converted_amount": 150000.0,
  "updated_at": "2025-01-15T12:00:00Z"
}

Ejemplo: Marcar como Pagado

{
  "state": "paid",
  "accounted_id": "ACC-2025-001",
  "paid_id": "PAY-2025-115",
  "paid_at": "2025-01-20T10:30:00Z"
}

Esto ejecuta mark_as_paid(), envía notificaciones internas (muted en tests) y persiste paid_at.


Códigos de Respuesta Comunes

CódigoSignificadoMotivo Común
200OKOperación exitosa de GET o PATCH.
400Bad RequestTransición inválida, campos faltantes o estado actual.
403ForbiddenAPI Key inválida o empresa diferente al path.
404Not FoundViático no existe dentro de la subsidiaria/empresa dada.

Mejores Prácticas

  1. Paginar: Cuando existan muchos viáticos, usar page_size para evitar timeouts.
  2. Idempotencia: Antes de reintentar un PATCH, lee el viático y verifica el estado actual.
  3. Registro externos: Guardar accounted_id y paid_id con tus IDs para conciliación.
  4. Expand selectivo: Solo pedir expand cuando realmente necesites el detalle, para respuestas más rápidas.
  5. Zonas Horarias: Todos los timestamps (paid_at, created_at) deben enviarse/interpretarse en ISO8601 UTC.

Con esto puedes integrar la API pública de viáticos a tus sistemas contables/financieros de forma segura y trazable.