Portal de Documentación de Logicware CRM
Guías, referencias e integración técnica para clientes y partners.
Introducción
Bienvenido al portal de documentación de Logicware CRM. Aquí encontrarás especificaciones de integración, manuales funcionales y recursos para desarrolladores. Usa el menú lateral para navegar por las diferentes secciones disponibles.
Webhooks
Resumen
Nuestros webhooks notifican eventos de negocio en tiempo real a tu endpoint mediante HTTP POST con application/json. Implementan reintentos con exponential backoff y envían un identificador único por mensaje para idempotencia.
Seguridad
Si configuras un Secret, cada petición incluye X-Webhook-Signature como sha256=<hash_hex>, calculada con HMAC‑SHA256 sobre el cuerpo crudo del payload. Valida en tu servidor comparando la firma en tiempo constante y usa siempre HTTPS.
Estructura del payload
{
"messageId": "uuid",
"eventType": "proforma.created",
"eventTimestamp": "ISO8601",
"data": { /* campos específicos del evento */ },
"sourceId": "id interno",
"correlationId": "cadena única"
} Campos del Payload
| Campo | Tipo | Descripción |
|---|---|---|
messageId | string (UUID) | Identificador único del mensaje para idempotencia |
eventType | string | Tipo de evento (ver lista de eventos disponibles) |
eventTimestamp | datetime (ISO 8601) | Fecha y hora en que ocurrió el evento |
data | object | Datos específicos del evento (varía según eventType) |
sourceId | string | ID interno de la entidad que generó el evento |
correlationId | string | Identificador único para rastreo y debugging |
Eventos disponibles
Actualmente se soportan 16 tipos de eventos organizados por categoría:
📋 Gestión de Leads y Actividades
activity.created- Actividad creadaappointment.created- Cita programadavisit.created- Visita registradalead.updated- Lead actualizado
💰 Proceso de Ventas
proforma.created- Proforma creadasales.process.started- Proceso de venta iniciadosales.process.completed- Proceso de venta completado
🔒 Proceso de Separación
separation.process.started- Separación iniciadaseparation.process.completed- Separación completada
↩️ Proceso de Devolución
refund.process.started- Devolución iniciadarefund.process.completed- Devolución completada
💳 Pagos y Cronogramas
payment.created- Pago de cuota registradoschedule.created- Cronograma creado
🏗️ Proyectos y Unidades
project.created- Proyecto creadounit.created- Unidad creadaunit.updated- Unidad actualizada
El catálogo puede ampliarse en futuras versiones. Eventos desconocidos: registrar o ignorar de forma segura.
Detalles de Eventos
| Tipo de Evento | Nombre | Descripción |
|---|---|---|
activity.created | Actividad Creada | Se dispara cuando se crea una nueva actividad |
appointment.created | Cita Creada | Se dispara cuando se programa una nueva cita |
visit.created | Visita Creada | Se dispara cuando se registra una nueva visita |
sales.process.started | Proceso de Venta Iniciado | Se dispara cuando se inicia un proceso de venta |
sales.process.completed | Proceso de Venta Completado | Se dispara cuando se completa un proceso de venta |
separation.process.started | Proceso de Separación Iniciado | Se dispara cuando se inicia un proceso de separación |
separation.process.completed | Proceso de Separación Completado | Se dispara cuando se completa un proceso de separación |
refund.process.started | Proceso de Devolución Iniciado | Se dispara cuando se inicia un proceso de devolución |
refund.process.completed | Proceso de Devolución Completado | Se dispara cuando se completa un proceso de devolución |
project.created | Proyecto Creado | Se dispara cuando se crea un nuevo proyecto |
payment.created | Pago de Cuota Creado | Se dispara cuando se registra un nuevo pago de cuota |
schedule.created | Cronograma Creado | Se dispara cuando se crea un nuevo cronograma |
lead.updated | Lead Actualizado | Se dispara cuando se actualiza un lead existente |
proforma.created | Proforma Creada | Se dispara cuando se crea una nueva proforma |
unit.created | Unidad Creada | Se dispara cuando se crea una nueva unidad |
unit.updated | Unidad Actualizada | Se dispara cuando se actualiza una unidad |
Ejemplo (proforma.created)
{
"messageId":"a2e4bf25-c970-4d69-9336-9b6d09b89459",
"eventType":"proforma.created",
"eventTimestamp":"2025-09-02T23:46:11.634-05:00",
"data": {
"ord_correlative":"202509-000000274",
"ord_total":493.08,
"client":{
"type_document":"DNI",
"document":"12345678",
"full_name":"JUAN PEREZ PEREZ"
},
"units":[
{ "unit_number":"M-01", "sub_total":493.08 }
]
},
"sourceId":"5376",
"correlationId":"proforma.created-5376-..."
} Más detalles, pruebas y ejemplos por lenguaje en la guía completa de Webhooks.
¿Dudas? Nuestro equipo puede ayudarte con la validación de firmas y reintentos.
Recomendaciones de Implementación
✅ Mejores Prácticas
- Idempotencia: Usa
messageIdpara evitar procesar el mismo evento múltiples veces - Validación: Siempre valida la firma
X-Webhook-Signatureantes de procesar - Respuesta rápida: Responde con HTTP 200 lo antes posible y procesa el evento de forma asíncrona
- Eventos desconocidos: Ignora eventos que no reconozcas para mantener compatibilidad futura
- Logs: Registra
correlationIdpara facilitar el rastreo y debugging
⚠️ Errores Comunes a Evitar
- Procesamiento sincrónico: No bloquees la respuesta HTTP con procesamiento largo
- Sin validación de firma: Siempre valida para evitar webhooks maliciosos
- Ignorar messageId: Puede causar procesamiento duplicado
- Timeouts largos: Responde en menos de 5 segundos
- No manejar reintentos: El sistema reintentará si fallas, prepara tu lógica
API de Proveedores v2.1
Introducción
La API de Proveedores de Logicware permite a los proveedores autorizados consultar stock de unidades, gestionar leads, crear citas y registrar actividades en tiempo real.
🔐 Seguro
Autenticación robusta con tokens JWT y API Keys. Todas las comunicaciones sobre HTTPS.
⚡ Rápido
Rate limiting de 200 req/min. Respuestas optimizadas y reintentos automáticos.
📚 Documentado
Ejemplos completos en cURL, JavaScript, C# y Python con casos de uso reales.
Requisitos Previos
Credenciales proporcionadas
| Credencial | Descripción | Ejemplo |
|---|---|---|
X-API-Key | Clave única de identificación | pk_live_abc123... |
X-Subdomain | Subdominio asignado | proveedor-demo |
projectCode | Código de proyecto(s) | PROJ-2025-001 |
Headers Comunes
Todos los endpoints requieren los siguientes headers:
X-API-Key: {su-api-key} (solo al generar token)
X-Subdomain: {su-subdomain}
Authorization: Bearer {accessToken}
Accept: application/json
X-Request-ID: {UUID-v4-único} // Recomendado
Content-Type: application/json // Solo en POST X-Request-ID es fundamental para trazabilidad y soporte técnico. Mantenga sus credenciales seguras y nunca las exponga en código público.
Autenticación
Flujo de autenticación
- Generar token usando su API Key
- Incluir el token en el header
Authorization - Renovar el token antes de su expiración (1 hora)
Generar Token
POST /auth/external/token
Headers:
X-API-Key: {su-api-key}
X-Subdomain: {su-subdomain}
Accept: application/json
Body: (vacío) Respuesta exitosa (200)
{
"succeeded": true,
"message": "Token generated successfully",
"data": {
"accessToken": "eyJhbGciOiJIUzI1NiIs...",
"tokenType": "Bearer",
"expiresIn": 3600,
"expiresAt": "2025-09-25T02:39:17.0346763Z",
"provider": {
"id": "PROV002",
"name": "LOGICWARE S.A.C",
"accessType": "standard"
},
"rateLimits": {
"requestsPerMinute": 200
}
},
"statusCode": 200
} Endpoints Disponibles
Endpoints de Consulta (Read)
Stock de Unidades
Obtiene el inventario disponible de unidades para un proyecto y etapa específicos, incluyendo información detallada de dimensiones, precios y estado de disponibilidad.
Consultar Stock de Unidades
GET /external/units/stock?projectCode={code}&stageId={id}
Headers:
Authorization: Bearer {accessToken}
X-Subdomain: {su-subdomain} Parámetros Query
| Parámetro | Tipo | Requerido | Descripción |
|---|---|---|---|
projectCode | string | Sí | Código único del proyecto inmobiliario |
stageId | integer | Sí | ID de la etapa del proyecto |
Respuesta exitosa (200)
{
"succeeded": true,
"message": "Product stock retrieved successfully",
"data": {
"properties": [
{
"id": 1223,
"stageName": "ETAPA 2",
"blockName": "MZ E2",
"code": "E2-01",
"description": "",
"remarks": "",
"areaSqm": 108.00,
"dimensions": {
"front": 6.00,
"right": 18.00,
"left": 18.00,
"back": 6.00
},
"pricePerSqm": 520.93,
"totalPrice": 56260.58,
"currency": "PEN",
"status": "Disponible"
},
{
"id": 1224,
"stageName": "ETAPA 2",
"blockName": "MZ E2",
"code": "E2-02",
"description": "Lote esquinero con vista panorámica",
"remarks": "Ubicación privilegiada, frente a parque",
"areaSqm": 120.00,
"dimensions": {
"front": 8.00,
"right": 15.00,
"left": 15.00,
"back": 8.00
},
"pricePerSqm": 520.83,
"totalPrice": 62500.00,
"currency": "PEN",
"status": "Reservado"
}
],
"summary": {
"total": 2,
"available": 1,
"reserved": 1,
"sold": 0
}
},
"statusCode": 200
} Nota: La respuesta incluye un array de unidades (properties) y un resumen (summary) con totales por estado. Solo se devuelven unidades de la etapa especificada.
Campos de la Unidad
| Campo | Tipo | Descripción |
|---|---|---|
id | integer | ID único de la unidad |
stageName | string | Nombre de la etapa del proyecto |
blockName | string | Nombre de la manzana o bloque |
code | string | Código único identificador del lote (ej: E2-01) |
description | string | Descripción de la unidad |
remarks | string | Observaciones o características especiales |
areaSqm | decimal | Área total en metros cuadrados |
dimensions | object | Medidas de los lados de la unidad |
dimensions.front | decimal | Medida del frente en metros |
dimensions.right | decimal | Medida del lado derecho en metros |
dimensions.left | decimal | Medida del lado izquierdo en metros |
dimensions.back | decimal | Medida del fondo en metros |
pricePerSqm | decimal | Precio por metro cuadrado |
totalPrice | decimal | Precio total de la unidad |
currency | string | Moneda del precio (PEN, USD) |
status | string | Estado actual de la unidad |
Estados de Unidad
- Disponible: Unidad lista para venta, sin restricciones
- Reservado: Unidad con reserva activa de un cliente
- Vendido: Unidad ya vendida, no disponible
- Bloqueado: Unidad temporalmente no disponible para venta
Campos del Resumen (Summary)
| Campo | Tipo | Descripción |
|---|---|---|
total | integer | Total de unidades en la etapa |
available | integer | Unidades disponibles para venta |
reserved | integer | Unidades con reserva activa |
sold | integer | Unidades vendidas |
Códigos de Error Comunes
| Código | Mensaje | Descripción |
|---|---|---|
400 | Bad Request | Parámetros faltantes o inválidos |
401 | Unauthorized | Token de autenticación inválido o expirado |
404 | Not Found | Proyecto o etapa no encontrada |
Parámetros Faltantes (400)
{
"succeeded": false,
"message": "Parámetros requeridos faltantes",
"errors": [
"El parámetro projectCode es obligatorio",
"El parámetro stageId es obligatorio"
],
"data": null,
"statusCode": 400
} Proyecto No Encontrado (404)
{
"succeeded": false,
"message": "Proyecto no encontrado",
"data": null,
"statusCode": 404
} Etapa No Encontrada (404)
{
"succeeded": false,
"message": "Etapa no encontrada para el proyecto especificado",
"data": null,
"statusCode": 404
} Sin Unidades en la Etapa (200)
{
"succeeded": true,
"message": "Product stock retrieved successfully",
"data": {
"properties": [],
"summary": {
"total": 0,
"available": 0,
"reserved": 0,
"sold": 0
}
},
"statusCode": 200
} Nota: Cuando una etapa no tiene unidades configuradas, la respuesta es exitosa (200) pero el array properties está vacío y el resumen muestra ceros.
Etapas de Proyecto
Obtiene todas las etapas disponibles para un proyecto inmobiliario específico, incluyendo fechas de entrega y configuración.
Consultar Etapas
GET /external/stages?projectCode={code}
Headers:
Authorization: Bearer {accessToken}
X-Subdomain: {su-subdomain} Parámetros Query
| Parámetro | Tipo | Requerido | Descripción |
|---|---|---|---|
projectCode | string | Sí | Código único del proyecto inmobiliario |
Respuesta exitosa (200)
{
"succeeded": true,
"message": "Stages retrieved successfully",
"data": [
{
"stageId": 1,
"stageName": "Etapa 1",
"projectCode": "CASABONITA",
"deliveryDate": "2025-06-30T00:00:00"
},
{
"stageId": 2,
"stageName": "Etapa 2",
"projectCode": "CASABONITA",
"deliveryDate": "2026-03-15T00:00:00"
},
{
"stageId": 3,
"stageName": "Etapa 3",
"projectCode": "CASABONITA",
"deliveryDate": "2026-12-20T00:00:00"
}
],
"statusCode": 200
} Nota: La respuesta incluye todas las etapas configuradas para el proyecto especificado, ordenadas por stageId. El stageId es necesario para consultar stock de unidades y bloques.
Campos de la Etapa
| Campo | Tipo | Descripción |
|---|---|---|
stageId | integer | ID único de la etapa |
stageName | string | Nombre descriptivo de la etapa |
projectCode | string | Código del proyecto al que pertenece |
deliveryDate | datetime | Fecha estimada de entrega de la etapa |
Códigos de Error Comunes
| Código | Mensaje | Descripción |
|---|---|---|
400 | Bad Request | Parámetro projectCode faltante o inválido |
401 | Unauthorized | Token de autenticación inválido o expirado |
404 | Not Found | Proyecto no encontrado |
Parámetro Faltante (400)
{
"succeeded": false,
"message": "Parámetro requerido faltante",
"errors": [
"El parámetro projectCode es obligatorio"
],
"data": null,
"statusCode": 400
} Proyecto No Encontrado (404)
{
"succeeded": false,
"message": "Proyecto no encontrado",
"data": null,
"statusCode": 404
} Proyecto sin Etapas (200)
{
"succeeded": true,
"message": "Stages retrieved successfully",
"data": [],
"statusCode": 200
} Nota: Cuando un proyecto no tiene etapas configuradas, la respuesta es exitosa (200) pero el array data está vacío.
Manzanas de Proyecto
Obtiene todas las manzanas (bloques) disponibles para un proyecto inmobiliario específico, útil para organizar y consultar unidades por sectores.
Consultar Manzanas
GET /external/blocks?projectCode={code}
Headers:
Authorization: Bearer {accessToken}
X-Subdomain: {su-subdomain} Parámetros Query
| Parámetro | Tipo | Requerido | Descripción |
|---|---|---|---|
projectCode | string | Sí | Código único del proyecto inmobiliario |
Respuesta exitosa (200)
{
"succeeded": true,
"message": "Blocks retrieved successfully",
"data": [
{
"blockId": 101,
"blockName": "MZ A",
"projectCode": "CASABONITA",
"deliveryDate": "2025-08-15T00:00:00"
},
{
"blockId": 102,
"blockName": "MZ B",
"projectCode": "CASABONITA",
"deliveryDate": "2025-08-15T00:00:00"
},
{
"blockId": 103,
"blockName": "MZ C",
"projectCode": "CASABONITA",
"deliveryDate": "2026-02-28T00:00:00"
}
],
"statusCode": 200
} Nota: La respuesta incluye todas las manzanas configuradas para el proyecto especificado, ordenadas por blockId.
Campos de la Manzana
| Campo | Tipo | Descripción |
|---|---|---|
blockId | integer | ID único de la manzana/bloque |
blockName | string | Nombre identificador de la manzana (ej: MZ A, MZ B) |
projectCode | string | Código del proyecto al que pertenece |
deliveryDate | datetime | Fecha estimada de entrega del bloque |
Códigos de Error Comunes
| Código | Mensaje | Descripción |
|---|---|---|
400 | Bad Request | Parámetro projectCode faltante o inválido |
401 | Unauthorized | Token de autenticación inválido o expirado |
404 | Not Found | Proyecto no encontrado |
Parámetro Faltante (400)
{
"succeeded": false,
"message": "Parámetro requerido faltante",
"errors": [
"El parámetro projectCode es obligatorio"
],
"data": null,
"statusCode": 400
} Proyecto No Encontrado (404)
{
"succeeded": false,
"message": "Proyecto no encontrado",
"data": null,
"statusCode": 404
} Proyecto sin Manzanas (200)
{
"succeeded": true,
"message": "Blocks retrieved successfully",
"data": [],
"statusCode": 200
} Nota: Cuando un proyecto no tiene manzanas configuradas, la respuesta es exitosa (200) pero el array data está vacío.
Información de Lead
Obtiene información completa de un lead específico, incluyendo datos personales, vendedor asignado, proyecto de interés, canales de adquisición y estado actual.
Consultar Lead por ID
GET /external/leads/{leadId}
Headers:
Authorization: Bearer {accessToken}
X-Subdomain: {su-subdomain} Parámetros de Ruta
| Parámetro | Tipo | Requerido | Descripción |
|---|---|---|---|
leadId | integer | Sí | ID único del lead en el sistema |
Respuesta exitosa (200)
{
"succeeded": true,
"message": "Lead retrieved successfully",
"data": {
"id": 12345,
"documentNumber": "72845936",
"firstName": "Carlos",
"paternalSurname": "Mendoza",
"maternalSurname": "Rivera",
"fullName": "Carlos Mendoza Rivera",
"phone": "+51987654321",
"email": "carlos.mendoza@example.com",
"createdAt": "2025-03-15T10:30:00",
"firstEntryDate": "2025-03-15T10:30:00",
"createdMonth": "March",
"status": "Activo",
"segmentName": "Calificados",
"projectName": "Residencial Vista Hermosa",
"stageName": "Etapa 2",
"quotationPortal": "WHATSAPP MANTRA",
"acquisitionChannel": "Publicidad Digital",
"entryChannel": "WhatsApp",
"utmCampaign": "verano2025",
"utmContent": "lotes-norte",
"utmMedium": "social",
"utmSource": "facebook",
"utmTerm": "wpp",
"seller": {
"firstName": "Andrea",
"paternalSurname": "Vargas",
"maternalSurname": "Mendoza",
"fullName": "Andrea Vargas Mendoza",
"email": "andrea.vargas@inmobiliaria.com",
"phone": "+51960859432"
}
},
"statusCode": 200
} Nota: La respuesta incluye información completa del lead, incluyendo datos de contacto, proyecto de interés, tracking UTM y vendedor asignado. Algunos campos pueden ser null o estar vacíos si no se han configurado.
Campos del Lead
| Campo | Tipo | Descripción |
|---|---|---|
id | integer | ID único del lead |
documentNumber | string | Número de documento (DNI/RUC) |
firstName | string | Nombre del lead |
paternalSurname | string | Apellido paterno |
maternalSurname | string | Apellido materno |
fullName | string | Nombre completo concatenado |
phone | string | Número de teléfono/celular |
email | string | Correo electrónico |
createdAt | datetime | Fecha y hora de creación del lead |
firstEntryDate | datetime | Fecha de primer contacto |
createdMonth | string | Mes de creación en texto inglés |
status | string | Estado del lead (Activo, Cerrado, etc.) |
segmentName | string | Segmento o etapa del funnel (Nuevos, Calificados, etc.) |
projectName | string | Nombre del proyecto de interés |
stageName | string | Etapa del proyecto de interés |
quotationPortal | string | Portal/sistema de origen del lead |
acquisitionChannel | string | Canal de adquisición del lead |
entryChannel | string | Canal de entrada (WhatsApp, Web, Teléfono, etc.) |
utmCampaign | string | Campaña de marketing (parámetro UTM) |
utmContent | string | Contenido específico (parámetro UTM) |
utmMedium | string | Medio de marketing (parámetro UTM) |
utmSource | string | Fuente de tráfico (parámetro UTM) |
utmTerm | string | Término de búsqueda (parámetro UTM) |
Campos del Vendedor
| Campo | Tipo | Descripción |
|---|---|---|
seller.firstName | string | Nombre del vendedor asignado |
seller.paternalSurname | string | Apellido paterno del vendedor |
seller.maternalSurname | string | Apellido materno del vendedor |
seller.fullName | string | Nombre completo del vendedor |
seller.email | string | Correo electrónico del vendedor |
seller.phone | string | Teléfono del vendedor |
Estados de Lead
- Activo: Lead activo en proceso de seguimiento
- Cerrado: Lead cerrado sin conversión
- Cerrado por duplicado: Lead duplicado, cerrado automáticamente
Crear Lead
Crea un nuevo lead en el sistema con información del prospecto, origen de marketing y preferencias de contacto.
Crear Nuevo Lead
POST /external/leads/create
Headers:
Authorization: Bearer {accessToken}
X-Subdomain: {su-subdomain}
Content-Type: application/json Cuerpo de la Solicitud (JSON)
{
"portalCode": "LOGICWAREBOT",
"projectCode": "ALAMEDA2",
"documentType": 1,
"documentNumber": "12345678",
"firstName": "Carlos",
"paternalLastname": "Rodriguez",
"maternalLastname": "Lopez",
"email": "carlos.rodriguez@email.com",
"phoneNumber": "+51987654321",
"comments": "Interesado en departamentos de 3 dormitorios",
"availabilityType": "1month",
"preferredContactTime": "afternoon",
"marketingConsent": "si",
"interestedProperties": "Departamentos 3 dorm",
"budgetRange": "150000-200000",
"utmCampaign": "verano2025",
"utmContent": "chat",
"utmMedium": "social",
"utmSource": "facebook",
"utmTerm": "departamentos lima",
"codSeller": 0,
"emailSeller": "",
"udfField1": null,
"udfField2": null,
"udfField3": null,
"udfField4": null,
"udfField5": null
} Respuesta Exitosa - Nuevo Lead (201 Created)
{
"succeeded": true,
"message": "Lead created successfully",
"data": {
"leadId": 1523,
"assignedTo": "Maria Fernandez Torres",
"createdAt": "2025-10-27T14:30:00"
},
"statusCode": 201
} Comportamiento con duplicados: Si ya existe un lead con el mismo teléfono o email, el sistema crea un nuevo lead pero lo marca como "Cerrado por duplicado" y lo asigna al vendedor del lead original activo. La respuesta es exitosa (200) e incluye tanto el ID del nuevo lead como el ID del lead original.
Campos requeridos:
portalCode- Código del portal origen (asignado por Logicware)projectCode- Código del proyecto (asignado por Logicware)documentType- Tipo de documentofirstName- Nombres del prospectoemailOphoneNumber- Al menos uno de los dos debe ser proporcionado
Los demás campos son opcionales pero se recomienda enviar la mayor cantidad de información posible para mejorar la calidad del lead.
Campos de la Solicitud
Información Básica (Requeridos)
| Campo | Tipo | Requerido | Descripción |
|---|---|---|---|
portalCode | string | Sí | Código del portal o fuente de origen del lead (asignado por Logicware) |
projectCode | string | Sí | Código del proyecto inmobiliario de interés (asignado por Logicware) |
documentType | integer | Sí | Tipo de documento (ver tabla de tipos disponibles) |
firstName | string | Sí | Nombres del prospecto |
email | string | Condicional* | Correo electrónico (requerido si no se envía phoneNumber) |
phoneNumber | string | Condicional* | Número de teléfono con código de país (requerido si no se envía email) |
* Al menos uno de los dos campos (email o phoneNumber) debe ser proporcionado. Se recomienda enviar ambos cuando estén disponibles.
Información Adicional (Opcionales)
| Campo | Tipo | Descripción |
|---|---|---|
documentNumber | string | Número de documento de identidad |
paternalLastname | string | Apellido paterno |
maternalLastname | string | Apellido materno |
comments | string | Comentarios o notas adicionales |
availabilityType | string | Disponibilidad (inmediate, 1week, 1month, 3months, 6months) |
preferredContactTime | string | Horario preferido (morning, afternoon, evening) |
marketingConsent | string | Consentimiento de marketing (si/no) |
interestedProperties | string | Propiedades o tipos de unidad de interés |
budgetRange | string | Rango de presupuesto |
Parámetros UTM (Tracking)
| Campo | Tipo | Descripción |
|---|---|---|
utmSource | string | Fuente del tráfico (google, facebook, bot_logicware) |
utmMedium | string | Medio de marketing (cpc, email, chat, social) |
utmCampaign | string | Nombre de la campaña |
utmContent | string | Contenido específico del anuncio |
utmTerm | string | Término de búsqueda |
Asignación de Vendedor y Campos Personalizados
| Campo | Tipo | Descripción |
|---|---|---|
codSeller | integer | Código/ID del vendedor para asignación directa (0 = asignación automática) |
emailSeller | string | Email del vendedor para asignación directa (vacío = asignación automática) |
udfField1-5 | string | Campos personalizados definidos por el usuario |
- Con codSeller o emailSeller: El lead se asigna directamente al vendedor especificado
- Sin especificar vendedor: El sistema asigna automáticamente según las reglas de distribución configuradas (round-robin, carga balanceada, etc.)
- Lead duplicado: Se asigna al vendedor del lead original activo, ignorando codSeller/emailSeller
Tipos de Documento Válidos
| ID | Tipo de Documento | Descripción |
|---|---|---|
1 | DNI | Documento Nacional de Identidad (Perú) |
2 | RUC | Registro Único de Contribuyentes (Perú - Empresas) |
3 | CARNÉ DE EXTRANJERÍA | Documento para extranjeros residentes en Perú |
4 | CARNET DIPLOMÁTICO | Documento para personal diplomático |
5 | PASAPORTE | Documento de viaje internacional |
6 | INDOCUMENTADO | Sin documento de identidad |
Códigos de Error
| Código | Descripción |
|---|---|
400 | Faltan campos requeridos o datos inválidos |
401 | Unauthorized - Token inválido o expirado |
Campos Requeridos Faltantes (400)
{
"succeeded": false,
"message": "Validation failed",
"errors": [
"El campo firstName es obligatorio",
"Debe proporcionar al menos email o phoneNumber"
],
"data": null,
"statusCode": 400
} Estructura de la Respuesta
| Campo | Tipo | Descripción |
|---|---|---|
leadId | integer | ID del lead creado (siempre se crea un nuevo registro) |
assignedTo | string | Nombre completo del vendedor asignado |
createdAt | datetime | Fecha y hora de creación del lead |
Importante: El endpoint siempre retorna código 201 y crea un nuevo lead. Si es duplicado, el nuevo lead se crea con estado "Cerrado por duplicado" y se asigna al vendedor del lead original.
Códigos de Error Comunes (Consulta)
| Código | Mensaje | Descripción |
|---|---|---|
401 | Unauthorized | Token de autenticación inválido o expirado |
404 | Not Found | Lead no encontrado con el ID especificado |
Lead No Encontrado (404)
{
"succeeded": false,
"message": "Lead no encontrado",
"data": null,
"statusCode": 404
} Ventas de Clientes
Obtiene datos de ventas de todos los clientes con filtros de fecha, útil para consultar documentos separación y venta en un rango temporal específico.
Consultar Ventas de Clientes
GET /external/clients/sales?startDate={startDate}&endDate={endDate}
Headers:
Authorization: Bearer {accessToken}
X-Subdomain: {su-subdomain} Parámetros Query
| Parámetro | Tipo | Requerido | Descripción |
|---|---|---|---|
startDate | datetime | No | Fecha inicial del rango (por defecto: primer día del mes actual) |
endDate | datetime | No | Fecha final del rango (por defecto: último día del mes actual) |
startDate y endDate es de 1 año (365 días). Rangos mayores retornarán un error 400.
Respuesta exitosa (200)
{
"succeeded": true,
"message": "Client sales data retrieved successfully",
"data": [
{
"documentNumber": "12345678",
"fullName": "JUAN CARLOS GARCIA LOPEZ",
"firstName": "JUAN CARLOS",
"paternalSurname": "GARCIA",
"maternalSurname": "LOPEZ",
"phone": "+51987654321",
"email": "jgarcia@email.com",
"gender": "Masculino",
"birthDate": "1985-05-15T00:00:00",
"address": "AV. PRINCIPAL 123",
"department": "LIMA",
"province": "LIMA",
"district": "MIRAFLORES",
"documents": [
{
"proformaId": 1001,
"correlative": "202510-000000123",
"status": "En Proceso Separación",
"startDate": "2025-10-15T10:30:00",
"endDate": null,
"proformaStartDate": "2025-10-15T10:20:00",
"separationStartDate": "2025-10-15T10:30:00",
"separationEndDate": null,
"saleStartDate": null,
"saleEndDate": null,
"seller": "MARIA FERNANDEZ TORRES",
"project": "RESIDENCIAL VERDE",
"stage": "ETAPA 1",
"units": [
{
"unitNumber": "B-15",
"unitArea": 85.50,
"basePrice": 45000.00,
"unitPrice": 42000.00,
"discountPercentage": 6.67,
"discount": 3000.00,
"total": 42000.00
}
],
"financing": {
"financingType": "Financiado",
"currency": "PEN",
"initialInstallments": 2,
"financingInstallments": 24,
"totalInstallments": 26,
"reservationAmount": 500.00,
"downPayment": 4200.00,
"amountToFinance": 37300.00,
"totalPaid": 500.00,
"totalPending": 41500.00
}
}
]
},
{
"documentNumber": "87654321",
"fullName": "ANA LUCIA MARTINEZ SILVA",
"firstName": "ANA LUCIA",
"paternalSurname": "MARTINEZ",
"maternalSurname": "SILVA",
"phone": "+51912345678",
"email": "amartinez@email.com",
"gender": "Femenino",
"birthDate": "1990-08-22T00:00:00",
"address": "CALLE LAS FLORES 456",
"department": "AREQUIPA",
"province": "AREQUIPA",
"district": "CAYMA",
"documents": [
{
"proformaId": 1002,
"correlative": "202510-000000124",
"status": "Venta",
"startDate": "2025-10-10T14:15:00",
"endDate": "2025-10-18T16:00:00",
"proformaStartDate": "2025-10-10T14:00:00",
"separationStartDate": "2025-10-10T14:15:00",
"separationEndDate": "2025-10-18T15:45:00",
"saleStartDate": "2025-10-18T15:45:00",
"saleEndDate": "2025-10-18T16:00:00",
"seller": "CARLOS MENDOZA RUIZ",
"project": "MIRADOR DEL SUR",
"stage": "ETAPA 2",
"units": [
{
"unitNumber": "C-08",
"unitArea": 72.00,
"basePrice": 38500.00,
"unitPrice": 35000.00,
"discountPercentage": 9.09,
"discount": 3500.00,
"total": 35000.00
}
],
"financing": {
"financingType": "Contado",
"currency": "USD",
"initialInstallments": 1,
"financingInstallments": 0,
"totalInstallments": 1,
"reservationAmount": 0.00,
"downPayment": 35000.00,
"amountToFinance": 0.00,
"totalPaid": 35000.00,
"totalPending": 0.00
}
}
]
}
],
"statusCode": 200
} Estructura de Datos del Cliente
| Campo | Tipo | Descripción |
|---|---|---|
documentNumber | string | Número de documento del cliente (DNI, RUC, etc.) |
fullName | string | Nombre completo del cliente |
firstName | string | Nombres del cliente |
paternalSurname | string | Apellido paterno |
maternalSurname | string | Apellido materno |
phone | string | Número de teléfono con código de país |
email | string | Correo electrónico del cliente |
gender | string | Género (Masculino/Femenino) |
birthDate | datetime | Fecha de nacimiento |
address | string | Dirección completa |
department | string | Departamento de residencia |
province | string | Provincia de residencia |
district | string | Distrito de residencia |
documents | array | Lista de documentos de venta asociados al cliente |
Estructura del Documento de Venta
| Campo | Tipo | Descripción |
|---|---|---|
proformaId | integer | ID único de la proforma |
correlative | string | Número correlativo del documento (YYYYMM-XXXXXXXXX) |
status | string | Estado del documento (Proforma/En Proceso Separación/Separación/Venta) |
startDate | datetime | Fecha de inicio del proceso actual |
endDate | datetime | Fecha de finalización del proceso actual (null si está activo) |
seller | string | Nombre del vendedor asignado |
project | string | Nombre del proyecto inmobiliario |
stage | string | Etapa del proyecto |
units | array | Unidades incluidas en el documento |
financing | object | Detalles del financiamiento |
Estructura de Unidad
| Campo | Tipo | Descripción |
|---|---|---|
unitNumber | string | Número identificador de la unidad |
unitArea | decimal | Área de la unidad en m² |
basePrice | decimal | Precio base de lista |
unitPrice | decimal | Precio final con descuentos aplicados |
discountPercentage | decimal | Porcentaje de descuento aplicado |
discount | decimal | Monto total del descuento |
total | decimal | Precio total de la unidad |
Estructura de Financiamiento
| Campo | Tipo | Descripción |
|---|---|---|
financingType | string | Tipo de financiamiento (Contado/Financiado) |
currency | string | Moneda (PEN/USD) |
initialInstallments | integer | Número de cuotas iniciales |
financingInstallments | integer | Número de cuotas de financiamiento |
totalInstallments | integer | Total de cuotas |
reservationAmount | decimal | Monto de reserva |
downPayment | decimal | Monto de cuota inicial/enganche |
amountToFinance | decimal | Monto a financiar |
totalPaid | decimal | Total pagado hasta el momento |
totalPending | decimal | Total pendiente de pago |
Flujo de estados:
Principal: Proforma → En Proceso Separación → Separación → En Proceso Venta → Venta
Devolución (opcional): Venta → En Proceso Devolución → Devolución
Códigos de Error Comunes
| Código | Mensaje | Descripción |
|---|---|---|
400 | Bad Request | Rango de fechas inválido o excede 1 año |
401 | Unauthorized | Token de autenticación inválido o expirado |
Rango de Fechas Inválido (400)
{
"succeeded": false,
"message": "El rango de fechas no puede exceder 1 año",
"data": null,
"statusCode": 400
} Sin Ventas en el Período (200)
{
"succeeded": true,
"message": "Client sales data retrieved successfully",
"data": [],
"statusCode": 200
} Nota: Cuando no hay ventas en el período especificado, la respuesta es exitosa (200) pero el array data está vacío.
Ventas de Cliente por Documento
Obtiene todos los datos de ventas asociados a un cliente específico utilizando su número de documento, incluyendo todas sus proformas, separaciones y ventas históricas.
Consultar Ventas por Documento
GET /external/clients/{documentNumber}/sales
Headers:
Authorization: Bearer {accessToken}
X-Subdomain: {su-subdomain} Parámetros de Ruta
| Parámetro | Tipo | Requerido | Descripción |
|---|---|---|---|
documentNumber | string | Sí | Número de documento del cliente (DNI, RUC, Carnet de Extranjería, etc.) |
Ejemplo de Solicitud
GET /external/clients/12345678/sales
Headers:
Authorization: Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...
X-Subdomain: miempresa Respuesta exitosa (200)
{
"succeeded": true,
"message": "Client sales data retrieved successfully",
"data": {
"documentNumber": "12345678",
"fullName": "ROBERTO CARLOS MENDEZ VARGAS",
"firstName": "ROBERTO CARLOS",
"paternalSurname": "MENDEZ",
"maternalSurname": "VARGAS",
"phone": "+51998765432",
"email": "rmendez@email.com",
"gender": "Masculino",
"birthDate": "1982-11-08T00:00:00",
"address": "JR. LOS PINOS 789",
"department": "CUSCO",
"province": "CUSCO",
"district": "WANCHAQ",
"documents": [
{
"proformaId": 2001,
"correlative": "202509-000000567",
"status": "Separación",
"startDate": "2025-09-20T11:30:00",
"endDate": "2025-09-25T14:20:00",
"proformaStartDate": "2025-09-20T11:15:00",
"separationStartDate": "2025-09-20T11:30:00",
"separationEndDate": "2025-09-25T14:20:00",
"saleStartDate": null,
"saleEndDate": null,
"seller": "PATRICIA GOMEZ RIOS",
"project": "CIUDAD JARDÍN",
"stage": "ETAPA 3",
"units": [
{
"unitNumber": "E-22",
"unitArea": 68.00,
"basePrice": 36500.00,
"unitPrice": 33850.00,
"discountPercentage": 7.26,
"discount": 2650.00,
"total": 33850.00
}
],
"financing": {
"financingType": "Financiado",
"currency": "PEN",
"initialInstallments": 1,
"financingInstallments": 48,
"totalInstallments": 49,
"reservationAmount": 200.00,
"downPayment": 3385.00,
"amountToFinance": 30265.00,
"totalPaid": 3585.00,
"totalPending": 30265.00
}
},
{
"proformaId": 2102,
"correlative": "202510-000000789",
"status": "Venta",
"startDate": "2025-10-05T09:45:00",
"endDate": "2025-10-22T16:30:00",
"proformaStartDate": "2025-10-05T09:30:00",
"separationStartDate": "2025-10-05T09:45:00",
"separationEndDate": "2025-10-22T16:15:00",
"saleStartDate": "2025-10-22T16:15:00",
"saleEndDate": "2025-10-22T16:30:00",
"seller": "PATRICIA GOMEZ RIOS",
"project": "CIUDAD JARDÍN",
"stage": "ETAPA 3",
"units": [
{
"unitNumber": "E-23",
"unitArea": 72.00,
"basePrice": 38900.00,
"unitPrice": 35010.00,
"discountPercentage": 10.00,
"discount": 3890.00,
"total": 35010.00
}
],
"financing": {
"financingType": "Financiado",
"currency": "PEN",
"initialInstallments": 2,
"financingInstallments": 36,
"totalInstallments": 38,
"reservationAmount": 300.00,
"downPayment": 3501.00,
"amountToFinance": 31209.00,
"totalPaid": 7302.00,
"totalPending": 27708.00
}
}
]
},
"statusCode": 200
} Nota: La respuesta incluye todos los documentos históricos del cliente, ordenados cronológicamente. Un cliente puede tener múltiples documentos en diferentes estados.
Estructura de la Respuesta
La estructura de datos es idéntica al endpoint de ventas generales, pero retorna la información de un único cliente en lugar de un array.
| Campo Raíz | Tipo | Descripción |
|---|---|---|
succeeded | boolean | Indica si la operación fue exitosa |
message | string | Mensaje descriptivo del resultado |
data | object | Objeto con información del cliente y sus documentos |
statusCode | integer | Código de estado HTTP |
Información del Cliente
El objeto data contiene los siguientes campos del cliente:
documentNumber: Número de documentofullName: Nombre completofirstName: NombrespaternalSurname: Apellido paternomaternalSurname: Apellido maternophone: Teléfono con código de paísemail: Correo electrónicogender: Género (Masculino/Femenino)birthDate: Fecha de nacimientoaddress: Dirección completadepartment: Departamentoprovince: Provinciadistrict: Distritodocuments: Array de documentos de venta
Estados de Documento
Los documentos pueden tener los siguientes estados en su ciclo de vida:
Flujo Principal
| Estado | Descripción | Siguiente Estado |
|---|---|---|
Proforma | Documento inicial de cotización sin compromiso | En Proceso Separación |
En Proceso Separación | Se está gestionando la separación de la unidad | Separación |
Separación | Unidad separada con compromiso de compra | En Proceso Venta |
En Proceso Venta | Se está tramitando la formalización de la venta | Venta |
Venta | Transacción completada y formalizada | En Proceso Devolución (opcional) |
Flujo de Devolución
| Estado | Descripción | Siguiente Estado |
|---|---|---|
En Proceso Devolución | Se está gestionando la devolución de la unidad vendida | Devolución |
Devolución | Devolución completada, unidad liberada | - |
Flujo completo:
Principal: Proforma → En Proceso Separación → Separación → En Proceso Venta → Venta
Devolución (opcional): Venta → En Proceso Devolución → Devolución
Nota: Las fechas proformaStartDate, separationStartDate, saleStartDate y returnStartDate registran cuándo el documento entró en cada estado. Las fechas endDate correspondientes indican cuándo finalizó ese estado (o son null si es el estado actual).
Códigos de Error Comunes
| Código | Mensaje | Descripción |
|---|---|---|
400 | Bad Request | Número de documento inválido o mal formado |
401 | Unauthorized | Token de autenticación inválido o expirado |
Documento Inválido (400)
{
"succeeded": false,
"message": "Número de documento inválido",
"errors": [
"El número de documento debe contener solo dígitos"
],
"data": null,
"statusCode": 400
} Cliente sin Documentos de Venta (200)
{
"succeeded": true,
"message": "Client sales data retrieved successfully",
"data": {
"documentNumber": "12345678",
"fullName": "LUIS ALBERTO TORRES DIAZ",
"firstName": "LUIS ALBERTO",
"paternalSurname": "TORRES",
"maternalSurname": "DIAZ",
"phone": "+51987654321",
"email": "ltorres@email.com",
"gender": "Masculino",
"birthDate": "1995-03-15T00:00:00",
"address": "AV. PRINCIPAL 123",
"department": "LIMA",
"province": "LIMA",
"district": "SAN ISIDRO",
"documents": []
},
"statusCode": 200
} Nota: Cuando un cliente existe pero no tiene documentos de venta asociados, la respuesta es exitosa (200) con el array documents vacío.
Cronograma de Pagos
Obtiene el cronograma completo de pagos mediante el correlativo de proforma, incluyendo el encabezado del cronograma, todas las cuotas y la próxima cuota por vencer.
Consultar Cronograma de Pagos
GET /external/payment-schedules/{correlative}
Headers:
Authorization: Bearer {accessToken}
X-Subdomain: {su-subdomain} Parámetros de Ruta
| Parámetro | Tipo | Requerido | Descripción |
|---|---|---|---|
correlative | string | Sí | Número correlativo de la proforma (ej: 202510-000000123) |
Ejemplo de Solicitud
GET /external/payment-schedules/202510-000000123
Headers:
Authorization: Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...
X-Subdomain: miempresa Respuesta exitosa (200)
{
"succeeded": true,
"message": "Payment schedule retrieved successfully",
"data": {
"scheduleId": 501,
"proformaId": 1001,
"correlative": "202510-000000123",
"productPrice": 42000.00,
"initialFeePercentage": 10.00,
"initialGross": 4200.00,
"reservationAmount": 500.00,
"netInitial": 3700.00,
"numberInitialInstallments": 2,
"downPaymentInitial": 1850.00,
"dateBeginInitial": "2025-11-01T00:00:00",
"tea": 12.50,
"tem": 0.99,
"numberFinancingInstallments": 24,
"amountToFinance": 37300.00,
"downPaymentFinancing": 1621.83,
"dateBeginFinancing": "2026-01-01T00:00:00",
"totalPrincipal": 37300.00,
"totalInterest": 5412.00,
"totalPayment": 42712.00,
"totalPaid": 3850.00,
"totalPending": 38862.00,
"overdueCuotas": 1,
"installmentCount": 26,
"paymentFrequency": "MONTHLY",
"firstPaymentDate": "2025-11-01T00:00:00",
"currency": "PEN",
"createdBy": "MARIA FERNANDEZ TORRES",
"createdAt": "2025-10-15T10:30:00",
"installments": [
{
"scheduleDetId": 5001,
"scheduleId": 501,
"label": "Cuota Inicial",
"installmentNumber": 1,
"dueDate": "2025-11-01T00:00:00",
"balance": 42000.00,
"principal": 1850.00,
"interest": 0.00,
"payment": 1850.00,
"paidPrincipal": 1850.00,
"paidInterest": 0.00,
"paidPenalty": 0.00,
"totalPaidAmount": 1850.00,
"remainingBalance": 40150.00,
"status": "PAID",
"paymentDate": "2025-10-28T14:30:00"
},
{
"scheduleDetId": 5002,
"scheduleId": 501,
"label": "Cuota Inicial",
"installmentNumber": 2,
"dueDate": "2025-12-01T00:00:00",
"balance": 40150.00,
"principal": 1850.00,
"interest": 0.00,
"payment": 1850.00,
"paidPrincipal": 1850.00,
"paidInterest": 0.00,
"paidPenalty": 0.00,
"totalPaidAmount": 1850.00,
"remainingBalance": 38300.00,
"status": "PAID",
"paymentDate": "2025-11-29T16:45:00"
},
{
"scheduleDetId": 5003,
"scheduleId": 501,
"label": "Saldo a Financiar",
"installmentNumber": 3,
"dueDate": "2026-01-01T00:00:00",
"balance": 38300.00,
"principal": 1552.17,
"interest": 69.66,
"payment": 1621.83,
"paidPrincipal": 150.00,
"paidInterest": 0.00,
"paidPenalty": 25.00,
"totalPaidAmount": 175.00,
"remainingBalance": 36747.83,
"status": "PARTIAL",
"paymentDate": "2026-01-15T10:20:00"
},
{
"scheduleDetId": 5004,
"scheduleId": 501,
"label": "Saldo a Financiar",
"installmentNumber": 4,
"dueDate": "2026-02-01T00:00:00",
"balance": 36747.83,
"principal": 1567.52,
"interest": 54.31,
"payment": 1621.83,
"paidPrincipal": 0.00,
"paidInterest": 0.00,
"paidPenalty": 0.00,
"totalPaidAmount": 0.00,
"remainingBalance": 36747.83,
"status": "OVERDUE",
"paymentDate": null
},
{
"scheduleDetId": 5005,
"scheduleId": 501,
"label": "Saldo a Financiar",
"installmentNumber": 5,
"dueDate": "2026-03-01T00:00:00",
"balance": 35180.31,
"principal": 1582.98,
"interest": 38.85,
"payment": 1621.83,
"paidPrincipal": 0.00,
"paidInterest": 0.00,
"paidPenalty": 0.00,
"totalPaidAmount": 0.00,
"remainingBalance": 35180.31,
"status": "PENDING",
"paymentDate": null
}
],
"nextInstallmentDue": {
"scheduleDetId": 5004,
"scheduleId": 501,
"label": "Saldo a Financiar",
"installmentNumber": 4,
"dueDate": "2026-02-01T00:00:00",
"balance": 36747.83,
"principal": 1567.52,
"interest": 54.31,
"payment": 1621.83,
"status": "OVERDUE"
}
},
"statusCode": 200
} Nota: El cronograma incluye cuotas iniciales (sin interés) y cuotas financiadas (con interés calculado). La respuesta muestra el detalle completo de cada cuota, incluyendo penalidades si aplican.
Estructura del Cronograma de Pagos
Encabezado del Cronograma
| Campo | Tipo | Descripción |
|---|---|---|
scheduleId | integer | ID único del cronograma de pagos |
proformaId | integer | ID de la proforma asociada |
correlative | string | Número correlativo de la proforma |
productPrice | decimal | Precio total del producto/unidad |
initialFeePercentage | decimal | Porcentaje de cuota inicial |
initialGross | decimal | Monto bruto de cuota inicial |
reservationAmount | decimal | Monto de reserva |
netInitial | decimal | Cuota inicial neta (bruto - reserva) |
numberInitialInstallments | integer | Número de cuotas iniciales |
downPaymentInitial | decimal | Monto de cada cuota inicial |
dateBeginInitial | datetime | Fecha de inicio de cuotas iniciales |
tea | decimal | Tasa Efectiva Anual (%) |
tem | decimal | Tasa Efectiva Mensual (%) |
numberFinancingInstallments | integer | Número de cuotas financiadas |
amountToFinance | decimal | Monto total a financiar |
downPaymentFinancing | decimal | Monto de cada cuota financiada |
dateBeginFinancing | datetime | Fecha de inicio de cuotas financiadas |
totalPrincipal | decimal | Total del capital/principal |
totalInterest | decimal | Total de intereses |
totalPayment | decimal | Pago total (principal + intereses) |
totalPaid | decimal | Total pagado hasta el momento |
totalPending | decimal | Total pendiente de pago |
overdueCuotas | integer | Número de cuotas vencidas |
installmentCount | integer | Total de cuotas en el cronograma |
paymentFrequency | string | Frecuencia de pago (Mensual) |
firstPaymentDate | datetime | Fecha del primer pago |
currency | string | Moneda (PEN/USD) |
createdBy | string | Usuario que creó el cronograma |
createdAt | datetime | Fecha de creación del cronograma |
installments | array | Lista de todas las cuotas del cronograma |
nextInstallmentDue | object | Próxima cuota por vencer o vencida (puede ser null) |
Estructura de Cuota (Installment)
| Campo | Tipo | Descripción |
|---|---|---|
scheduleDetId | integer | ID único del detalle de cuota |
scheduleId | integer | ID del cronograma padre |
label | string | Etiqueta descriptiva de la cuota |
installmentNumber | integer | Número de cuota secuencial |
dueDate | datetime | Fecha de vencimiento de la cuota |
balance | decimal | Saldo antes de esta cuota |
principal | decimal | Monto del capital en esta cuota |
interest | decimal | Monto de interés en esta cuota |
payment | decimal | Pago total de la cuota (principal + interés) |
paidPrincipal | decimal | Capital pagado de esta cuota |
paidInterest | decimal | Interés pagado de esta cuota |
paidPenalty | decimal | Penalidad pagada (por mora) |
totalPaidAmount | decimal | Total pagado de esta cuota (no incluye penalidades) |
remainingBalance | decimal | Saldo restante después de esta cuota |
status | string | Estado de la cuota (PAID/PARTIAL/OVERDUE/PENDING) |
paymentDate | datetime | Fecha de pago real (null si no ha sido pagada) |
Próxima Cuota por Vencer (NextInstallmentDue)
| Campo | Tipo | Descripción |
|---|---|---|
scheduleDetId | integer | ID único del detalle de cuota |
scheduleId | integer | ID del cronograma padre |
label | string | Etiqueta descriptiva de la cuota |
installmentNumber | integer | Número de cuota secuencial |
dueDate | datetime | Fecha de vencimiento |
balance | decimal | Saldo antes de esta cuota |
principal | decimal | Monto del capital |
interest | decimal | Monto de interés |
payment | decimal | Pago total requerido |
status | string | Estado de la cuota (OVERDUE/PENDING) |
Estados de Cuota
Las cuotas pueden tener los siguientes estados:
| Estado | Descripción | Condición |
|---|---|---|
PAID | Cuota pagada completamente | totalPaidAmount = payment |
PARTIAL | Cuota pagada parcialmente | 0 < totalPaidAmount < payment |
OVERDUE | Cuota no pagada y fecha vencida | dueDate < hoy AND totalPaidAmount = 0 |
PENDING | Cuota por vencer, aún no pagada | dueDate >= hoy AND totalPaidAmount = 0 |
Importante: Las cuotas con estado "OVERDUE" o "PARTIAL" pueden generar penalidades por mora. El campo paidPenalty muestra el monto de penalidad pagado si aplica.
Códigos de Error Comunes
| Código | Mensaje | Descripción |
|---|---|---|
400 | Bad Request | Cronograma de pagos no encontrado |
401 | Unauthorized | Token de autenticación inválido o expirado |
Cronograma No Encontrado (400)
{
"succeeded": false,
"message": "El documento especificado no existe o está inactiva",
"data": null,
"statusCode": 400
} Endpoints de Gestión (Write)
Gestión de Actividades
Permite crear y gestionar actividades de seguimiento para leads. El sistema automáticamente asigna la actividad al vendedor del lead.
Crear Actividad
POST /external/leads/{leadId}/activities
Headers:
Authorization: Bearer {accessToken}
X-Subdomain: {su-subdomain}
Content-Type: application/json
Body:
{
"activityType": 1,
"levelInterest": 2,
"description": "Llamar al cliente para confirmar interés en departamentos",
"scheduledAt": "2025-10-20T15:00:00",
"notes": "Cliente mencionó preferencia por zona norte, 3 dormitorios"
} Parámetros del Body
| Campo | Tipo | Requerido | Descripción |
|---|---|---|---|
activityType | integer | Sí | ID del tipo de actividad (ver endpoint de tipos) |
levelInterest | integer | Sí | Nivel de interés del lead (ver endpoint de nivel de interes) |
description | string | Sí | Descripción de la actividad |
scheduledAt | datetime | Sí | Fecha y hora programada en hora local (UTC-5, Lima-Perú). |
notes | string | No | Notas adicionales sobre la actividad |
Respuesta exitosa (201)
{
"succeeded": true,
"message": "Activity created successfully",
"data": {
"id": 40323,
"activityType": "Llamada",
"description": "Llamar al cliente para confirmar interés en departamentos",
"notes": "Cliente mencionó preferencia por zona norte, 3 dormitorios",
"scheduledAt": "2025-10-20T15:00:00",
"status": "Pendiente",
"completedComments": null,
"completedAt": null,
"userCompleted": null,
"createdAt": "2025-10-05T22:08:05.69",
"updatedAt": null,
"seller": {
"firstName": "María",
"paternalSurname": "González",
"maternalSurname": "Rojas",
"fullName": "María González Rojas",
"email": "maria.gonzalez@inmobiliaria.com",
"phone": "+51960859432"
}
},
"statusCode": 201
} Estados de Actividad
- Pendiente: Actividad programada, aún no completada
- Completada: Actividad realizada exitosamente
- Vencida: Actividad no completada en la fecha programada
Consultar Actividades de un Lead
GET /external/leads/{leadId}/activities
Headers:
Authorization: Bearer {accessToken}
X-Subdomain: {su-subdomain} Parámetros de Ruta
| Parámetro | Tipo | Descripción |
|---|---|---|
leadId | integer | ID del lead del cual consultar actividades |
Respuesta exitosa (200)
{
"succeeded": true,
"message": "Activities retrieved successfully",
"data": {
"lead": {
"id": 19902,
"fullName": "Carlos Ramírez Torres",
"phone": "+51928519178",
"email": "carlos.ramirez@example.com"
},
"activities": [
{
"id": 40278,
"activityType": "Llamada",
"description": "Llamada",
"notes": "<p>INTERACCIÓN 1 Y SEGUIMIENTO</p>",
"scheduledAt": "2025-09-19T15:00:00",
"status": "Vencida",
"completedComments": null,
"completedAt": null,
"userCompleted": null,
"createdAt": "2025-09-18T21:15:37.583",
"updatedAt": null,
"seller": {
"firstName": "Ana",
"paternalSurname": "Martínez",
"maternalSurname": "Silva",
"fullName": "Ana Martínez Silva",
"email": "ana.martinez@inmobiliaria.com",
"phone": "+51924212619"
}
},
{
"id": 39639,
"activityType": "Llamada",
"description": "Llamada",
"notes": "Se ha creado la actividad Llamada con fecha de vencimiento 18/09/2025 a las 13:14",
"scheduledAt": "2025-09-18T13:14:14.467",
"status": "Completada",
"completedComments": "Contacto establecido exitosamente",
"completedAt": "2025-09-18T21:15:37.38",
"userCompleted": "Ana Martínez Silva",
"createdAt": "2025-09-18T11:14:14.467",
"updatedAt": "2025-09-18T21:15:37.38",
"seller": {
"firstName": "Ana",
"paternalSurname": "Martínez",
"maternalSurname": "Silva",
"fullName": "Ana Martínez Silva",
"email": "ana.martinez@inmobiliaria.com",
"phone": "+51924212619"
}
}
]
},
"statusCode": 200
} Nota: La respuesta incluye información completa del lead y un array de todas sus actividades, ordenadas por fecha de creación descendente. Cada actividad incluye los detalles del vendedor asignado.
Campos de la Actividad
| Campo | Tipo | Descripción |
|---|---|---|
id | integer | ID único de la actividad |
activityType | string | Tipo de actividad (Llamada, Email, WhatsApp, etc.) |
description | string | Descripción breve de la actividad |
notes | string | Notas detalladas (puede contener HTML) |
scheduledAt | datetime | Fecha y hora programada |
status | string | Estado actual: Pendiente, Completada, Vencida |
completedComments | string/null | Comentarios al completar la actividad |
completedAt | datetime/null | Fecha de finalización de la actividad |
userCompleted | string/null | Nombre del usuario que completó la actividad |
createdAt | datetime | Fecha de creación de la actividad |
updatedAt | datetime/null | Fecha de última actualización |
seller | object | Información completa del vendedor asignado |
Actualizar Actividad
PUT /external/leads/{leadId}/activities/{activityId}
Headers:
Authorization: Bearer {accessToken}
X-Subdomain: {su-subdomain}
Content-Type: application/json
Body:
{
"levelInterest": 3,
"description": "Seguimiento de propuesta enviada",
"scheduledAt": "2025-10-15T16:00:00",
"notes": "Cliente solicitó información adicional sobre financiamiento"
} Parámetros de Ruta
| Parámetro | Tipo | Descripción |
|---|---|---|
leadId | integer | ID del lead propietario de la actividad |
activityId | integer | ID de la actividad a actualizar |
Parámetros del Body
| Campo | Tipo | Requerido | Descripción |
|---|---|---|---|
levelInterest | integer | No | Nivel de interés actualizado (ver endpoint de nivel de interes) |
description | string | No | Nueva descripción de la actividad |
scheduledAt | datetime | No | Nueva fecha y hora programada |
notes | string | No | Notas actualizadas |
Respuesta exitosa (200)
{
"succeeded": true,
"message": "Activity updated successfully",
"data": {
"id": 40322,
"activityType": "Llamada",
"description": "Seguimiento de propuesta enviada",
"notes": "Cliente solicitó información adicional sobre financiamiento",
"scheduledAt": "2025-10-15T16:00:00",
"status": "Pendiente",
"completedComments": null,
"completedAt": null,
"userCompleted": null,
"createdAt": "2025-10-05T19:54:16.4",
"updatedAt": "2025-10-05T22:10:45.827",
"seller": {
"firstName": "Roberto",
"paternalSurname": "Vega",
"maternalSurname": "López",
"fullName": "Roberto Vega López",
"email": "roberto.vega@inmobiliaria.com",
"phone": "+51923634231"
}
},
"statusCode": 200
} Códigos de Error Comunes
| Código | Mensaje | Descripción |
|---|---|---|
400 | Bad Request | Datos inválidos o falta información requerida |
401 | Unauthorized | Token de autenticación inválido o expirado |
404 | Not Found | Lead o actividad no encontrada |
Ejemplos de Error (400)
{
"succeeded": false,
"message": "Conflicto: El cliente potencial tiene una actividad pendiente. Complétela antes de crear una nueva.",
"data": null,
"statusCode": 400
} {
"succeeded": false,
"message": "Errores de validación.",
"errors": [
"La descripción es requerida",
"La fecha programada debe ser futura"
],
"data": null,
"statusCode": 400
} Gestión de Citas
Permite crear y gestionar citas para leads. El sistema automáticamente asigna la cita al vendedor del lead.
Crear Cita
POST /external/leads/{leadId}/appointments
Headers:
Authorization: Bearer {accessToken}
X-Subdomain: {su-subdomain}
Content-Type: application/json
Body:
{
"scheduledAt": "2025-10-18T17:30:00",
"mediumType": "P",
"medium": "PRESENCIAL",
"location": "Oficina de ventas - Sede Central",
"meetingUrl": null,
"notes": "Cliente interesado en departamentos de 3 dormitorios"
} Parámetros del Body
| Campo | Tipo | Requerido | Descripción |
|---|---|---|---|
scheduledAt | datetime | Sí | Fecha y hora programada en hora local (UTC-5, Lima-Perú). |
mediumType | string | Sí | Tipo: "P" (Presencial), "D" (Digital/Virtual) |
medium | string | Sí | Presencial: "PRESENCIAL". Digital: "ZOOM", "TEAMS", "MEET", "VIDEO-WHATSAPP" |
location | string | Condicional | Ubicación física (requerido si mediumType = "P") |
meetingUrl | string | Condicional | URL de reunión (requerido si mediumType = "D") |
notes | string | No | Notas adicionales sobre la cita |
Respuesta exitosa (201)
{
"succeeded": true,
"message": "Appointment created successfully",
"data": {
"id": 2614,
"medium": "PRESENCIAL",
"description": "Cliente interesado en departamentos de 3 dormitorios",
"location": "Oficina de ventas - Sede Central",
"createdAt": "2025-10-05T22:32:24.077",
"scheduledAt": "2025-10-18T17:30:00",
"status": "Pendiente",
"completedComments": null,
"completedAt": null,
"userCompleted": null,
"seller": {
"firstName": "Andrea",
"paternalSurname": "Vargas",
"maternalSurname": "Mendoza",
"fullName": "Andrea Vargas Mendoza",
"email": "andrea.vargas@inmobiliaria.com",
"phone": "+51960859432"
}
},
"statusCode": 201
} Estados de Cita
- Pendiente: Cita creada, esperando ejecución
- Completada: Cita realizada exitosamente
- Vencida: Cita no gestionada en la fecha programada
Tipos de Medio
| MediumType | Medium | Descripción |
|---|---|---|
P | PRESENCIAL | Cita en persona, requiere location |
D | ZOOM | Reunión por Zoom, requiere meetingUrl |
D | TEAMS | Reunión por Microsoft Teams, requiere meetingUrl |
D | MEET | Reunión por Google Meet, requiere meetingUrl |
D | VIDEO-WHATSAPP | Videollamada por WhatsApp, requiere meetingUrl |
Consultar Citas de un Lead
GET /external/leads/{leadId}/appointments
Headers:
Authorization: Bearer {accessToken}
X-Subdomain: {su-subdomain} Parámetros de Ruta
| Parámetro | Tipo | Descripción |
|---|---|---|
leadId | integer | ID del lead del cual consultar citas |
Respuesta exitosa (200)
{
"succeeded": true,
"message": "Appointments retrieved successfully",
"data": {
"lead": {
"id": 19985,
"fullName": "Patricia Flores Gutiérrez",
"phone": "+51906250790",
"email": "patricia.flores@example.com"
},
"appointments": [
{
"id": 2601,
"medium": "PRESENCIAL",
"description": "<p>Cliente muy interesado para adquirir su casa</p>",
"location": "Oficina Santa Isabel",
"createdAt": "2025-09-18T19:58:33.14",
"scheduledAt": "2025-09-27T19:57:00",
"status": "Vencida",
"completedComments": null,
"completedAt": null,
"userCompleted": null,
"seller": {
"firstName": "Jorge",
"paternalSurname": "Salazar",
"maternalSurname": "Cruz",
"fullName": "Jorge Salazar Cruz",
"email": "jorge.salazar@inmobiliaria.com",
"phone": "+51924124093"
}
},
{
"id": 2599,
"medium": "ZOOM",
"description": "<p>Presentación virtual del proyecto residencial</p>",
"location": null,
"createdAt": "2025-09-15T14:30:00",
"scheduledAt": "2025-09-20T16:00:00",
"status": "Completada",
"completedComments": "Cita exitosa, cliente solicitó cotización",
"completedAt": "2025-09-20T17:15:00",
"userCompleted": "Jorge Salazar Cruz",
"seller": {
"firstName": "Jorge",
"paternalSurname": "Salazar",
"maternalSurname": "Cruz",
"fullName": "Jorge Salazar Cruz",
"email": "jorge.salazar@inmobiliaria.com",
"phone": "+51924124093"
}
}
]
},
"statusCode": 200
} Nota: La respuesta incluye información completa del lead y un array de todas sus citas, ordenadas por fecha de creación. Cada cita incluye los detalles del vendedor asignado.
Campos de la Cita
| Campo | Tipo | Descripción |
|---|---|---|
id | integer | ID único de la cita |
medium | string | Medio de la cita (PRESENCIAL, ZOOM, TEAMS, MEET, VIDEO-WHATSAPP) |
description | string | Descripción de la cita (puede contener HTML) |
location | string/null | Ubicación física (null para citas digitales) |
createdAt | datetime | Fecha de creación de la cita |
scheduledAt | datetime | Fecha y hora programada |
status | string | Estado actual: Pendiente, Completada, Vencida |
completedComments | string/null | Comentarios al completar la cita |
completedAt | datetime/null | Fecha de finalización de la cita |
userCompleted | string/null | Nombre del usuario que completó la cita |
seller | object | Información completa del vendedor asignado |
Actualizar Cita
PUT /external/leads/{leadId}/appointments/{appointmentId}
Headers:
Authorization: Bearer {accessToken}
X-Subdomain: {su-subdomain}
Content-Type: application/json
Body:
{
"scheduledAt": "2025-10-20T15:00:00",
"mediumType": "D",
"medium": "MEET",
"location": null,
"meetingUrl": "https://meet.google.com/xyz-abcd-efg",
"notes": "Cambio a modalidad virtual por solicitud del cliente"
} Parámetros de Ruta
| Parámetro | Tipo | Descripción |
|---|---|---|
leadId | integer | ID del lead propietario de la cita |
appointmentId | integer | ID de la cita a actualizar |
Parámetros del Body
| Campo | Tipo | Requerido | Descripción |
|---|---|---|---|
scheduledAt | datetime | No | Nueva fecha y hora programada |
mediumType | string | No | Tipo actualizado: "P" o "D" |
medium | string | No | Medio actualizado |
location | string | No | Nueva ubicación (para presencial) |
meetingUrl | string | No | Nueva URL de reunión (para digital) |
notes | string | No | Notas actualizadas |
Respuesta exitosa (200)
{
"succeeded": true,
"message": "Appointment updated successfully",
"data": {
"id": 2613,
"medium": "MEET",
"description": "Cambio a modalidad virtual por solicitud del cliente",
"location": null,
"createdAt": "2025-10-05T21:39:22.367",
"scheduledAt": "2025-10-20T15:00:00",
"status": "Pendiente",
"completedComments": null,
"completedAt": null,
"userCompleted": null,
"seller": {
"firstName": "Luis",
"paternalSurname": "Morales",
"maternalSurname": "Ríos",
"fullName": "Luis Morales Ríos",
"email": "luis.morales@inmobiliaria.com",
"phone": "+51960859432"
}
},
"statusCode": 200
} Códigos de Error Comunes
| Código | Mensaje | Descripción |
|---|---|---|
400 | Bad Request | Datos inválidos, cita pendiente existente o errores de validación |
401 | Unauthorized | Token de autenticación inválido o expirado |
404 | Not Found | Lead o cita no encontrada |
Cita Pendiente Existente (400)
{
"succeeded": false,
"message": "El lead ya tiene una cita pendiente programada para 18/10/2025 17:30. Debe completar la cita existente (Exitosa/Fallida) antes de crear una nueva.",
"data": null,
"statusCode": 400
} Errores de Validación (400)
{
"succeeded": false,
"message": "Errores de validación.",
"errors": [
"El medio de contacto es requerido",
"Para citas digitales, el medio debe ser uno de: ZOOM, TEAMS, MEET, VIDEO-WHATSAPP"
],
"data": null,
"statusCode": 400
} Ejemplos de Errores de Validación
- Medio inválido para citas digitales: "Para citas digitales, el medio debe ser uno de: ZOOM, TEAMS, MEET, VIDEO-WHATSAPP"
- Falta ubicación para presencial: "Para citas presenciales, la ubicación es requerida"
- Falta URL para digital: "Para citas digitales, la URL de reunión es requerida"
- Fecha inválida: "La fecha de la cita debe ser futura"
Ejemplo de Cita Virtual
POST /external/leads/8870/appointments
Body:
{
"scheduledAt": "2025-10-25T10:00:00",
"mediumType": "D",
"medium": "ZOOM",
"location": null,
"meetingUrl": "https://zoom.us/j/123456789",
"notes": "Presentación de opciones de financiamiento"
}
Respuesta:
{
"succeeded": true,
"message": "Appointment created successfully",
"data": {
"id": 2615,
"medium": "ZOOM",
"description": "Presentación de opciones de financiamiento",
"location": null,
"scheduledAt": "2025-10-25T10:00:00",
"status": "Pendiente",
"seller": {
"fullName": "Sofía Herrera Campos",
"email": "sofia.herrera@inmobiliaria.com",
"phone": "+51945123789"
}
},
"statusCode": 201
} Gestión de Notas
Permite agregar, actualizar y consultar notas asociadas a un lead para registro de interacciones y seguimiento.
Crear Nota
POST /external/leads/{leadId}/notes
Headers:
Authorization: Bearer {accessToken}
X-Subdomain: {su-subdomain}
Content-Type: application/json
Body:
{
"Title": "Seguimiento importante",
"Content": "Cliente interesado en lotes de 150m², consultar disponibilidad en Manzana C. Solicita información sobre financiamiento directo."
} Parámetros del Body
| Campo | Tipo | Requerido | Descripción |
|---|---|---|---|
Title | string | Sí | Título descriptivo de la nota |
Content | string | Sí | Contenido detallado de la nota |
Respuesta exitosa (201)
{
"succeeded": true,
"message": "Note created successfully",
"data": {
"id": 39,
"title": "Seguimiento importante",
"content": "Cliente interesado en lotes de 150m², consultar disponibilidad en Manzana C. Solicita información sobre financiamiento directo.",
"createdAt": "2025-10-05T22:41:25.9579501-05:00",
"updatedAt": null
},
"statusCode": 201
} Consultar Notas de un Lead
GET /external/leads/{leadId}/notes
Headers:
Authorization: Bearer {accessToken}
X-Subdomain: {su-subdomain} Parámetros de Ruta
| Parámetro | Tipo | Descripción |
|---|---|---|
leadId | integer | ID del lead del cual consultar notas |
Respuesta exitosa (200)
{
"succeeded": true,
"message": "Notes retrieved successfully",
"data": {
"lead": {
"id": 8869,
"fullName": "Carmen Rodríguez Vargas",
"phone": "+51924156656",
"email": "carmen.rodriguez@example.com"
},
"notes": [
{
"id": 38,
"title": "Actualización de preferencias",
"content": "Cliente confirma interés en zona norte, prefiere lotes con vista al parque",
"createdAt": "2025-10-05T21:58:03.7",
"updatedAt": "2025-10-05T21:58:49.54",
"createdBy": "Roberto Vega López"
},
{
"id": 37,
"title": "Primera llamada",
"content": "Contacto inicial exitoso, cliente solicita información sobre proyecto residencial",
"createdAt": "2025-10-04T15:30:22.45",
"updatedAt": null,
"createdBy": "Ana Martínez Silva"
}
]
},
"statusCode": 200
} Nota: La respuesta incluye información completa del lead y todas sus notas ordenadas por fecha de creación descendente (más recientes primero). El campo updatedAt es null si la nota nunca ha sido modificada.
Campos de la Nota
| Campo | Tipo | Descripción |
|---|---|---|
id | integer | ID único de la nota |
title | string | Título de la nota |
content | string | Contenido detallado de la nota |
createdAt | datetime | Fecha y hora de creación (mantiene fecha original) |
updatedAt | datetime/null | Fecha y hora de última modificación |
createdBy | string | Nombre completo del usuario que creó la nota |
Actualizar Nota
PUT /external/leads/{leadId}/notes/{noteId}
Headers:
Authorization: Bearer {accessToken}
X-Subdomain: {su-subdomain}
Content-Type: application/json
Body:
{
"Title": "Seguimiento actualizado",
"Content": "Cliente decidió por lote esquinero en Manzana D, coordinar visita para esta semana"
} Parámetros de Ruta
| Parámetro | Tipo | Descripción |
|---|---|---|
leadId | integer | ID del lead propietario de la nota |
noteId | integer | ID de la nota a actualizar |
Parámetros del Body
| Campo | Tipo | Requerido | Descripción |
|---|---|---|---|
Title | string | Sí | Nuevo título de la nota |
Content | string | Sí | Nuevo contenido de la nota |
Respuesta exitosa (200)
{
"succeeded": true,
"message": "Notes updated successfully",
"data": {
"id": 34,
"title": "Seguimiento actualizado",
"content": "Cliente decidió por lote esquinero en Manzana D, coordinar visita para esta semana",
"createdAt": "2025-10-05T11:26:08.197",
"updatedAt": "2025-10-05T22:42:47.3860893-05:00"
},
"statusCode": 200
} Importante: El campo createdAt mantiene la fecha original de creación, mientras que updatedAt se actualiza con la fecha y hora de la modificación.
Códigos de Error Comunes
| Código | Mensaje | Descripción |
|---|---|---|
400 | Bad Request | Errores de validación en los datos enviados |
401 | Unauthorized | Token de autenticación inválido o expirado |
404 | Not Found | Lead o nota no encontrada |
Errores de Validación (400)
{
"succeeded": false,
"message": "Errores de validación.",
"errors": [
"El campo Title es obligatorio.",
"El campo Content es obligatorio."
],
"data": null,
"statusCode": 400
} Lead No Encontrado (404)
{
"succeeded": false,
"message": "Lead no encontrado",
"data": null,
"statusCode": 404
} Nota No Encontrada (404)
{
"succeeded": false,
"message": "Nota no encontrada",
"data": null,
"statusCode": 404
} Lead sin Notas (200)
{
"succeeded": true,
"message": "Notes retrieved successfully",
"data": {
"lead": {
"id": 8869,
"fullName": "Carmen Rodríguez Vargas",
"phone": "+51924156656",
"email": "carmen.rodriguez@example.com"
},
"notes": []
},
"statusCode": 200
} Nota: Cuando un lead no tiene notas, la respuesta es exitosa (200) pero el array notes está vacío.
Tipos de Financiamiento
Obtiene el catálogo de opciones de financiamiento disponibles para informar a los clientes sobre las modalidades de pago, con opción de incluir cuotas personalizadas (condiciones de pago).
Consultar Tipos de Financiamiento
GET /external/catalogs/financing-types?includeConditionalPayments={true|false}
Headers:
Authorization: Bearer {accessToken}
X-Subdomain: {su-subdomain} Parámetros Query
| Parámetro | Tipo | Requerido | Descripción |
|---|---|---|---|
includeConditionalPayments | boolean | No | Incluir condiciones de pago personalizadas (por defecto: false) |
Respuesta sin Condiciones de Pago (includeConditionalPayments=false)
{
"succeeded": true,
"message": "Financing types retrieved successfully",
"data": [
{
"id": 1,
"name": "Financiado",
"requiresBankApproval": false,
"isActive": true,
"createdAt": "2024-07-19T05:04:07.273",
"conditionalPayments": []
},
{
"id": 3,
"name": "Contado",
"requiresBankApproval": false,
"isActive": true,
"createdAt": "2025-01-05T22:42:34.05",
"conditionalPayments": []
},
{
"id": 4,
"name": "Hipotecario",
"requiresBankApproval": true,
"isActive": false,
"createdAt": "2025-01-05T22:42:44.863",
"conditionalPayments": []
}
],
"statusCode": 200
} Respuesta con Condiciones de Pago (includeConditionalPayments=true)
{
"succeeded": true,
"message": "Financing types retrieved successfully",
"data": [
{
"id": 1,
"name": "Financiado",
"requiresBankApproval": false,
"isActive": true,
"createdAt": "2024-07-19T05:04:07.273",
"conditionalPayments": [
{
"code": "CUOTA_BALON",
"name": "C. Balón 1",
"currency": "PEN",
"amount": 3000.00,
"validFrom": "2025-09-03T00:00:00",
"validTo": null,
"isActive": true,
"createdAt": "2025-09-03T01:35:06.533"
},
{
"code": "CUOTA_BUEN_PAGADOR",
"name": "B. Pagador",
"currency": "PEN",
"amount": 3000.00,
"validFrom": "2025-09-03T00:00:00",
"validTo": null,
"isActive": true,
"createdAt": "2025-09-03T01:35:18.847"
}
]
},
{
"id": 3,
"name": "Contado",
"requiresBankApproval": false,
"isActive": true,
"createdAt": "2025-01-05T22:42:34.05",
"conditionalPayments": []
},
{
"id": 6,
"name": "Techo Propio",
"requiresBankApproval": false,
"isActive": true,
"createdAt": "2025-09-07T02:21:26.493",
"conditionalPayments": []
}
],
"statusCode": 200
} Nota: La respuesta incluye todos los tipos de financiamiento configurados, tanto activos como inactivos. Se recomienda filtrar por isActive: true para mostrar solo las opciones disponibles.
Estructura de Datos
Tipo de Financiamiento
| Campo | Tipo | Descripción |
|---|---|---|
id | integer | ID único del tipo de financiamiento |
name | string | Nombre descriptivo del tipo de financiamiento |
requiresBankApproval | boolean | Indica si requiere aprobación bancaria |
isActive | boolean | Indica si está activo y disponible para usar |
createdAt | datetime | Fecha de creación del tipo de financiamiento |
conditionalPayments | array | Lista de condiciones de pago personalizadas (vacío si includeConditionalPayments=false) |
Condición de Pago (ConditionalPayment)
| Campo | Tipo | Descripción |
|---|---|---|
code | string | Código único de la condición de pago |
name | string | Nombre corto de la condición |
currency | string | Moneda de la condición (PEN/USD) |
amount | decimal | Monto de la condición de pago |
validFrom | datetime | Fecha de inicio de vigencia |
validTo | datetime | Fecha de fin de vigencia (null si no tiene fecha de expiración) |
isActive | boolean | Indica si la condición está activa |
createdAt | datetime | Fecha de creación de la condición |
Tipos de Financiamiento Comunes
- Contado: Pago total al momento de la compra, sin financiamiento
- Financiado: Financiamiento directo con la inmobiliaria, sin banco intermediario
- Hipotecario: Crédito hipotecario con entidad bancaria, requiere aprobación
- Techo Propio: Programa estatal de vivienda para sectores de bajos recursos
- Fondo MIVIVIENDA: Fondo estatal que facilita el acceso a crédito hipotecario
Condiciones de Pago Personalizadas
Las condiciones de pago son cuotas especiales que pueden aplicarse a ciertos tipos de financiamiento:
- Cuota Balón: Pago único de un monto mayor en una fecha específica del cronograma
- Bono Buen Pagador: Descuento o beneficio por cumplir con los pagos puntualmente
Importante: Las condiciones de pago solo se incluyen cuando includeConditionalPayments=true. Por defecto, el array conditionalPayments estará vacío para todos los tipos de financiamiento.
Códigos de Error Comunes
| Código | Mensaje | Descripción |
|---|---|---|
401 | Unauthorized | Token de autenticación inválido o expirado |
404 | Not Found | Endpoint no encontrado (verificar ruta) |
Sin Tipos Configurados (200)
{
"succeeded": true,
"message": "Financing types retrieved successfully",
"data": [],
"statusCode": 200
} Nota: Si no hay tipos de financiamiento configurados, la respuesta es exitosa (200) pero el array data está vacío.
Parámetros de Financiamiento
Obtiene todos los parámetros de financiamiento disponibles en el sistema, organizados por proyecto inmobiliario.
Consultar Parámetros de Financiamiento
GET /external/catalogs/financing-parameters
Headers:
Authorization: Bearer {accessToken}
X-Subdomain: {su-subdomain} Respuesta exitosa (200)
{
"succeeded": true,
"message": "Financing parameters retrieved successfully",
"data": [
{
"projectCode": "VERDE2024",
"projectName": "RESIDENCIAL VERDE",
"reservationAmount": 500.00,
"initialFeePercent": 10.00,
"financedBalancePercent": 90.00,
"isActive": true,
"createdAt": "2024-01-15T10:30:00"
},
{
"projectCode": "MIRADOR2024",
"projectName": "MIRADOR DEL SUR",
"reservationAmount": 750.00,
"initialFeePercent": 15.00,
"financedBalancePercent": 85.00,
"isActive": false,
"createdAt": "2024-03-20T14:15:00"
},
{
"projectCode": "JARDIN2023",
"projectName": "CIUDAD JARDÍN",
"reservationAmount": 300.00,
"initialFeePercent": 20.00,
"financedBalancePercent": 80.00,
"isActive": false,
"createdAt": "2023-11-08T09:45:00"
},
{
"projectCode": "PLAZA2022",
"projectName": "PLAZA CENTRAL",
"reservationAmount": 1000.00,
"initialFeePercent": 25.00,
"financedBalancePercent": 75.00,
"isActive": false,
"createdAt": "2022-06-12T16:20:00"
}
],
"statusCode": 200
} Nota: La respuesta incluye tanto parámetros de financiamiento activos como inactivos. Use el campo isActive para filtrar solo el financiamiento vigente.
Estructura de Parámetros de Financiamiento
| Campo | Tipo | Descripción |
|---|---|---|
projectCode | string | Código único del proyecto inmobiliario |
projectName | string | Nombre descriptivo del proyecto |
reservationAmount | decimal | Monto fijo de reserva requerido para separar una unidad |
initialFeePercent | decimal | Porcentaje de cuota inicial sobre el precio de venta |
financedBalancePercent | decimal | Porcentaje del saldo que puede ser financiado |
isActive | boolean | Indica si está activo |
createdAt | datetime | Fecha de creación de la configuración de parámetros |
Casos de Uso
1. Calcular Plan de Pagos
Utilice los parámetros para calcular automáticamente el desglose de pagos de una unidad:
- Precio de venta: S/ 50,000
- Parámetros del proyecto:
initialFeePercent = 10%,reservationAmount = 500 - Cuota inicial bruta: S/ 5,000
- Menos reserva: S/ 500
- Cuota inicial neta: S/ 4,500
- Monto a financiar: S/ 45,000 (90%)
Importante: Los parámetros son específicos por proyecto. Asegúrese de usar los parámetros correctos del proyecto al que pertenece la unidad que está cotizando.
Códigos de Respuesta
| Código | Mensaje | Descripción |
|---|---|---|
200 | OK | Parámetros obtenidos exitosamente |
401 | Unauthorized | Token de autenticación inválido o expirado |
Sin Parámetros Configurados (200)
{
"succeeded": true,
"message": "Financing parameters retrieved successfully",
"data": [],
"statusCode": 200
} Nota: Si no hay parámetros de financiamiento configurados en el sistema, la respuesta es exitosa (200) pero el array data está vacío.
Tipos de Actividad
Obtiene el catálogo de tipos de actividad disponibles para clasificar las interacciones y gestiones con clientes potenciales.
Consultar Tipos de Actividad
GET /external/catalogs/activity-types
Headers:
Authorization: Bearer {accessToken}
X-Subdomain: {su-subdomain} Respuesta exitosa (200)
{
"succeeded": true,
"message": "Activity types retrieved successfully",
"data": [
{
"id": 1,
"name": "Llamada",
"isActive": true,
"createdAt": "2025-03-15T10:30:00"
},
{
"id": 2,
"name": "Correo Electrónico",
"isActive": true,
"createdAt": "2025-03-15T10:30:00"
},
{
"id": 4,
"name": "WhatsApp",
"isActive": true,
"createdAt": "2025-03-15T10:30:00"
}
],
"statusCode": 200
} Nota: La respuesta incluye todos los tipos de actividad configurados. Se recomienda filtrar por isActive: true para mostrar solo las opciones disponibles.
Campos del Tipo de Actividad
| Campo | Tipo | Descripción |
|---|---|---|
id | integer | ID único del tipo de actividad |
name | string | Nombre descriptivo del tipo de actividad |
isActive | boolean | Indica si está activo y disponible para usar |
createdAt | datetime | Fecha de creación del registro |
Tipos de Actividad Comunes
- Llamada: Contacto directo por voz con el cliente
- Correo Electrónico: Envío de información o cotizaciones por email
- WhatsApp: Mensajería instantánea y compartir multimedia
- Otros
Códigos de Error Comunes
| Código | Mensaje | Descripción |
|---|---|---|
401 | Unauthorized | Token de autenticación inválido o expirado |
404 | Not Found | Endpoint no encontrado (verificar ruta) |
500 | Internal Server Error | Error interno del servidor al procesar la solicitud |
Sin Tipos Configurados (200)
{
"succeeded": true,
"message": "Activity types retrieved successfully",
"data": [],
"statusCode": 200
} Nota: Si no hay tipos de actividad configurados, la respuesta es exitosa (200) pero el array data está vacío.
Niveles de Interés
Obtiene el catálogo de niveles de interés disponibles para clasificar y priorizar clientes potenciales según su grado de intención de compra.
Consultar Niveles de Interés
GET /external/catalogs/interest-levels
Headers:
Authorization: Bearer {accessToken}
X-Subdomain: {su-subdomain} Respuesta exitosa (200)
{
"succeeded": true,
"message": "Interest levels retrieved successfully",
"data": [
{
"id": 1,
"name": "Alto",
"isActive": true,
"createdAt": "2025-03-15T10:30:00"
},
{
"id": 2,
"name": "Medio",
"isActive": true,
"createdAt": "2025-03-15T10:30:00"
},
{
"id": 3,
"name": "Bajo",
"isActive": true,
"createdAt": "2025-03-15T10:30:00"
}
],
"statusCode": 200
} Nota: La respuesta incluye todos los niveles de interés configurados. Se recomienda filtrar por isActive: true para clasificar correctamente a los clientes.
Campos del Nivel de Interés
| Campo | Tipo | Descripción |
|---|---|---|
id | integer | ID único del nivel de interés |
name | string | Nombre descriptivo del nivel de interés |
isActive | boolean | Indica si está activo y disponible para usar |
createdAt | datetime | Fecha de creación del registro |
Niveles de Interés Comunes
- Alto: Cliente muy interesado, evaluación avanzada
- Medio: Cliente interesado, comparando opciones
- Bajo: Cliente en fase exploratoria inicial
Recomendación: Los niveles de interés son configurables según las necesidades de cada empresa. Utilízalos para clasificar y priorizar el seguimiento de clientes de acuerdo con tu estrategia de ventas.
Códigos de Error Comunes
| Código | Mensaje | Descripción |
|---|---|---|
401 | Unauthorized | Token de autenticación inválido o expirado |
404 | Not Found | Endpoint no encontrado (verificar ruta) |
500 | Internal Server Error | Error interno del servidor al procesar la solicitud |
Sin Niveles Configurados (200)
{
"succeeded": true,
"message": "Interest levels retrieved successfully",
"data": [],
"statusCode": 200
} Nota: Si no hay niveles de interés configurados, la respuesta es exitosa (200) pero el array data está vacío.
Códigos de Error Comunes
Estos códigos de error aplican a todos los endpoints de la API:
| Código | Descripción | Acción recomendada |
|---|---|---|
| 400 | Parámetros inválidos | Verificar parámetros enviados |
| 401 | Token inválido o expirado | Renovar token de autenticación |
| 403 | Sin permisos para el recurso | Verificar accesos con Logicware |
| 404 | Recurso no encontrado | Verificar códigos e IDs enviados |
| 429 | Rate limit excedido | Implementar throttling y reintentos |
| 500 | Error interno del servidor | Reintentar más tarde o contactar soporte |
| 503 | Servicio no disponible | Sistema en mantenimiento, reintentar después |
Manuales
Guías funcionales
- Gestión de Leads y Segmentación
- Oportunidades, Proformas y Ventas
- Posventa y SLA
- Conexión WhatsApp con Logicware
Guías técnicas
- Instalación on‑premise / IIS
- Gateway con YARP
- Observabilidad (TraceId / OpenTelemetry)
Conexión WhatsApp con Logicware
Introducción
Este manual explica el procedimiento para activar y mantener la conexión de WhatsApp con el CRM Logicware. El uso correcto asegura que los mensajes y clientes que lleguen a WhatsApp se sincronicen automáticamente con el sistema y puedan enviar plantillas.
Icono de Estado
En la parte superior derecha del CRM hay un ícono de WhatsApp que indica el estado:
- Verde: Conectado
- Naranja/Rojo: Desconectado
- Gris: Estado desconocido
Procedimiento de Conexión
- Haz clic en el ícono de WhatsApp en la parte superior.
- Se abrirá una ventana emergente con un código QR.
- En tu WhatsApp móvil entra a Dispositivos vinculados.
- Escanea el código QR mostrado.
- Recarga la página del CRM para validar el estado de la conexión.
Recomendaciones
- Verifica diariamente el estado de conexión de WhatsApp.
- Si hay problemas frecuentes, contacta soporte (953 448 476).
- Mantén actualizada la aplicación de WhatsApp.
- No compartas tu acceso de WhatsApp corporativo.
Sugerencia
Revisa periódicamente el estado de tu conexión de WhatsApp. Si está inactiva o desconectada, repite el procedimiento de conexión para mantener la sincronización óptima.
Problemas comunes y solución
Si no aparece el código QR al intentar vincular tu cuenta:
- Ir a Configuración > Integraciones.
- Seleccionar Conexión WhatsApp.
- Dar clic en Agregar Instancia.
- Ingresar datos proporcionados por Logicware (Instancia, URL servicio, Token).
- Si no cuentas con credenciales, solicítalas a Logicware.
- Guardar cambios e intentar nuevamente.
APIs
Documentación de endpoints REST, autenticación (OAuth2/JWT), límites de uso y ejemplos de respuesta. Próximamente publicaremos especificaciones OpenAPI (Swagger) descargables.
SDKs / Ejemplos
Bibliotecas disponibles
- Node.js: receptor de webhooks y verificación de firma
- C#: cliente de API y manejo de reintentos
- Python: utilidades de integración
Ejemplo de implementación
// Node.js — receptor mínimo
import express from "express";
const app = express();
app.use(express.json());
app.post("/webhooks/proforma", (req, res) => {
const e = req.body;
console.log(e.eventType, e.data?.ord_correlative);
res.status(200).send("ok");
});
app.listen(3000, () => console.log("Webhook listener en :3000")); Changelog
- 2025‑09‑30: Agregada documentación completa de API de Proveedores v2.1 con ejemplos en múltiples lenguajes.
- 2025‑09‑02: Nuevos eventos de separación/venta/devolución. Estructura base de payload.
- 2025‑01‑15: Firma HMAC‑SHA256 opcional por endpoint.
Soporte
Canales de contacto
Al reportar un problema incluye:
X-Request-IDde la solicitud fallida- Timestamp del error
- Código de estado HTTP recibido
- Mensaje de error completo
- Endpoint y parámetros utilizados (sin credenciales)
¿Necesitas ayuda con webhooks? Incluye también messageId y correlationId de tus eventos para acelerar el diagnóstico.
Seguridad
Todos los accesos deben realizarse por HTTPS. Si activas la firma de webhook, valida el HMAC con comparación en tiempo constante. Mantén listas de eventos soportados y registra auditoría básica (messageId, correlationId, resultado).
Recomendaciones adicionales:
- Usa variables de entorno para credenciales
- Implementa rotación de API Keys cada 90 días
- Audita logs de acceso regularmente
- Nunca expongas credenciales en código cliente
- Valida siempre certificados SSL/TLS
Asistente Virtual de IA v2.0
Resumen
El Asistente Virtual de IA de Logicware es un widget conversacional para tu web que responde consultas de disponibilidad, precios, promociones y financiamiento, y además capta leads en tu CRM.
🤖 Conversacional
NLP y contexto para flujos inmobiliarios comunes.
⚡ Rápido
Carga asíncrona, bajo peso <100KB y sin bloquear tu sitio.
📈 Enfocado en ventas
Deriva a asesor y registra lead en tu CRM.
Introducción
El Asistente de IA responde en lenguaje natural sobre proyectos, lotes/departamentos, precios, promociones y financiamiento. Solicita nombre y celular para registrar el lead en tu CRM y, cuando corresponde, deriva a un asesor humano.
- Consulta inventario comercial en tiempo real.
- Mantiene el contexto de la conversación.
- 100% responsive y seguro (HTTPS).
Instalación del widget
Inserta el siguiente script antes de </body> en tu sitio.
<!-- Asistente Virtual IA Logicware -->
<script src="https://widgets.logicwareperu.com/widget/tu_cliente_id.js"></script> WordPress (rápido)
- Instala “Insert Headers and Footers”.
- Pega el script en Scripts in Footer y guarda.
HTML estático
<!DOCTYPE html>
<html lang="es">
<head>...</head>
<body>
<!-- Tu contenido -->
<!-- Asistente Virtual IA Logicware -->
<script src="https://widgets.logicwareperu.com/widget/tu_cliente_id.js"></script>
</body>
</html> Verificación
- Limpia caché (Ctrl/Cmd + Shift + Supr) e ingresa en incógnito.
- Abre tu web y confirma el botón flotante del asistente.
- Haz clic y verifica: mensaje de bienvenida y atajos (Disponibilidad, Precios, Promos, Visitas).
Si no aparece: verifica que el script esté antes de </body>, el ID sea correcto y no haya extensiones bloqueando scripts. Revisa la Consola (F12) y comparte una captura a soporte.
Personalización
Podemos ajustar apariencia y textos del asistente a tu marca.
- Colores/Logo: envía paleta (hex) y logotipo.
- Bienvenida: texto por proyecto/ciudad (opcional).
- Atajos: Disponibilidad, Precios, Promociones, Visitas, Financiamiento.
FAQ & Soporte
¿Responde en tiempo real?
Sí, consulta inventario comercial en el momento de la pregunta.
¿Qué datos mínimos solicita?
Nombre y celular. Correo y preferencia de contacto son opcionales.
¿Afecta el rendimiento?
No. Carga asíncrona y tamaño ligero (<100KB).
¿Funciona en móviles?
100% responsive.
Soporte
📧 soporte@logicwareperu.com
💬 WhatsApp: +51 953 448 476