Skip to main content
POST
Crear transacción

Resumen

Crea una nueva transacción. Con executeRules: true (por defecto), el motor de reglas corre en forma síncrona y la respuesta incluye un rulesExecutionSummary completo cuando las reglas terminan en la misma request. Si no enviás asyncRules (por defecto false), el comportamiento es el de siempre — las integraciones existentes no cambian.

Endpoint

Autenticación

Requiere una API key válida en el header Authorization:

Parámetros de query

boolean
default:"false"
Con true y executeRules distinto de false, la transacción se crea al instante y la evaluación de reglas se encola en background. La respuesta HTTP vuelve antes de que terminen las reglas. El query param tiene prioridad sobre el mismo campo en el body JSON.Valores truthy aceptados: true, 1, "true", "1", "yes".No aplica en endpoints batch — solo POST /transactions (creación unitaria).

Cuerpo de la petición

Campos requeridos

string
required
Tu identificador único para esta transacción en tu sistema
string
required
Tipo de transacción. Opciones:
  • PAYMENT - Pago
  • TRANSFER - Transferencia
  • WITHDRAWAL - Retiro
  • DEPOSIT - Depósito
  • REFUND - Reembolso
  • CHARGEBACK - Contracargo
  • REVERSAL - Reversión
  • FEE - Comisión
  • ADJUSTMENT - Ajuste
  • OTHER - Otro
number
required
Monto (debe ser cero o positivo)
string
required
Código de moneda (3-4 caracteres, ej. “USD”, “EUR”, “BRL”)
number
Tipo de cambio opcional, usado solo cuando la conversión automática a la moneda base de la organización no está disponible (error del proveedor, timeout o par no soportado). Si omitís este campo, el comportamiento es el de siempre — Gueno consulta el servicio de monedas como hoy.Semántica: unidades de moneda base por 1 unidad de currency. Monto normalizado en la moneda base de la org: montoNormalizado = amount × exchangeRate.Se ignora si la conversión automática tiene éxito (gana la tasa del proveedor).Necesario cuando la conversión automática no está disponible para monedas no convertibles (ver abajo). Ver Conversión de moneda.

Campos opcionales

string
default:"CREATED"
Estado. Opciones:
  • CREATED - Creada (por defecto)
  • PROCESSING - En proceso
  • SUSPENDED - Suspendida
  • SENT - Enviada
  • EXPIRED - Expirada
  • DECLINED - Rechazada
  • REFUNDED - Reembolsada
  • SUCCESSFUL - Exitosa
string
Método de pago. Opciones: CARD, ACH, PIX, TED, BOLETO, WALLET, SWIFT, IBAN, CBU, CVU, DEBIN, GENERIC_BANK_ACCOUNT, MPESA, UPI, CHECK, ECHECK, QR_CODE, ONLINE_PAYMENT, WITHDRAWAL_ORDER
string
Descripción o notas
string
Categoría de la transacción
string
Fecha/hora ISO 8601 del hecho (por defecto: momento de creación). Se guarda en UTC. Usá Z u offset ±HH:MM en el string, o datetime sin offset junto con timeZone (hora local en ese huso).
boolean
default:"true"
Si se ejecuta el motor de reglas. Con false se omiten reglas por completo (sync y async).
boolean
default:"false"
Misma semántica que el query asyncRules. Para ingestión de alto volumen: persistir la transacción rápido y revisar alertas después en gu1. Requiere executeRules: true (default). Ignorado si executeRules es false.
object
Ajuste opcional de la ejecución de reglas tras el alta (sync o async). No desactiva acciones createAlert ni la consolidación de investigaciones.Con notifications: false, gu1 omite notificaciones in-app de la evaluación de reglas (matriz de riesgo / cambios de estado). Alertas e investigaciones siguen el flujo normal.Legacy KYT POST /legacy/kyt/verifyTransaction: mismo objeto en el body Gu2 como configRulesExecution; si se omite, Paytime prod recibe notifications: false por defecto (igual que POST /transactions).
Con false (por defecto): Gu1 igual auto-vincula si hay match. Si no, la TX se crea igual (sin vínculo). Un UUID *EntityId inexistente se limpia (no 404). También ?linkEntityStrict=true.Con true: refs sin resolver → 400 INVALID_ENTITY_REFERENCES y no crea.
boolean
default:"false"
Alias legacy de linkEntityStrict: true. Preferí linkEntityStrict.

Matrices de riesgo (opcional)

string | string[]
Compatible con clientes legacy: un UUID o un array de UUIDs de matrices de la organización. Si se envía una lista no vacía, solo se evalúan reglas activas asociadas a esas matrices (sin mezclar con reglas “sueltas” solo por triggers). Omití riskMatrixId y riskMatrixIds para conservar el comportamiento histórico basado en triggers.
string[]
Forma preferida para varias matrices: lista ordenada de UUIDs. Tiene precedencia sobre riskMatrixId cuando viene informada y no vacía.

Origen (entidad)

Cómo se vincula el origen en gu1 (en orden; se aplica el primer criterio que resuelva):
  1. ID de entidad — si enviás originEntityId, se usa esa entidad (debe existir en tu organización).
  2. ID externo — si no enviaste originEntityId pero sí originExternalId y existe una persona/empresa con el mismo externalId, se vincula automáticamente.
  3. Tercer fallback: tax / documento (root) — si aún no hay vinculación, pero enviás en la raíz de la transacción originTaxId, el API busca una persona/empresa cuyo taxId coincida tras normalizar (solo letras y números, sin puntuación ni espacios; la comparación ignora mayúsculas).
Si resuelve el paso 2 o 3, se rellenan originEntityId y, si no los enviaste, se pueden completar originName y originCountry desde la entidad.Denormalización canónica (origen vinculado): cuando el origen queda vinculado a una persona/empresa — enviaste originEntityId, o el auto-link resolvió por originExternalId / originTaxId — gu1 sincroniza las columnas denormalizadas desde la fila de la entidad antes del insert:Si la entidad no tiene taxId o externalId, la columna correspondiente en la transacción queda en null, aunque hayas enviado valores en el body.Nota para integradores: podés mandar cualquier combinación de identificadores para vincular (precedencia: originEntityIdoriginExternalIdoriginTaxId). Tras el vínculo, los valores persistidos de originTaxId / originExternalId reflejan la entidad en gu1, no necesariamente lo que tipeaste. Esto alinea reglas transaccionales con eventos de usuario (entityId, entityExternalId, taxId en el evento).Si no hay coincidencia, la transacción se crea igual (comportamiento por defecto); quedan guardados los campos que enviaste, sin enlace a entidad. Con validateExistingEntity: true, si enviaste algún identificador de origen y no hay entidad, la API responde 400 y no crea la transacción.
(En originDetails también podés enviar un tax para el grafo, pero eso no vincula entidades: para vincular por documento usá originTaxId a nivel raíz.)
string
UUID de la entidad origen en gu1
string
Tu ID externo de la entidad origen. Segundo criterio de vinculación si omitís originEntityId. Tras vincular, el valor guardado es entities.external_id (no se conserva el del cliente si difiere).
string
CUIT o identificador fiscal / documento del origen a nivel raíz (no dentro de originDetails). Es el tercer criterio, después de originEntityId y originExternalId. Se compara con el taxId de entidades (persona/empresa) con la misma normalización alfanumérica. Si hay match, se rellenan enlace, nombre y país. Tras vincular, el valor guardado es entities.tax_id. Opcional, máx. 50 caracteres.
string
Nombre del origen
string
Código de país ISO 2 del origen (ej. “US”, “BR”, “AR”)
object
Detalles del origen (dispositivo, cuenta, etc.). Ver Esquema de payment details para estructuras sugeridas. Campos extra permitidos. Si el origen no es una entidad en gu1, podés enviar identificadores en originDetails.paymentDetails para agrupar nodos pseudo en grafos (taxId, cbu, cvu, pixKey, clabe, alias, iban, holderId, debinId, cardFingerprint, accountNumber + bankCode opcional — ver prioridad en el schema).Gu1 agrega el campo reservado linkedEntityGu1 al crear la transacción: linked indica que el origen quedó vinculado, unresolved que se envió al menos una referencia raíz (originEntityId, originExternalId u originTaxId) pero no se resolvió en modo soft-link, y not_requested que no se envió ninguna referencia. El campo pertenece al servidor: cualquier valor enviado por el integrador se ignora y se sobrescribe.

Destino (entidad)

Vinculación del destino: misma precedencia que origen: destinationEntityIddestinationExternalIddestinationTaxId.Cuando el destino queda vinculado, gu1 siempre sincroniza destinationTaxId y destinationExternalId desde la entidad (mismas reglas que origen). Si no hay vínculo, se conservan los valores enviados.
string
UUID de la entidad destino en gu1
string
Tu ID externo de la entidad destino. Tras vincular, se guarda como entities.external_id.
string
CUIT o documento del destino a nivel raíz; tercer criterio de vinculación, después de destinationEntityId y destinationExternalId. Misma lógica que originTaxId (normalización, enriquecimiento de nombre y país). Tras vincular, se guarda como entities.tax_id. Opcional, máx. 50 caracteres.
string
Nombre del destino
string
Código de país ISO 2 del destino
object
Detalles del destino (comercio, cuenta, etc.). Campos opcionales: mcc, merchantId, merchantName, deviceId, accountNumber, bankCode, bankName, etc. Campos extra permitidos. Si el destino no es una entidad en gu1, podés enviar los mismos identificadores en destinationDetails.paymentDetails para agrupar nodos pseudo (misma prioridad que origen — ver Payment Details Schema).Gu1 agrega el campo reservado linkedEntityGu1 al crear la transacción: linked indica que el destino quedó vinculado, unresolved que se envió al menos una referencia raíz (destinationEntityId, destinationExternalId o destinationTaxId) pero no se resolvió en modo soft-link, y not_requested que no se envió ninguna referencia. El campo pertenece al servidor: cualquier valor enviado por el integrador se ignora y se sobrescribe.

Ubicación y dispositivo

object
Ubicación: country, city, region, address, latitude, longitude, postalCode, etc.
object
Dispositivo: deviceId, platform, osName, model, ipAddress, isVpn, isTor, etc.
string
Canal (máx. 50 caracteres): mobile_app, web_browser, pos_terminal, api, atm, etc.
string
Motivo del resultado (opcional). Ver Enum de motivos. Si se omite se usa WITHOUT_REASON.
string
Zona horaria IANA opcional (independiente de operationalHours de la entidad). Valores de transaction_time_zone. Si se omite, queda null.Normalización de transactedAt: si transactedAt trae Z (como exige el validador de este endpoint), se guarda ese instante en UTC; timeZone es metadata opcional y no se usa para parsear. Con datetime local + timeZone (herramientas internas/lote), la API puede convertir hora local a UTC. Las integraciones que no envían timeZone siguen igual que antes. Las reglas de horario operativo usan el instante guardado + operationalHours.timezone de la entidad, no transaction.timeZone.Lista completa: Enum zona horaria.
object
Metadatos adicionales: tags, purpose, enhanced_due_diligence, block_reason, compliance_alert, etc. Campos custom permitidos.

Respuesta

object
La transacción creada (objeto). Incluye: id, externalId, organizationId, type, amount (string), currency, status, riskScore (string), flagged, channel, reason, timeZone (string | null), originDetails, destinationDetails, locationDetails, deviceDetails, processingTimeMs, processedAt, transactedAt, createdAt, updatedAt.
object
Presente cuando executeRules es true.Síncrono (default): completo tras terminar las reglas en la misma request.Async (asyncRules=true): placeholder con success: true, rulesHit / rulesNoHit vacíos y matchedRulesCount: 0. Alertas y score se actualizan cuando termina el procesamiento en background.Omitido si executeRules es false. Ver Resumen de Ejecución de Reglas.
boolean
Presente y true solo cuando las reglas fueron encoladas. Omitido en el flujo síncrono por defecto.
string
En modo async: "queued". Omitido cuando las reglas corrieron síncronamente.

Ejemplo básico

Reglas async (ingestión de alto volumen)

Para respuestas rápidas y revisar alertas después en gu1. Las reglas corren en background; rulesExecutionSummary.rulesHit viene vacío en la respuesta HTTP.
No uses la respuesta síncrona para aprobar o bloquear pagos cuando asyncRules=true. No hay un segundo webhook al terminar las reglas en background — monitoreá alertas en gu1 o consultá APIs de transacción/investigación.

Conversión de moneda

Cuando currency difiere de la moneda base de la organización (default USD), Gueno obtiene el tipo de cambio automáticamente. El comportamiento no cambia si omitís exchangeRate.

Orden de resolución

Semántica de exchangeRate

  • Dirección: unidades de moneda base por 1 unidad de currency (igual que las tasas del proveedor).
  • Fórmula: montoNormalizado = amount × exchangeRate (persistido en la moneda base de la org).
  • No es override: si el paso 2 tiene éxito, se ignora exchangeRate del cliente.

Monedas no convertibles (conversión automática)

Gueno no obtiene tipo de cambio automático para estos códigos hoy. La conversión automática queda no disponible salvo que envíes exchangeRate: El resto de códigos ISO sigue el flujo automático habitual (proveedor o histórico con transactedAt). Enviá exchangeRate si necesitás monto normalizado en base para reglas y reportes.

Ejemplo — WLD con tasa del cliente

Respuesta (base USD — monto normalizado 63.05, rateSource: client-provided):
El batch (POST /transactions/batch, upload, JSON) acepta el mismo exchangeRate opcional en cada fila, con la misma semántica.
Con Redis configurado, los jobs van a la cola transaction-rules-eval (workers dedicados si DISABLE_INPROCESS_BULL_WORKERS=true). Si Redis no está o falla el enqueue, la API igual responde 200 con asyncRules: true y ejecuta las reglas en el proceso de esa instancia (adecuado para dev o una sola instancia; alto volumen multi-instancia: Redis + workers).

Ejemplo de respuesta

Errores

400 - Datos inválidos

409 - Transacción duplicada

429 - Límite de tasa

Próximos pasos