# Nómina electrónica

> Nómina electrónica (102) y su nota de ajuste (103, Reemplazar y Eliminar) por la API de Trevol.

Fuente: https://platform.trevol.si/docs/nomina

Emite el documento soporte de pago de nómina electrónica (102) de cada trabajador y, si hay que cambiarlo, su nota de ajuste (103): Reemplazar o Eliminar. Trevol calcula los totales, numera, firma y envía a la DIAN.

## Antes de emitir

- **La nómina de la empresa tiene que estar habilitada** ante la DIAN (en la app: Nómina → Configurar habilitación). Con una llave de producción (`tvl_live_…`) debe estar `habilitada`; con una de pruebas basta con el set de pruebas registrado. `GET /v1/company` → `capabilities.payroll.status` dice `enabled`, `testing`, `not_registered` o `not_enabled` para el ambiente de tu llave. Si no, `422 company_not_enabled` con `reason: "payroll_not_enabled"`, antes de numerar.
- Los prefijos de la nómina (`capabilities.payroll.prefixes`) se cambian en la app.

## Emitir una nómina

`POST /v1/payrolls` (`createPayroll`)

#### cURL

```bash
curl -X POST "https://api.trevol.si/v1/payrolls" \
  -H "Authorization: Bearer $TREVOL_API_KEY" \
  -H "Idempotency-Key: $(uuidgen)" \
  -H "Content-Type: application/json" \
  -d '{
  "external_id": "NOM-2026-09-001",
  "period": {
    "hire_date": "2024-03-01",
    "start": "2026-09-01",
    "end": "2026-09-30"
  },
  "pay_period": "5",
  "notes": [
    "Nómina de septiembre de 2026"
  ],
  "employee": {
    "type": "01",
    "subtype": "00",
    "high_risk_pension": false,
    "document_type": "13",
    "document_number": "1000000101",
    "first_surname": "PRUEBA",
    "second_surname": "NOMINA01",
    "first_name": "TRABAJADOR",
    "other_names": "DE PRUEBA",
    "workplace": {
      "country": "CO",
      "municipality_code": "76001",
      "address": "Calle 1 # 1-1"
    },
    "integral_salary": false,
    "contract_type": "2",
    "salary": "1423500",
    "code": "TRAB-01"
  },
  "payment": {
    "form": "1",
    "method": "42",
    "bank": "Banco de Pruebas",
    "account_type": "Ahorros",
    "account_number": "0001234501"
  },
  "payment_dates": [
    "2026-09-30"
  ],
  "earnings": {
    "basic": {
      "days": 30,
      "amount": "1423500"
    },
    "transport": [
      {
        "allowance": "200000"
      }
    ]
  },
  "deductions": {
    "health": {
      "percent": "4",
      "amount": "56940"
    },
    "pension": {
      "percent": "4",
      "amount": "56940"
    }
  }
}'
```

#### Respuesta 201

```json
{
  "id": "pr_3f0c1a2b3f0c1a2b3f0c1a2b3f0c1a2b",
  "object": "payroll",
  "environment": "live",
  "status": "accepted",
  "number": "NE15",
  "prefix": "NE",
  "external_id": "NOM-2026-09-001",
  "origin": "api",
  "cune": "abababababababababababababababababababababababababababababababababababababababababababababababab",
  "qr": "https://catalogo-vpfe.dian.gov.co/document/searchqr?documentkey=abababababababababababababababababababababababababababababababababababababababababababababababab",
  "issued_at": "2026-10-23T09:15:02-05:00",
  "submission": "sync",
  "period": {
    "hire_date": "2024-03-01",
    "start": "2026-09-01",
    "end": "2026-09-30"
  },
  "pay_period": "5",
  "currency": "COP",
  "notes": [
    "Nómina de septiembre de 2026"
  ],
  "employee": {
    "type": "01",
    "subtype": "00",
    "high_risk_pension": false,
    "document_type": "13",
    "document_number": "1000000101",
    "first_surname": "PRUEBA",
    "second_surname": "NOMINA01",
    "first_name": "TRABAJADOR",
    "other_names": "DE PRUEBA",
    "workplace": {
      "country": "CO",
      "municipality_code": "76001",
      "address": "Calle 1 # 1-1"
    },
    "integral_salary": false,
    "contract_type": "2",
    "salary": "1423500",
    "code": "TRAB-01"
  },
  "payment": {
    "form": "1",
    "method": "42",
    "bank": "Banco de Pruebas",
    "account_type": "Ahorros",
    "account_number": "0001234501"
  },
  "payment_dates": [
    "2026-09-30"
  ],
  "earnings": {
    "basic": {
      "days": 30,
      "amount": "1423500"
    },
    "transport": [
      {
        "allowance": "200000"
      }
    ]
  },
  "deductions": {
    "health": {
      "percent": "4",
      "amount": "56940"
    },
    "pension": {
      "percent": "4",
      "amount": "56940"
    }
  },
  "totals": {
    "earnings": "1623500.00",
    "deductions": "113880.00",
    "net": "1509620.00"
  },
  "dian": {
    "status_code": "00",
    "message": "Procesado Correctamente.",
    "rules": []
  },
  "files": {
    "xml": true,
    "zip": true,
    "dian_response": true
  },
  "created_at": "2026-10-23T09:15:02-05:00",
  "updated_at": "2026-10-23T09:15:03-05:00"
}
```

[Probar en el Playground](https://platform.trevol.si/playground?op=createPayroll&ejemplo=mensual)

## Reemplazar o eliminar: la nota de ajuste

Reemplazar: la nómina completa corregida, más `type` y `predecessor`. Eliminar: solo el predecesor y las notas.

`POST /v1/payroll_adjustments` (`createPayrollAdjustment`)

#### cURL

```bash
curl -X POST "https://api.trevol.si/v1/payroll_adjustments" \
  -H "Authorization: Bearer $TREVOL_API_KEY" \
  -H "Idempotency-Key: $(uuidgen)" \
  -H "Content-Type: application/json" \
  -d '{
  "external_id": "NOM-2026-09-001-R",
  "period": {
    "hire_date": "2024-03-01",
    "start": "2026-09-01",
    "end": "2026-09-30"
  },
  "pay_period": "5",
  "notes": [
    "Nómina de septiembre de 2026"
  ],
  "employee": {
    "type": "01",
    "subtype": "00",
    "high_risk_pension": false,
    "document_type": "13",
    "document_number": "1000000101",
    "first_surname": "PRUEBA",
    "second_surname": "NOMINA01",
    "first_name": "TRABAJADOR",
    "other_names": "DE PRUEBA",
    "workplace": {
      "country": "CO",
      "municipality_code": "76001",
      "address": "Calle 1 # 1-1"
    },
    "integral_salary": false,
    "contract_type": "2",
    "salary": "1423500",
    "code": "TRAB-01"
  },
  "payment": {
    "form": "1",
    "method": "42",
    "bank": "Banco de Pruebas",
    "account_type": "Ahorros",
    "account_number": "0001234501"
  },
  "payment_dates": [
    "2026-09-30"
  ],
  "earnings": {
    "basic": {
      "days": 30,
      "amount": "1423500"
    },
    "transport": [
      {
        "allowance": "210000"
      }
    ]
  },
  "deductions": {
    "health": {
      "percent": "4",
      "amount": "56940"
    },
    "pension": {
      "percent": "4",
      "amount": "56940"
    }
  },
  "type": "replace",
  "predecessor": {
    "id": "pr_3f0c1a2b3f0c1a2b3f0c1a2b3f0c1a2b"
  }
}'
```

[Probar en el Playground](https://platform.trevol.si/playground?op=createPayrollAdjustment&ejemplo=reemplazar)

`POST /v1/payroll_adjustments` (`createPayrollAdjustment`)

#### cURL

```bash
curl -X POST "https://api.trevol.si/v1/payroll_adjustments" \
  -H "Authorization: Bearer $TREVOL_API_KEY" \
  -H "Idempotency-Key: $(uuidgen)" \
  -H "Content-Type: application/json" \
  -d '{
  "external_id": "NOM-2026-09-001-E",
  "type": "delete",
  "predecessor": {
    "id": "pr_3f0c1a2b3f0c1a2b3f0c1a2b3f0c1a2b"
  },
  "notes": [
    "Enviada por error"
  ]
}'
```

[Probar en el Playground](https://platform.trevol.si/playground?op=createPayrollAdjustment&ejemplo=eliminar)

## Lo que hay que saber

- **Un 102 por trabajador y por mes** en producción. Otro igual es `409 duplicate_document` (con `existing_id`, solo de la misma empresa y ambiente); para cambiarlo se usa la nota de ajuste. Dos pedidos simultáneos del mismo trabajador y mes no pasan los dos.
- **Set de pruebas.** En habilitación con el set pendiente, la respuesta es `202` con `status: "validating"` en las dos versiones; reintentar con la misma clave o `POST …/send` no lo reenvía, y `PUT` en ese estado es `409 invalid_state`.
- **Sin PDF ni correo.** Se descargan `…/xml`, `…/zip` y `…/dian_response`.
- **Datos del trabajador.** Solo salen en las respuestas de tu llave. Los avisos (webhooks) llevan un resumen sin trabajador ni montos, el registro de peticiones no guarda cuerpos, y lo que se guarda para repetir una `Idempotency-Key` es solo `{id, object, status, number}`. Por eso **no se puede filtrar por la cédula**: las listas se filtran por `employee_code` (tu código interno del empleado), `external_id` y `period_end_from` / `period_end_to`.
- El `second_surname` del trabajador es obligatorio.
- El `external_id` es único entre las nóminas y sus ajustes (aparte de las facturas).
- **Cobro por empleado:** cada nómina o nota de ajuste de producción se cobra con la lista de nómina del canal API; la habilitación no cobra.

Las respuestas son las de [toda la API](/docs/respuestas). Referencia: [Nómina electrónica](/docs/api/payrolls) y [sus ajustes](/docs/api/payroll-adjustments).
