CrossPay Hub API

Una API REST unificada para verificación KYC/AML y análisis de transacciones blockchain (KYT). Integra compliance en tu plataforma en minutos.

KYC Multi-pais

Verifica identidades contra OFAC, INTERPOL, ONU, PEP y mas. 13+ tipos de documento.

KYT Blockchain

Análisis de riesgo de wallets en Bitcoin, Ethereum, Tron, Solana y más.

Sandbox integrado

Prueba todos los endpoints sin costo con claves de prueba (cp_test_).

Base URL: https://compliance.crosspaysolutions.com/api/v1

Formato: Todas las respuestas son JSON con la estructura { success, data, meta }

Autenticación

Todas las solicitudes requieren una API key válida.

Incluye tu API key en el header Authorization de cada solicitud:

Header de autenticación
Authorization: Bearer cp_live_xxxxxxxxxxxxxxxxxx

Tipos de API Key

cp_live_Producción

Consultas reales contra proveedores KYC/KYT. Cada llamada consume créditos según el endpoint.

cp_test_Sandbox

Respuestas simuladas (mock). No se cobran créditos. Ideal para desarrollo e integración.

Importante: Nunca expongas tu API key en código frontend o repositorios públicos. Usa variables de entorno en tu servidor.

Quick Start

Integra CrossPay en 3 pasos.

1

Obtener tu API Key

Registrate en el Dashboard y genera una API key. Empieza con una clave de test (cp_test_) para desarrollo.

Ve a Dashboard → API Keys y haz clic en "Generar Clave".

2

Realiza tu primera verificación KYC

Envía una solicitud POST al endpoint de verificación.

Tu primera llamada
curl -X POST https://compliance.crosspaysolutions.com/api/v1/kyc/verify \
  -H "Authorization: Bearer cp_test_TU_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "documentNumber": "12345678",
    "documentType": "CC",
    "country": "CO"
  }'
3

Procesa la respuesta

La respuesta incluye los resultados de verificación, créditos cobrados y un requestId único.

Respuesta exitosa (sandbox)
{
  "success": true,
  "data": {
    "presentaRiesgo": false,
    "pep": false,
    "nombre": "SANDBOX TEST USER",
    "resultados": [
      { "fuente": "OFAC", "riesgo": false, "detalle": null, "tipo": null },
      { "fuente": "INTERPOL", "riesgo": false, "detalle": null, "tipo": null },
      { "fuente": "ONU", "riesgo": false, "detalle": null, "tipo": null },
      { "fuente": "POLICIA NACIONAL", "riesgo": false, "detalle": null, "tipo": null },
      { "fuente": "PEP COLOMBIA", "riesgo": false, "detalle": null, "tipo": null }
    ],
    "totalFuentesConsultadas": 5,
    "idConsulta": "sandbox-1711378200000"
  },
  "meta": {
    "requestId": "req_a1b2c3d4e5f67890abcd",
    "creditsCharged": 0,
    "creditsRemaining": 50,
    "responseTimeMs": 245
  }
}

Endpoints

Referencia completa de todos los endpoints disponibles.

POST/api/v1/kyc/verify1 crédito

KYC Verify

Verifica una identidad contra listas internacionales de riesgo (OFAC, INTERPOL, ONU, PEP, Policia Nacional, etc.).

Request Body

{
  "documentNumber": "12345678",   // Requerido — Número de documento
  "documentType": "CC",           // Requerido — Tipo de documento
  "country": "CO",                // Opcional — Código ISO país
  "name": "Juan Perez"            // Opcional — Nombre completo
}

Response

{
  "success": true,
  "data": {
    "presentaRiesgo": false,
    "pep": false,
    "nombre": "JUAN PEREZ",
    "resultados": [
      { "fuente": "OFAC", "riesgo": false, "detalle": null, "tipo": null },
      { "fuente": "INTERPOL", "riesgo": false, "detalle": null, "tipo": null },
      { "fuente": "ONU", "riesgo": false, "detalle": null, "tipo": null },
      { "fuente": "POLICIA NACIONAL", "riesgo": false, "detalle": null, "tipo": null },
      { "fuente": "PEP COLOMBIA", "riesgo": false, "detalle": null, "tipo": null }
    ],
    "totalFuentesConsultadas": 5,
    "idConsulta": "abc123"
  },
  "meta": {
    "requestId": "req_a1b2c3d4e5f67890abcd",
    "creditsCharged": 1,
    "creditsRemaining": 499,
    "responseTimeMs": 1250
  }
}
POST/api/v1/kyc/score1 crédito

KYC Risk Score

Obtiene un puntaje numerico de riesgo (0-100) para una identidad. Util para automatizar decisiones de onboarding.

Este endpoint ejecuta una consulta completa + calculo de score. El tiempo de respuesta es mayor (~3-4s).

Request Body

{
  "documentNumber": "12345678",   // Requerido
  "documentType": "CC",           // Requerido
  "country": "CO",                // Opcional
  "name": "Juan Perez"            // Opcional
}

Response

{
  "success": true,
  "data": {
    "scoreRiesgo": 69,
    "presentaRiesgo": false,
    "nombre": "JUAN PEREZ",
    "idConsulta": "308503136"
  },
  "meta": {
    "requestId": "req_x1y2z3w4v5u67890abcd",
    "creditsCharged": 1,
    "creditsRemaining": 498,
    "responseTimeMs": 3500
  }
}
POST/api/v1/kyc/report1 crédito

KYC Report (PDF)

Genera un informe PDF completo de verificación KYC. La respuesta es un binario PDF (application/pdf), no JSON.

La respuesta exitosa devuelve directamente el binario PDF. Guardalo como archivo .pdf.

Request Body

{
  "documentNumber": "12345678",   // Requerido
  "documentType": "CC",           // Requerido
  "country": "CO",                // Opcional
  "name": "Juan Perez"            // Opcional
}

Response

// Content-Type: application/pdf
// El cuerpo de la respuesta es el archivo PDF binario.
//
// En caso de error, la respuesta sera JSON con el formato estandar:
{
  "success": false,
  "error": { "code": "VALIDATION_ERROR", "message": "..." },
  "meta": { "requestId": "req_..." }
}
POST/api/v1/kyt/wallet/check2 créditos

KYT Wallet Check

Analiza una wallet de blockchain para detectar exposiciones de riesgo, flujos de fondos y asociaciones con entidades conocidas.

Request Body

{
  "address": "1A1zP1eP5QGefi2DMPTfTL5SLmv7DivfNa",  // Requerido
  "blockchain": "bitcoin"                              // Requerido
}

Response

{
  "success": true,
  "data": {
    "id": "kyt-abc123",
    "blockchain": "bitcoin",
    "address": "1A1zP1eP5QGefi2DMPTfTL5SLmv7DivfNa",
    "riskScore": 1.2,
    "riskLevel": "LOW",
    "flagged": false,
    "exposures": [
      {
        "name": "Coinbase",
        "category": "exchange",
        "riskScore": 0.5,
        "isPrimary": true
      },
      {
        "name": "Unknown Wallet",
        "category": "unknown",
        "riskScore": 1.8,
        "isPrimary": false
      }
    ],
    "totalInflows": 150.25,
    "totalOutflows": 148.10,
    "firstSeen": "2020-01-15T00:00:00Z",
    "lastSeen": "2026-03-20T14:30:00Z",
    "evaluatedAt": "2026-03-25T12:00:00Z"
  },
  "meta": {
    "requestId": "req_k1y2t3w4a5l67890abcd",
    "creditsCharged": 2,
    "creditsRemaining": 496,
    "responseTimeMs": 2100
  }
}
GET/api/v1/usageGratis

Usage

Consulta el estado actual de tu plan, créditos disponibles y ciclo de facturación.

Response

{
  "success": true,
  "data": {
    "planTier": "COMPLIANCE",
    "monthlyCredits": 500,
    "creditsUsed": 45,
    "creditsRemaining": 455,
    "billingCycleStart": "2026-03-01T00:00:00Z",
    "autoRecharge": false
  },
  "meta": {
    "requestId": "req_u1s2a3g4e5x67890abcd",
    "creditsCharged": 0,
    "creditsRemaining": 455,
    "responseTimeMs": 50
  }
}
GET/api/v1/webhooksGratis

Listar Webhooks

Lista todos los webhooks registrados para tu organización.

Response

{
  "success": true,
  "data": {
    "webhooks": [
      {
        "id": "wh_abc123",
        "url": "https://tu-servidor.com/webhook",
        "events": "kyc.completed,kyt.completed",
        "status": "ACTIVE",
        "failCount": 0,
        "lastTriggeredAt": "2026-03-20T10:00:00Z",
        "createdAt": "2026-03-01T00:00:00Z",
        "updatedAt": "2026-03-20T10:00:00Z"
      }
    ],
    "total": 1
  },
  "meta": {
    "requestId": "req_w1h2k3l4i5s67890abcd",
    "creditsCharged": 0,
    "creditsRemaining": 455,
    "responseTimeMs": 30
  }
}
POST/api/v1/webhooksGratis

Crear Webhook

Registra un nuevo webhook para recibir notificaciones de eventos en tiempo real.

Guarda el secret inmediatamente. No se mostrará de nuevo. Límite: 10 webhooks por organización.

Request Body

{
  "url": "https://tu-servidor.com/webhook",     // Requerido — debe ser HTTPS
  "events": ["kyc.completed", "kyt.completed"]  // Requerido — array de eventos
}

Response

{
  "success": true,
  "data": {
    "id": "wh_new456",
    "url": "https://tu-servidor.com/webhook",
    "secret": "whsec_a1b2c3d4e5f6...",
    "events": ["kyc.completed", "kyt.completed"],
    "status": "ACTIVE",
    "createdAt": "2026-03-25T12:00:00Z",
    "message": "Webhook created. Save the secret — it will not be shown again."
  },
  "meta": {
    "requestId": "req_w1h2k3c4r5e67890abcd",
    "creditsCharged": 0,
    "creditsRemaining": 455,
    "responseTimeMs": 80
  }
}

Tipos de Documento Soportados

CC

Cedula Colombia

CE

Cedula Extranjeria

NIT

NIT Colombia

EIN

EIN EEUU

PASSPORT

Pasaporte

DRIVER_LICENSE

Licencia Conducir

RG

RG Brasil

CPF

CPF Brasil

INE

INE Mexico

RUN

RUN Chile

SSN

SSN EEUU

DNI

DNI Espana/Peru

NIE

NIE Espana

NRIC

NRIC Singapur

FIN

FIN Singapur

CrossCheck — Motor de Compliance

Endpoints que conectan con el motor CrossCheck para screening avanzado, análisis de fraude documental, verificación biométrica y workflows automatizados.

POST/api/v1/crosscheck/screen1 crédito

CrossCheck Screen

Busca una persona contra 69K+ entradas de sanciones (OFAC, EU, UK, UN, FBI) + INTERPOL + PEP Colombia + registros LATAM.

Request Body

{
  "name": "Juan Carlos Rodriguez",      // Requerido — Nombre completo
  "date_of_birth": "1985-03-15",        // Opcional — Fecha nacimiento
  "nationality": "CO",                  // Opcional — Código ISO país
  "document_number": "1234567890",      // Opcional — Número documento
  "document_type": "CC"                 // Opcional — Tipo documento
}

Response

{
  "success": true,
  "data": {
    "risk_level": "LOW",
    "score": 0.0,
    "matches": [],
    "sources_checked": ["OFAC_SDN", "UN_SANCTIONS", "EU_CFSP", "UK_HMT", "FBI_WANTED", "INTERPOL", "PEP_COLOMBIA"],
    "cached": false,
    "screening_id": "scr-abc123",
    "registry_results": [
      { "source": "procuraduria", "status": "success", "records": [], "scraped_at": "2026-04-03T...", "response_time_ms": 120 }
    ]
  },
  "meta": { "requestId": "req_...", "creditsCharged": 1, "creditsRemaining": 499, "responseTimeMs": 850 }
}
POST/api/v1/crosscheck/verify2 créditos

CrossCheck Verify (Consolidado)

Verificación consolidada: screening + OCR documento + biometría + scoring FATF/Basel + análisis de fraude. Todo en una sola llamada.

Este endpoint ejecuta TODOS los checks disponibles en paralelo. Tiempo de respuesta tipico: 2-4 segundos.

Request Body

{
  "name": "Juan Carlos Rodriguez",      // Requerido — Nombre completo
  "date_of_birth": "1985-03-15",        // Opcional
  "nationality": "CO",                  // Opcional
  "document_number": "1234567890"       // Opcional
}

Response

{
  "success": true,
  "data": {
    "verification_id": "ver-abc123",
    "risk_score": 12.0,
    "risk_level": "LOW",
    "decision": "approve",
    "factors": [
      { "source": "screening", "finding": "No matches", "weight": 0.5, "contribution": 2.5, "detail": "No matches", "source_reference": "OFAC SDN, EU CFSP" },
      { "source": "country_risk", "finding": "Colombia - moderate", "weight": 0.15, "contribution": 4.5, "detail": "Basel AML Index: 6.12" },
      { "source": "document_fraud", "finding": "PDF clean", "weight": 0.05, "contribution": 0.5, "detail": "fraud_score: 15" },
      { "source": "deepfake", "finding": "Authentic", "weight": 0.05, "contribution": 0.25, "detail": "score: 0.95" }
    ],
    "checks_performed": ["screening", "country_risk", "document", "biometric", "document_fraud", "deepfake"],
    "partial_failure": false,
    "failed_checks": []
  },
  "meta": { "requestId": "req_...", "creditsCharged": 2, "creditsRemaining": 498, "responseTimeMs": 3200 }
}
POST/api/v1/crosscheck/networkGratis

CrossCheck Network

Obtiene el grafo de relaciones de una persona: entidades vinculadas, grados de separacion, cadena UBO.

Request Body

{
  "name": "Juan Carlos Rodriguez"  // Requerido — Nombre completo
}

Response

{
  "success": true,
  "data": {
    "nodes": [
      { "id": "query", "label": "JUAN CARLOS RODRIGUEZ", "type": "person", "source": "query", "sanctioned": false }
    ],
    "edges": [],
    "max_degree": 0,
    "total_nodes": 1
  },
  "meta": { "requestId": "req_...", "creditsCharged": 0, "creditsRemaining": 498, "responseTimeMs": 320 }
}
POST/api/v1/crosscheck/fraud/analyze1 crédito

CrossCheck Fraud — Análisis PDF

Analiza un documento PDF en busca de senales de fraude: metadatos, fuentes tipograficas, firmas digitales, modificaciones post-creacion, clasificacion de tipo.

El campo file_b64 debe ser el contenido completo del PDF codificado en Base64. Tamano maximo: 10MB.

Request Body

{
  "file_b64": "JVBERi0xLjQK...",        // Requerido — PDF en Base64
  "filename": "extracto_bancario.pdf",   // Opcional — Nombre original
  "document_type": "bank_statement"      // Opcional — bank_statement, certificate, constancia, id
}

Response

{
  "success": true,
  "data": {
    "fraud_id": "frd-abc123",
    "fraud_score": 15.0,
    "risk_level": "LOW",
    "document_type": "bank_statement",
    "signals": [
      {
        "type": "metadata_creator_mismatch",
        "severity": "low",
        "confidence": 0.3,
        "description": "Creator y producer son aplicaciones diferentes",
        "details": { "creator": "Microsoft Word", "producer": "macOS Quartz PDFContext" }
      }
    ],
    "metadata_analysis": { "creator": "Microsoft Word", "producer": "macOS Quartz PDFContext" },
    "structural_analysis": { "incremental_saves": 0, "eof_count": 1, "suspicious": false },
    "font_analysis": { "fonts_found": 3, "inconsistent": false },
    "signature_analysis": { "has_signature": false }
  },
  "meta": { "requestId": "req_...", "creditsCharged": 1, "creditsRemaining": 497, "responseTimeMs": 2800 }
}
POST/api/v1/crosscheck/fraud/analyze-image2 créditos

CrossCheck Fraud — Análisis Imagen

Análisis forense de imagen de documento: Error Level Analysis (ELA), detección copy-move, validación códigos de barras/QR, consistencia de campos.

Soporta JPG, PNG, TIFF. Para cedulas colombianas, valida automaticamente el PDF417 del reverso contra los campos OCR.

Request Body

{
  "image_b64": "/9j/4AAQSkZJRg...",      // Requerido — Imagen en Base64
  "filename": "cedula_frente.jpg",        // Opcional — Nombre original
  "document_type": "cedula_co"            // Opcional — Tipo de documento
}

Response

{
  "success": true,
  "data": {
    "forensic_id": "for-abc123",
    "fraud_score": 8.0,
    "risk_level": "LOW",
    "document_type": "cedula_co",
    "signals": [],
    "ela_analysis": { "suspicious_regions": 0, "max_deviation": 12.5, "threshold": 25.0 },
    "copy_move_analysis": { "clones_detected": 0, "regions": [] },
    "barcode_analysis": { "barcodes_found": 1, "mismatches": 0 },
    "field_consistency": { "fields_checked": 4, "inconsistencies": 0 }
  },
  "meta": { "requestId": "req_...", "creditsCharged": 2, "creditsRemaining": 495, "responseTimeMs": 3500 }
}
GET/api/v1/crosscheck/workflowsGratis

CrossCheck Workflows — Listar

Lista todos los workflows de verificación configurados para tu organización.

Response

{
  "success": true,
  "data": {
    "workflows": [
      {
        "id": "wf-001",
        "name": "Standard KYC",
        "description": "Workflow estandar de onboarding",
        "version": 1,
        "steps": [
          { "name": "screening", "type": "screening", "order": 1 },
          { "name": "document_verification", "type": "document_ocr", "order": 2 },
          { "name": "biometric_check", "type": "biometric", "order": 3 }
        ],
        "is_active": true,
        "created_at": "2026-01-01T00:00:00Z"
      }
    ]
  },
  "meta": { "requestId": "req_...", "creditsCharged": 0, "creditsRemaining": 495, "responseTimeMs": 50 }
}
POST/api/v1/crosscheck/workflows/execute3 créditos

CrossCheck Workflows — Ejecutar

Ejecuta un workflow de verificación completo. El motor ejecuta cada paso secuencialmente con branching condicional basado en riesgo.

Los workflows con resultado 'review' se envían automáticamente a la cola de revisión manual con toda la evidencia acumulada.

Request Body

{
  "workflow_id": "wf-001",               // Opcional — Si no se envia, usa el default del tipo de documento
  "document_type": "cedula_co",          // Opcional — Para resolver workflow default
  "subject_name": "Juan Carlos Rodriguez", // Requerido — Nombre del sujeto
  "document_number": "1234567890",       // Opcional
  "nationality": "CO",                  // Opcional
  "document_image_b64": "/9j/4AAQ...",  // Opcional — Imagen del documento
  "selfie_image_b64": "/9j/4BBR...",    // Opcional — Selfie para biometría
  "pdf_file_b64": "JVBERi0xLj..."       // Opcional — PDF para análisis de fraude
}

Response

{
  "success": true,
  "data": {
    "execution_id": "exec-abc123",
    "workflow_id": "wf-001",
    "workflow_version": 1,
    "status": "completed",
    "final_result": "pass",
    "risk_score": 18.5,
    "steps_completed": [
      {
        "step_name": "screening",
        "step_type": "screening",
        "result": "pass",
        "reason_code": "NO_MATCHES",
        "output": { "matches": 0, "sources_checked": 7 },
        "duration_ms": 450
      },
      {
        "step_name": "document_verification",
        "step_type": "document_ocr",
        "result": "pass",
        "reason_code": "VALID_DOCUMENT",
        "output": { "document_type": "cedula_co", "fields_extracted": 6 },
        "duration_ms": 1200
      }
    ],
    "routed_to_review": false,
    "started_at": "2026-04-03T10:00:00Z",
    "completed_at": "2026-04-03T10:00:03Z"
  },
  "meta": { "requestId": "req_...", "creditsCharged": 3, "creditsRemaining": 492, "responseTimeMs": 4500 }
}

Ejemplos de Código

Ejemplos listos para copiar y pegar en tu lenguaje favorito.

Los siguientes ejemplos muestran cómo hacer una verificación KYC con el endpoint POST /api/v1/kyc/verify.

curl
curl -X POST https://compliance.crosspaysolutions.com/api/v1/kyc/verify \
  -H "Authorization: Bearer cp_live_TU_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "documentNumber": "12345678",
    "documentType": "CC",
    "country": "CO",
    "name": "Juan Perez"
  }'
Python (requests)
import requests

API_KEY = "cp_live_TU_API_KEY"
BASE_URL = "https://compliance.crosspaysolutions.com/api/v1"

response = requests.post(
    f"{BASE_URL}/kyc/verify",
    headers={
        "Authorization": f"Bearer {API_KEY}",
        "Content-Type": "application/json",
    },
    json={
        "documentNumber": "12345678",
        "documentType": "CC",
        "country": "CO",
        "name": "Juan Perez",
    },
)

data = response.json()

if data["success"]:
    result = data["data"]
    print(f"Riesgo: {result['presentaRiesgo']}")
    print(f"PEP: {result['pep']}")
    print(f"Fuentes consultadas: {result['totalFuentesConsultadas']}")
    print(f"Créditos restantes: {data['meta']['creditsRemaining']}")
else:
    print(f"Error: {data['error']['code']} - {data['error']['message']}")
Node.js (fetch)
const API_KEY = "cp_live_TU_API_KEY";
const BASE_URL = "https://compliance.crosspaysolutions.com/api/v1";

async function verifyKYC(documentNumber, documentType, country, name) {
  const response = await fetch(`${BASE_URL}/kyc/verify`, {
    method: "POST",
    headers: {
      "Authorization": `Bearer ${API_KEY}`,
      "Content-Type": "application/json",
    },
    body: JSON.stringify({
      documentNumber,
      documentType,
      country,
      name,
    }),
  });

  const data = await response.json();

  if (!data.success) {
    throw new Error(`${data.error.code}: ${data.error.message}`);
  }

  return data;
}

// Uso
const result = await verifyKYC("12345678", "CC", "CO", "Juan Perez");
console.log("Riesgo:", result.data.presentaRiesgo);
console.log("Créditos restantes:", result.meta.creditsRemaining);
PHP (cURL)
<?php

$apiKey = "cp_live_TU_API_KEY";
$baseUrl = "https://compliance.crosspaysolutions.com/api/v1";

$payload = json_encode([
    "documentNumber" => "12345678",
    "documentType" => "CC",
    "country" => "CO",
    "name" => "Juan Perez",
]);

$ch = curl_init("$baseUrl/kyc/verify");
curl_setopt_array($ch, [
    CURLOPT_RETURNTRANSFER => true,
    CURLOPT_POST => true,
    CURLOPT_POSTFIELDS => $payload,
    CURLOPT_HTTPHEADER => [
        "Authorization: Bearer $apiKey",
        "Content-Type: application/json",
    ],
]);

$response = curl_exec($ch);
$httpCode = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);

$data = json_decode($response, true);

if ($data["success"]) {
    echo "Riesgo: " . ($data["data"]["presentaRiesgo"] ? "SI" : "NO") . "\n";
    echo "PEP: " . ($data["data"]["pep"] ? "SI" : "NO") . "\n";
    echo "Créditos restantes: " . $data["meta"]["creditsRemaining"] . "\n";
} else {
    echo "Error: " . $data["error"]["code"] . " - " . $data["error"]["message"] . "\n";
}

Los siguientes ejemplos muestran como analizar un PDF con POST /api/v1/crosscheck/fraud/analyze y ejecutar un workflow con POST /api/v1/crosscheck/workflows/execute.

CrossCheck Fraud — curl
# Analizar un PDF en busca de fraude
# Primero, codificar el archivo en Base64:
# FILE_B64=$(base64 -w0 extracto_bancario.pdf)

curl -X POST https://compliance.crosspaysolutions.com/api/v1/crosscheck/fraud/analyze \
  -H "Authorization: Bearer cp_live_TU_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "file_b64": "'$FILE_B64'",
    "filename": "extracto_bancario.pdf",
    "document_type": "bank_statement"
  }'
CrossCheck Fraud — Python
import requests
import base64

API_KEY = "cp_live_TU_API_KEY"
BASE_URL = "https://compliance.crosspaysolutions.com/api/v1"

# Leer y codificar el PDF
with open("extracto_bancario.pdf", "rb") as f:
    file_b64 = base64.b64encode(f.read()).decode()

response = requests.post(
    f"{BASE_URL}/crosscheck/fraud/analyze",
    headers={
        "Authorization": f"Bearer {API_KEY}",
        "Content-Type": "application/json",
    },
    json={
        "file_b64": file_b64,
        "filename": "extracto_bancario.pdf",
        "document_type": "bank_statement",
    },
)

data = response.json()

if data["success"]:
    result = data["data"]
    print(f"Fraud Score: {result['fraud_score']}")
    print(f"Risk Level: {result['risk_level']}")
    print(f"Senales: {len(result['signals'])}")
    for signal in result["signals"]:
        print(f"  - {signal['type']}: {signal['description']} (severity: {signal['severity']})")
else:
    print(f"Error: {data['error']['code']} - {data['error']['message']}")
CrossCheck Fraud — Node.js
const API_KEY = "cp_live_TU_API_KEY";
const BASE_URL = "https://compliance.crosspaysolutions.com/api/v1";
const fs = require("fs");

async function analyzeFraud(pdfPath) {
  const fileBuffer = fs.readFileSync(pdfPath);
  const fileB64 = fileBuffer.toString("base64");

  const response = await fetch(`${BASE_URL}/crosscheck/fraud/analyze`, {
    method: "POST",
    headers: {
      "Authorization": `Bearer ${API_KEY}`,
      "Content-Type": "application/json",
    },
    body: JSON.stringify({
      file_b64: fileB64,
      filename: "extracto_bancario.pdf",
      document_type: "bank_statement",
    }),
  });

  const data = await response.json();

  if (!data.success) {
    throw new Error(`${data.error.code}: ${data.error.message}`);
  }

  console.log("Fraud Score:", data.data.fraud_score);
  console.log("Senales:", data.data.signals.length);
  return data;
}

analyzeFraud("./extracto_bancario.pdf");
CrossCheck Workflow — curl
# Ejecutar un workflow de verificación completo
curl -X POST https://compliance.crosspaysolutions.com/api/v1/crosscheck/workflows/execute \
  -H "Authorization: Bearer cp_live_TU_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "subject_name": "Juan Carlos Rodriguez",
    "document_number": "1234567890",
    "nationality": "CO",
    "document_type": "cedula_co"
  }'
CrossCheck Workflow — Python
import requests

API_KEY = "cp_live_TU_API_KEY"
BASE_URL = "https://compliance.crosspaysolutions.com/api/v1"

response = requests.post(
    f"{BASE_URL}/crosscheck/workflows/execute",
    headers={
        "Authorization": f"Bearer {API_KEY}",
        "Content-Type": "application/json",
    },
    json={
        "subject_name": "Juan Carlos Rodriguez",
        "document_number": "1234567890",
        "nationality": "CO",
        "document_type": "cedula_co",
    },
)

data = response.json()

if data["success"]:
    result = data["data"]
    print(f"Status: {result['status']}")
    print(f"Final Result: {result['final_result']}")
    print(f"Risk Score: {result['risk_score']}")
    print(f"Steps: {len(result['steps_completed'])}")
    for step in result["steps_completed"]:
        print(f"  - {step['step_name']}: {step['result']} ({step['reason_code']}) [{step['duration_ms']}ms]")
    if result["routed_to_review"]:
        print("ATENCION: Caso enviado a revisión manual")
else:
    print(f"Error: {data['error']['code']} - {data['error']['message']}")
CrossCheck Workflow — Node.js
const API_KEY = "cp_live_TU_API_KEY";
const BASE_URL = "https://compliance.crosspaysolutions.com/api/v1";

async function executeWorkflow(subjectName, documentNumber, nationality) {
  const response = await fetch(`${BASE_URL}/crosscheck/workflows/execute`, {
    method: "POST",
    headers: {
      "Authorization": `Bearer ${API_KEY}`,
      "Content-Type": "application/json",
    },
    body: JSON.stringify({
      subject_name: subjectName,
      document_number: documentNumber,
      nationality: nationality,
      document_type: "cedula_co",
    }),
  });

  const data = await response.json();

  if (!data.success) {
    throw new Error(`${data.error.code}: ${data.error.message}`);
  }

  console.log("Status:", data.data.status);
  console.log("Result:", data.data.final_result);
  console.log("Risk Score:", data.data.risk_score);
  data.data.steps_completed.forEach(step => {
    console.log(`  ${step.step_name}: ${step.result} (${step.reason_code})`);
  });

  return data;
}

executeWorkflow("Juan Carlos Rodriguez", "1234567890", "CO");

Webhooks

Recibe notificaciones en tiempo real cuando se completan verificaciones.

Eventos disponibles

EventoDescripcion
kyc.completedVerificación KYC completada (verify, score o report)
kyt.completedAnálisis KYT de wallet completado
usage.alert.80Has consumido el 80% de tus créditos mensuales
usage.alert.100Has agotado todos tus créditos mensuales
*Suscribirse a todos los eventos

Verificación de firma

Cada webhook incluye un header X-CrossPay-Signature con una firma HMAC-SHA256 del cuerpo de la solicitud. Verifica la firma usando el secret que recibiste al crear el webhook.

Node.js — Verificar firma
import crypto from "crypto";

function verifyWebhookSignature(body, signature, secret) {
  const expected = crypto
    .createHmac("sha256", secret)
    .update(body, "utf8")
    .digest("hex");
  return crypto.timingSafeEqual(
    Buffer.from(signature),
    Buffer.from(expected)
  );
}

// En tu endpoint de webhook:
app.post("/webhook", (req, res) => {
  const signature = req.headers["x-crosspay-signature"];
  const rawBody = JSON.stringify(req.body);

  if (!verifyWebhookSignature(rawBody, signature, WEBHOOK_SECRET)) {
    return res.status(401).json({ error: "Invalid signature" });
  }

  // Procesar el evento
  const { event, data } = req.body;
  console.log("Evento recibido:", event, data);

  res.status(200).json({ received: true });
});

Política de reintentos

Si tu endpoint no responde con un código 2xx dentro de 10 segundos, CrossPay reintentara la entrega:

  • Reintento 1: despues de 1 minuto
  • Reintento 2: despues de 5 minutos
  • Reintento 3: despues de 30 minutos
  • Reintento 4: despues de 2 horas
  • Reintento 5: despues de 24 horas

Despues de 5 intentos fallidos consecutivos, el webhook se desactiva automaticamente (status: DISABLED).

Payload de ejemplo

Payload — kyc.completed
{
  "event": "kyc.completed",
  "timestamp": "2026-03-25T12:00:00Z",
  "data": {
    "requestId": "req_a1b2c3d4e5f67890abcd",
    "checkType": "KYC_VERIFY",
    "documentType": "CC",
    "country": "CO",
    "result": {
      "presentaRiesgo": false,
      "pep": false,
      "nombre": "JUAN PEREZ",
      "totalFuentesConsultadas": 5
    }
  }
}

Manejo de Errores

Todos los errores siguen un formato consistente con codigos predecibles.

Cuando ocurre un error, la respuesta tiene success: false y un objeto error con código y mensaje:

Formato de error
{
  "success": false,
  "error": {
    "code": "VALIDATION_ERROR",
    "message": "documentNumber is required and must be a string"
  },
  "meta": {
    "requestId": "req_e1r2r3o4r5x67890abcd"
  }
}
CódigoHTTPDescripcion
INVALID_API_KEY401API key inválida, expirada o no proporcionada
EXPIRED_API_KEY401La API key ha expirado. Genera una nueva en el Dashboard
INSUFFICIENT_SCOPE403Tu API key no tiene permisos para este endpoint (ej: key KYC-only intentando KYT)
INSUFFICIENT_CREDITS402No tienes créditos suficientes. Upgrade tu plan o activa auto-recharge
RATE_LIMITED429Has excedido el límite de solicitudes por minuto de tu plan
VALIDATION_ERROR400Cuerpo de la solicitud inválido o campos requeridos faltantes
PROVIDER_ERROR502Error del proveedor externo de KYC/KYT. Reintenta mas tarde

Buenas practicas

  • Siempre verifica success antes de acceder a data
  • Implementa retry con backoff exponencial para errores 429 y 502
  • Guarda el requestId para soporte y debugging
  • Monitorea creditsRemaining en meta para evitar interrupciones

Planes y Precios

Elige el plan que mejor se adapte a tu volumen de verificaciones.

PlanPrecioCréditos/mesRate limitScopes
Free$05010 req/minKYC
Compliance$99/mes50060 req/minKYC
Compliance ProPopular$150/mes2,000120 req/minKYC + KYT
KYT Bundle$500/mes5,000300 req/minKYC + KYT
EnterpriseDesde $1,000/mesCustomCustomKYC + KYT + Custom

Costo por endpoint

  • KYC Verify1 crédito
  • KYC Score1 crédito
  • KYC Report (PDF)1 crédito
  • KYT Wallet Check2 créditos
  • Usage / WebhooksGratis

Notas

  • Las claves sandbox (cp_test_) no consumen créditos
  • Los créditos se reinician al inicio de cada ciclo de facturación
  • Auto-recharge disponible proximamente
  • Enterprise: contacta a ventas para volumenes personalizados

Modo Sandbox

Prueba la API sin consumir créditos usando claves de prueba.

Cualquier API key que comience con cp_test_ activa automaticamente el modo sandbox. Las llamadas sandbox:

  • No consumen créditos - creditsCharged: 0 en cada respuesta
  • Devuelven datos simulados - respuestas mock realistas pero no reales
  • Se registran en el historial - puedes ver las llamadas sandbox en el Dashboard
  • Disparan webhooks - los webhooks configurados reciben los eventos normalmente

Respuestas sandbox

Cada endpoint devuelve datos mock predecibles:

KYC Verify (sandbox)

  • presentaRiesgo: false
  • pep: false
  • nombre: "SANDBOX TEST USER"
  • 5 fuentes consultadas (todas sin riesgo)

KYC Score (sandbox)

  • scoreRiesgo: 12
  • presentaRiesgo: false
  • nombre: "SANDBOX TEST USER"

KYT Wallet (sandbox)

  • riskScore: 1.2
  • riskLevel: "LOW"
  • flagged: false
  • 2 exposures (Coinbase + Unknown)

KYC Report (sandbox)

  • Devuelve un PDF mock
  • Content-Type: application/pdf
  • No es un reporte real

Generar claves de prueba

Ve a Dashboard → API Keys y genera una clave seleccionando el tipo "Test". Puedes tener multiples claves de prueba activas simultaneamente.

API Playground

Prueba los endpoints directamente desde el navegador.

POST/api/v1/kyc/verify1 crédito
curl equivalente
curl -X POST "https://tu-dominio.com/api/v1/kyc/verify" \
  -H "Authorization: Bearer cp_test_TU_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
  "documentNumber": "12345678",
  "documentType": "",
  "country": "CO",
  "name": "Juan Perez"
}'