Cuentas y bancos
Administra tus cajas, cuentas bancarias y tarjetas (CuentaDinero).
El saldo no se guarda: se calcula siempre como
saldo_inicial + Σ movimientos. Los movimientos nacen de tres
formas: manuales (ajustes/ingresos/egresos que registras a mano),
transferencias internas entre dos cuentas, y automáticos cuando registras
un cobro o un
pago a proveedor con
cuenta_dinero_id.
Autenticación
X-API-Key con una API key que tenga permisos sobre el
recurso cuentas_dinero. Igual que el resto de la API, el
tenant se resuelve por la propia key (no hace falta
X-Tenant-Id en integraciones vía API pública).
Listar cuentas
GET /api/v1/cuentas-dinero?incluir_inactivas= — Lista las cuentas de dinero del tenant, con su saldo_actual calculado
| Parámetro | Tipo | Descripción |
|---|---|---|
incluir_inactivas optional | boolean | Si es true, incluye también las cuentas dadas de baja (activo=false). Default false. |
[
{
"id": 1,
"nombre": "Caja chica",
"tipo": "caja",
"banco": null,
"numero_mascarado": null,
"saldo_inicial": 100.0,
"activo": true,
"creado_en": "2026-01-10T08:00:00",
"saldo_actual": 62.5
},
{
"id": 3,
"nombre": "Banco Pichincha corriente",
"tipo": "banco",
"banco": "Banco Pichincha",
"numero_mascarado": "****4321",
"saldo_inicial": 500.0,
"activo": true,
"creado_en": "2026-01-15T09:00:00",
"saldo_actual": 1280.5
}
]Crear una cuenta
POST /api/v1/cuentas-dinero — Crea una caja, cuenta bancaria o tarjeta
Body
| Parámetro | Tipo | Descripción |
|---|---|---|
nombre required | string | Nombre de la cuenta. Máx 120 caracteres. |
tipo required | string | 'caja', 'banco' o 'tarjeta'. |
banco optional | string | Nombre del banco emisor. Máx 120 caracteres. |
numero_mascarado optional | string | Número de cuenta/tarjeta enmascarado (ej. '****4321'). Máx 30 caracteres. |
saldo_inicial optional | number | Saldo con el que arranca la cuenta antes de cualquier movimiento. Default 0. |
import { Emitoo } from "emitoo";
const client = new Emitoo(); // lee la API key de EMITOO_API_KEY
const cuenta = await client.cuentasDinero.crear({
nombre: "Banco Pichincha corriente",
tipo: "banco",
banco: "Banco Pichincha",
numero_mascarado: "****4321",
saldo_inicial: 500.0,
});from emitoo import EmitooClient
client = EmitooClient() # lee la API key de EMITOO_API_KEY
cuenta = client.cuentas_dinero.crear({
"nombre": "Banco Pichincha corriente",
"tipo": "banco",
"banco": "Banco Pichincha",
"numero_mascarado": "****4321",
"saldo_inicial": 500.00,
})client, err := emitoo.New("") // lee la API key de EMITOO_API_KEY
if err != nil {
log.Fatal(err)
}
ctx := context.Background()
cuenta, err := client.CuentasDinero.Crear(ctx, emitoo.M{
"nombre": "Banco Pichincha corriente",
"tipo": "banco",
"banco": "Banco Pichincha",
"numero_mascarado": "****4321",
"saldo_inicial": 500.0,
})
if err != nil {
log.Fatal(err)
}curl -X POST https://api.emitoo.io/api/v1/cuentas-dinero \
-H "X-API-Key: $EMITOO_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"nombre": "Banco Pichincha corriente",
"tipo": "banco",
"banco": "Banco Pichincha",
"numero_mascarado": "****4321",
"saldo_inicial": 500.00
}'Respuesta (201 Created)
{
"id": 3,
"nombre": "Banco Pichincha corriente",
"tipo": "banco",
"banco": "Banco Pichincha",
"numero_mascarado": "****4321",
"saldo_inicial": 500.0,
"activo": true,
"creado_en": "2026-01-15T09:00:00",
"saldo_actual": 1280.5
}Errores
| Código | Cuándo ocurre |
|---|---|
422 | tipo no es 'caja', 'banco' ni 'tarjeta'. |
Obtener una cuenta
GET /api/v1/cuentas-dinero/{id} — Detalle de una cuenta, con su saldo_actual calculado
Actualizar una cuenta
PATCH /api/v1/cuentas-dinero/{id} — Actualiza campos de la cuenta (parcial)
| Parámetro | Tipo | Descripción |
|---|---|---|
nombre optional | string | Nuevo nombre. |
tipo optional | string | 'caja', 'banco' o 'tarjeta'. |
banco optional | string | Nombre del banco emisor. |
numero_mascarado optional | string | Número enmascarado. |
saldo_inicial optional | number | Redefine el punto de partida del saldo calculado. No reescribe movimientos ya registrados: para corregir el saldo actual sin tocar el histórico, registra un movimiento de ajuste en su lugar. |
activo optional | boolean | false = baja lógica (equivalente a DELETE). true = reactiva una cuenta dada de baja. |
saldo_inicial no es un ajuste de saldo
saldo_inicial desplaza el saldo calculado de TODA la
vida de la cuenta (pasado incluido), porque saldo_actual =
saldo_inicial + Σ movimientos. Si lo que quieres es corregir el
saldo actual en una fecha puntual, usa
POST /cuentas-dinero/{id}/movimientos con
ajuste_ingreso o ajuste_egreso.
Desactivar una cuenta
DELETE /api/v1/cuentas-dinero/{id} — Baja lógica (activo=false). No borra la cuenta ni su historial de movimientos
Responde 204 No Content. Una cuenta inactiva no admite
movimientos nuevos ni transferencias (409); para volver a
usarla, reactívala con PATCH y { "activo": true }.
Transferencias entre cuentas
POST /api/v1/cuentas-dinero/transferencias — Mueve dinero entre dos cuentas propias: crea dos movimientos enlazados en una sola transacción
Body
| Parámetro | Tipo | Descripción |
|---|---|---|
origen_id required | integer | Cuenta de la que sale el dinero. |
destino_id required | integer | Cuenta a la que entra el dinero. Debe ser distinta de origen_id. |
monto required | number | Monto a transferir. Mayor que 0. |
fecha required | datetime | Fecha del movimiento (ISO 8601). |
descripcion optional | string | Nota libre. Máx 300 caracteres. Se copia en ambos movimientos. |
Crea un movimiento transferencia_out en origen_id
y uno transferencia_in en destino_id, con
origen_tipo="transferencia" y origen_id apuntando
al id del movimiento espejo (así puedes reconstruir el par desde
cualquiera de los dos lados).
Respuesta (200 OK)
Un arreglo de los dos movimientos creados: [movimiento_out, movimiento_in].
[
{
"id": 160,
"cuenta_id": 3,
"fecha": "2026-07-06T10:00:00",
"tipo": "transferencia_out",
"monto": 200.0,
"origen_tipo": "transferencia",
"origen_id": 161,
"descripcion": "Traspaso a caja chica",
"conciliado": false,
"creado_en": "2026-07-06T10:00:01"
},
{
"id": 161,
"cuenta_id": 1,
"fecha": "2026-07-06T10:00:00",
"tipo": "transferencia_in",
"monto": 200.0,
"origen_tipo": "transferencia",
"origen_id": 160,
"descripcion": "Traspaso a caja chica",
"conciliado": false,
"creado_en": "2026-07-06T10:00:01"
}
]Errores
| Código | Cuándo ocurre |
|---|---|
404 | origen_id o destino_id no existen (o no son del tenant). |
409 | Alguna de las dos cuentas está inactiva. |
400 / 422 | origen_id es igual a destino_id. |
Movimientos de una cuenta
GET /api/v1/cuentas-dinero/{id}/movimientos?desde=&hasta=&tipo=&limit=&offset= — Historial de movimientos de una cuenta, más reciente primero
| Parámetro | Tipo | Descripción |
|---|---|---|
desde optional | date | Fecha inicial (inclusive). |
hasta optional | date | Fecha final (inclusive). |
tipo optional | string | Filtra por un tipo exacto: ingreso, egreso, transferencia_in, transferencia_out, ajuste_ingreso o ajuste_egreso. |
limit optional | integer | Default 100. |
offset optional | integer | Default 0. |
Cada movimiento trae origen_tipo (cobro,
pago_proveedor, manual o
transferencia) y origen_id (el id del cobro,
pago o movimiento espejo correspondiente) para que puedas reconstruir de
dónde vino cada línea. conciliado queda en false
por defecto: la conciliación bancaria (marcarlo true contra
un extracto importado) llega en una fase posterior de la plataforma.
Registrar un movimiento manual
POST /api/v1/cuentas-dinero/{id}/movimientos — Registra un ingreso, egreso o ajuste manual (no ligado a un cobro/pago/transferencia)
Body
| Parámetro | Tipo | Descripción |
|---|---|---|
tipo required | string | Solo 'ingreso', 'egreso', 'ajuste_ingreso' o 'ajuste_egreso'. 'transferencia_in'/'transferencia_out' están reservados a POST /transferencias. |
monto required | number | Mayor que 0. |
fecha required | datetime | Fecha del movimiento (ISO 8601). |
descripcion optional | string | Nota libre. Máx 300 caracteres. |
import { Emitoo } from "emitoo";
const client = new Emitoo(); // lee la API key de EMITOO_API_KEY
const movimiento = await client.cuentasDinero.crearMovimiento(3, {
tipo: "egreso",
monto: 45.0,
fecha: new Date().toISOString(),
descripcion: "Compra de suministros de oficina",
});from emitoo import EmitooClient
client = EmitooClient() # lee la API key de EMITOO_API_KEY
movimiento = client.cuentas_dinero.crear_movimiento(3, {
"tipo": "egreso",
"monto": 45.00,
"fecha": "2026-07-06T09:30:00",
"descripcion": "Compra de suministros de oficina",
})client, err := emitoo.New("") // lee la API key de EMITOO_API_KEY
if err != nil {
log.Fatal(err)
}
ctx := context.Background()
movimiento, err := client.CuentasDinero.CrearMovimiento(ctx, 3, emitoo.M{
"tipo": "egreso",
"monto": 45.0,
"fecha": time.Now().Format(time.RFC3339),
"descripcion": "Compra de suministros de oficina",
})
if err != nil {
log.Fatal(err)
}curl -X POST https://api.emitoo.io/api/v1/cuentas-dinero/3/movimientos \
-H "X-API-Key: $EMITOO_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"tipo": "egreso",
"monto": 45.00,
"fecha": "2026-07-06T09:30:00",
"descripcion": "Compra de suministros de oficina"
}'Respuesta (201 Created)
{
"id": 152,
"cuenta_id": 3,
"fecha": "2026-07-06T09:30:00",
"tipo": "egreso",
"monto": 45.0,
"origen_tipo": "manual",
"origen_id": null,
"descripcion": "Compra de suministros de oficina",
"conciliado": false,
"creado_en": "2026-07-06T09:30:04"
}Errores
| Código | Cuándo ocurre |
|---|---|
404 | La cuenta no existe (o no es del tenant). |
409 | La cuenta está inactiva. |
422 | tipo no es uno de los 4 valores permitidos para movimiento manual. |
Movimientos automáticos desde cobros y pagos
No hay un endpoint separado para esto: POST /cobros y
POST /pagos-proveedor aceptan un cuenta_dinero_id
opcional. Si lo mandas, el backend crea el movimiento (ingreso
para un cobro, egreso para un pago) en la misma
transacción que el cobro/pago, con origen_tipo igual
a "cobro" o "pago_proveedor" y
origen_id apuntando al id del cobro/pago que lo generó. Si
omites cuenta_dinero_id, el cobro/pago se registra igual,
simplemente sin tocar ninguna cuenta de dinero.
{
"id": 153,
"cuenta_id": 3,
"fecha": "2026-07-06T15:00:00",
"tipo": "ingreso",
"monto": 150.0,
"origen_tipo": "cobro",
"origen_id": 88,
"descripcion": null,
"conciliado": false,
"creado_en": "2026-07-06T15:00:03"
}
Los eventos relevantes para engancharte vía webhook son los del propio
cobro/pago — cobro.registrado y
pago_proveedor.registrado (documentados en
Cobros y
Pagos a proveedores) —, no
uno nuevo de cuentas_dinero: este módulo todavía no emite
eventos propios.
Conciliación bancaria
Fuera de alcance en esta fase
conciliado es
siempre false salvo que lo gestiones tú mismo por fuera de
estos endpoints.