PROMO - Manual de Integración 6.5



CONTENIDO



Acerca del manual

Propósito y alcance


El presente manual tiene como finalidad la capacitación al usuario que desee integrar su aplicación de ventas con el Motor de Promociones.
Se provee una descripción detallada de los mensajes que deben ser enviados al mismo y de cómo interpretar los mensajes de respuesta que dará ante un requerimiento.

Documentación de PROMO


PROMO provee la siguiente documentación:

  • Manual de usuario:


Este documento tiene la finalidad de capacitar al usuario que desee utilizar la consola de Administración de Promociones de PROMO.

  • Manual de instalación:


Este documento describe los procedimientos para instalar los componentes de Motor y Consola, la creación e inicialización de la Base de Datos y los requerimientos necesarios para el correcto funcionamiento de dichos componentes.

  • Manual de integración:


Este documento describe detalladamente los mensajes que deben ser enviados al Motor de Promociones y la forma de interpretar los mensajes de respuesta que el mismo dará ante un requerimiento.


Nota: Antes de continuar con la lectura del presente manual, se recomienda leer los capítulos 2 y 3 del Manual de usuario.

Introducción a la Integración

El motor de promociones es el componente de PROMO encargado de recibir requerimientos desde el punto de venta y luego responderlos. Esta interacción se realizará a través de una serie de mensajes con formato XML que siguen un Protocolo de Comunicación definido. En este sentido el motor de promociones puede funcionar tanto como servidor TCP/IP o bien como servidor REST, dependiendo de las necesidades, preferencias y requerimientos tecnológicos que posea el punto de venta.
Por otra parte, hay casos en que es necesaria la interacción con las bases de datos que posee la consola, como puede ser consultas directas a los elementos de fidelidad existentes (Ejemplo: Cupones y Tarjetas existentes). Para estos casos, la consola de Promo es la encargada de exponer una serie de servicios para exponer o brindar dicha información a los sistemas externos. Esta forma de integración, como es de notar, en realidad tiene objetivos muy diferentes a la primera y se trata en una sección especial en este documento.
A continuación describiremos las dos opciones de integración con el motor de promociones mencionadas anteriormente.

Comunicación con el Motor de Promociones


Como mencionamos anteriormente, la forma de dialogar con el Motor de Promociones es a través de la mensajería XML presentada más adelante en este documento. Estos mensajes utilizan como transporte dos formas de comunicación:

Servidor TCP/IP

Uno de los protocolos más comunes en la actualidad. Permite enrutamiento y envío seguro. En este caso, el motor actúa como un servidor que espera conexiones entrantes en un puerto TCP/IP determinado. El punto de venta debe enviar y recibir paquetes TCP/IP que poseen el siguiente formato:
HEADER | MESSAGE
Donde:

  • Header (encabezado): son 6 Bytes que indican la cantidad de bytes que tendrá el cuerpo del mensaje que se envía al motor de promociones.
  • Message (mensaje): mensaje enviado al Motor de Promociones con el formato XML descripto en este documento.


Servidor REST

REST (Representational State Transfer) es un estilo de arquitectura utilizado en aplicaciones distribuidas en red. Se basa en protocolos cliente-servidor, sin estado, y como en el caso de PROMO mayoritariamente se implementa utilizando protocolo HTTP. La idea es una alternativa simple al uso de mecanismos más complejos como CORBA, RPC o SOAP.
El motor de promociones se presenta aquí como un servidor HTTP que espera conexiones en un puerto TCP/IP determinado.
Para utilizar esta forma de comunicación la aplicación cliente debe enviar requerimientos HTTP y esperar las respuestas correspondientes. La invocación o formato de utilización es: (puede realizarse en un browser como FireFox, Chrome, etc.)
http://servidor:puerto/engine/evaluate?request=message
Donde:

  • http://servidor:puerto: es la url para acceder al servidor donde se encuentra en ejecución el motor de PROMO.
  • message: es el mensaje correspondiente que debe evaluar el motor, como se especifica en el presente documento.


Importante

  • Si el motor posee la opción de seguridad vía https, entonces todas las referencias a http:// deben leerse como https://
  • Si se encuentra activa la autenticación por usuario/clave, entonces los request deberán incorporar en el encabezado(headers) las siguiente propiedad:  "Authorization":"Basic user:encrypted_password_MD5"
  • Para mayor información consultar el manual de instalación y configuración


Presentaremos aquí varios ejemplos utilizando dos clientes: el navegador Firefox y la aplicación "curl" de dominio público (https://curl.haxx.se/). Suponemos entonces que necesitamos enviar el siguiente mensaje para ser evaluado por el motor:

Ejemplo
<message companyId="sts" store="9905" terminal="001" date-time="2016-11-20 23:01" messageId="0001" void-trx="false" suggest="true" response="true" init-tck="true" evaluate="true" msg-version="2.4" status="init" ><item-add seq="1" unitprice="1" xprice="1" qty="1" magnitude="1" code="P001" discountable="true"/>
 </message>


Al mismo tiempo el servidor donde se encuentra disponible el motor de PROMO es http://demoserver.net y el puerto 3625.
En Firefox la url que usamos para esta prueba es:

http://demoserver.net:3625/engine/evaluate?request=<?xml version="1.0"?><message companyId="sts" store="9905" terminal="001" date-time="2016-11-20 23:01" messageId="0001" void-trx="false" suggest="true" response="true" init-tck="true" evaluate="true" msg-version="2.4" status="init" ><item-add seq="1" unitprice="1" xprice="1" qty="1" magnitude="1" code="P001" discountable="true"/>
</message>


Esto en una sola línea como se ve en la figura siguiente.

Acorde a los resultados de la evaluación del mapa se verá en el browser una respuesta del tipo:

De la misma forma, otro ejemplo es realizar lo mismo pero utilizando curl. En este caso entonces por línea de comandos se envía el mensaje de la siguiente forma:

curl -v http://demoserver.net:3625/engine/evaluate?request=%3C?xml%20version=%221.0%22?%3E%3Cmessage%20store= %229901%22%20terminal=%22001%22%20date-time=%222016-11-20%2023:01%22%20messageId=%220001%22%20void-trx=%22false%22%20suggest=%22true%22%20response=%22true%22%20init-tck=%22true%22%20evaluate=%22true%22%20msg-version=%222.4%22%20status=%22init%22%20%20%3E%3Citem-add%20seq=%221%22%20unitprice=%22219%22%20xprice=%22219%22%20qty=%221%22%20magnitude=%221%22%20code=%22P001%22%20discountable=%22true%22/%3E%3C/message%3E

Nótese que el mensaje xml debe ser codificado, cosa que en caso como Firefox, el navegador se encarga de esta conversión automáticamente.
En la siguiente figura se muestra el ejemplo completo con el requerimiento y la respuesta. Se han borrado algunos datos relativos al servidor en que se ejecutó ya que no hacen al ejemplo.


Sesiones


Antes de comenzar con la descripción del mensaje utilizado para el envío de requerimientos al Motor de Promociones, es necesario introducir al lector en el manejo de sesiones que éste realiza.
Una sesión es un espacio reservado dentro del Motor de Promociones para el manejo de la información que respecta a una transacción. De esta forma es capaz de manejar diversas transacciones concurrentemente, teniendo una sesión por cada una de ellas. Podemos asimilar este concepto con la apertura de una transacción que ha comenzado a realizarse en el punto de venta y que irá incorporando elementos hasta el cierre de la misma.
La sesión se identifica por la concatenación de los siguientes campos contenidos en el encabezado del mensaje (explicado en la sección siguiente):
SessionId = CompanyId + Store + Terminal
Al iniciarse una nueva sesión los datos de la transacción correspondiente estarán vacíos, pudiendo ser luego completados como se indicará más adelante, es decir se reserva solamente una transacción sin elementos pero con los datos de encabezado como puede ser la fecha y hora de la misma, más la tienda y terminal donde ocurre.
Asimismo, la sesión tendrá un time-out (tiempo de expiración) configurable, el cual una vez transcurrido sin que se registre alguna recepción de mensaje hará que la sesión se elimine automáticamente, haciendo necesaria la apertura de una nueva y, si se continúa con la transacción, el reenvío de los datos que la sesión expirada contenía. Ver el manual de instalación y Configuración para mayor detalle.

Hay que notar de lo visto hasta aquí, que tanto se opte por comunicaciones con el motor de promociones en su servidor TCP/IP como REST, ambos utilizan la misma mensajería que será presentada en este documento y que se ha denominado "MESSAGE" en ambos casos.

Motor: Engine Request

Anteriormente mencionamos que el motor de promociones es el componente de PROMO encargado de recibir requerimientos desde el punto de venta y luego responderlos. Esta interacción se realizará a través de una serie de mensajes con formato XML que seguirá una serie de reglas definidas.

Importante: Se debe tener en cuenta que si en el ticket se encuentran caracteres que no pertenezcan al alfabeto inglés o caracteres reservados XML (como ser '>', '<', '"'), no se asegura que éstos sean interpretados correctamente por el Motor de Promociones.


En esta sección se presentará la estructura de los mensajes XML enviados por el punto de venta que desea interactuar con Promo. Estos mensajes se denominan REQUEST o solicitudes. El formato General es:

<message ... propiedades del encabezado ...>

... elementos del cuerpo del mensaje ...

</message>


Encabezado


Como se mencionó anteriormente, los mensajes que se envíen al Motor de Promociones serán en XML. El elemento raíz de ese mensaje XML deberá ser la etiqueta <message>, siendo esta etiqueta a la que se le llamará encabezado, y contendrá una serie de atributos que serán utilizados por el Motor de Promociones para conocer el momento y lugar de la transacción, si debe o no iniciar una nueva sesión, etc. Contenidos dentro de esta etiqueta se encontrarán los comandos que quieran ejecutarse en el Motor, los cuales formarán el cuerpo del mensaje, tema desarrollado en la sección siguiente.
Los atributos que puede poseer el encabezado son:

Propiedad

Tipo de dato

Descripción

Requerido

Valor ante ausencia

companyId

Alfanumérico

Identifica la compañía que envía el mensaje

SI


store

Alfanumérico

Identifica el local que envía el mensaje.


terminal

Numérico

Identifica la terminal emisora


date-time

YYYY-MM-DD HH:MM:SS

Fecha y hora del mensaje. (date-time="2017-03-21 15:20:26")


messageId

Numérico positivo

Identifica cada uno de los mensajes enviados por la terminal, siendo este número utlizado por el Motor de Promociones como identificador cuando envíe una respuesta.


void-trx

Booleano

Indica si la transacción es una devolución.

No

"false"

response

Booleano

Indica si se desea que el Motor dé una respuesta ante el mensaje enviado.

No

"false"

init-tck

Booleano

Indica si con este mensaje se debe iniciar una nueva sesión.

No

"false"

evaluate

Booleano

Le indica al motor que calcule las promociones utilizando los elementos ingresado hasta ese momento.

No

"false"

status

Alfanumérico

Indica en que estado se encuentra el punto de venta

  • sales
  • total
  • payment
    Existen valores específicos de esta propiedad que serán presentados en la sección de Fidelidad

No

""

msg-version

Alfanumérico

Indica la versión del mensaje en cuestión

No

""

map-version

Entero positivo

Indica al motor que mapa utilizar. Tendrá sentido sólo si el valor de "void-trx" es verdadero.

No

""

suggest

Booleano

Le indica al motor si debe sugerir promociones o no. Si suggest-seq y suggest-seq-type no están presentes se tomará todo el contexto para realizar la sugerencia.

No

"false"

suggest-seq

Numérico

Indica el número de secuencia sobre el que el motor realizará la sugerencia en caso de que el atributo suggest="true". Este atributo será acompañado por el suggest-seq-type, que de no ser especificado, se asumirá suggest-seq-type="item"

No

"1" o null

suggest-seq-type

Alfabético

Indica el tipo de línea sobre la que deberá hacerse la sugerencia en caso de que el atributo suggest="true". Este atributo será acompañado por el suggest-seq, que de no estar especificado, se asumirá sugget-seq="1". Los valores que puede tomar este atributo son: item, coupon, payment, event, customer.

No

"item" o null

suggest-per-type

Booleano

Le indica al motor si deben sugerir promociones teniendo en cuenta el tipo de los conjuntos participantes de la promoción o no. Si suggest-filter-type no está presente se sugerirán todas las promociones que estén disponibles para sugerencia teniendo en cuenta el atributo suggest del mapa y las promociones. Si está presente y en verdadero, los atributos suggest, suggest-seq y suggest-seq-type serán ignorados.

No

"false"

suggest-filter-type

Alfabético

Indica el tipo de conjunto participante de la promoción que deberá tenerse en cuenta para la sugerencia en caso de que el atributo suggest-per-type="true". Los valores que puede tomar este atributo son: ítem, coupon, payment, event, customer. Si no estuviera presente, se asume todos los tipos de conjuntos.

No

"null"

suggest-extended

Booleano

Le indica al motor si debe mostrar la información de los beneficios de cada promocion sugerida. Si suggest es false, el valor de este campo no tiene relevancia.

No

"false"

offline

Booleano

Le indica al motor que la transacción será tratada en modo offline, es decir ante una contingencia de comunicación con PROMO Central se almacenará para su posterior envío.

No

"false"

originalTransaction

Alfabético

Para el caso de un valor de status = requestTransaction, esta propiedad indicará la transacción que se requiere consultar

No

""

chosenOptionEntero positivioEn el caso de que el resultado de la evaluación haya resultado en una serie de opciones (varios bloques "optional") este atributo permite que el sistema externo informe al motor de Promo, cual de esas opciones fue la que finalmente se han aplicado u otorgado al cliente.  El valor es basado en 0, es decir la primer opción es la número 0, la siguiente la número 1 y así sucesivamente.No0
tenderGroupCodeAlfabéticoCuando se utilice preciadores, si se envia el valor "cr" retornara el precio a crédito, en caso de otro valor o de no enviarlo retornara el precio de venta.No""
channelAlfabéticoCanal de la tienda desde donde se realiza la operación.No""
storeChainAlfabéticoCadena de la tienda.No""
formatAlfabéticoFormato de la tiendaNo""
zoneAlfabéticoZona a la cual pertenece la tiendaNo""
subZoneAlfabéticoSubzona a la cual pertenece la tiendaNo""


Comportamiento de Promo en modo offline

Si por regla de negocio, el POS envía al motor de Promo en el encabezado en el atributo offline=true. Si se corta la comunicación entre el POS y el motor de Promo, dependiendo del momento en que se haya cortado la comunicación, Promo podrá grabar la transacción localmente y cuando haya comunicación la enviará al POS. Es el POS el que decide si la transacción offline se puede realizar o no.

  • El loyaltyvalidation no se puede usar offline.
  • Si está offline al momento de enviar el finish o el rollback, Promo guardará la transacción. Luego hace un commit automático. Si había cupones o consumo de tarjetas, si puede Promo realiza la operación y si no puede da error y se lo guarda.
  • Se pueden agregar cupones, tarjetas, y si están bien los datos, la promo los consume. Es como hacer una transacción de débito offline: se asume que el saldo alcanza, es una decisión de negocio permitir o no ese tipo de transacción.
  • Si se está offline y viene una persona con un cupón: si por regla de negocio el POS decide que es válido tomar un cupón y otorgar la promo que lo canjea, lo toma offline y cuando llega a la consola se quema el cupón.
  • Si se va a aplicar una promo que emite un cupón: lo genera, lo emite, pero Promo se lo guarda. Promo no envía los datos del cupón. Para el caso de los tipos de cupones virtuales, esto no tiene ningún impacto porque no necesitan el barcode, en el próximo loyaltyvalidation tendrán el total. Pero sí genera un barcode. Y después cuando se restablece la conexión el motor manda automáticamente todos los offline que son finish con commit.
  • Si no hay conexión al comenzar la transacción (o sea si no se pudo hacer el loyatyvalidation) no se van a dar las promociones con límites. Si el offline se produce en el finish: va a tomar lo que evaluó durante la promo (en ese caso ya realizó el  loyaltyvalidation y por lo tanto ya tiene los límites actualizados).
  • El motor embebido usa el mismo directorio offline que el motor estándar. Usa los directorios defaults.

Ejemplo:

<message companyId="sts" store="00001" terminal="010" date-time="2017-12-04 12:30:33:00" messageId="0010" void-trx="false" response="true" init-tck="true" evaluate="true" status="payment" msg-version="2.0" map-version="15">

... cuerpo del mensaje ...

</message>


Con sugerencia sobre el tipo de línea; en este caso "payment"(suggest-seq-type):

<message companyId="sts" store="00001" terminal="010" date-time="2017-12-04 12:30:50:00" messageId="0010" void-trx="false" response="true" init-tck="true" evaluate="true" status="payment" msg-version="2.0" map-version="15" suggest="true" suggest-seq="3" suggest-seq-type="payment">

... cuerpo del mensaje ...

</message>


EJ: la sugerencia se debe hacer sobre el cupòn(suggest-filter-type="coupon):

<message companyId="sts" store="00001" terminal="010" date-time="2017-12-04 12:30:50:00" messageId="0010" void-trx="false" response="true" init-tck="true" evaluate="true" status="payment" msg-version="2.0" map-version="15" suggest-per-type="true" suggest-filter-type="coupon">

... cuerpo del mensaje ...

</message>


Ej  el motor debe mostrar información de los beneficios de cada promoción sugerida(suggest-extended="true):

<message companyId="sts" store="00001" terminal="010" date-time="2017-12-04 12:30:50:00" messageId="0010" void-trx="false" response="true" init-tck="true" evaluate="true" status="payment" msg-version="2.0" map-version="15" suggest="true" suggest-extended="true">

... cuerpo del mensaje ...

</message>


Cuerpo


El cuerpo del mensaje que se envía al Motor de Promociones estará compuesto por los comandos que se quieran ejecutar. Básicamente, los comandos pueden ser de dos tipos:

Acción

Descripción

add

Agrega el elemento a la sesión.

void

Elimina el elemento de la sesión. El elemento se identifica por el número de secuencia.


Estos comandos pueden ser utilizados sobre los distintos elementos que pueden pertenecer a un ticket. A su vez, estos elementos pueden ser tipificados en 5 clases:

Elemento

Descripción

item

Identifica a los artículos.

coupon

Identifica a los cupones.

loyaltycard

Identifica a las tarjetas loyalty.

payment

Identifica a los medios de pago.

event

Identifica a los eventos u otros elementos no representables mediante los otros tipos.

customer

Identifica a los clientes.

benefitIdentifica a los beneficios externos


La manera de ejecutar un comando es utilizando una etiqueta con la forma <elemento-comando>.
De esta manera, si se desea, por ejemplo, agregar un nuevo artículo a la sesión el comando a utilizar será <item-add>, si se quiere cancelar un cupón agregado anteriormente se enviará un comando del tipo <coupon-void> etc.
En el cuerpo del mensaje podrá contener uno, ninguno o varios de estos comandos.
Pueden ser enviados los comandos, al mismo tiempo que se abre una nueva sesión o se pide una evaluación.
También puede enviarse un mensaje sin comandos para, por ejemplo, solicitar la evaluación de un ticket.

Atributos de comandos


Cada uno de los comandos que se envían Motor de Promociones posee diversos atributos, los cuales identifican al elemento que se está enviando y definen diversas propiedades que poseen los mismos. Tanto add, como void poseerán un número de secuencia, el cual identifica cada elemento unívocamente:

Propiedad

Tipo de dato

Descripción

Requerido

seq

Entero positivo

Número identificador único del elemento dentro de la transacción.


Este será el único atributo que poseerán los comandos del tipo void, siendo este el atributo que indica el elemento que se desea eliminar.
Por otro lado, el comando add poseerá una serie de atributos que definirán las distintas propiedades del elemento que se está agregando (además del número de secuencia antes mencionado). Dependiendo del elemento en cuestión, los atributos serán los siguientes:

Elemento

Propiedad

Tipo de dato

Descripción

Requerido

Valor ante ausencia

Ítem

unitprice

Numérico positivo

Precio unitario del artículo en cuestión.

Si



xprice

Numérico positivo

Precio extendido del artículo en cuestión. Es igual a la cantidad por el precio unitario.

Si



qty

Entero positivo

Cantidad de artículos en la línea.

Si



magnitude

Numérico positivo

Si el artículo es mensurable por otro unidad que no sea la cantidad, deberá ser expresad en esta propiedad.

No

0


code

Alfanumérico

Código propio del artículo.

No

"-"


brand

Alfanumérico

Marca del artículo.

No

"-"


supplier

Alfanumérico

Proveedor al que pertenece el artículo.

No

"-"


discountable

Alfanumérico

Si el artículo es puede recibir descuentos o no.

No

"-"


level1

Alfanumérico

Nivel 1 de categorización del artículo. Anteriormente este nivel se conocía con el nombre de Departamento.

No

"-"


level2

Alfanumérico

Nivel 2 de categorización del artículo. Anteriormente este nivel se conocía como la Familia del artículo.

No

"-"


level3

Alfanumérico

Nivel 3 de categorización del artículo. Anteriormente este nivel se conocía como la Categoría del artículo.

No

"-"


level4

Alfanumérico

Nivel 4 de categorización del artículo. Anteriormente este nivel se conocía como la subcategoría del artículo.

No

"-"


discontinuousbooleanoDetermina si el producto es un producto discontinuoNofalse

lowTurnoverbooleanoDetermina si el producto es un producto de baja rotaciónNofalse

keyProductbooleanoDetermina si el producto es un producto estrellaNofalse

applyCatalogRedeembooleano(desde v6.5.2) Determina si el producto participa en el Canje de Puntos por CatálogoNofalse

Coupon

amount

Numérico positivo

Se utiliza para indicar el valor monetario del cupón. Si no tiene no se utiliza.

No

0


type

Alfanumérico

Tipo de cupón.

No

"-"


qty

Entero positivo

Cantidad

No

1


id

Alfanumérico

Identificador del cupón.

No

"-"

LoyaltyCard

type

Alfanumérico

Tipo de tarjeta loyalty

No

"-"


id

Alfanumérico

Idenficiador de la tarjeta loyalty

Si

"-"


amount

Numérico positivo

Saldo de la tarjeta loyalty

No

0


chargeAmount

Numérico positivo

Saldo a acreditar a una tarjeta loyalty

No

0


consumeAmount

Numérico positivo

Saldo a debitar a una tarjeta loyalty

No

0


status

Alfanumérico

ENABLED o DISABLED para habilitar o deshabilitar una tarjeta fidelidad (solo valido en status LoyatyActivation)

ENABLED para habilitar una tarjeta fidelidad (solo valido en status FINISH)

No

"ENABLED"


nextExpDate

Numérico(Desde 6.5.4) Fecha de la proxima expiracion de puntos en format YYYYmmdd.  Solo es informado en tarjetas que posean vencimiento de carga definido.No-

nextExpValue

Numérico(Desde 6.5.4) Cantidad de puntos que venceran en el proximo vencimiento (nextExpDate) y se informa solo si la tarjeta posee vencimiento de carga definido.No-

reason

Alfanumérico

(Desde 6.5.10) Código del motivo por el cual se está realizando el chargeAmount o consumeAmount pertinente.  Este código corresponde a los valores de motivos definidos en la consola de PromoNo-

cvv

Alfanumérico

Indica el cvv correspondiente a la tarjeta si es utilizado.No-

Customer

type

Alfanumérico

Tipo de cliente.

No

"-"


id

Alfanumérico

Identifica al cliente a través del Código.

No

"-"


remainingAmount

Numérico positivo

Propiedad que se puede utilizar para indicar el saldo a favor o en contra del cliente en cuestión. (compatibilidad con PROMO 4 y versiones anteriores)

No

0


points

Entero positivo

Saldo que posee el cliente. (compatibilidad con PROMO 4 y versiones anteriores)

No

0


email

Alfanumérico

Atributo incluido para la consulta de clientes

No

""


name

Alfanumérico

Atributo incluido para la consulta de clientes

No

""


lastName

Alfanumérico

Atributo incluido para la consulta de clientes

No

""


Identifier

Numérico positivo

Atributo incluido para la consulta de clientes

No

""


cardNumber

Numérico positivo

Atributo incluido para la consulta de clientes

No

""


creditCampaignCode

Alfanumérico

Código de la Campaña crediticia

No

""


profileCode

Alfanumérico

Código del perfil del cliente

No

""


segmentAlfanuméricoLista de Códigos de Segmento a los cuales pertenece el cliente, separados por ;No""

remainingAmount

Numérico positivo

Propiedad que se puede utilizar para indicar el saldo a favor o en contra del cliente en cuestión. (compatibilidad con PROMO 4 y versiones anteriores)

No

0


amountNumérico positivoPropiedad que se puede utilizar para indicar el saldo correspondiente a un clienteNo0

"Payment Los atributos amount e itemamount son excluyentes y su uso depende de la versión de la promoción codificada que se
configure en el motor para manejar los pagos parciales.

type

Alfanumérico

Tipo de medio de pago.

No

"-"


id

Alfanumérico

Identificador del pago.

No

"-"


plan

Alfanumérico

Plan del medio de pago.

No

"-"


amount

Numérico positivo

Dinero que se utiliza con ese medio de pago. Dado que el monto del pago (PA) se calcula como PA = PIA  (1 - %desc) o PA = PIA * (1+%recargo)*
se obtiene que el monto de los ítems que se desea pagar (PIA) se calcula como PIA = PA / (1 - %desc) o PIA = PA / (1+%recargo)

No

0


bank

Alfanumérico

Banco relacionado con el medio de pago.

No

"-"


itemamount

Numérico positivo

Dinero que representa el monto de items que se desea pagar.

No

0


balance

Booleano

Indica si con este medio de pago se cancela el saldo de la transacción.Si el valor es true, entonces no es necesario enviar el amount o itemaount.

No

false

Event

type

Alfanumérico

Tipo de evento.

No

"-"


id

Alfanumérico

Identificador del evento.

No

"-"


value

Alfanumérico

Valor que representa el evento.

No

"-"

BenefitidAlfanumérico

Identificador del beneficio externo.

Si

typeAlfanumérico

Tipo de beneficio externo.

Si

amountNumérico positivo

Se utiliza para indicar el monto a descontar o el porcentaje de descuento (de acuerdo al benefitType).

Si

benefitTypeAlfanumérico

Indica el tipo de beneficio a generar.

  • desc: aplica el descuento sobre los ítem. Valor por defecto.
  • porc: porcentaje de descuento
No"desc"

seqItemAlfanumérico

Número de secuencia de los items a los cuales hay que aplicar el descuento. Si no viene el atributo o viene vacio se asume que es para todo el ticket. En caso de tener varios secuencias, las mismas deben venir separados por coma. Si algun alguna secuencia tiene mas de una cantidad, se debe concatenar con un =. Ejemplo: 1=2,2,3=3 (indica que el descuento se aplica a dos elementos de la secuencia uno, uno de la secuencia dos y tres la secuencia 3

No


Nota: El número de secuencia debe ser único para cada tipo de elemento, pudiendo existir, por ejemplo, un cliente y un ítem la misma secuencia; pero nunca dos elementos con el mismo número de secuencia.


Importante: Si se agrega un elemento al contexto con un número de secuencia ya utilizado por un elemento del mismo tipo, el último enviado reemplazará al anterior.


Ejemplo:
A continuación se presenta un ejemplo de un mensaje que agrega a la sesión del Motor de Promociones un ítem y un medio de pago (ambos con secuencia "1"), y elimina un cupón (de secuencia "2"):

<message companyId="sts" store="00001" terminal="010" date-time="2017-12-04 12:30:00:" messageId="0010" void-trx="false" response="true" init-tck="true" evaluate="true" status="payment" msg-version="2.0" map-version="15">
<item-add seq="1" code="0001" discountable="true" unitPrice="25.0" qty="1.0" level1="MEN" level2="CASUAL" supplier="" brand="LEVIS" xPrice="25.0" magnitude="1.0" />
<payment-add seq="1" type="CreditCard" amount="" id="000009" planId="10"/>
<coupon-void seq="2" />
<loyaltycard-add seq="5" id="3330000000222" type="puntos" />
</message>



Engine Response

En esta sección se describirá la estructura e interpretación del mensaje de respuesta que entregará el Motor de Promociones.
Como se mencionó con anterioridad, al igual que el mensaje de solicitud, el mensaje de respuesta que ofrece el Motor de Promociones tendrá un formato XML y constará de un encabezado y un cuerpo. En el encabezado contendrá información relativa a la terminal a la que se está respondiendo, errores que hayan podido suceder y versión del Motor.
En el cuerpo del mensaje se encontrarán las promociones que deberán aplicarse o sugerirse, los artículos a beneficiar, etc. En caso que no existan promociones a aplicar o sugerir o que no se haya solicitado la evaluación o sugerencia, el mensaje de respuesta constará sólo del encabezado.

Encabezado


Al igual que en el mensaje de solicitud el elemento raíz de la respuesta será la etiqueta <message>, siendo esta también lo que se denominará encabezado de la respuesta. Contendrá atributos que indican la tienda y terminal a la que va dirigido, identificación del mensaje, versión del mapa y del Motor con el que se realizó la evaluación, y código de retorno (acknowledge); siendo todos ellos enviados con obligatoriedad:

Propiedad

Tipo de dato

Descripción

mapversion

Alfanumérico

Versión del mapa utilizado para la evaluación de las promociones.

companyId

Alfanumérico

El mismo que se envió en el en el mensaje de solicitud.

store

Alfanumérico

El mismo que se envió en el en el mensaje de solicitud.

terminal

Entero

El mismo que se envió en el en el mensaje de solicitud.

messageId

Entero

El mismo que se envió en el en el mensaje de solicitud.

engine

Alfanumérico

Versión del Motor de promociones que realizó la evaluación.

ack

entero

Código de retorno (ver apartado siguiente).

transaction

Alfanumérico

Código que identifica la transacción en PROMO central (solo se informa con la respuesta a un status de Loyalty)
transaction="1_1_20170321152000" (toma los datos de data-time del request para armar el nro de transaccion en PROMO central)


Valores del atributo "ack"


El atributo ack Del inglés acknowledge. es un atributo dentro del encabezado del mensaje de respuesta que indica la existencia o no de errores en la recepción y/o procesamiento del mensaje de solicitud. Dependiendo del tipo de error o si el mensaje fue recibido correctamente, este atributo tendrá un valor particular:

Valor de ack

Descripción

Acción recomendada

0

No existieron errores.

Utilizar la respuesta.

1

Error de comunicación o el mensaje es ilegible.

Reenviar el mensaje y si el error persiste re validar su formato.

2

La sesión no fue inicializada o no existe dicha sesión.

Iniciar sesión como se indica en "Manejo de sesiones".

3

Error de validación en el mensaje.

Revalidar el formato del mensaje. También puede consultarse el archivo de log del Motor establecer con mayor exactitud cuál fue el error.

2001

Error de evaluación.

Comunicarse con el administrador del Motor de Promociones para que, por medio del archivo de log, se establezca cuál fue el error.

2002

No existe un mapa válido para el cálculo del ticket o mensaje recibido.

Utilizar un mapa previo existente o no aplicar promociones.

2003

La sesión se encuentra en uso.

Esperar unos 3 segundos aproximadamente y reintentar el envío.

2004

Error general de instanciamiento de la sesión.

Comunicarse con el administrador del Motor de Promociones para monitorear el equipo donde esté en funcionamiento el Motor.

2005

Time out de la sesión. La sesión expiró.

Si durante la evaluación de la sesión, la misma termina por time out, se envía un mensaje con ack 2005. Esperar y reintentar el envío.

4001

El motor se encuentra en proceso de inicialización.

Esperar porque el motor está arrancando y cargando la información.

8296

Existen errores en la validación

Este error se da con Status=LoyaltyValidationEx y FinishEx, debera analizarse el archivo de log a fin de establecer cual fue el error. Este error de validacion sera informado dentro del tag </errors> en el cuerpo de la respuesta con el ACK="8296".

8297

Se indica cuerpo del message es vacío.

Este error se da con Status=LoyaltyValidation, LoyaltyActivation y LoyaltyTransfer, y ocurre cuando el tag message no contienen ningún elemento de fidelidad.

8298

Si solicita recuperar la transacción original pero no envía cual es.

Revisar la conformación del mensaje que se envía del pos a PROMO Central a fin de chequear la existencia del atributo originalTransaction.

8299

Error genérico en el envío a PROMO central.

Comunicarse con el administrador de PROMO para monitorear el equipo donde esté en funcionamiento la consola de PROMO.



A partir de PROMO 5, se han agregado la serie de errores 9xxx los cuales aplican a Errores producidos en el procesamiento de la Consola de PROMO Central.
Dichos errores son:

1

Valor de ack

Descripción

Acción recomendada

2

9000

El mensaje no posee un ticket asociado.

Reenviar el mensaje y si el error persiste re validar su formato. Verificar la secuencia que mensajes que se está enviando.

3

9001

Existe una transacción pendiente. Se ha recibido una nueva transacción para ser procesada pero existe una anterior que se encuentra pendiente.

Se debe enviar un mensaje con status=commit/rollback para finalizar la transacción anterior.

4

9002

No existe transacción pendiente. Se ha recibido un mensaje con status=commit o rollback pero no existía una transacción previa pendiente.

Revisar la mensajería que se está enviando al motor, mayormente en su secuencia lógica.

5

9003

Se ha solicitado la información de una transacción previa pero no se ha informado el identificador de la misma.

Verificar que la propiedad originalTransaction tenga un valor y sea válido.

6

9004

Se ha solicitado la información de una transacción previa pero la transacción no existe.

Verificar el identificador de la transacción original que se está informando.

7

9005

Indica que la Consola está en modo Offline

En algunos casos como loyaltyTransfer, si la consola está en modo Offline, esta operación no se puede realizar. Contactar al administrador de PROMO para que chequee el equipo donde se encuentra corriendo la consola de PROMO.

8

9006

Job de Finalización de Transacciones

Contactar al administrador de la aplicación y revisar las configuraciones de la consola para restablecer el servicio.

9

9007

No se indica "CompanyId" en el header del mensaje.

Verificar los datos enviados

10

9101

No se ha encontrado el Cupón

Verificar los datos solicitados

11

9102

Cupón Consumido

Verificar que el cupón no haya sido utilizado

12

9103

Cupón Inactivo

Verificar que el cupón solicitado se encuentre activo.

13

9104

No se ha encontrado el tipo de cupón

Verificar valor informado en el mensaje.

14

9105

El Cupón ha expirado.

La fecha de vencimiento del cupón se ha alcanzado, con lo cual verificar dicha situación.

15

9106

Se ha alcanzado el máximo número de usos

Verificar dicha situación

16

9107

El cupón es nominado y no se ha informado un cliente

Verificar dicha situación

17

9108

El tipo de cupón no está activo

Verificar el tipo de cupón

18

9109

El monto enviado no corresponde al monto del cupón

Verificar monto del cupón

19

9110

Cupón no usado

El cupón ingresado a la transacción no ha participado de ninguna promoción.

20

9201

No se encontró el encabezado de la transacción.

Normalmente debido a un error interno, consultar con el administrador del sistema.

21

9500

No se encontró la tarjeta loyalty

Verificar los datos solicitados

22

9501

Tarjeta fidelidad inhabilitada

Verificar los datos solicitados. Para algunas acciones, solo se puede procesar Tarjetas fidelidad habilitadas

23

9502

Tarjeta fidelidad cancelada

Verificar los datos solicitados. No se puede interactuar con tarjetas fidelidad canceladas

24

9503

No se encontró el Tipo de tarjeta loyalty

Verificar los datos solicitados

25

9504

Tipo de tarjeta no activa

Verificar los datos solicitados. No se puede interactuar con tipos de tarjeta inactivos

26

9505

Tipo de tarjeta no recargable

Verificar los datos solicitados. Para opciones de Carga o Recarga, el tipo de tarjeta debe ser recargable

27

9506

La tarjeta ya tiene un cliente asociado

Verificar que la tarjeta en la activación el customer enviado.

28

9507

El estado enviado de tarjeta no existe.

Verificar que se haya enviado un estado de tarjeta, en la activación, valido (ENABLED, DISABLED) – En Mayúscula –

29

9508

La tarjeta no aplica al beneficio

Verificar que el tipo de tarjeta sea recargable o que la tarjeta este habilitada. Otro error puede ser que el tipo de tarjeta con el que se armó el beneficio, este inactivo o no exista en la transacción.

30

9509

La tarjeta requiere un cliente

Verificar si el tipo de tarjeta es requerido, en la transacción debe viajar al menos un cliente.

31

9510

Tarjeta no autorizada

Esto se da, si el tipo de tarjeta requiere CVV y no fue enviado o se ingresó mal

32

9511

Amount invalido

Cuando se intenta descontar un amount que es mayor al total del amount de la tarjeta, este mensaje aparecerá. Verificar que el amount sea menor al total.
Se informara este error cuando el tipo de tarjeta exija consumo total del monto en una sola transacción y se esté enviando un amount con valor menor
Se informara este error cuando el tipo de tarjeta exija transferencia total del monto a otra tarjeta del mismo tipo y se esté enviando un chargeAmount con valor menor.

33

9512

Se requiere al menos dos tarjetas

Este mensaje se utiliza para las transferencias. Se requiere que haya dos tarjetas en el mensaje. La de origen en la Seq="1" y la de destino en la Seq="2"

34

9513

La tarjeta no admite transferencia.

Verificar que la tarjeta origen admita Transferencia. Ya sea parcial o total.

35

9514

La tarjeta destino esta activa

Verificar que la tarjeta destino esta inactiva para realizar una transferencia total.

36

9515

Los tipos de tarjetas no son iguales

Verificar que los tipos de tarjeta sean iguales, es decir, el mismo.

37

9516

El saldo ingresado es mayor al tope de saldo

Verificar que el valor ingresado para la carga de una tarjeta, no sea mayor al Tope de saldo del tipo de tarjeta.

38

9603

Cliente inexistente

Verificar datos de cliente ingresado en la transacción

39

9610

identificador de cliente vacío

Verificar datos de cliente ingresado en la transacción

40

9611

Nombre de cliente vacío

Verificar datos de cliente ingresado en la transacción

41

9612

Apellido de cliente vacío

Verificar datos de cliente ingresado en la transacción

42

9613

ID de cliente Vacío

Verificar datos de cliente ingresado en la transacción

43

9614

No se recibieron parámetros del cliente

Verificar datos de cliente ingresado en la transacción

44

9620

Cliente ya existente

Verificar datos de cliente ingresado en la transacción

45

9629

Cliente inactivo

Verificar datos de cliente ingresado en la transacción

46

9901

Error de Cupón inesperado.

Todo error relacionado al procesamiento de cupones que no se encuentre tipificado en los códigos anteriores. Consultar al administrador del sistema.

47

9999

Error inesperado

Todo error en el procesamiento de PROMO Central que no se encuentre tipificado en los casos anteriores.


Ejemplo de Respuesta correcta pero sin elementos informados
<message ack="0" engine="2.6" mapversion="1" messageId="1" companyId="sts" store="1" terminal="1" transaction="1_1_20170515152511">
<loyalty>
<loyaltycards/>
<coupons/>
<errors/>
</loyalty>
</message>

Cuerpo


El cuerpo del mensaje de respuesta otorgado por el Motor de Promociones informa las promociones que deben ser aplicadas al ticket enviado hasta el momento y las promociones que deben ser sugeridas de acuerdo a lo especificado en el requerimiento. Estará compuesto por:

  • Una o más opciones
    • Cada opciones estará compuesta por una o más promociones
      • Cada promoción contendrá los participantes de condición (pueden no informarse)
      • Cada promoción estará compuesta por uno o más beneficios
        • Cada beneficio contendrá los participantes de combo (puede ser vacío)
        • Cada beneficio contendrá también los elementos ítem aplicados (puede ser vacío)
  • Un conjunto de sugerencias (esta parte del contenido puede no estar presente)
    • Las sugerencias están compuestas por una o más promociones
      • Por cada promoción se informará descripción, nombre, secuencias y tipos de secuencia que dieron lugar a la sugerencia.


Para el caso de evaluaciones a realizarse en PROMO Central, la composición de la respuesta será:

  • Un elemento fidelidad
    • Cada elemento de fidelidad puede estar compuesto por uno o más elementos fidelidad (cupones y/o tarjetas)
      • Cada cupón contendrá el detalle de los mismos para su emisión(opcional, puede no existir dicha información)
      • Cada tarjeta contendrá el detalle de la tarjeta
    • Cada elemento de fidelidad puede estar compuesto también por errores
    • Sección conteniendo la Tabla de Canje de Puntos


Opciones


Una opción, es uno de los tipos de funciones disponibles al generar un mapa, que permite optar al cliente entre dos o más promociones. Cada una surge de la aplicación de la función de convivencia OPTION (ver Manual de usuario). De esta forma, PROMO ya informa las combinaciones posibles. Las opciones se representan con la etiqueta <optional>. De no existir opciones, el cuerpo del mensaje de respuesta constará de una sola opción, es decir, existirá sólo una etiqueta <optional> que contendrá a las promociones a aplicar. Esta etiqueta no posee atributos.

Request de Opciones
<message companyId="napse" store="tienda 1" terminal="1" date-time="2022-12-05 18:00:00" init-tck="true" messageId="1" void-trx="false" response="true" status="sale" evaluate="true" map-version="139" suggest="false">
<item-add seq="1" unitprice="1400" xprice="1400" qty="1"  code="Coca-Cola" discountable="true"/>
</message>  

El pos muestra al cliente todas las promociones que contiene el mapa:

Response de Opciones
----- message ------
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<message ack="0" companyId="napse" engine="7.2.2#236" mapversion="139" messageId="1" store="tienda 1" terminal="1">
  <optional>
    <promo id="PromoO1" nro="638e15f77e8f8e2654b40864">
      <benefit TLOGMessage="PromoO1" account="" applicationMethod="resume" baseAmount="1400.00" benefitType="PercentageDiscount" discountPercentage="50.00" displayMessage="PromoO1" name="638e15f77e8f8e2654b40864" nro="638e16157e8f8e2654b4086b" order="1" printerMessage="PromoO1" prorationMethod="PROPORTIONAL" unit="qty">
        <apply>
          <item magnitude="0.000" qty="1.000" seq="1" value="700.00" valueWithTaxes="700.00" xprice="1400.00"/>
        </apply>
      </benefit>
    </promo>
  </optional>
  <optional>
    <promo id="PromoO2" nro="638e16317e8f8e2654b4086e">
      <benefit TLOGMessage="PromoO2" account="" applicationMethod="resume" baseAmount="1400.00" benefitType="FixedDiscount" discountAmount="1000.00" displayMessage="PromoO2" name="638e16317e8f8e2654b4086e" nro="638e16427e8f8e2654b40872" order="1" printerMessage="PromoO2" prorationMethod="PROPORTIONAL" unit="qty">
        <apply>
          <item magnitude="0.000" qty="1.000" seq="1" value="1000.00" valueWithTaxes="1000.00" xprice="1400.00"/>
        </apply>
      </benefit>
    </promo>
  </optional>
  <optional>
    <promo id="PromoO3" nro="638e16757e8f8e2654b40878">
      <benefit TLOGMessage="PromoO3" account="" amount="" applicationMethod="resume" baseAmount="1400.00" benefitType="CouponBenefit" couponId="601" displayMessage="PromoO3" infoPos="0" name="638e16757e8f8e2654b40878" nro="638e16997e8f8e2654b4087f" order="1" printerMessage="PromoO3" qty="1.000">
        <apply>
          <item magnitude="0.000" qty="1.000" seq="1" value="0.00" valueWithTaxes="0.00" xprice="1400.00"/>
        </apply>
      </benefit>
    </promo>
  </optional>
</message>

Siempre va a haber por lo menos un optional (sin importar que función de convivencia se esté utilizando). Solo la función de convivencia OPTION tiene un tag. Las otras funciones de convivencia modifican el resultado sin tener un tag, lo maneja internamente el motor. En el caso que se utilice la función de convivencia "OPTION" pueden venir varios optional para que puedan ser informados en pantalla, y la persona elija en el POS qué opción va a preferir. El POS deberá usar el campo "chosenOption" en el mensaje Finish, para informarle a Promo qué opción eligió la persona en la pantalla del POS. Para elegir la primer promoción deberá ingresar en chosenOption="0", para la segunda promoción chosenOption="1", y así sucesivamente.


Promociones



Como se mencionó anteriormente, cada una de las opciones contendrá una o más promociones.
Estas estarán identificadas por su nombre, siendo este su único atributo.
Las promociones estarán representadas con la etiqueta <promo>, teniendo el atributo id representando su nombre:

Propiedad

Tipo de dato

Descripción

id

Alfanumérico

Nombre de la promoción.

nro

Alfanumérico

Identificador de la base de datos de la promoción


Ejemplo
<message companyId="sts" store="MX" mapversion="3241" messageId="160" terminal="100" engine="2.6" ack="0">
<optional>
<promo id="Promoción navideña" nro="1">

… participantes de condición …

… beneficios …

</promo>
<promo id="Promoción 2x1 en juguetes" nro="2">

… participantes de condición …

… beneficios …

</promo>
</optional>
</message>


A su vez, cada promoción podrá informar una serie de elementos participantes de condición y beneficios, ambos detallados en las secciones siguientes.


Participantes de condición


Los participantes de condición son un componente opcional que indica los elementos que influyeron en la condición (ver Manual de usuario) que provocaron que se otorgue el beneficio. Estos elementos estarán agrupados dentro de una etiqueta del tipo <conditionParticipants>. Los elementos participantes de condición estarán representados por la etiqueta que corresponda al tipo de elemento, agrupados como ya se describió dentro de <conditionParticipants>. Los elementos participantes poseerán los atributos informados al momento de agregarlos a la sesión.
Los participantes de condición son completamente opcionales, pudiendo no ser informados si así se configura en el archivo de definición de promociones (mapa) o si no existen participantes de condición. En ese caso la etiqueta <conditionParticipants> no formará parte de la promoción. Esta etiqueta no posee atributos.

Ejemplo
<message companyId="sts" store="MX" mapversion="3241" messageId="160" terminal="100" engine="2.6" ack="0">
<optional>
<promo id="Promoción navideña" nro="1">
<conditionParticipants>
<item code="0056" brand="PANASONIC" xprice="99.0" magnitude="0.0" family="TV" type="qty" dept="ELECTRONIC" qty="1.0" seq="2"/>
<customer seq="2" id="000004" type="preferred" />
<coupon seq="1" id="0001" amount="" qty="1.0" type="A" />
</conditionParticipants>

… beneficios …

</promo>
</optional>
</message>


Beneficios


Dentro de cada promoción existirá uno o más beneficios. Los beneficios son los elementos más importantes de la respuesta y definen la ventaja (económica o no) que debe darse al cliente, correspondientes a la promoción a la que pertenecen. Se definirán a través de la etiqueta <benefit>.
Existen beneficios de diversos tipos, cada uno con diferentes características. Es por ello que dependiendo del beneficio que se trate variarán los atributos correspondientes a la etiqueta <benefit> que lo representa. No obstante, existen algunos atributos que son comunes a todos ellos:

Propiedad

Tipo de dato

Descripción

order

Entero positivo

Número que identifica unívocamente al beneficio dentro del mensaje de respuesta. Su valor surge del orden en que se realizó su aplicación al realizar la evaluación.

benefitType

Alfanumérico

Tipo de beneficio que se trata.

displayMessage

Alfanumérico

Mensaje a mostrar por display en el punto de venta.

printerMessage

Alfanumérico

Mensaje a imprimir en la boleta o ticket al finalizar la compra.

applicationMethod

Alfanumérico

Forma de mostrar el beneficio. Puede poseer dos valores:

  • "lineByLine" (el beneficio debe mostrarse luego de cada artículo beneficiado)
  • "resume" (el beneficio debe mostrarse al final del ticket)

baseAmount

Real positivo

Indica el monto total sobre el cual se calculó el beneficio en cuestión.

TLOGMessage

Alfanumérico

Mensaje a guardar en el TLOG

account

Alfanumérico

Cuenta contable a la cual será imputado el beneficio.

nro

Alfanumérico

Identificador de la base de datos del beneficio.

name

Alfanumérico

Identificador de la base de datos de la promoción que contiene al beneficio.


Sin importar de qué tipo de beneficio se trate, estos pueden tener elementos aplicados y participantes de combo. Cada uno de estos se detallarán en las secciones siguientes.

Tipos de beneficios

PROMO posee ocho tipos de beneficio, siendo tres de ellos monetarios y cinco no monetarios. Los beneficios monetarios son aquellos que otorgan una ventaja económica al cliente, mientras que los no monetarios no.
Los tipos de beneficio estarán dados por el valor del atributo benefitType de la etiqueta <benefit>, y son los siguientes:

  1. Monetarios:
    1. FixedDiscount
      • Es un descuento fijo que se realiza sobre un conjunto de artículos.
    2. PercentageDiscount
      • Representa un porcentaje de descuento sobre un conjunto de artículos.
    3. NewPrice
      • Asigna un nuevo precio a uno o varios artículos.
    4. TenderDiscountBenefit
      • Representa un % de descuento o recargo sobre un conjunto de artículos. La información para calcular este porcentaje se obtiene de los planes de pago (PaymentPlanBenefit) aplicados.
    5. RedeemPointsBenefit
      • Realiza la conversión de saldo a dinero e informa un monto de descuento a aplicar en base al valor informado.
    6. CalculatedCouponApplicationBenefit
      • Aplica como descuento el monto informado por un cupón calculado
    7. CatalogRedeemBenefit
      • Realiza una conversión de puntos y otorga un monto de descuento basado en datos tabulares definidos para los productos (desde v6.5.2)


  1. No monetarios
    1. PaymentPlanBenefit
      • Otorga un plan de pagos específico para una serie de artículos o para la compra.
    2. CouponBenefit
      • Otorga una cierta cantidad de cupones específicos al cliente.
    3. GiftBenefit
      • Entrega al cliente uno o más regalos específicos.
    4. LoyaltyBenefit
      • Beneficia al cliente con una cierta cantidad de saldo de fidelidad (millas, puntos de monedero, dinero, etc.). A partir de la versión 2.8.0, este beneficio calcula la cantidad de saldo por cada elemento de aplicación y la cantidad de saldo en total que otorga.
    5. FactorLoyaltyBenefit
      • Representa el otorgamiento de puntos, dinero, millas, etc. de fidelidad en relación a un factor dado.
    6. PercentLoyaltyBenefit
      • Representa el otorgamiento de puntos, dinero, millas, etc. de fidelidad en relación a un porcentaje dado. Este beneficio calcula la cantidad de puntos, dinero, millas, etc. por cada elemento de aplicación y la cantidad de puntos, dinero, millas, etc. en total que otorga.
    7. CalculatedCouponBenefit
      • Representa el otorgamiento de un cupón cuyo monto de descuento a otorgar está definido por un porcentaje de los participantes.




Como se mencionó en párrafos anteriores, cada tipo de beneficio tendrá atributos propios. Cada uno de estos atributos representa un parámetro específico del beneficio al que pertenece (indicado en benefitType). En la siguiente tabla se enumeran dichos atributos y en la columna "Requerido" se indica si el atributo estará siempre presente en la respuesta ("Si") o bien dependerá de su valor para ser incluido o no en la misma ("No")

Beneficio

Propiedad

Tipo de dato

Requerido

Descripción

FixedDiscount

unit

Alfanumérico

No

El valor de "unit" indicará si el descuento estará aplicado sobre todo el conjunto o sobre cada unidad de la propiedad seleccionada. Los valores posibles son:

  • "qty" (se aplica el descuento a cada unidad de cantidad)
  • "magnitude" (se aplica el descuento a cada unidad de cantidad)
    Si no se informase la unidad (atributo vacío), la aplicación es sobre todo el conjunto de aplicados (ver "Elementos aplicados").


discountAmount

Real positivo

Si

Descuento que se realizará sobre los elementos aplicados. El valor a descontar a cada artículo variará dependiendo de la unidad de aplicación.


prorationMethod

Alfanumérico

Si

Método que se utilizará para prorratear el beneficio entre los elementos aplicados, pudiendo ser:

  • "default"
  • "proportional" (prorratea el beneficio proporcionalmente al precio)
  • "most-expensive-first" (aplica el beneficio al artículo más caro)
  • "cheapest-first" (aplica el beneficio al artículo más barato)

PercentageDiscount

unit

Alfanumérico

No

Indicará si debe aplicarse el porcentaje de descuento a cada unidad o al total. Los valores que puede tener son los indicados anteriormente.


discountPercentage

Real positivo

Si

Porcentaje de descuento que se realizará sobre los elementos participantes. El valor a descontar a cada artículo variará dependiendo de la unidad de aplicación.


name

Alfanumérico

No

Nombre de la promoción que ha originado el beneficio.


prorationMethod

Alfanumérico

Si

Método que se utilizará para prorratear el beneficio entre los elementos aplicados. Los valores que a tomar son los mismos indicados anteriormente.

NewPrice

unit

Alfanumérico

No

Indicará si debe aplicarse el nuevo precio a cada unidad o al total. Los valores que puede tener son los indicados anteriormente.


newPrice

Real positivo

Si

Descuento fijo que se realizará sobre los elementos participantes. El valor a descontar a cada artículo variará dependiendo de la unidad de aplicación.


prorationMethod

Alfanumérico

Si

Método que se utilizará para prorratear el beneficio entre los elementos aplicados. Los valores que puede tomar son los mismos indicados anteriormente.

TenderDiscountBenefit

tender

Alfanumérico

Si

Medio/s de pago que se pueden utilizar. Puede ser una lista separada por comas.


limit

Real positivo

No

Indica el máximo que se podrá abonar con el medio de pago. Este tope sólo tendrá utilidad en el punto de venta sin afectar los calculos del Motor de Promociones. Si este valor es vacío significa que el monto es ilimitado.


planId

Alfanumérico

Si

Identificador del plan que se otorga.


Type

Alfanumérico

No

Tipo de medio de pago.


Bank

Alfanumérico

No

Banco asociado al medio de pago.


Percent

Real positivo

Si

Porcentaje de descuento o recargo que se realizará sobre los elementos participantes.


percenttype

Alfanumérico

No

Indica si el porcentaje es un descuento (valor=discount) o recargo (valor=surcharge).


tenderseq

Entero positivo

Si

Número identificador único del elemento medio de pado (payment) dentro de la transacción.


amount

Real positivo

Si

Dinero que se utiliza con ese medio de pago


itemamount

Real positivo

Si

Dinero que representa el monto de items que se desea pagar.


paymentAmount

Real positivo

Si

Indica el monto total sobre el cual se calculó el beneficio en cuestión.


installments

Real positivo

No

Indica la cantidad de cuotas asociadas al plan de pago


benefitedamount

Real positivo

Si

Descuento que se realizará sobre los elementos aplicados.

RedeemPointsBenefit

Type

Alfanumérico

Si

Indica el tipo de tarjeta a la que se aplicara el beneficio


factor

Real positivo

Si

Indica el factor de conversión para el cálculo del descuento en base al monto informado en el amount


usedPoints

Real positivo

Si

Indica la cantidad de saldo (punto, dinero, etc.) que será utilizado para la aplicación de dicho beneficio


discountAmount

Real positivo

Si

Descuento que se realizará sobre los elementos aplicados. El valor a descontar a cada artículo variará dependiendo de la unidad de aplicación.


prorationMethod

Alfanumérico

Si

Método que se utilizará para prorratear el beneficio entre los elementos aplicados. Los valores que puede tomar son los mismos indicados anteriormente.


unit

Alfanumérico

Si

Indicará si debe aplicarse el nuevo precio a cada unidad o al total. Los valores que puede tener son los indicados anteriormente.

CalculatedCouponApplicationBenefit

discountAmount

Real positivo

Si

Descuento que se realizará sobre los elementos aplicados. El valor a descontar a cada artículo variará dependiendo de la unidad de aplicación.


couponId

Alfanumérico

Si

Identificador del cupón a redimir.

PaymentPlanBenefit

tender

Alfanumérico

Si

Medio/s de pago que se pueden utilizar. Puede ser una lista separada por comas. Cuando en el request de una transacción no se especifica el Id y/o el nombre, y/o cuotas, y/o tipos, y/o plan, y/o prefijo y/o pocket del plan de pago; el mismo igual se aplica.


limitAmount

Real positivo

No

Indica el máximo que se podrá abonar con el medio de pago. Este tope sólo tendrá utilidad en el punto de venta sin afectar los calculos del Motor de Promociones. Si este valor es vacío significa que el monto es ilimitado.


planid

Alfanumérico

Si

Identificador del plan que se otorga.


type

Alfanumérico

No

Tipo de medio de pago.


bank

Alfanumérico

Si

Banco asociado al medio de pago.


percent

Real positivo

No

Porcentaje de descuento o recargo que se realizará sobre los elementos participantes. El descuento o recargo será informado como un beneficio TenderDiscountBenefit


percenttype

Alfanumérico

No

Indica si el porcentaje es un descuento (valor=discount) o recargo (valor=surcharge).


installments

Real positivo

No

Indica la cantidad de cuotas asociadas al plan de pago


paymentAmount

Real positivo

Si

Indica el monto total sobre el cual se calculó el beneficio en cuestión.


nominalAnnualRateReal positivoNoTNA: Tasa Nominal Anual.  Es un valor informativo especificado en la Promocion.

effectiveMonthlyRateReal positivoNoTEM: Tasa Efectiva Mensual.  Es un valor informativo especificado en la Promocion.

totalFinancialCostAssumedReal positivoNoCFT Asumido: Costo Financiero Total Asumido.  Es un valor informativo especificado en la Promocion.
BankRefundBenefit


ver PaymentPlanBenefit ya que posee las mismas propiedades.

CouponBenefit

couponId

Alfanumérico

Si

Identificador del cupón a otorgar.


amount


Si

Indicara el monto asociado a un cupon cuyo monto fue calculado


qty

Entero positivo

Si

Cantidad de cupones a otorgar.

GiftBenefit

giftid

Alfanumérico

Si

Identificador del regalo a entregar. En caso de que sea un producto en stock, puede representar el código del artículo a regalar.


giftType

Alfanumérico

Si

Tipo de regalo a entregar. Puede ser vacío.


qty

Entero positivo

Si

Cantidad de regalos con el identificador indicado.

LoyaltyBenefit

type

Alfanumérico

Si

Tipo de valor (puntos, dinero, millas, etc.) de fidelidad que se están otorgando.


amount

Entero positivo

Si

Cantidad de puntos, dinero, millas, etc. a otorgar del tipo especificado en el atributo anterior.


unit

Alfanumérico

Si

Indicará si debe aplicarse la cantidad de puntos, dinero, millas, etc. a cada unidad o al total. Los valores que puede tener son los indicados anteriormente.


totalpoints

Real positivo

Si

Indica la cantidad total de puntos, dinero, millas, etc. que otorga el beneficio luego de ser calculado.

FactorLoyaltyBenefit

type

Alfanumérico

Si

Tipo de puntos, dinero, millas, etc. de fidelidad que se están otorgando.


factor

Real positivo

Si

Factor multiplicador a utilizar para el cálculo de los puntos, dinero, millas, etc.

PercentLoyaltyBenefit

type

Alfanumérico

Si

Tipo de puntos, dinero, millas, etc. de fidelidad que se están otorgando.


percent

Real positivo

Si

Porcentaje de puntos, dinero, millas, etc., que se aplica sobre el xprice u originalXPrice para calcular la cantidad de puntos, dinero, millas, etc. que corresponden otorgar.


totalpoints

Real positivo

Si

Indica la cantidad total de puntos, dinero, millas, etc. que otorga el beneficio luego de ser calculado.

CalculatedCouponBenefit

couponId

Alfanumérico

Si

Identificador del cupón a otorgar.


amount

Entero positivo

Si

Indicara el monto asociado a un cupon cuyo monto fue calculado


Percentage

Alfanumérico

Si

Indica el porcentaje en base al cual fue calculado el monto del cupon


qty

Entero positivo

Si

Cantidad de cupones a otorgar.

(desde v6.5.2)

CatalogRedeemBenefit

discountAmount

Real positivo

Si

Descuento que se realizará sobre los elementos aplicados. El valor a descontar a cada artículo variará dependiendo de la unidad de aplicación.


type

Alfanumérico

Si

Tipo de puntos, dinero, millas, etc. de fidelidad que se están otorgando.


unit

Alfanumérico

Si

Actualmente el beneficio se aplica sobre la cantidad o magnitud de cada producto en cuestión por lo cual no se espera funcionalidad en este atributo.


usedPoints

Real positivo

Si

Indica la cantidad de saldo (punto, dinero, etc.) que será utilizado para la aplicación de dicho beneficio



Ejemplos:

FixedDiscount
<message companyId="sts" store="MX" mapversion="3241" messageId="160" terminal="100" engine="2.6" ack="0">
<optional>
<promo id="Promoción navideña" nro="1">
<conditionParticipants>
<item code="0056" brand="PANASONIC" xprice="99.0" magnitude="0.0" family="TV" type="qty" dept="ELECTRONIC" qty="1.0" seq="2"/>
<customer seq="2" id="000004" type="preferred" />
<coupon seq="1" id="0001" amount="" qty="1.0" type="A" />
</conditionParticipants>
<benefit order="1" benefitType="FixedAmount" displayMessage="" printerMessage="" unit="qty" prorationMethod="PROPORTIONAL" applicationMethod="lineByLine" nro="3" amount="20.00" baseAmount="165.00">

… participantes de combo y/o elementos aplicados …

</benefit>
</promo>
</optional>
</message>


PercentageDiscount
<message companyId="sts" store="MX" mapversion="3241" messageId="160" terminal="100" engine="2.6" ack="0">
<optional>
<promo id="Promoción navideña" nro="1">
<benefit order="1" benefitType="PercentageDiscount" displayMessage="" printerMessage="" unit="" prorationMethod="PROPORTIONAL" applicationMethod="lineByLine" nro="3" Percentage="20.00" baseAmount="165.00">

… participantes de combo y/o elementos aplicados …

</benefit>
</promo>
</optional>
</message>



TenderDiscountBenefit
<message companyId="sts" store="MX" mapversion="3241" messageId="160" terminal="100" engine="2.6" ack="0">
<optional>
<promo id="Promoción navideña" nro="1">
<benefit order="1" benefitType="TenderDiscountBenefit" displayMessage="" printerMessage="" applicationMethod="lineByLine" nro="3" tender="VISA" planId="0A3" limitAmount="200.00" baseAmount="165.00" bank="HSBC" percent="5.000" percenttype="discount" amount="2375.000" itemamount="2500.000" paymentAmount="2500.000" benefitedamount="125.000" tenderseq="1" >

… participantes de combo y/o elementos aplicados …

</benefit>
</promo>
</optional>
</message>


RedeemPointsBenefit
<message ack="0" engine="2.6" mapversion="2" messageId="1" companyId="sts" store="1" terminal="1">
  <optional>
    <promo id="redime puntos" nro="58ff57be6772781234e7915e">
      <benefit TLOGMessage="redime puntos" account="" applicationMethod="resume" baseAmount="100.00"
      benefitType="RedeemPointsBenefit" discountAmount="100.00" displayMessage="redime puntos" factor="1"
      name="58ff57be6772781234e7915e" nro="58ff57e76772781234e79164" order="1" printerMessage="redime puntos"
      prorationMethod="PROPORTIONAL" unit="" usedPoints="100.0">
        <apply>
          <item magnitude="0.000" qty="1.000" seq="2" value="100.00" xprice="100.00"/>
        </apply>
      </benefit>
    </promo>
  </optional>
</message">


calculatedcouponaplicationbenefit
<message ack="0" engine="2.6" mapversion="2" messageId="1" companyId="sts" store="1" terminal="1">
<optional>
<promo id="redime impreso calculado" nro="5900e1a6a846390de08a7afe">
<benefit TLOGMessage="redime impreso calculado" account="" applicationMethod="resume" baseAmount="100.00" benefitType="CalculatedCouponApplicationBenefit" couponId="1" discountAmount="10.00" displayMessage="redime impreso calculado" name="5900e1a6a846390de08a7afe" nro="5900e1bca846390de08a7b04" order="1" printerMessage="redime impreso calculado" prorationMethod="PROPORTIONAL" unit="">
<apply>
<item magnitude="0.000" qty="1.000" seq="2" value="10.00" xprice="100.00"/>
</apply>
</benefit>
</promo>
</optional>
</message>


PaymentPlanBenefit
<message companyId="sts" store="MX" mapversion="3241" messageId="160" terminal="100" engine="2.6" ack="0">
<optional>
<promo id="Promoción navideña" nro="1">
<benefit order="1" benefitType="PaymentPlanBenefit" displayMessage="" printerMessage="" applicationMethod="lineByLine" nro="3" tender="VISA" planId="A3" limitAmount="200.00" baseAmount="165.00" bank="HSBC" percent="5.000" percenttype="discount" paymentAmount="2500.00">

… participantes de combo y/o elementos aplicados …

</benefit>
</promo>
</optional>
</message>


BankRefundBenefit
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<message ack="0" companyId="napse" engine="2.6" mapversion="3" messageId="1" store="1" terminal="1">
  <optional>
    <promo id="Reintegro bancario" nro="1">
      <benefit TLOGMessage="Reintegro bancario" account="" amount="90.00" applicationMethod="resume" baseAmount="100.00" benefitType="BankRefundBenefit" benefitedamount="10.00" displayMessage="Reintegro bancario" installments="1" itemamount="100.00" order="2" paymentAmount="100.00" percent="10" planId="1" printerMessage="Reintegro bancario" tender="1" tenderseq="1" type="1">
        <apply>
          <item magnitude="0.000" qty="1.000" seq="2" value="1.00" valueWithTaxes="0.00" xprice="10.00"/>
          <item magnitude="0.000" qty="1.000" seq="4" value="2.00" valueWithTaxes="0.00" xprice="20.00"/>
          <item magnitude="0.000" qty="1.000" seq="6" value="3.00" valueWithTaxes="0.00" xprice="30.00"/>
          <item magnitude="0.000" qty="1.000" seq="8" value="4.00" valueWithTaxes="0.00" xprice="40.00"/>
        </apply>
      </benefit>
    </promo>
  </optional>
</message>



CouponBenefit
<message companyId="sts" store="MX" mapversion="3241" messageId="160" terminal="100" engine="2.6" ack="0">
<optional>
<promo id="Promoción navideña" nro="1">
<conditionParticipants>
<item code="0056" brand="PANASONIC" xprice="99.0" magnitude="0.0" family="TV" type="qty" dept="ELECTRONIC" qty="1.0" seq="2"/>
<customer seq="2" id="000004" type="preferred" />
<coupon seq="1" id="0001" amount="" qty="1.0" type="A" />
</conditionParticipants>
<benefit order="1" benefitType="CouponBenefit" displayMessage="" printerMessage="" applicationMethod="lineByLine" nro="3" couponId="C0032" qty="2" baseAmount="165.00">

… participantes de combo y/o elementos aplicados …

</benefit>
</promo>
</optional>
</message>



GiftBenefit
<message companyId="sts" store="MX" mapversion="3241" messageId="160" terminal="100" engine="2.6" ack="0">
<optional>
<promo id="Promoción navideña" nro="1">
<benefit order="1" benefitType="GiftBenefit" displayMessage="" printerMessage="" applicationMethod="lineByLine" nro="3" qty="2" giftType="A" giftId="00452" baseAmount="165.00">

… participantes de combo y/o elementos aplicados …

</benefit>
</promo>
</optional>
</message>


LoyaltyBenefit
<message companyId="sts" store="MX" mapversion="3241" messageId="160" terminal="100" engine="2.6" ack="0">
<optional>
<promo id="Promoción navideña" nro="1">
<conditionParticipants>
<item code="0056" brand="PANASONIC" xprice="99.0" magnitude="0.0" family="TV" type="qty" dept="ELECTRONIC" qty="1.0" seq="2"/>
<customer seq="2" id="000004" type="preferred" />
<coupon seq="1" id="0001" amount="" qty="1.0" type="A" />
</conditionParticipants>
<benefit order="1" benefitType="LoyaltyBenefit" displayMessage="" printerMessage="" applicationMethod="lineByLine" nro="3" value="1000" type="points" baseAmount="99.00" totalpoints="1000.00" >

… participantes de combo y/o elementos aplicados …

<item value="0.000" seq="2" qty="1.000" points="1000.00" xprice="99.00"/>
</benefit>
</promo>
</optional>
</message>
<message companyId="sts" store="MX" mapversion="3241" messageId="160" terminal="100" engine="2.6" ack="0">
<optional>
<promo id="Promoción navideña" nro="1">
<conditionParticipants>
<item code="0056" brand="PANASONIC" xprice="99.0" magnitude="0.0" family="TV" type="qty" dept="ELECTRONIC" qty="2.0" seq="2"/>
<customer seq="2" id="000004" type="preferred" />
<coupon seq="1" id="0001" amount="" qty="1.0" type="A" />
</conditionParticipants>
<benefit order="1" benefitType="LoyaltyBenefit" displayMessage="" printerMessage="" applicationMethod="lineByLine" nro="3" value="1000" type="points" baseAmount="99.00" unit="qty" totalpoints="2000.00" >

… participantes de combo y/o elementos aplicados …



<item value="0.000" seq="2" qty="2.000" points="2000.00" xprice="99.00"/>
</benefit>
</promo>
</optional>
</message>



FactorLoyaltyBenefit
<message companyId="sts" store="MX" mapversion="3241" messageId="160" terminal="100" engine="2.6" ack="0">
<optional>
<promo id="Promoción navideña" nro="1">
<benefit order="1" benefitType="FactorLoyaltyBenefit " displayMessage="" printerMessage="" applicationMethod="lineByLine" nro="3" factor="2" type="points" baseAmount="165.00">

… participantes de combo y/o elementos aplicados …

</benefit>
</promo>
</optional>
</message>


PercentLoyaltyBenefit
<message companyId="sts" store="MX" mapversion="3241" messageId="160" terminal="100" engine="2.6" ack="0">
<optional>
<promo id="Promoción navideña" nro="1">
<conditionParticipants>
<item code="0056" brand="PANASONIC" xprice="99.0" magnitude="0.0" family="TV" type="qty" dept="ELECTRONIC" qty="1.0" seq="2"/>
<customer seq="2" id="000004" type="preferred" />
<coupon seq="1" id="0001" amount="" qty="1.0" type="A" />
</conditionParticipants>
<benefit order="1" benefitType="PercentLoyaltyBenefit" displayMessage="" printerMessage="" applicationMethod="lineByLine" nro="3" percent="10.0" type="points" baseAmount="165.00" totalpoints="16.50" >

… participantes de combo y/o elementos aplicados …


<item value="0.000" seq="2" qty="1.000" points="16.50" xprice="99.00"/>
</benefit>
</promo>
</optional>
</message>


CalculatedCouponBenefit
<message ack="0" engine="2.6" mapversion="2" messageId="1" companyId="sts" store="1" terminal="1">
<optional>
<promo id="emite impreso calculado" nro="5900e173a846390de08a7af7">
<benefit TLOGMessage="emite impreso calculado" account="" amount="10.00" applicationMethod="resume" baseAmount="100.00" benefitType="CalculatedCouponBenefit" couponId="1" displayMessage="emite impreso calculado" name="5900e173a846390de08a7af7" nro="5900e18ea846390de08a7afd" order="1" percentage="10" printerMessage="emite impreso calculado" qty="1.000">
<apply>
<item magnitude="0.000" qty="1.000" seq="2" value="0.00" xprice="100.00"/>
</apply>
</benefit>
</promo>
</optional>
</message>

(desde v6.5.2) (Para mayor detalle ver la sección loyalty en este documento)

CatalogRedeemBenefit
<message ack="0" companyId="napse" engine="6.5.1" mapversion="5555" messageId="5" store="b320" terminal="1">
<optional>
<promo code="catred01" id="catred01" nro="5e937332c142d70ac486ebb3">
<benefit TLOGMessage="catred01" account="" applicationMethod="qty" baseAmount="7000.00" benefitType="CatalogRedeemBenefit" type="02" discountAmount="1201.22" displayMessage="catred01" name="5e937332c142d70ac486ebb3" nro="5e937384c142d70ac486ebb7" order="1" printerMessage="catred01" prorationMethod="PROPORTIONAL" unit="" usedPoints="330.00">
<apply>
<item magnitude="0.000" points="100.00" qty="1.000" seq="1" value="100.00" valueWithTaxes="100.00" xprice="1000.00"/>
<item magnitude="0.000" points="30.00" qty="1.000" seq="2" value="50.00" valueWithTaxes="50.00" xprice="1000.00"/>
<item magnitude="0.000" points="60.00" qty="1.000" seq="3" value="27.00" valueWithTaxes="27.00" xprice="1000.00"/>
<item magnitude="0.000" points="140.00" qty="2.000" seq="4" value="1024.22" valueWithTaxes="1024.22" xprice="2000.00"/>
<item magnitude="0.000" points="0.00" qty="2.000" seq="5" value="0.00" valueWithTaxes="0.00" xprice="2000.00"/>
</apply>
</benefit>
</promo>
</optional>
</message>

Participantes de combo


En el caso de que la promoción contenga asociado algún combo Agrupación finita de elementos. Para mayor detalle se recomienda consultar el Manual de usuario "condición por composición"., los beneficios de la promoción que se apliquen a este combo asociado contendrán una etiqueta denominada <comboParticipants>. Dentro de ella se enumerarán los elementos que forman el combo al cual se aplica el beneficio al que pertenecen, denominados participantes de combo, de manera similar a los participantes de condición y poseyendo los mismos atributos.
Si la promoción no está definida por combos o no se exige el cálculo de participantes en el archivo de definición (mapa), <comboParticipants> no estará presente. Esta etiqueta no posee atributos.

Ejemplo
<message companyId="sts" store="MX" mapversion="3241" messageId="160" terminal="100" engine="2.6" ack="0">
<optional>
<promo id="Promoción navideña" nro="1">
<benefit order="1" benefitType="FactorLoyaltyBenefit " displayMessage="" printerMessage="" applicationMethod="lineByLine" nro="3" factor="2" type="points" baseAmount="165.00">
<comboParticipants>
<item seq="1" code="0010" qty="2.0" magnitude="1.0" xPrice="90.0" unitPrice="50.0" />
<item seq="2" code="0011" qty="2.0" magnitude="1.0" xPrice="72.0" unitPrice="40.0" />
</comboParticipants>

… elementos aplicados …


</benefit>
</promo>
</optional>
</message>


Elementos aplicados


Los beneficios siempre son aplicados sobre artículos. Para representar esto el Motor de Promociones al informar beneficios utiliza la etiqueta <apply>, donde se enumerarán los artículos sobre los cuales debe aplicarse el beneficio. Debido a que los beneficios solo pueden ser aplicados sobre artículos, los elementos contenidos en <apply> serán siempre <item>.
A diferencia de los elementos que se informan en los participantes (ya sean de condición, como de combo), los elementos <item> que se encontrarán dentro de <apply> poseerán los siguientes atributos:

Propiedad

Tipo de dato

Descripción

seq

Entero positivo

Número que identifica al elemento dentro de la transacción al que se aplica el beneficio.

value

Número En caso que se asigne a un ítem un nuevo precio que sea mayor al precio de venta informado, este valor puede tomar un valor negativo. Por este motivo deberán implementarse rutinas para el manejo de este tipo de valores.

Monto total a descontar al elemento indicado por el atributo seq.

qty

Entero positivo

Cantidad de ítems afectados entre los cuales deberá repartirse el descuento expresado en value.

magnitude

Real positivo

Magnitud afectada sobre la que deberá aplicarse el descuento expresado en value. Si no se definió una magnitud para el ítem, se informará como "0.0". Cuando se calculen puntos, dinero, millas, etc., si este valor es "0.0" entonces no se informará.

points

Real positivo

Cantidad total de puntos, dinero, millas, etc. que otorga la secuencia identificada por seq. Aparece siempre que el elemento de aplicación forme parte de un beneficio LoyaltyBenefit o PercentLoyaltyBenefit para los cuales se calculan los puntos, dinero, millas, etc.

xprice

Real positivo

Xprice o precio original de la secuencia en el momento en que se calculó el beneficio. El que sea xprice o precio original dependerá de cómo esté configurado el beneficio y sobre cuál de estos dos valores aplique (a partir de versión 2.8.0).


Los beneficios del tipo monetario siempre informarán elementos aplicados, mientras que los no monetarios pueden no hacerlo. Por otro lado, dentro de los artículos aplicados de beneficios no monetarios el atributo value de estos artículos será siempre "0.0", dado que no existe un descuento para realizar.

Ejemplo
<message companyId="sts" store="MX" mapversion="3241" messageId="160" terminal="100" engine="2.6" ack="0">
<optional>
<promo id="Promoción navideña" nro="1">
<benefit order="1" benefitType="PercentageDiscount" displayMessage="" printerMessage="" unit="" prorationMethod="PROPORTIONAL" applicationMethod="lineByLine" nro="3" Percentage="20.00" baseAmount="162.00">
<comboParticipants>
<item seq="1" code="0010" qty="2.0" magnitude="1.0" xPrice="90.0" unitPrice="50.0" />
<item seq="2" code="0011" qty="2.0" magnitude="1.5" xPrice="72.0" unitPrice="40.0" />
</comboParticipants>
<apply>
<item seq="1" value="18.00" magnitude="0.0" qty="1.0" xprice="90.00"/>
<item seq="2" value="14.40" magnitude="1.5" qty="1.0" xprice="72.00" />
</apply>
</benefit>
</promo>
</optional>
</message>

Elementos no aplicados


En los beneficios externos (ExternalBenefit) pueden existir ítems que no son aplicados porque no están presentes en el contexto. Para representar esto el Motor de Promociones al informar beneficios utiliza la etiqueta <notApply>, donde se enumerarán los artículos sobre los cuales no pudo aplicarse el beneficio. Debido a que los beneficios solo pueden ser aplicados sobre artículos, los elementos contenidos en <notApply> serán siempre <item>.
A diferencia de los elementos que se informan en los participantes (ya sean de condición, como de combo), los elementos <item> que se encontrarán dentro de <notApply> poseerán los siguientes atributos:

Propiedad

Tipo de dato

Descripción

seq

Entero positivo

Número que identifica al elemento dentro de la transacción al que se aplica el beneficio.

value

Número En caso que se asigne a un ítem un nuevo precio que sea mayor al precio de venta informado, este valor puede tomar un valor negativo. Por este motivo deberán implementarse rutinas para el manejo de este tipo de valores.

Monto total que no se pudo descontar al elemento indicado por el atributo seq.

qty

Entero positivo

Cantidad de ítems que no fueron afectados.

magnitude

Real positivo

Magnitud que no fue afectada

xprice

Real positivo

Ira siempre en cero.


Ejemplo
<message engine="2.6" companyId="sts" store="0236" terminal="004" mapversion="114" ack="0" messageId="3777">
<optional>
<promo id="Desc5" nro="3">
<conditionParticipants>
<benefit benefitType="desc" amount="100.00" seqItem="2=2,3=2,5" type="MktExc" seq="1" id="1234"/>
</conditionParticipants>
<benefit benefitType="ExternalBenefit" discountAmount="60.00" type="MktExc" TLOGMessage="" account="" applicationMethod="" displayMessage="" order="1" prorationMethod="PROPORTIONAL" nro="3" baseAmount="3000.00" printerMessage="">
<apply>
<item value="20.00" magnitude="0.000" xprice="1000.00" seq="2" qty="1.000"/>
<item value="40.00" magnitude="0.000" xprice="2000.00" seq="3" qty="2.000"/>
</apply>
<notApply>
<item value="20.000" magnitude="0.000" xprice="0.000" seq="2" qty="1.000"/>
<item value="20.000" magnitude="0.000" xprice="0.000" seq="5" qty="1.000"/>
</notApply>
</benefit>
</promo>
</optional>
</message>

Sugerencias


Las sugerencias agregan al mensaje de respuesta aquellas promociones que no han sido otorgadas, ya sea porque la condición de la misma no puede ser verdadera o el combo no se pudo formar, o el beneficio no se pudo aplicar. Esta información puede ser utilizada por el vendedor para ofrecer las condiciones necesarias para que la promoción se aplique antes de proceder a cerrar la venta. Las sugerencias se representan con la etiqueta <suggestions> que aparecerá posterior a la última etiqueta <optional>. De no existir sugerencias, la etiqueta <suggestions> no aparecerá en el mensaje de respuesta. Esta etiqueta no posee atributos.

Ejemplo
<message companyId="sts" store="MX" mapversion="3241" messageId="160" terminal="100" engine="2.6" ack="0">
<optional>

… promociones que componen la opción …

</optional>
<optional>

… promociones que componen la opción …

</optional>
<suggestions>

… promociones que pueden ser sugeridas …


</suggestions>
</message>



Promociones sugeridas


Como se mencionó anteriormente, cada una de las sugerencias contendrá una o más promociones. Estas estarán identificadas por su nombre. Las promociones estarán representadas con la etiqueta <promo>, teniendo el atributo id representando su nombre.

Propiedad

Tipo de dato

Descripción

id

Alfanumérico

Nombre de la promoción.

descriptor

Alfanumérico

Descripción de sugerencia de la promoción. Puede no estar en la etiqueta si no fue especificado para la promoción que se sugiere.

item-seq

Lista de números

Las secuencias de tipo ítem que hacen posible que la promoción sea sugerida. Si no hubiera secuencias de este tipo para la promoción, entonces este atributo no se incluye en la etiqueta.

payment-seq

Lista de números

Las secuencias de tipo medio de pago que hacen posible que la promoción sea sugerida. Si no hubiera secuencias de este tipo para la promoción, entonces este atributo no se incluye en la etiqueta.

customer-seq

Lista de números

Las secuencias de tipo cliente que hacen posible que la promoción sea sugerida. Si no hubiera secuencias de este tipo para la promoción, entonces este atributo no se incluye en la etiqueta.

event-seq

Lista de números

Las secuencias de tipo evento que hacen posible que la promoción sea sugerida. Si no hubiera secuencias de este tipo para la promoción, entonces este atributo no se incluye en la etiqueta.

coupon-seq

Lista de números

Las secuencias de tipo cupón que hacen posible que la promoción sea sugerida. Si no hubiera secuencias de este tipo para la promoción, entonces este atributo no se incluye en la etiqueta.

loyaltycard-seq

Lista de Tarjetas de Fidelidad

Las secuencias de tipo tarjetas de fidelidad que hacen posible que la promoción sea sugerida. Si no hubiera secuencias de este tipo para la promoción, entonces este atributo no se incluye en la etiqueta.


Ejemplo
<message companyId="sts" store="MX" mapversion="3241" messageId="160" terminal="100" engine="2.6" ack="0">
<suggestions>
<promo id="Promoción navideña" descriptor="llevando un árbol de navidad te regalamos las guirnaldas" item-seq="1,2,3"/>
<promo id="Promoción 2x1 en juguetes" item-seq="1,2" coupon-seq="2" payment-seq="1"/>
</suggestions>
</message>
<message companyId="sts" store="MX" mapversion="3241" messageId="160" terminal="100" engine="2.6" ack="0">
<optional>

… promociones que componen la opción …


</optional>
<suggestions>
<promo id="Promoción navideña" descriptor="llevando un árbol de navidad te regalamos las guirnaldas" item-seq="1,2,3"/>
<promo id="Promoción 2x1 en juguetes" item-seq="1,2" coupon-seq="2" payment-seq="1"/>
</suggestions>
</message>
<message companyId="sts" store="MX" mapversion="3241" messageId="160" terminal="100" engine="2.6" ack="0">
<suggestions>
<promo id="Promoción navideña" descriptor="llevando un árbol de navidad te regalamos las guirnaldas" />
<promo id="Promoción 2x1 en juguetes"/>
</suggestions>
</message>

Servicio Prorrateo entre participantes

Cuando un beneficio, tenga tildada la opción de "Prorratear entre Participantes", el monto del descuento a otorgar será distribuido proporcionalmente entre los ítems participantes de la promoción.

Ejemplo de mensajería donde se visualiza la distribucion del descuento entre los participantes.

Prorrateo entre participantes - INPUT
<?xml version="1.0" encoding="UTF-8"?>
<message companyId="napse" store="1" terminal="1" date-time="2021-03-01 10:35:22" init-tck="true" messageId="1" void-trx="false" response="true" limitBalances="true" status="sales" evaluate="true" map-version="7" tckpath="Y" suggest="true">
<item-add seq="1" qty="1" code="123" level1="1121" magnitude="0" brand="Kumho" xprice="150" unitprice="150" />
<item-add seq="2" qty="1" code="456" level1="1121" magnitude="0" brand="Kumho" xprice="90" unitprice="90" />
<item-add seq="4" qty="1" code="789" level1="1121" magnitude="0" brand="Kumho" xprice="75" unitprice="75" />
</message>
Prorrateo entre participantes - OUTPUT
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<message ack="0" companyId="napse" engine="7.0.0-SNAPSHOT#78" mapversion="7" messageId="1" store="1" terminal="1">
  <optional>
    <promo id="Prorratear entre Participantes" nro="603afe841082e836908173d1">
      <benefit TLOGMessage="Prorratear entre Participantes" account="" applicationMethod="resume" baseAmount="75.0000" benefitType="PercentageDiscount" discountPercentage="100.0000" displayMessage="Prorratear entre Participantes" name="603afe841082e836908173d1" nro="603afed81082e836908173e1" order="1" printerMessage="Prorratear entre Participantes" prorateBCP="true" prorationMethod="PROPORTIONAL" unit="qty">
        <apply>
          <item magnitude="0.000" qty="1.000" seq="1" value="35.71" valueWithTaxes="150.00" xprice="150.00"/>
          <item magnitude="0.000" qty="1.000" seq="2" value="21.43" valueWithTaxes="90.00" xprice="90.00"/>
          <item magnitude="0.000" qty="1.000" seq="4" value="17.86" valueWithTaxes="75.00" xprice="75.00"/>
        </apply>
      </benefit>
    </promo>
  </optional>
</message>



Promociones Disponibles

PROMO expone un servicio que permite consultar promociones disponibles utilizando un filtro por compañía y versión de mapa (obligatorios) y el código de Promoción como parámetro de filtro opcional.

Para utilizar este servicio se debe realizar una solicitud del tipo GET con los parámetros correspondientes a la siguiente URL:

promotionAvailable
http://servidor:puerto/promo/api/rest/promotionAvailable 


La siguiente figura muestra el contenido del request de ejemplo:

Los parámetros de entrada son:

PropiedadTipo de DatoDescripción
mapVersion*AlfanuméricoVersión de Mapa que contiene la promoción. Requerido
companyId*AlfanuméricoIdentificador único de la empresa. Requerido
promotionCodeAlfanuméricocódigo de la promoción que forma parte del mapa. Optativo


Los parámetros de salida son:

PropiedadTipo de DatoDescripción
mapVersionAlfanuméricoVersión del mapa requerido
codeAlfanuméricocódigo de la promoción que está contenida en el mapa
nameStringnombre de la promoción
conditionSimpleStringcondición simple de la promoción
conditionComboStringcondición combo de la promoción
conditionDateAlfanuméricocondición de fechas de la promoción
benefitTypeDescriptionStringDescripción del tipo de beneficio de la promoción
benefitClassDescriptionStringDescripción de la clase de beneficio de la promoción
benefitStringDescripción del beneficio de la promoción

la respuesta es el Json:

promotionAvailable
[
    {
        "mapVersion": "1",
        "code": "",
        "name": "promo 1",
        "conditionSimple": "Productos con Codigo (SKU) IGUAL a 1111",
        "conditionCombo": "",
        "conditionDate": "",
        "benefitTypeDescription": "<p>1.- Monetario</p><br/>",
        "benefitClassDescription": "<p>1.- Descuento porcentaje</p><br/>",
        "benefit": "<p>1.- Productos con Codigo (SKU) IGUAL a 1111.Descuento porcentaje. El siguiente porcentaje (%)
50. Por cada unidad de Cantidad. Aplicar sobre Precio original -</p> "
    }
]


Fidelidad

Nuevos Status en <Loyalty>

Históricamente, el valor de la propiedad Status, era de libre uso y no tenía restricciones. A partir de PROMO 5 existen valores específicos y reservados para la propiedad "status" que indicarán al motor determinadas acciones a realizar con la Consola de PROMO Central.
Estas acciones son:

LoyaltyValidation

Consulta estado de cupones, clientes y tarjetas a PROMO central.

Request
<message companyId="2" store="1" terminal="1" date-time="2023-04-24 13:00:00" init-tck="true" messageId="1" void-trx="false" response="true" status="loyaltyvalidation" evaluate="true" suggest="false">
<customer-add seq="1" id="2"/>
</message>

Existen dos funciones opcionales (a habilitar) respecto a validación de clientes: (desde 6.5.2)

  1. Creación de clientes:  Si se envía información de cliente completa (es decir email o identifier) y el cliente no existe en Promo, el mismo será dado de alta automáticamente.
  2. Actualización de clientes: Si se recibe información de un cliente completa y el cliente existe, entonces se considera que la validación no es una mera consulta de datos sino que al enviar datos como el "nombre del cliente" se requiere hacer una actualización de los mismos.


(Ver también,Engine Response - LoyaltyValidation)
Esta acción no requiere tercer mensaje (commit o rollback), y cancela el elemento fidelidad que se informe.

LoyaltyActivation

Realiza la activación de una tarjeta de fidelidad.
Para activar una tarjeta que se encuentre en estado inactiva podrá enviarse un mensaje con Status="loyaltyActivation".
Deberá enviarse con el formato y atributos que se muestran en los siguientes ejemplos.

Request
<message companyId="2" store="1" terminal="1" date-time="2023-04-19 17:30:00" init-tck="true" messageId="1" void-trx="false" response="true" status="loyaltyactivation" evaluate="true" suggest="false">
<loyaltycard-add seq="1" id="1000000008"/>
</message>  


También pude realizarse la inactivación de una tarjeta activa con el LoyaltyActivation, agregando en el tag <loyaltycard-add/> el status="DISABLED".

Request
<message companyId="2" store="1" terminal="1" date-time="2023-04-19 17:30:00" init-tck="true" messageId="1" void-trx="false" response="true" status="loyaltyactivation" evaluate="true" suggest="false">
<loyaltycard-add seq="1" id="1000000007" status="DISABLED"/>
</message>   

(Ver también Engine Response – LoyaltyActivation)
Esta acción no requiere tercer mensaje (commit o rollback), y cancela el elemento fidelidad que se informe.


Crear Tarjetas de Fidelidad

Desde la versión 6.4 de Promo, se ha incorporado al status "loyaltyActivation" un valor para la propiedad status del elemento loyaltcard, un valor CREATE para indicar que se desea crear la tarjeta.

Procedemos a la creación sin carga de la primer tarjeta:

Request
<message companyId="2" store="1" terminal="10" date-time="2023-04-23 18:00:00" init-tck="true" messageId="1" void-trx="false" response="true" status="loyaltyActivation" evaluate="false" offline="false">
<loyaltycard-add seq="1" id="1000000011" type="1" status="CREATE" />
</message> 

La respuesta es: (Ack =0 es correcto)

Request
<?xml version="1.0" encoding="UTF-8"?><message ack="0" companyId="2" engine="6.5.33" mapversion="5" messageId="1" store="1" terminal="10" transaction="2_1_10_20230423180000">
  <loyalty>
    <loyaltycards>
      <loyaltycard ack="0" amount="0.00" id="1000000011" seq="1" type="1"/>
    </loyaltycards>
    <coupons/>
    <errors/>
    <customers/>
    <redeemTable/>
  </loyalty>
</message>
 

Adicionalmente si se desea dar una carga inicial se puede agregar la propiedad "chargeAmount" del elemento loyaltyCard.   De esta forma además de crearla, se cargara inicialmente ese saldo.

Luego procedemos a crear una segunda con saldo:

Request
<message companyId="2" store="1" terminal="10" date-time="2023-04-23 18:00:00" init-tck="true" messageId="1" void-trx="false" response="true" status="loyaltyActivation" evaluate="false" offline="false">
<loyaltycard-add seq="1" id="1000000012" type="1" status="CREATE" chargeAmount="105.00" />
</message> 


Respuesta

Request
<?xml version="1.0" encoding="UTF-8"?><message ack="0" companyId="2" engine="6.5.33" mapversion="5" messageId="1" store="1" terminal="10" transaction="2_1_10_20230423180000">
  <loyalty>
    <loyaltycards>
      <loyaltycard ack="0" amount="105.00" id="1000000012" seq="1" type="1"/>
    </loyaltycards>
    <coupons/>
    <errors/>
    <customers/>
    <redeemTable/>
  </loyalty>
</message>
    


LoyaltyTransfer

Realiza la transferencia de saldo de una tarjeta de fidelidad a otra del mismo tipo.
Para poder realizar una transferencia de saldos, tanto la tarjeta de origen (la que da saldo) como la de destino (la que recibe saldo) deben ser del mismo tipo.
En la seq=1 enviada por el POS se informara la tarjeta origen, es decir, a quien se le descontaran los puntos, dinero, millas, etc.
En la seq=2 enviada por el POS se informara la tarjeta destino, es decir, la que recibirá los puntos, dinero, millas, etc.
(Ver también Manual de Usuario, "Conceptos de Tarjetas de Fidelidad" para más detalle sobe los distintos tipos de transferencia posible,)

Request
<message companyId="sts"
 store="1" terminal="1" date-time="2017-12-29 16:49:16" init-tck="true" 
messageId="1" void-trx="false" response="true" status="loyaltyTransfer" msg-version="9" map-version="1">
 <loyaltycard-add seq="1" type="2" id="2220000000000"/>
 <loyaltycard-add seq="2" type="2" id="2220000000001" chargeAmount="4" />
 </message>  

(Ver también Engine Response - LoyaltyTransfer)
Se requiere COMMIT o ROLLBACK para confirmar o reversar la transacción.

LoyaltyVoid

Este status se utilizara para anular elementos de fidelidad que iban a ser emitidos u otorgados, pero donde la transacción en curso que los emitía no prospero.
Los cupones dados de baja por medio de este mensaje quedaran en estado "Rechazados" (rejected).

Request
<message companyId="2" store="1" terminal="10" date-time="2023-04-23 18:00:00" init-tck="true" messageId="1" void-trx="false" response="true" status="loyaltyVoid" evaluate="false" offline="false">
<loyaltycard-add seq="1" id="1000000006" type="1"/>
</message>    

(Ver también Engine Response – Loyalty Void)
Esta acción no requiere tercer mensaje (commit o rollback), y cancela el elemento fidelidad que se informe.

LoyaltyAssign

El Status "LoyaltyAssign" permitira al POS, o cualquier canal, informar a qué cliente se asocia una tarjeta. Se validara que la tarjeta no tenga previamente asociado a un cliente, que el tipo de tarjeta exista,  y que requiera asociación vía "Canal de Ventas".


Request
<message companyId="2" store="1" terminal="10" date-time="2023-04-23 18:00:00" init-tck="true" messageId="1" void-trx="false" response="true" status="loyaltyAssign" evaluate="false" offline="false">
<loyaltycard-add seq="2" id="5010000010" type="1"/>
<customer-add seq="1" id="3"/>
</message> 

(Ver también Engine Response – Loyalty Void)
Se requiere COMMIT o ROLLBACK para confirmar o reversar la transacción.

FINISH

Indica el procesamiento del ticket en PROMO Central.

Request
<message companyId="sts" store="00001" terminal="010" date-time="2017-01-04 12:30:00" messageId="0010" void-trx="false" response="true" init-tck="true" evaluate="true" status="finish" msg-version="2.0" map-version="15" suggest="true" suggest-seq="3">
.. cuerpo del mensaje ...
</message>


Otra opción con la que se cuenta para la activación de una tarjeta de fidelidad es mediante el envío del atributo "status" en el tag <LoyaltyCard-ADD> cuando se envía un "Finish", en donde deberá indicarse el estado ENABLED a fin de que la tarjeta incluida en la transacción sea activada

Request
<message companyId="sts" store="1" terminal="1" date-time="2017-05-30 12:06:10" init-tck="true" messageId="1" void-trx="false" response="true" status="finish" evaluate="true" map-version="1" suggest="true"> 
 <loyaltycard-add seq="2" id="3330000000002" type="3" status="ENABLED" />
 </message> 

(Ver también Engine Response – Activación en Finish)


COMMIT

Confirma la transacción en curso.

Request
<message companyId="sts" store="1" terminal="1" date-time="2017-05-30 12:06:10" init-tck="true" messageId="1" void-trx="false" response="true" status="commit" msg-version="2.0" map-version="15" suggest="true" suggest-seq="3">
... cuerpo del mensaje ...
</message>


ROLLBACK

Reversa la transacción en curso.

Request
<message companyId="sts" store="1" terminal="1" date-time="2017-05-30 12:06:10" init-tck="true" messageId="1" void-trx="false" response="true" status="rollback" msg-version="2.0" map-version="15" suggest="true" suggest-seq="3">... cuerpo del mensaje ...
</message>
 



TransactionRequest

Consulta información de una transacción de PROMO determinada. (La transacción a consultar debe ser Informada en el atributo "OriginalTransaction")

Request
<message companyId="sts" store="1" terminal="1" date-time="2017-05-30 12:06:10" init-tck="true" messageId="1" void-trx="false" response="true" status="transactionrequest" originalTransaction ="001_025_20161212134555" map-version="15" suggest="true" suggest-seq="3"> 
 </message>


ReturnFinish

Registra todos los elementos de una transacción de devolución en PROMO y marca para el proceso background los elementos de fidelidad participantes de la devolución para ser procesados y reversados en caso de que aplique. Deberá informarse junto con el ReturnFinish el cambo OriginalTransaction para que la operación sea tomada correctamente.
Se requiere COMMIT o ROLLBACK para confirmar o reversar la transacción.

Se aplica en transacciones donde intervengan los siguientes elementos de fidelidad:

  • Cupones emitidos (sean cupones o cupones calculados)
  • Puntos otorgados (los descuenta, para devolver los puntos el POS tiene que mandar un Charge amount)

En cambio no aplica cuando en la transacción intervienen:

  • Cupón calculado aplicado ( ya redimido), se debe generar otro nuevo que reemplace el anterior
  • Redención de puntos (no devuelve los puntos canjeados).

En el ejemplo se han registrado cada uno de los ítem que se desean devolver, junto al cupón que recibió en la compra

Request
<message companyId="sts" store="00001" terminal="010" date-time="2017-06-04 12:30:00" messageId="0010" void-trx="false" response="true" init-tck="true" evaluate="true" " status="returnFinish" originalTransaction="001_025_20161212134555" map-version="15" suggest="true" suggest-seq="3">
 <item-add seq="2" qty="1" code="1" magnitude="0" xprice="100" unitprice="100"/>
 <payment-add seq="1" type="CreditCard" amount="100" id="000009" planId="10"/>
 <loyaltycard-add seq="5" id="3330000000133" />
 <coupon-add seq="1" qty="1" id="xxxxxxxxxx" type="yyy" />
 <customer-add seq="1" id="1"/>
 </message>
Response
<?xml version="1.0" encoding="UTF-8"?><message ack="0" companyId="sts" engine="6.5.32#730" mapversion="23" messageId="1" store="3" terminal="1" transaction="001_025_20161212140055">
   <loyalty>
    <loyaltycards/>
    <coupons/>
    <errors/>
    <customers/>
    <redeemTable/>
    <goalsPrograms/>
    <redeemTable/>   
   </loyalty>
</message>

Nota

El atributo void-trx es solo informativo para dejar registro, pero no realiza ningún cambio en la operatoria

CatalogRedeemValidation (desde v6.5.2)

Basado en los items que se informen en el request y teniendo en cuanta la tienda desde la cual se realiza la transacción, informará los productos existentes en la tabla de Canje de Puntos por Catálogo (explicado en este documento mas adelante).

Es importante comprender que para que se aplique una redención de Puntos por Catálogo se deberá enviar previamente este mensaje.

En el siguiente ejemplo se envia un mensaje de este tipo informando 5 codigos de Producto  diferentes:

Request
<message companyId="napse" store="b320" terminal="1" date-time="2020-04-12 19:09" messageId="5" void-trx="false" suggest="true" response="true" init-tck="true" evaluate="true" msg-version="2.4" status="catalogRedeemValidation">
<item-add seq="1" code="1000" qty="1" unitprice="1000" xprice="1000" applyCatalogRedeem="true" />
<item-add seq="2" code="3000" qty="1" unitprice="1000" xprice="1000" applyCatalogRedeem="true" />
<item-add seq="3" code="2000" qty="1" unitprice="1000" xprice="1000" applyCatalogRedeem="true" />
<item-add seq="4" code="1002" qty="2" unitprice="1000" xprice="2000" applyCatalogRedeem="true" />
<item-add seq="5" code="9004" qty="2" unitprice="1000" xprice="2000" applyCatalogRedeem="true" />
</message>

Como respuesta al anterior se recibirá la tabla correspondiente, por ejemplo:

Request
<message ack="0" companyId="napse" engine="6.5.1" mapversion="5555" messageId="5" store="b320" terminal="1" transaction="napse_b320_1_20200411190900">
<loyalty>
<loyaltycards/>
<coupons/>
<errors/>
<customers/>
<redeemTable>
<redeemItem code="1000" discountType="perc" discountValue="10.00" points="100.00"/>
<redeemItem code="1002" discountType="nprice" discountValue="487.89" points="70.00"/>
<redeemItem code="2000" discountType="fix" discountValue="27.00" points="60.00"/>
<redeemItem code="3000" discountType="perc" discountValue="5.00" points="30.00"/>
</redeemTable>
</loyalty>

Ver definiciones de los elementos en las tablas correspondientes en este documento.


Fidelidad: Engine Response


Cada uno de los elementos de fidelidad informados en la respuesta a un "finish" contendrá los datos de los beneficios obtenidos por la aplicación de un beneficio.
Dentro del tag <loyalty> podrán informarse uno o varios de los siguientes elementos:

  • <coupons/>
  • <loyaltycards/>
  • <errors/>
  • <customers/>


Request
<?xml version="1.0" encoding="UTF-8"?><message ack="0" companyId="2" engine="6.5.33" mapversion="5" messageId="1" store="1" terminal="1" transaction="2_1_1_20230419160000">
 <coupons/>
 <loyaltycards/>
 <errors/>
 <customers/>
 <redeemTable/>  
 </loyalty>
 </message>


Las propiedades para el encabezado de la respuesta de fidelidad serán los mismos que los informados en la respuesta de cualquier otro elemento PROMO (Ver capítulo 3.1 Encabezado),

Response - LoyaltyValidation

Como respuesta a una consulta de uno o varios elementos de fidelidad

Response OK
<?xml version="1.0" encoding="UTF-8"?><message ack="0" companyId="2" engine="6.5.33" mapversion="5" messageId="1" store="1" terminal="1" transaction="2_1_1_20230424130000">
  <loyalty>
    <loyaltycards/>
    <coupons/>
    <errors/>
    <customers>
      <customer code="2" email="[email protected]" identifier="222233" lastName="Gonzalez" limitedBenefits="" name="Sofia" segment="" seq="1" type="FRECUENTE">
        <loyaltycard ack="0" amount="1000.00" id="1010000008" status="Activa" type="2"/>
      </customer>
    </customers>
    <redeemTable/>
  </loyalty>
</message>


Output – No OK (Ver capítulo 3.1.1 Valores del atributo "ack")

Response
<?xml version="1.0" encoding="UTF-8"?><message ack="0" companyId="2" engine="6.5.33" mapversion="5" messageId="1" store="1" terminal="1" transaction="2_1_1_20230424130000">
  <loyalty>
    <loyaltycards/>
    <coupons/>
    <errors>
      <error ack="9500" amount="0.00" cardType="10008" info="10008" seq="1" type="loyaltycard-redeem"/>
    </errors>
    <customers/>
    <redeemTable/>
  </loyalty>
</message>


Nota: Cuando la tarjeta que se consulte este inactiva, se informara en el atributo "amount" el saldo de la tarjeta al momento de la consulta y en "cardType" el tipo de tarjeta.
(ver también Engine Request – loyaltyValidation)

Response - Cupones

Se agregan al mensaje de respuesta aquellos cupones que han sido otorgados como resultado de los beneficios de una promoción. Vale aclarar que se trata del detalle de los cupones otorgados, es decir, si como resultado de evaluar una promoción han sido otorgados X cantidad de cupones de algún tipo, entonces la respuesta de fidelidad contendrá el detalle de esos X cupones otorgados.

Request
<?xml version="1.0" encoding="UTF-8"?><message ack="0" companyId="2" engine="6.5.33" mapversion="5" messageId="1" store="1" terminal="1" transaction="2_1_1_20230419160000">
  <loyalty>
    <loyaltycards>
      <loyaltycard ack="0" amount="1000.00" amountChargeLimit="0.00" contract="" customer="" id="1010000009" seq="2" type="2" usePartial="true"/>
    </loyaltycards>
    <coupons>
      <coupon ack="0" amount="0.00" barcode="1030BC0030533" couponId="3" seq="1"/>
    </coupons>
    <errors/>
    <customers>
      <customer code="2" email="[email protected]" identifier="222233" lastName="Gonzalez" limitedBenefits="" name="Sofia" segment="" seq="1" type="FRECUENTE">
        <loyaltycard ack="0" amount="1000.00" id="1010000008" status="Activa" type="2"/>
      </customer>
    </customers>
    <redeemTable/>
  </loyalty>
</message>


Como hemos mencionado por cada uno de los cupones generados tendremos un elemento cupón, como se muestra en el siguiente ejemplo para 3 cupones:

Response
<?xml version="1.0" encoding="UTF-8"?><message ack="0" companyId="2" engine="6.5.33" mapversion="5" messageId="1" store="1" terminal="1" transaction="2_1_1_20230419160000">
  <loyalty>
    <loyaltycards/>
    <coupons>
      <coupon ack="0" amount="0.00" barcode="1030BC0030540" couponId="3" seq="1"/>
      <coupon ack="0" amount="0.00" barcode="1030BC0030557" couponId="3" seq="2"/>
      <coupon ack="0" amount="0.00" barcode="1030BC0030564" couponId="3" seq="3"/>
    </coupons>
    <errors/>
    <customers>
      <customer code="2" email="[email protected]" identifier="222233" lastName="Gonzalez" limitedBenefits="" name="Sofia" segment="" seq="1" type="FRECUENTE">
        <loyaltycard ack="0" amount="1000.00" id="1010000008" status="Activa" type="2"/>
      </customer>
    </customers>
    <redeemTable/>
  </loyalty>
</message>
 


Las propiedades de cada elemento cupón será:


Propiedad

Tipo de dato

Descripción

barcode

Alfanumérico

Código de barras del cupón, o lo que es lo mismo, el identificador unívoco del mismo.

ack

entero

Código de retorno

couponId

Alfanumérico

Identificador del tipo de cupón.

format

Alfanumérico

Formato del cupón. Los valores posibles son: PRINTED (impreso), ELECTRONIC (Electrónico), THIRD_PARTY (de terceros), EXTERNAL (Externo), PRE_PRINTED (Pre impreso).

encoding

Alfanumérico

Formato en que deberá imprimirse el barcode (EAN13 - UPCA – CODE128)

promotionName

Alfanumérico

Es el nombre que se le dio a la promoción que aplica el beneficio

promotionNro

Alfanumérico

Identifica a la promoción que aplica el beneficio.

benefitNro

Alfanumérico

Identifica al beneficio que aplica la promoción

amount

Entero positivo

Indicara el monto asociado a un cupon cuyo monto fue calculado


Response - Tarjetas Fidelidad


En la respuesta del motor se agregan al mensaje los datos de la o las tarjetas que han sido beneficiadas como resultado de la aplicación de beneficios.
Vale aclarar que se trata del detalle de los puntos, dinero, millas, etc. otorgados, es decir, si como resultado de evaluar una promoción han sido otorgado o redimidos X cantidad de puntos, dinero, millas, etc., entonces la respuesta de fidelidad contendrá el detalle para esa tarjeta.

Request
<?xml version="1.0" encoding="UTF-8"?><message ack="0" companyId="2" engine="6.5.33" mapversion="5" messageId="1" store="1" terminal="1" transaction="2_1_1_20230419160000">
  <loyalty>
    <loyaltycards/>
    <coupons/>
    <errors/>
    <customers>
      <customer code="2" email="[email protected]" identifier="222233" lastName="Gonzalez" limitedBenefits="" name="Sofia" segment="" seq="1" type="FRECUENTE">
        <loyaltycard ack="0" amount="1000.00" id="1010000008" status="Activa" type="2"/>
      </customer>
    </customers>
    <redeemTable/>
  </loyalty>
</message>


Como hemos mencionado por cada una de las tarjetas tendremos un elemento, como en el siguiente ejemplo:

Response
<?xml version="1.0" encoding="UTF-8"?><message ack="0" companyId="2" engine="6.5.33" mapversion="5" messageId="1" store="1" terminal="1" transaction="2_1_1_20230419160000">
  <loyalty>
    <loyaltycards>
      <loyaltycard ack="0" amount="105.00" amountChargeLimit="0.00" contract="" customer="" id="1000000012" seq="2" type="1" usePartial="true"/>
      <loyaltycard ack="0" amount="1000.00" amountChargeLimit="0.00" contract="1" customer="2" id="1010000008" seq="3" type="2" usePartial="true"/>
      <loyaltycard ack="0" amount="1000.00" amountChargeLimit="0.00" contract="" customer="1" id="3010000000" seq="4" type="4" usePartial="true"/>
    </loyaltycards>
    <coupons/>
    <errors/>
    <customers/>
    <redeemTable/>
  </loyalty>
</message>


Las propiedades de cada elemento tarjeta será:

Propiedad

Tipo de dato

Descripción

Id

Alfanumérico

Número identificador de Tarjeta fidelidad

Type

Alfanumérico

Identificador del tipo de tarjeta.

ack

entero

Código de retorno

amount

Número positivo

Saldo con el que quedaría la tarjeta

cardType

Alfanumérico

Informa el tipo de la tarjeta (se informara solo en el tag <errors/> cuando el ACK sea 9501 – tarjeta inactiva)


Response - Activación de tarjeta (en LoyaltyActivation)


Response OK (ACK="0" se informan los datos en el tag de loyaltycards)

Response
<?xml version="1.0" encoding="UTF-8"?><message ack="0" companyId="2" engine="6.5.33" mapversion="5" messageId="1" store="1" terminal="1" transaction="2_1_1_20230419173000">
  <loyalty>
    <loyaltycards>
      <loyaltycard ack="0" id="1000000008" seq="1" type="1"/>
    </loyaltycards>
    <coupons/>
    <errors/>
    <customers/>
    <redeemTable/>
  </loyalty>
</message>


Response – No OK (Ver capítulo 3.1.1 Valores del atributo "ack")

Response
<?xml version="1.0" encoding="UTF-8"?><message ack="0" companyId="2" engine="6.5.33" mapversion="5" messageId="1" store="1" terminal="1" transaction="2_1_1_20230419173008"> 
<loyalty> 
<loyaltycards/>
 <coupons/>
 <errors>
 <error ack="9500" info="4010000007" seq="1" type="loyaltycard-activation"/>
 </errors>
 <customers/>
 <redeemTable/>  
 </loyalty>
 </message> 

(Ver también Engine Request - LoyaltyActivation)

Response - Activación de tarjeta (en Finish)


Response OK (ACK="0" y se informan los datos de la tarjeta que se esta activando")

Response
<?xml version="1.0" encoding="UTF-8"?><message ack="0" companyId="2" engine="6.5.33" mapversion="5" messageId="1" store="1" terminal="1" transaction="2_1_1_20230419173000">
  <loyalty>
    <loyaltycards>
      <loyaltycard ack="0" id="1000000007" seq="1" type="1"/>
    </loyaltycards>
    <coupons/>
    <errors/>
    <customers/>
    <redeemTable/>
  </loyalty>
</message>
 


Output – No OK (Ver capítulo3.1.1 Valores del atributo "ack")

Response
<?xml version="1.0" encoding="UTF-8"?><message ack="0" companyId="2" engine="6.5.33" mapversion="5" messageId="1" store="1" terminal="1" transaction="2_1_1_20230419173008"> 
<loyalty>
<loyaltycards/>
<coupons/>
<errors>
<error ack="9500" info="4010000005" seq="2" type="loyaltycard-consume"/>
</errors>
<customers/>
<redeemTable/>  
</loyalty>
</message>



(Ver también Engine Request – FINISH)

Response - LoyaltyTransfer


Response OK
En el mensaje de respuesta se informa en cada una de las seq el saldo final y el estado con el que quedaran las tarjetas luego de la transacción de transferencia.

Response
 <?xml version="1.0" encoding="UTF-8"?><message ack="0" companyId="2" engine="6.5.33" mapversion="5" messageId="1" store="1" terminal="1" transaction="2_1_1_20230420100000">
  <loyalty>
<loyaltycards>
<loyaltycard ack="0" amount="996.0" id="4010000009" seq="1" type="5"/>
<loyaltycard ack="0" amount="4.0" id="4010000008" seq="2" type="5"/>
</loyaltycards>
<coupons/>
<errors/>
<customers/>
<redeemTable/>
</loyalty>
</message>


Nota: Deberá de enviarse un mensaje con status "Commit" para que los saldos sean imputados.


Response– No OK (Ver capítulo 3.1.1 Valores del atributo "ack")

Response
<?xml version="1.0" encoding="UTF-8"?><message ack="0" companyId="2" engine="6.5.33" mapversion="5" messageId="1" store="1" terminal="1" transaction="2_1_1_20230420100000">
  <loyalty>
    <loyaltycards/>
    <coupons/>
    <errors>
      <error ack="9511" id="4010000011" info="4010000009" seq="1" type="loyaltycard-transfer"/>
    </errors>
    <customers/>
    <redeemTable/>
  </loyalty>
</message>

 

(Ver también Engine Request - LoyaltyTransfer)

Response - LoyaltyVoid

Response OK – Cupón y Tarjetas

Response
<?xml version="1.0" encoding="UTF-8"?><message ack="0" companyId="2" engine="6.5.33" mapversion="5" messageId="1" store="1" terminal="10" transaction="2_1_10_20230423180000">
  <loyalty>
    <loyaltycards>
      <loyaltycard ack="0" id="1000000006" seq="1" type="1"/>
    </loyaltycards>
    <coupons/>
    <errors/>
    <customers/>
    <redeemTable/>
  </loyalty>
</message>
  

(Ver también Engine Request – LoyaltyVoid)

Imputación de saldos en tarjeta



Request
<message companyId="2" store="1" terminal="10" date-time="2023-04-200 10:00:00" messageId="11" void-trx="false" response="true" init-tck="false" evaluate="false" status="finish">
<loyaltycard-add seq="2" type="5" id="4010000008" chargeAmount="10" />
</message> 



Response
<?xml version="1.0" encoding="UTF-8"?><message ack="0" companyId="2" engine="6.5.33" mapversion="5" messageId="11" store="1" terminal="10" transaction="2_1_10_20231017100000">
  <loyalty>
    <loyaltycards>
      <loyaltycard ack="0" amount="10.00" id="4010000008" seq="2" type="5"/>
    </loyaltycards>
    <coupons/>
    <errors/>
    <customers/>
    <redeemTable/>
  </loyalty>
</message>
 



Nota: Deberá de enviarse un mensaje con status "Commit" para que los saldos sean imputados.
Nota 2: En el atributo "amount" se informara el saldo con que quedara la tarjeta luego de realizado el commit.

Response– No OK (Ver capítulo 3.1.1 Valores del atributo "ack")

Response
<?xml version="1.0" encoding="UTF-8"?><message ack="0" companyId="2" engine="6.5.33" mapversion="5" messageId="11" store="1" terminal="10" transaction="2_1_10_20231017100000">
 <loyalty>
<loyaltycards/>
<coupons/>
<errors>
<error ack="9500" info="22200000001" seq="2" type="loyaltycard-recharge"/>
</errors>
<customers/>
<redeemTable/>
</loyalty>
</message>


Descuento de saldo en tarjeta


Request
<message companyId="sts" store="00001" terminal="010" date-time="2005-01-04 12:35:28" messageId="11" void-trx="false" response="true" init-tck="false" evaluate="false" status="finish" msg-version="2.0" map-version="1">
<loyaltycard-add seq="2" type="gold" id="2220000000002" consumeAmount="6" />
</message>


Response OK
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<message ack="0" engine="2.6" mapversion="1" messageId="1" companyId="sts" store="1" terminal="1" transaction="1_1_20170515152511"> <loyalty>
<loyaltycards>
<loyaltycard ack="0" amount="18.0" id="2220000000002" seq="2" type="gold"/>
</loyaltycards>
<coupons/>
<errors/>
<redeemTable/>
</loyalty>
</message>

Nota: Deberá de enviarse un mensaje con status "Commit" para que los saldos sean imputados.
Nota 2: En el atributo "amount" se informara el saldo con que quedara la tarjeta luego de realizado el commit.


Response – No OK (Ver capítulo 3.1.1 Valores del atributo "ack")

Response ERROR
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<message ack="0" engine="2.6" mapversion="1" messageId="1" companyId="sts" store="1" terminal="1" transaction="1_1_20170515152511"> <loyalty>
<loyaltycards/>
<coupons/>
<errors>
<error ack="9500" info="4445000002200" seq="2" type="loyaltycard-recharge"/>
</errors>
<redeemTable/>
</loyalty>
</message>


Tarjetas de Fidelidad: Proceso de actualización de saldos

Se ha incorporado al status "loyaltyActivation" un valor para la propiedad status del elemento loyaltcard, un valor CONFIRM para indicar que se desea confirmar los puntos utilizados en una transacción previa referenciada en el atributo: "confirmationReference".

Realizar un consumo con vencimiento el 14/11:

Ejemplo
<message companyId="test" store="1" terminal="10" date-time="2018-11-09 10:51:50" init-tck="true" messageId="1" void-trx="false" response="true" status="finish" evaluate="true" offline="false">
<loyaltycard-add seq="1" id="10012" type="t1" amount="1000" consumeAmount="10" confirmationDate="201811141400" />
<item-add seq="2" code="2" unitprice="20" xprice="10000" qty="500" discountable="true" taxes="2100"  />
<item-add seq="3" code="3" unitprice="10" xprice="10000" qty="1000" discountable="true" taxes="2100" />
</message>


Respuesta:

Ejemplo
<message ack="0" companyId="test" engine="6.1.4" mapversion="0" messageId="1" store="1" terminal="10" transaction="test_1_10_20181116163505">  
	<loyalty>    
		<loyaltycards>      
			<loyaltycard ack="0" amount="35.0" id="10012" seq="1" type="t1"/>    
		</loyaltycards>    
		<coupons/>    
		<errors/>    
		<customers/>
        <redeemTable/>
        </loyalty>
</message>


Confirmamos la transacción con Commit:

Ejemplo
<message companyId="test" store="1" terminal="10" date-time="2018-11-09 10:51:50" init-tck="false" messageId="1" void-trx="false" response="true" status="commit" evaluate="true" 
offline="false"></message>


Respuesta:

Ejemplo
<?xml version="1.0" encoding="UTF-8"?><message ack="0" companyId="test" engine="6.1.4" mapversion="0" messageId="1" store="1" terminal="10" transaction="test_1_10_20181116163505"/>


Ahora vamos a realizar otra pero confirmando el consumo:

Primero como hicimos anteriormente, generamos un consumo con vencimiento 18-11

Ejemplo
<message companyId="test" store="1" terminal="10" date-time="2018-11-09 10:51:50" init-tck="true" messageId="1" void-trx="false" response="true" status="finish" evaluate="true" offline="false"><loyaltycard-add seq="1" id="10012" type="t1" amount="1000" consumeAmount="10" confirmationDate="201811181400" />
<item-add seq="2" code="2" unitprice="20" xprice="10000" qty="500" discountable="true" taxes="2100"  />
<item-add seq="3" code="3" unitprice="10" xprice="10000" qty="1000" discountable="true" taxes="2100"  />
</message>

Respuesta

Ejemplo
<?xml version="1.0" encoding="UTF-8"?><message ack="0" companyId="test" engine="6.1.4" mapversion="0" messageId="1" store="1" terminal="10" transaction="test_1_10_20181116165337">  
<loyalty>
 <loyaltycards>
 <loyaltycard ack="0" amount="35.0" id="10012" seq="1" type="t1"/>    
 </loyaltycards>
 <coupons/>
 <errors/>    
<customers/>
<redeemTable/>
</loyalty>
</message>

Confirmamos la transacción:

Ejemplo
<message companyId="test" store="1" terminal="10" date-time="2018-11-09 10:51:50" init-tck="true" messageId="1" void-trx="false" response="true" status="commit" evaluate="true" offline="false"><loyaltycard-add seq="1" id="10012" type="t1" amount="1000" consumeAmount="10" confirmationDate="201811181400" />
<item-add seq="2" code="2" unitprice="20" xprice="10000" qty="500" discountable="true" taxes="2100"  />
<item-add seq="3" code="3" unitprice="10" xprice="10000" qty="1000" discountable="true" taxes="2100"  />
</message>

Respuesta

Ejemplo
<?xml version="1.0" encoding="UTF-8"?><message ack="0" companyId="test" engine="6.1.4" mapversion="0" messageId="1" store="1" terminal="10" transaction="test_1_10_20181116165337"/>


Ahora enviamos la confirmación

Ejemplo
<message companyId="test" store="1" terminal="10" date-time="2018-11-09 09:51:50" init-tck="true" messageId="1" void-trx="false" response="true" status="loyaltyActivation" evaluate="false" offline="false">
<loyaltycard-add seq="1" id="10012" type="t1" status="CONFIRM" confirmationReference="test_1_10_20181116165337" />
</message>

Respuesta

Ejemplo
<?xml version="1.0" encoding="UTF-8"?><message ack="0" companyId="test" engine="6.1.4" mapversion="0" messageId="1" store="1" terminal="10" transaction="test_1_10_20181116165603">  
<loyalty>    
<loyaltycards/>
 <coupons/>    
<errors/>
<customers/>
<redeemTable/>
</loyalty>
</message>

Mediante esta operación entonces el consumo ha sido confirmado y pasado el 18-11 no será reversado.


Engine Response: Tag Errors

Además de cupones y tarjetas, puede agregarse al elemento fidelidad de la respuesta, un bloque de reportes de errores. Dentro del mismo se informarán los errores en el procesamiento de determinados cupones y/o tarjetas, tanto en su emisión como en su redención.

Ejemplo
<message ack="0" engine="2.6" mapversion="1" messageId="1" companyId="sts" store="1" terminal="1" transaction="1_1_20170515152511"> <loyalty>
<loyaltycards/>
<errors>
<error ack="9505" id="4445901938700" info="4445901938700" amount= "" seq="1" type="loyaltycard-activation"/>
</errors>
<redeemTable/>
</loyalty>
</message>
Ejemplo
<message ack="0" engine="2.6" mapversion="1" messageId="1" companyId="sts" store="1" terminal="1" transaction="1_1_20170515152511"> <loyalty>
<coupons/>
<loyaltycards/>
<errors>
<error ack="9501" id="5550010012948" info="5550010012948" amount= "100" seq="1" type="loyaltycard-validation"/>
</errors>
<redeemTable/>
</loyalty>
</message>

Las propiedades de los elementos informados en el Tag <Errors/> son:

Propiedad

Tipo de dato

Descripción

type

Alfanumérico

Informa el tipo de transacción asociado. Valores actuales son: "coupon-create", "coupon-redeem", "loyalty-redeem", "loyalty-sale", "loyalty-activation"

ack

Alfanumérico

El valor del código de error como se ha descripto en los valores de la propiedad ack antes en este documento. Ver capítulo 3.1.1 Valores del atributo "ACK"

id

Alfanumérico

En el caso de Cupones y Tarjetas aquí se informa el id/barcode de los mismos

info

Alfanumérico

Información adicional que depende del valor del campo "type". Por ejemplo puede ser el valor del tipo de cupón a generarse, el valor del barcode informado para su redención, etc.
En el caso de las tarjetas fidelidad, el valor será el id de la tarjeta informada

description

Alfanumérico

Es un atributo extra para dar una mejor lectura al error ocurrido. En el caso de las tarjetas fidelidad, se puede identificar el nombre de la promociones + el número de beneficio donde ocurrió el error

amount

Numérico

Opcional – Solo se mostrara este atributo cuando se esté informando un error para la consulta de validación (loyaltyValidation)

seq

Entero positivo

Número que identifica al elemento dentro de la transacción al que se aplica el beneficio.


Fidelidad: Status Extendidos

(desde v6.5.25)

Con la finalidad de atender a necesidades especiales, como podría ser el caso de ecommerce, se han agregados versiones extendidas a algunos de los valores de status ya conocidos.

LOYALTYVALIDATIONEX

Este valor de estado unifica en un mismo mensaje lo ya conocido en loyaltyValidation mas una evaluación de Promociones. Si la validación retorna errores, no se evaluaran promociones y la respuesta será la respuesta tradicional del loyaltyValidation. Si no existen errores la respuesta incluirá los resultados de la validación mas la respuesta de la evaluación de promociones.


Caso: Se envía el siguiente mensaje para validar y evaluar

Request
<message companyId="test" store="test" terminal="001" date-time="2020-12-28 11:25" messageId="0011" void-trx="false" response="true" init-tck="true" evaluate="true" status="loyaltyvalidtionex">
<customer-add seq="1" id="12345" />
<coupon-add seq="1" id="1010BCup10000x" />
<item-add seq="1" qty="1" code="111" magnitude="0" xprice="5000" unitprice="5000" />
</message>


Respuesta 1: Todo ocurre correctamente

Request
<message ack="0" companyId="test" engine="2.6" mapversion="2" messageId="0014" store="test" terminal="001" transaction="test_test_001_20201228112802">
<loyalty>
<loyaltycards/>
<coupons/>
<errors/>
<customers/>
<redeemTable/>
</loyalty>
<optional>
<promo code="TEST" id="TEST" nro="5fe9e7d1abe76823b4bd151d">
<benefit TLOGMessage="TEST" account="" applicationMethod="resume" baseAmount="5000.00" benefitType="PercentageDiscount" discountPercentage="10.00" displayMessage="TEST"
name="5fe9e7d1abe76823b4bd151d" nro="5fe9e84fabe76823b4bd1529" order="1" printerMessage="TEST" prorationMethod="PROPORTIONAL" unit="qty">
<apply>
<item magnitude="0.000" qty="1.000" seq="1" value="500.00" valueWithTaxes="500.00" xprice="5000.00"/>
</apply>
</benefit>
</promo>
</optional>
</message>


Respuesta 2: Existen errores en la validación

Request
message ack="8296" companyId="test" engine="2.6" mapversion="2" messageId="0011" store="test" terminal="001" transaction="test_test_001_20201228112501">
<loyalty>
<loyaltycards/>
<coupons/>
<errors>
<error ack="9101" id="1010BCup10000x" info="1010BCup10000x" seq="1" type="coupon-redeem"/>
</errors>
<customers>
<customer code="123456" email="[email protected]" identifier="1" lastName="perez" limitedBenefits="" name="jorge" segment="" seq="1" type="
test"/>
</customers>
<redeemTable/>
</loyalty>
</message>



Inyeccion automaticamente Segmentos en Clientes (loyaltyValidationex)

(desde v6.5.25)

Se incluye la funcionalidad de agregar de forma automática, en la validación del cliente, los segmentos a los que este pertenece, utilizando la funcionalidad loyaltyValidationex.


IMPORTANTE

Lo segmentos podrán ser dados de alta desde consola (Negocio/Segmentos) o vía servicio REST. Para mas información sobre asociación de clientes a Segmentos Promo vía REST, ver "Servicio de importación de Segmentos" en Manual de Integración Promo - Servicios.


Cuando se reciba en Promo una consulta del tipo loyaltyValidationex y se informe un cliente, se incluirán en el mensaje de respuesta los segmentos a los que este cliente pertenece junto con el resultado de la evaluación de promociones con el mapa vigente.


Input
<message companyId="napse" store="013" terminal="001" date-time="2021-08-06 01:30:00" messageId="0011" map-version="494"  void-trx="false" response="true" init-tck="true" evaluate="true" status="loyaltyvalidationex">
<item-add seq="1" qty="1" code="112233" magnitude="0" xprice="5000" unitprice="5000" type="555"/>
<customer-add seq="1" id="c4"  />
</message>


Output
<?xml version="1.0" encoding="UTF-8"?><message ack="0" companyId="napse" engine="6.5" mapversion="494" messageId="0011" store="013" terminal="001" transaction="napse_013_001_20210806013000">
  <loyalty>
    <loyaltycards/>
    <coupons/>
    <errors/>
    <customers>
      <customer code="c4" email="-" identifier="-" lastName="-" limitedBenefits="" name="-" segment="5500,555" type="EMPLEADO" seq="1"/>
    </customers>
    <redeemTable/>
    <stores/>
  </loyalty>
  <optional>
    <promo code="40705" id="segmento clientes" nro="610cb87616f79a30b457e44c">
      <benefit TLOGMessage="segmento clientes" account="" applicationMethod="resume" baseAmount="5000" benefitType="PercentageDiscount" discountPercentage="50" displayMessage="segmento clientes" name="610cb87616f79a30b457e44c" nro="610cb89b16f79a30b457e456" order="1" printerMessage="segmento clientes" prorationMethod="PROPORTIONAL" unit="qty">
        <apply>
          <item magnitude="0.000" qty="1.000" seq="1" value="2500" valueWithTaxes="2500" xprice="5000"/>
        </apply>
      </benefit>
    </promo>
  </optional>
</message>



FINISHEX

Consiste en un mensaje que unifica o realiza lo conocido en Finish y dependiendo de la evaluación de este, un commit (respuesta de finish exitosa) o rollback (finish reporta un error) automático.

Caso: Se envía el siguiente mensaje para finalizar la transacción

Request
<message companyId="test" store="test" terminal="001" date-time="2020-12-28 11:25" messageId="0011" void-trx="false" response="true" init-tck="true" evaluate="true" status="finishex">
<customer-add seq="1" id="12345" />
<coupon-add seq="1" id="1010BCup10000x" />
<item-add seq="1" qty="1" code="111" magnitude="0" xprice="5000" unitprice="5000" />
</message>


Respuesta 1: Todo ocurre correctamente(Finish+commit exitosos)

Request
<message ack="0" companyId="test" engine="2.6" mapversion="2" messageId="0014" store="test" terminal="001" transaction="test_test_001_20201228112802">
<loyalty><loyaltycards/>
<coupons/>
<errors/>
<customers/>
<redeemTable/>
</loyalty>
</message>


Respuesta 2: Existen errores en la validación (Finish+rollback fueron ejecutados)

Request
<message ack="8296" companyId="test" engine="2.6" mapversion="2" messageId="0011" store="test" terminal="001" transaction="test_test_001_20201228112501">
<loyalty>
<loyaltycards/>
<coupons/>
<errors>
<error ack="9101" id="1010BCup10000x" info="1010BCup10000x" seq="1" type="coupon-redeem"/>
</errors>
<customers>
<customer code="123456" email="[email protected]" identifier="1" lastName="perez" limitedBenefits="" name="jorge" segment="" seq="1" type="
test"/>
</customers>
<redeemTable/>
</loyalty>
</message>



Flujos de Tarjetas

En este apartado se expondrán los flujos desarrollados para tarjetas fidelidad donde se podrán observar los distintos mensajes que se podrán intercambiar el POS, el motor y la consola de PROMO.

Alta de tarjeta

El alta de una tarjeta se realizara en la consola de PROMO Central

Nota: El campo CVV tiene como largo máximo 5 posiciones.

Consulta de tarjeta


Activación de tarjeta (loyaltyActivation)


Activación de tarjeta (FINISH)


Transferencia entre tarjetas



Imputación o descuento de saldo fuera de una transacción



Imputación o descuento de saldo devenidos de la aplicación de un beneficio.






Engine Response: ReturnFinish

La evaluación de la devolución se realiza utilizando el motor de simulación en la consola. Se trata de un proceso Background, en donde el POS envía a PROMO la transacción con STATUS="returnfinish" informando el número de transacción original y los elementos devueltos.
De manera Online solo se validara que el número de transacción original exista en la base del cliente y que el mensaje este correctamente conformado.
En el proceso background, PROMO recuperara la transacción original, quitara del contexto los elementos devueltos y volverá a evaluar promociones con el nuevo contexto de transacción con el número de mapa con que se evaluó la venta, los beneficios NO informados en esta evaluación (en comparación con los beneficios informados en la venta), serán los beneficios a anular de la transacción original.
En caso de tratarse de una transacción de cambio, el ítem devuelto será tratado como una devolución, realizando los pasos y evaluaciones descriptos anteriormente. Los elementos que se informen al motor serán responsabilidad del POS.

Response OK
<?xml version="1.0" encoding="UTF-8"?><message ack="0" engine="2.6" mapversion="2" messageId="1" companyId="sts" store="1" terminal="1" transaction="1_1_20170829162054">
<loyalty>
<loyaltycards/>
<coupons/>
<errors/>
<customers/>
<redeemTable/> 
</loyalty>
</message>


Response – ERROR (Ver capítulo 3.1.1 Valores del atributo "ack")

Response ERROR
<?xml version="1.0" encoding="UTF-8"?><message ack="9004" engine="2.6" mapversion="2" messageId="1" companyId="sts" store="1" terminal="1" transaction="1_1_20170829162239"/>

Clientes

Se agregan al mensaje de respuesta al "LoyaltyValidation" los datos correspondientes al cliente consultado y los elementos de fidelidad que tiene asociado. Vale aclarar que si el cliente tiene tarjeta inactiva, esas tarjetas no regresaran en la respuesta del loyaltyvalidation del cliente. Solo se informaran los elementos de fidelidad activos que tengan asociados.


Ejemplo
<message ack="0" engine="2.6" mapversion="1" messageId="1" companyId="sts" store="1" terminal="1" transaction="1_1_20170515152511">
<loyalty>
<loyaltycards/>
<coupons/>
<errors/>
<customers>
<customer code="6666" email="[email protected]" identifier="3055881" lastName="" name="Rojo Marcos" seq="1">
<loyaltycard ack="0" amount="100.0" id="3330000000001" type="1"/>
<coupon ack="0" amount="0.0" barcode="1000010012948" couponId="1" seq="1"/>
</customer>
</customers>
<redeemTable/> 
</loyalty>
</message>


(Ver también Engine Request - LoyaltyValidation)

Operacion con Segmentos

Imaginemos que tenemos una Promocion que da un beneficio a los clientes con segmento "ABC1".  La Operatoria para trabajar con dicha Promocion seria:

  1. Realizamos una operacion de LoyaltyValidation (Ver Engine Request - LoyaltyValidation) para conocer los segmentos a los que pertenece el cliente 9991:
Request
<message companyId="sts" store="00001" terminal="010" date-time="2017-06-04 12:30:00" messageId="0010" void-trx="false" response="true" init-tck="true" evaluate="true" " status="loyaltyValidation" map-version="15" suggest="true" suggest-seq="3">
 <customer-add seq="1" id="9991"/>
 </message>

2. En respuesta al request anterior Promo nos informará como una de las propiedades los segmentos a los que pertenece ese cliente:  Como vemos en el ejemplo el cliente pertenece a los segmentos ABC1, D18 y K1

Ejemplo
<message ack="0" engine="2.6" mapversion="1" messageId="1" companyId="sts" store="1" terminal="1" transaction="1_1_20170515152511">
<loyalty>
<loyaltycards/>
<coupons/>
<errors/>
<customers>
<customer code="9991" email="[email protected]" identifier="3055881" lastName="" name="Rojo Marcos" seq="1" segment="ABC1,D18,K1">
<loyaltycard ack="0" amount="100.0" id="3330000000001" type="1"/>
<coupon ack="0" amount="0.0" barcode="1000010012948" couponId="1" seq="1"/>
</customer>
</customers>
<redeemTable/> 
</loyalty>
</message>

3. Por ultimo realizamos la transacción de venta con el cliente enviando su información completa:

Request
<message companyId="sts" store="00001" terminal="010" date-time="2017-06-04 12:30:00" messageId="0010" void-trx="false" response="true" init-tck="true" evaluate="true" status="Finish" map-version="15" suggest="true" suggest-seq="3">
 <customer-add seq="1" id="9991" segment="ABC1,D18,K1" />
 </message>

De esta forma la transacción será evaluada y al  ser un cliente que pertenece al segmento ABC1, le será otorgada la Promoción.


Crear Clientes (Nota: Solo si se ha habilitado el funcionamiento sin clientes pre-existentes)

Existen casos en que se requieren crear clientes en el momento por ejemplo para poder enviarles cupones electrónicos por email.  A este fin se ha incorporado la posibilidad de enviar la definición del cliente (datos mínimos necesarios) desde la mensajería de Promo.

Los clientes serán creados utilizando el estado "loyaltyValidation" en el caso de enviarse los datos mínimos y al mismo tiempo Promo detecte que el cliente no existe.  Los datos mínimos mencionados por ejemplo serian los marcados en negrita ne el siguiente ejemplo:


<customer-add seq="1" id="10090504" identifier="10090504" type="test" name="pepe" lastName="rodrigues" identifierType="cpf" email="mimail@test.com" />


Veamos ahora un ejemplo de intercambio de estos mensajes:


  1. Realizamos una petición con loyaltyValidation y el cliente no existe:

    Request
    <message companyId="napse" store="1" terminal="10" date-time="2018-08-09 10:51:50" init-tck="true" messageId="1" void-trx="false" response="true" status="loyaltyValidation" evaluate="true" offline="false" >
    <customer-add seq="1" id="10090504" type="test" limitedBenefits="5b7044246491fa1604a6d15b:200.00;" />
    </message>
    
    

    La respuesta entrega valores por defecto:

    Response
    <message ack="0" companyId="napse" engine="6.4.6" mapversion="1" messageId="1" store="1" terminal="10" transaction="napse_1_10_20180809105150">  
    <loyalty>    
    <loyaltycards/>    
    <coupons/>    
    <errors/>    
    <customers>      
    <customer code="10090504" email="-" identifier="-" lastName="-" limitedBenefits="" name="-" segment="" seq="1"/>    
    </customers>
    <redeemTable/>   
    </loyalty>
    </message>
    
    
  2. En este caso enviamos datos del cliente pero no completamos todos los campos necesarios:

    Code
    <message companyId="napse" store="1" terminal="10" date-time="2018-08-09 10:51:50" init-tck="true" messageId="1" void-trx="false" response="true" status="loyaltyValidation" evaluate="true" offline="false" >
    <customer-add seq="1" id="10090504" identifier="10090504" type="test" limitedBenefits="5b7044246491fa1604a6d15b:200.00;"  name="pepe" lastName="rodrigues" identifierType="cpf" />
    </message>
    
    

    La respuesta aun contiene datos por defecto:

    Response
    <message ack="0" companyId="napse" engine="6.4.6" mapversion="1" messageId="1" store="1" terminal="10" transaction="napse_1_10_20180809105150">
    <loyalty>
    <loyaltycards/>
    <coupons/>
    <errors/>
    <customers>
    <customer code="10090504" email="-" identifier="10090504" lastName="rodrigues" limitedBenefits="" name="pepe" segment="" seq="1"/>
    </customers>
    <redeemTable/>     
    </loyalty></message>
    
    
    
  3. Ahora enviamos TODOS los datos obligatorios para que el cliente sea creado

    Code
    <message companyId="napse" store="1" terminal="10" date-time="2018-08-09 10:51:50" init-tck="true" messageId="1" void-trx="false" response="true" status="loyaltyValidation" evaluate="true" offline="false" >
    <customer-add seq="1" id="10090504" identifier="10090504" type="test" limitedBenefits="5b7044246491fa1604a6d15b:200.00;"  name="pepe" lastName="rodrigues" identifierType="cpf" email="[email protected]" />
    </message>
    
    

    La respuesta es:

    Code
    <?xml version="1.0" encoding="UTF-8"?>
    <message ack="0" companyId="napse" engine="6.4.6" mapversion="1" messageId="1" store="1" terminal="10" transaction="napse_1_10_20180809105150">
    <loyalty>
    <loyaltycards/>
    <coupons/>
    <errors/>
    <customers>
    <customer code="10090504" email="[email protected]" identifier="10090504" lastName="rodrigues" limitedBenefits="" name="pepe" segment="" seq="1"/>    
    </customers>
    <redeemTable/>   
    </loyalty>
    </message>
    
    
  4. Ahora vamos a enviar el mensaje que enviamos en el punto 1, el cual tiene solo los datos básicos del cliente y por el cual en el punto 1 nos retornaba valores por defecto (el cliente no era conocido) mientras que ahora nos tendría que retornar todos los datos que ya conocemos y creamos en el punto 3.

    Code
    <message companyId="napse" store="1" terminal="10" date-time="2018-08-09 10:51:50" init-tck="true" messageId="1" void-trx="false" response="true" status="loyaltyValidation" evaluate="true" offline="false" >
    <customer-add seq="1" id="10090504" type="test" limitedBenefits="" />
    </message>
    
    

    La respuesta efectivamente es:

    Code
    <?xml version="1.0" encoding="UTF-8"?>
    <message ack="0" companyId="napse" engine="6.4.6" mapversion="1" messageId="1" store="1" terminal="10" transaction="napse_1_10_20180809105150">
    <loyalty>
    <loyaltycards/>
    <coupons/>
    <errors/>
    <customers>
    <customer code="10090504" email="[email protected]" identifier="10090504" lastName="rodrigues" limitedBenefits="" name="pepe" segment="" seq="1"/>    
    </customers>
    <redeemTable/>   
    </loyalty>
    </message>
    
    

Operatoria (en base a los posibles escenarios):

Operatoria

GiftCard

Monedero

Tarj de Puntos

Gift - Único Uso

Alta de tarjeta

Por ArchivoINACTIVAS

Por Archivo/ManualInactivas o Activas

Por ArchivoINACTIVAS

Por ArchivoINACTIVAS

Consulta de Tarjetas

Se informara en tag Errors (por estar inactiva)el Amount - Type

Se informara en tag Errors, si esta inactiva o en tag LoyaltyCard si esta activaType - Amount

Se informara en tag Errors (por estar inactiva)Amount –Customer-Type

Se informara en tag Errors (por estar inactiva)Amount - Type

Activación de Tarjeta

Deberá activarse por medio del mensaje "Loyaltyactivation" o "finish" Valida CVV

Podrá activarse por el mensaje "Loyaltyactivation", "finish" o cuando se realiza su primera recarga

Podrá activarse por el mensaje "Loyaltyactivation", "finish" o cuando se realiza su primera recarga Si se envía Cliente lo validará

Podrá activarse por el mensaje "Loyaltyactivation", "finish" o cuando se realiza su primera recarga. Valida CVV

Transferencia

Admite solo transferencia de saldo totales - Una vez transferido el saldo total de la tarjeta, ésta se cancela. Valida CVV

Admite transferencias parciales sin alterar el estado de tarjeta.

No admite transferencia de ningún tipo.

No admite transferencia de ningún tipo.

Imputación de Saldo

No admite recarga de saldo.

Admite recargas hasta un valor máximo.

Admite recargas sin tope. Si se envía cliente se validara.

Admite recargas sin tope. Valida CVV.

Consumo de Saldo

Admite consumir el saldo en más de una transacción sin alterar el estado de la tarjeta. Valida CVV

Admite consumir el saldo en más de una transacción sin alterar el estado de la tarjeta

Admite consumir el saldo en más de una transacción sin alterar el estado de la tarjeta Si se envía cliente se validara

Solo permite un único consumo de saldo ya sea total o parcial, luego de ese único consumo la tarjeta se INACTIVA. Valida CVV

Limites por clientes

Cuando el beneficio tenga limites por clientes, la operatoria del motor deberá ser la siguiente:

Para poder operar con limites de clientes el primer mensaje enviado desde el POS debe ser un status loyaltyValidation con el elemento customer, para poder cargar los limites del cliente antes de realizar la transacción.
El motor informara los limites consumidos dentro del elemento customer en el atributo limitedBenefits.


Importante: Para cargar el limite del cliente en el motor, se deberá hacer un loyaltyValidation con init-tck="true" con el elemento customer, debe ser el primer mensaje a operar.

Ejemplo para los mensajes de Limites

Nota: En este ejemplo se definió una promoción con un beneficio fijo monetario de 100, y con un limite monetario de 300 por cliente, es decir para este caso si el cliente realiza mas de 3 transacciones, en la 4 ya No aplicara por haber superado el limite configurado en la promoción.

A continuación se muestra como se debe operar:

Request LoyaltyValidation Limites por Clientes
<message companyId="napse" store="1" terminal="1" date-time="2019-02-25 12:02" init-tck="true" messageId="20" void-trx="false" response="true" status="loyaltyValidation" evaluate="false"  suggest="true"> 
	<customer-add seq="1"  id="2" type="test" /> 
	<item-add seq="2" qty="1" code="1" magnitude="0" xprice="200" unitprice="200"/>    
</message>


Response LoyaltyValidation Limites por Clientes
<?xml version="1.0" encoding="UTF-8"?><message ack="0" companyId="napse" engine="6.4.0" mapversion="25" messageId="20" store="1" terminal="1" transaction="napse_1_1_20190225125106">
  <loyalty>
    <loyaltycards/>
    <coupons/>
    <errors/>
    <customers>
      <customer code="2" email="[email protected]" identifier="25456742" lastName="Perez" limitedBenefits="5c73fa11a8b0ea2f888130c0:300.00;" name="Juan" seq="1">
        <loyaltycard ack="0" amount="2088.00" id="1110000000" status="Activa" type="test"/>
        <limit amount="300.00" id="5c73fa11a8b0ea2f888130c0" promotionDescription="promoLimite" promotionName="promoLimite"/>
      </customer>
    </customers>
    <redeemTable/>    
</loyalty>
</message>

En la respuesta podemos ver la información del cliente con el  limitedBenefits que nos indica el limite por cliente del beneficio. Es decir en esta promoción la podremos utilizar 3 veces por cliente, dado que el beneficio es un monto de 100 por beneficio y el limite monetario es de 300.

Request Sales Limites por Clientes
<message companyId="napse" store="1" terminal="1" date-time="2019-02-25 12:02" init-tck="false" messageId="20" void-trx="false" response="true" status="sales" evaluate="true"  suggest="true"> 
	<customer-add seq="1"  id="2" type="test" /> 
	<item-add seq="2" qty="1" code="1" magnitude="0" xprice="200" unitprice="200"/>    
</message>
Response sales Limites por Clientes
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<message ack="0" companyId="napse" engine="6.4.0" mapversion="25" messageId="20" store="1" terminal="1">
  <optional>
    <promo code="promoLimite" id="promoLimite" nro="5c73f81fa8b0ea2f888130ab">
      <benefit TLOGMessage="promoLimite" account="" applicationMethod="resume" baseAmount="200.00" benefitType="FixedDiscount" discountAmount="100.00" displayMessage="promoLimite" hasLimit="true" name="5c73f81fa8b0ea2f888130ab" nro="5c73fa11a8b0ea2f888130c0" order="1" printerMessage="promoLimite" prorationMethod="PROPORTIONAL" unit="qty">
        <apply>
          <item magnitude="0.000" qty="1.000" seq="2" value="100.00" valueWithTaxes="100.00" xprice="200.00"/>
        </apply>
      </benefit>
    </promo>
  </optional>
</message>

Luego hacemos el status finish

Request finish Limites por Clientes
<message companyId="napse" store="1" terminal="1" date-time="2019-02-25 12:02" init-tck="false" messageId="20" void-trx="false" response="true" status="finish" evaluate="true"  suggest="true"> 
	<customer-add seq="1"  id="2" type="test" /> 
	<item-add seq="2" qty="1" code="1" magnitude="0" xprice="200" unitprice="200"/>    
</message>
Response finish Limites por Clientes
<?xml version="1.0" encoding="UTF-8"?><message ack="0" companyId="napse" engine="6.4.0" mapversion="25" messageId="20" store="1" terminal="1" transaction="napse_1_1_20190225125233">
  <loyalty>
    <loyaltycards/>
    <coupons/>
    <errors/>
    <customers/>
    <redeemTable/>   
   </loyalty>
</message>

Por ultimo el commit

Request commit Limites por Clientes
<message companyId="napse" store="1" terminal="1" date-time="2019-02-25 12:02" init-tck="false" messageId="20" void-trx="false" response="true" status="commit" evaluate="true"  suggest="true"> 
	<customer-add seq="1"  id="2" type="test" /> 
	<item-add seq="2" qty="1" code="1" magnitude="0" xprice="200" unitprice="200"/>    
</message>


Response commit Limites por Clientes
<?xml version="1.0" encoding="UTF-8"?><message ack="0" companyId="napse" engine="6.4.0" mapversion="25" messageId="21" store="1" terminal="1" transaction="napse_1_1_20190225125233"/>


Haciendo nuevamente el loyaltyValidation veremos que hemos consumido 100 del limite, dado que la promoción otorgaba un beneficio de 100 por cada transacción.


Request LoyaltyValidation Limites por Clientes
<message companyId="napse" store="1" terminal="1" date-time="2019-02-25 12:05" init-tck="true" messageId="21" void-trx="false" response="true" status="loyaltyValidation" evaluate="false" suggest="true"> 
<customer-add seq="1" id="2" type="test" />  
</message>


Response LoyaltyValidation Limites por Clientes
<?xml version="1.0" encoding="UTF-8"?><message ack="0" companyId="napse" engine="6.4.0" mapversion="25" messageId="21" store="1" terminal="1" transaction="napse_1_1_20190225125107">
  <loyalty>
    <loyaltycards/>
    <coupons/>
    <errors/>
    <customers>
      <customer code="2" email="[email protected]" identifier="25456742" lastName="Perez" limitedBenefits="5c73fa11a8b0ea2f888130c0:200.00;" name="Juan" seq="1">
        <loyaltycard ack="0" amount="2088.00" id="1110000000" status="Activa" type="test"/>
        <limit amount="200.00" id="5c73fa11a8b0ea2f888130c0" promotionDescription="promoLimite" promotionName="promoLimite"/>
      </customer>
    </customers>
    <redeemTable/>   
    </loyalty>
</message>


De realizar 2 transacciones mas ya no aplicara la promoción por haber superado el limite.

Precios

A la mensajería del motor se agrego un nuevo status denominado prices, dicho estado nos informará los precios de los ítems a consultar, para consultar el precio se deberá informar los ítems con el atributo unitprice=0, este nuevo estado evaluara el ticket del mensaje enviado y responderá los precios solicitados según la evaluación de la lista de precios, en caso de agregar o quitar elementos para modificar la información del ticket usar las operaciones add y void de los elementos (para ver mas detalle de preciadores referirse al manual de usuario).

Las Listas de precios están asociadas a tiendas por lo que el campo store es clave para encontrar los precios.

Nota: Para que la funcionalidad de precios esta disponible, el motor tendrá que tener en el archivo de configuración (config.xml) en el tag general el atributo: <disablePrices>false</disablePrices>

Ejemplo de request de Prices
<message companyId="napse" store="test" terminal="1" date-time="2018-02-19 12:35" init-tck="true" messageId="1" void-trx="false" response="true" status="prices" evaluate="true"  suggest="true">
 <item-add seq="1" qty="2" code="00-1114298" magnitude="0" xprice="200" unitprice="0"/>
<item-add seq="2" qty="1" code="768-76-8409" magnitude="0" xprice="0" unitprice="0"/>   
</message>

Respuesta esperada

Ejemplo de Response de Prices
<message ack="0" companyId="napse" engine="6.4.0" mapversion="0" messageId="1" store="test" terminal="1">
  <prices lastUpdate="19/02/2019 13:22:08">
    <item code="00-1114298" discountable="true" magnitude="0.00" manualDiscount="true" priceLastUpdate="19/02/2019 13:18:06" priceListId="napse_LP0_test" qty="2.00" seq="1" supplierFinancial="PR3" supplierFinancialAmount="16070.00" supplierItem="PR1" supplierItemAmount="65988.00" unitprice="48535.46" xprice="97070.92"/>
    <item code="768-76-8409" discountable="true" magnitude="0.00" manualDiscount="true" priceLastUpdate="19/02/2019 13:18:00" priceListId="napse_LP0_test" qty="1.00" seq="2" supplierFinancial="PR1" supplierFinancialAmount="32340.00" supplierItem="PR3" supplierItemAmount="24791.00" unitprice="73921.00" xprice="73921.00"/>
  </prices>
</message>


Las propiedades de los elementos informados en el Tag <Prices/> son:

Propiedad

Tipo de dato

Descripción

lastUpdate

Fecha con hora

Informa la fecha de la ultima actualización de precios (la consola se comunico con el motor para informar precios.)

discountable

Booleano

Determina si el ítem admite descuento

manualDiscount

Booleano

Determina si el ítem admite descuento manual

priceLastUpdate

Alfanumérico

Fecha en la que fue actualizado el precio del ítem

priceListId

Alfanumérico

Es el código de la empresa mas el código de la lista de precio del cual se calculo el precio <codigoEmpresa>_<codigoListaDePrecios>

qtyEntero positivoNúmero que identifica la Cantidad del ítem

seq

Entero positivo

Número que identifica al elemento dentro de la transacción

supplierFinancialAlfanuméricoOpcional. Es el código del proveedor financiero del ítem
supplierFinancialAmount

Numérico

Opcional. Es el monto que el proveedor Financiero reconoce
supplierItemAlfanuméricoOpcional. Es el código del proveedor del ítem
supplierItemAmount

Numérico

Opcional. Es el monto que el proveedor reconoce
unitprice

Numérico

Es precio del ítem consultado al motor
xprice

Numérico

Es el precio del ítem multiplicado por la el atributo qty


También se puede calcular los precios en otros status enviando el ítem con unitprice=0

En este caso enviamos un status sales con 2 ítems con unitprice=0 y uno con precio

Request
<message companyId="napse" store="test" terminal="1" date-time="2019-02-19 14:35" init-tck="false" messageId="13" void-trx="false" response="true" status="sales" evaluate="true"  suggest="true">
 <item-add seq="1" qty="2" code="00-1114298" magnitude="0" xprice="200" unitprice="0"/>
<item-add seq="2" qty="1" code="768-76-8409" magnitude="0" xprice="0" unitprice="0"/> 
<item-add seq="3" qty="1" code="769-51-6063" magnitude="0" xprice="10000" unitprice="10000"/> 
</message>

En la respuesta vemos que el beneficio de la promoción del 10% sobre cada ítem se aplica para los 3 ítems, para los dos con ítem con unitprice=0 se calculo el precio y se le aplico el 10%, mas abajo se ve el bloque de prices de donde se sacaron los precios.

Response
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<message ack="0" companyId="napse" engine="6.4.0" mapversion="5" messageId="13" store="test" terminal="1">
  <optional>
    <promo code="test" id="test" nro="5c59964c47452a7b3c22724a">
      <benefit TLOGMessage="test" account="" applicationMethod="resume" baseAmount="180991.92" benefitType="PercentageDiscount" discountPercentage="10.00" displayMessage="test" name="5c59964c47452a7b3c22724a" nro="5c670e1ea8b0ea296089de8f" order="1" printerMessage="test" prorationMethod="PROPORTIONAL" unit="qty">
        <apply>
          <item magnitude="0.000" qty="2.000" seq="1" value="9707.09" valueWithTaxes="20.00" xprice="97070.92"/>
          <item magnitude="0.000" qty="1.000" seq="2" value="7392.10" valueWithTaxes="0.00" xprice="73921.00"/>
          <item magnitude="0.000" qty="1.000" seq="3" value="1000.00" valueWithTaxes="1000.00" xprice="10000.00"/>
        </apply>
      </benefit>
    </promo>
  </optional>
  <prices lastUpdate="19/02/2019 15:52:56">
    <item code="00-1114298" discountable="true" magnitude="0.00" manualDiscount="true" priceLastUpdate="19/02/2019 13:18:06" priceListId="napse_LP0_test" qty="2.00" seq="1" supplierFinancial="PR3" supplierFinancialAmount="16070.00" supplierItem="PR1" supplierItemAmount="65988.00" unitprice="48535.46" xprice="97070.92"/>
    <item code="768-76-8409" discountable="true" magnitude="0.00" manualDiscount="true" priceLastUpdate="19/02/2019 13:18:00" priceListId="napse_LP0_test" qty="1.00" seq="2" supplierFinancial="PR1" supplierFinancialAmount="32340.00" supplierItem="PR3" supplierItemAmount="24791.00" unitprice="73921.00" xprice="73921.00"/>
  </prices>
</message>

Nuevo atributo del header tenderGroupCode

 Para determinar si los preciadores aplican precio de crédito o precio de venta regular de la lista de precios, se agrego un atributo en el header el  tenderGroupCode.

Cuando el mensaje tengatenderGroupCode y su valor sea "cr" , el motor aplicara el precio de crédito, en caso que no tenga el atributo o tenga otro valor el precio a aplicar será precio de venta.

Ejemplo de mensaje con tenderGroupCode:

Request
<message companyId="napse" store="test" terminal="1" date-time="2019-02-19 14:35" init-tck="false" messageId="14" void-trx="false" response="true" status="sales" evaluate="true"  suggest="true"  tenderGroupCode="cr">
 <item-add seq="1" qty="2" code="00-1114298" magnitude="0" xprice="200" unitprice="0"/>
<item-add seq="2" qty="1" code="768-76-8409" magnitude="0" xprice="0" unitprice="0"/> 
<item-add seq="3" qty="1" code="769-51-6063" magnitude="0" xprice="10000" unitprice="10000"/>  
</message>


Response
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<message ack="0" companyId="napse" engine="6.4.0" mapversion="5" messageId="14" store="test" terminal="1" tenderGroupCode="cr">
<optional>
<promo code="test" id="test" nro="5c59964c47452a7b3c22724a">
<benefit TLOGMessage="test" account="" applicationMethod="resume" baseAmount="144668.20" benefitType="PercentageDiscount" discountPercentage="10.00" displayMessage="test" name="5c59964c47452a7b3c22724a" nro="5c670e1ea8b0ea296089de8f" order="1" printerMessage="test" prorationMethod="PROPORTIONAL" unit="qty">
<apply>
<item magnitude="0.000" qty="2.000" seq="1" value="6222.20" valueWithTaxes="20.00" xprice="62222.00"/>
<item magnitude="0.000" qty="1.000" seq="2" value="7244.62" valueWithTaxes="0.00" xprice="72446.20"/>
<item magnitude="0.000" qty="1.000" seq="3" value="1000.00" valueWithTaxes="1000.00" xprice="10000.00"/>
</apply>
</benefit>
</promo>
</optional>
<prices lastUpdate="19/02/2019 16:11:13">
<item code="00-1114298" discountable="true" magnitude="0.00" manualDiscount="true" priceLastUpdate="19/02/2019 13:18:06" priceListId="napse_LP0_test" qty="2.00" seq="1" supplierFinancial="PR3" supplierFinancialAmount="16070.00" supplierItem="PR1" supplierItemAmount="65988.00" unitprice="31111.00" xprice="62222.00"/>
<item code="768-76-8409" discountable="true" magnitude="0.00" manualDiscount="true" priceLastUpdate="19/02/2019 13:18:00" priceListId="napse_LP0_test" qty="1.00" seq="2" supplierFinancial="PR1" supplierFinancialAmount="32340.00" supplierItem="PR3" supplierItemAmount="24791.00" unitprice="72446.20" xprice="72446.20"/>
</prices>
</message>



Ejemplo de mensaje SIN tenderGroupCode

Request
<message companyId="napse" store="test" terminal="1" date-time="2019-02-19 14:36" init-tck="true" messageId="15" void-trx="false" response="true" status="sales" evaluate="true"  suggest="true">
 <item-add seq="1" qty="2" code="00-1114298" magnitude="0" xprice="200" unitprice="0"/>
<item-add seq="2" qty="1" code="768-76-8409" magnitude="0" xprice="0" unitprice="0"/> 
<item-add seq="3" qty="1" code="769-51-6063" magnitude="0" xprice="10000" unitprice="10000"/>  
</message>


Response
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<message ack="0" companyId="napse" engine="6.4.0" mapversion="5" messageId="15" store="test" terminal="1">
  <optional>
    <promo code="test" id="test" nro="5c59964c47452a7b3c22724a">
      <benefit TLOGMessage="test" account="" applicationMethod="resume" baseAmount="180991.92" benefitType="PercentageDiscount" discountPercentage="10.00" displayMessage="test" name="5c59964c47452a7b3c22724a" nro="5c670e1ea8b0ea296089de8f" order="1" printerMessage="test" prorationMethod="PROPORTIONAL" unit="qty">
        <apply>
          <item magnitude="0.000" qty="2.000" seq="1" value="9707.09" valueWithTaxes="20.00" xprice="97070.92"/>
          <item magnitude="0.000" qty="1.000" seq="2" value="7392.10" valueWithTaxes="0.00" xprice="73921.00"/>
          <item magnitude="0.000" qty="1.000" seq="3" value="1000.00" valueWithTaxes="1000.00" xprice="10000.00"/>
        </apply>
      </benefit>
    </promo>
  </optional>
  <prices lastUpdate="19/02/2019 16:15:14">
    <item code="00-1114298" discountable="true" magnitude="0.00" manualDiscount="true" priceLastUpdate="19/02/2019 13:18:06" priceListId="napse_LP0_test" qty="2.00" seq="1" supplierFinancial="PR3" supplierFinancialAmount="16070.00" supplierItem="PR1" supplierItemAmount="65988.00" unitprice="48535.46" xprice="97070.92"/>
    <item code="768-76-8409" discountable="true" magnitude="0.00" manualDiscount="true" priceLastUpdate="19/02/2019 13:18:00" priceListId="napse_LP0_test" qty="1.00" seq="2" supplierFinancial="PR1" supplierFinancialAmount="32340.00" supplierItem="PR3" supplierItemAmount="24791.00" unitprice="73921.00" xprice="73921.00"/>
  </prices>
</message>


Dado los request anteriores con y sin tenderGroupCode los precios varían uno es el precio de crédito y el otro el precio regular de venta


  • Se ve que con el tenderGroupCode el valor que respondió el motor es el siguiente:
          <item magnitude="0.000" qty="1.000" seq="2" value="7244.62" valueWithTaxes="0.00" xprice="72446.20"/>
  • Se ve que SIN el tenderGroupCode el valor que respondió el motor es el siguiente:
          <item magnitude="0.000" qty="1.000" seq="2" value="7392.10" valueWithTaxes="0.00" xprice="73921.00"/>

Integración de Listas negras y limites

  • Evaluación de la Lista Negra en el motor

    El motor se encargará de consultar los limites (beneficios que ya no aplican) previo a la evaluación de beneficios.

    Cuando se genere una transacción desde el motor si tienen en init-tck=true y la funcionalidad loyaltyValidation se cargará la lista de beneficios que están en la lista negra y se agregaran en el hasmap limits del CacheDataManager.

    Al momento de evaluar los beneficios de la transacción se consultara si el beneficio para el mapa actual se encuentra en la lista negra si es así no se aplicara el beneficio, en caso contrario de aplicar el beneficio se devolverá en la respuesta del beneficio que el mismo tiene limites con el atributo hashLimit.

    Carga de la lista Negra de beneficios desde el motor:

    El motor enviará a la consola de manera asincrónica el mapa y esta le devolverá la lista negra de beneficios, la lista negra se cargara en 2 ocasiones.

    •  init-tck="true"

    Cuando desde el motor se inicie la transacción con el init-tck="true" y esta habilitada la funcionalidad Loyalty, el motor le enviará a la consola de manera asincrónica el mapa de la transacción, la consola le devolverá la lista negra de los beneficios de las promociones del mapa cuyos limites de scope RETAILER Y SCOPE hayan sido superados.

    • LoyaltyValidation


    Cuando se realice un status del tipo LoyaltyValidation y tenga datos del customer, el motor se comunicara asincrónicamente con la consola para obtener la lista negra de los beneficios de las promociones del mapa cuyos limites de scope CUSTOMER hayan sido superados.

    Ejemplo de beneficios en la lista negra CacheDataManager.limits

    La key es de la siguiente forma <benefitId>_<storeId>_<customerId>

    Dependiendo del scope del limite el <storeId> o el <customerId> podrá estar con el carácter "-" por ejemplo

      • Si el beneficio con id = 1, tiene un limite del scope retailer la clave en limits será la siguiente: "1_-_-"
      • Si el beneficio con id = 1, tiene un limite del scope store por ejemplo el storeId es 33 la clave en limits será la siguiente: "1_33_-"
      • Si el beneficio con id = 1, tiene un limite del scope customer por ejemplo el customer es 55 la clave en limits será la siguiente: "1_-_55"

    Elementos agregados en el motor:

      1. ProcessorAsyncBlackList clase que se comunica con la consola a través de un post ping para solicitar la lista negra

    Elementos Modificados en el motor:

    1. CacheDataManager (se agregó el HashMap limits) la clave del mismo es <benefitId>_<storeId/"-">_<customer/"-">
    2. RequestInterpreter cuando se cargue el ticket con"init-tck" en "true"  y la funcionalidad loyalty se cargara los beneficios que estén en la lista negra a el hashMap limits

    3. BenefitBase se modificó agregándole la propiedad booleana hasLimit y la modificación del método  getBenefitSet (el cuál es llamado en el momento de la evaluación de los beneficios) El método antes de filtrar los ítems del ticket evaluará si el beneficio tiene limites y además de que no esté en el Hasmap del CacheDataManager.limits.
      Cuando el motor de respuesta al ticket el atributo del beneficio hasLimit solo se devolverá en caso de estar en true.
    4. TransactionBenefit se agrego el atributo hasLimit para luego poder ser consultado desde la consola.

    5. CentralBackgroundProcess se agrega el método runProcessorAsync el cual se ejecuta asincrónicamente (utilizado para obtener la lista negra).

    6. OperationLoyaltyvalidation se agrega el llamado a la lista negra del mapa actual para los customers.

ACTUALIZACION DE STATUS DE LIMITES

Al realizar el FINISH desde el motor, la consola recibirá la Transaction con los beneficios aplicados. La actualización de LimitStatus deberá recorrer cada beneficio con límites.Dependiendo del tipo de límite se obtendrá el acumulado en la transacción y se incrementará en el actualValue, en caso de superar el maxValue, el beneficio pasará la lista negra para la instancia del scope del limite. El paso a la lista negra de beneficios es llenar la tabla LimitBlackList insertara 1 registro que dependiendo del scope que tenga los datos que llenará. El armado de la instancia del beneficio evaluado se llenará a partir del scope más especifico, es decir en el siguiente orden customer,store y por ultimo retail.

Ejemplo de limites pasar a inactivos:

beneficioId

limiteId

scope

11retailer
12store


En el caso de que el limite 2 queda inactivo, se tendrá que registran en la tabla LimitBlackList  de la siguiente manera:

beneficioId

storeId

customer

102-

Ejemplo de limites pasar a inactivos:

beneficioId

limiteId

scope

23store
24customer


En el caso de que el limite 4 queda inactivo, se tendrá que registran en la tabla LimitBlackList  de la siguiente manera llenando:

beneficioId

storeId

customer

1-6


Ejemplo de limites pasar a inactivos:

beneficioId

limiteId

scope

35retailer
36retailer


En el caso de que el limite 6 queda inactivo, se tendrá que registrar en la tabla LimitBlackList  de la siguiente manera::

beneficioId

storeId

customer

3--

PROCESAMIENTO EN CONSOLA
El procesamiento en consola es el siguiente:

a. Una vez recibido  el status COMMIT, la transaccion es tomada por el TransactionService para su procesamiento.  Existe la opción de procesar limites al momento de recibir el commit (task separado) o bien con el proceso background mencionado.  Se va a comenzar con esta ultima opcion a priori.

b. Al procesamiento del COMMIT en el transactionService se agrega la llamada al procesamiento de limites (no debe arrojar exception para no cortar el resto del proceso).

c. El procesamiento se realiza de la siguiente forma:

Listas Negras

Donde:

1 = Se procesan los beneficios que han sido otorgados en la transacción siempre y cuando posean limites (hasLimits = true).

2 = Se buscan cada uno de los beneficios para conocer la definición de sus limites  (Tabla de Limites).

3 = Por cada uno de los limites que encontrados para ese beneficio.

4 = Acorde al tipo de limite se calcula el valor de incremento a computar para ese limite.  Esto depende del tipo y es:

    • a. Money: sumatoria del campo "Value" del beneficio.
    • b. Apply: Sumatoria de los campos qty de los elementos del apply.
    • c. Benefit Qty: El valor del incrmento es 1
    • d. Puntos: Sumatoria del campo "totalpoints" del beneficio.
    • e. Emmit: Sumatoria del campo qty del beneficio.
    • f. Gift: Sumatoria del campo qty del beneficio.

5 = Se procede a la  búsqueda de la instancia actual para ese limite.  Esta búsqueda depende del scope del limite ya que depende si es global, para la tienda o por cliente.

6 = Actualizar el historial de cambios con el valor actual (histórico).

7 = Actualizar el valor actual de ese limite.

8 = Si el limite ha sido alcanzado, entonces se procede a colocar el beneficio en la lista negra.  Obviamente esto depende del Scope.


6 - REINICIO PERIODICO DE CONTADORES

El proceso  general de inicio  de contadores es:

a - Se creó job de procesamiento especifico que utilice al LimitService.  (LimitsResetJob)  Se ejecuta 1 vez por día (ya que el periodo menor es diario).

b- se obtienen los registros de la tabla LimitStatus que se encuentran activos o no (ya que el reinicio es mas allá del valor actual).

c - Por cada uno de estos registros (ya renovables) grabar historial, y reiniciar su valor actual (método genérico en LimitService).


7 - DEPURACION DE LIMITES

La depuración de Limites se asocia a la depuración de transacciones, con lo cual al depurar transacciones anteriores a "Fecha", se eliminaran las entradas en el LimitStatus/History anteriores a dicha fecha.  La fecha que se toma es "processDate" para LimitStatusHistory,  y "lastUpdate" para el caso de LimitStatus.

El proceso es el siguiente:

 a. Se agrega al TransactionCleanerJob (transactionService→cleanTransactions) una llamada a apiLimitService→cleanLimits un a vez que se han depurado las transacciones.

b. Se crea la funcion ApiLImitService→cleanLimits la cual elimina los registros para este companyId y cuya fecha de procesamiento/actualización sea anterior a la fecha estipulada. (LimitStatusHistory/LimitStatus).

c. Se agrega T09_ApiLimitServiceSpec para comprobar la correcta implementación.

Consola: Servicios REST

Servicios REST – Consulta de Cliente

PROMO expone un servicio que permite consultar tarjetas a la BBDD utilizando el ID de cliente.
Junto con los campos del cliente, también se devuelve un listado de Tarjetas y Cupones, elementos de Fidelidad.
Si no tiene elementos de Fidelidad, se devolverán las Tarjetas o Cupones vacías
El código de la consulta debe ser exacto y solo se devolverá un resultado, si es que el cliente existe.
El formato en que se responde es en JSON.
Para los ejemplos se realizaron las consultas de clientes utilizando la herramienta "PostMan" de Chrome
Primero deberá de solicitarse el Tocken de acceso utilizando la APP cUrl (https://curl.haxx.se/) con el siguiente comando:

curl –v –X POST –u my-client: -d "grant_type=password" –d "username=sender" –d "password=mate" –d "scope=read" {*}http://localhost:8080/promo/oauth/token*


(Los datos de usuari0 y pass deberán ser los que correspondan al usuario de comunicación Motor/Consola. La URL de Acceso deberá referirse a la Ip y puerto en que se encuentre corriendo a laconsola de PROMO)

Obtenido el Token, podrá realizarse la consulta (postMan):

(curl -X GET -H "Authorization: Bearer 8c014b30-a674-456e-bc18-29a072a7a1f8" -H "Content-type: application/json" -H "Accept: application/json" "http://localhost:8080/promo/api/rest/customer?code=1")
Obteniéndose la siguiente respuesta:


Ejemplo
{
"_id": "59a992cacaec3625e8447663",
"code": "1",
"creationDate": "2017-09-01T17:03:06Z",
"email": "gala @sts.com",
"identificationType": "DNI",
"identifier": "54333222",
"isActive": true,
"lastName": "Higgins",
"name": "GALA",
"version": 0,

*"cards": \[*


{
"_id": "59a99439caec3625e84476f8",
"amount": 254,
"code": "2220000000001",
"created": "2017-09-01T17:09:13Z",
"isConsumed": false,
"status": "ENABLED",
"storeCode": "BLC",
"terminalCode": "2",
"transactionId": "BLC_201709011409677",
"type": "2",
"validFrom": "2017-09-01T03:00:00Z",
"validTo": "2018-09-01T03:00:00Z",
"version": 2,
"customerId": "1"
}
],

*"coupons": \[\]*


}


En caso de que el cliente no exista en la base la respuesta se devolverá vacía.-

Servicios REST – Consulta de Cupón

PROMO expone un servicio que permite consultar cupones a la BBDD utilizando solo el número de cupón y como respuesta se obtienen los movimientos asociados a dicho cupón.

(desde v6.5.10)  También se pueden realizar consultas sobre el historial de movimientos de cupones.


Los parámetros de entrada de la consulta son:

Propiedad

Tipo de dato

Descripción

companyIdAlfanuméricoCódigo de la compañía. Requerido
barcodeAlfanuméricoCódigo de la tarjeta la cual se quiere consultar. Requerido

limit

Numérico

Cantidad de registros de movimientos a retornar (default: 5) con un máximo de 100.000 por consulta. Requerido

dateFrom

Numérico

(desde 6.5.10) Fecha de Inicio en formato YYYYMMDD.  Si no se especifica code. Opcionales

dateTo

Numérico

(desde 6.5.10) Fecha de Final en formato YYYYMMDD. Si no se especifica code. Opcionales

couponAction

Alfanumérico

(desde 6.5.10) Código de Operación que se quiere consultar.  Si no se especifica code.  Por defecto son todas las operaciones. 

Los valores disponibles son: CREATE, REDEEM, VOID. Opcionales

timeFromNumérico(desde 6.5.10) Hora de Inicio con formato HHmm. Opcionales
timeToNumérico(desde 6.5.10) Hora de Fin con formato HHmm. Opcionales


Aclaración

Se pueden enviar el dateFrom y dateTo sin cargar los datos de timeFrom y timeTo, estos serán opcionales. Pero solo se utilizarán los parámetros timeFrom y timeTo si tiene cargados los parámetros de dateFrom y dateTo, caso contrario no serán utilizados.



 EJEMPLO 1: se solicitan los datos del cupón 1020000000007



(curl -X GET -H "Authorization: Bearer 8c014b30-a674-456e-bc18-29a072a7a1f8" -H "Content-type: application/json" -H "Accept: application/json" http://localhost:8080/promo/api/rest/coupon?barcode=1020000000007)
Obteniéndose la siguiente respuesta:


Ejemplo
{
"_id": "59a993d6caec3625e84476e1",
"barcode": "1020000000007",
"consumed": false,
"couponFormat": "PRE_PRINTED",
"couponStatus": "ACTIVE",
"couponType": "2",
"issuedDate": "2017-09-01T17:07:34Z",
"maxUsageTimes": 1,
"storeCode": "BC",
"terminalCode": "2",
"transactionId": "BC_201709011407171",
"usedTimes": 0,
"validFrom": "2017-09-01T17:07:34Z",
"validTo": "2117-08-08T17:07:34Z",
"version": 0,

*"couponHistory": \[*


{
"couponAction": "CREATE",
"date": "2017-09-01T17:07:34Z",
"storeCode": "BC"
}
]
}

En caso de que el cliente no exista en la base la respuesta se devolverá vacía.-


EJEMPLO 2: Se solicitan todos los cupones creados en el periodo 01/06/2020-01/07/2020, para la empresa napse con un limite de 100.000 registros.

(curl -X GET -H "Authorization: Bearer 8c014b30-a674-456e-bc18-29a072a7a1f8" -H "Content-type: application/json" -H "Accept: application/json"http://localhost:8080/promo/api/rest/coupon?dateFrom=20200601&dateTo=20200701&companyId=napse&limit=100000&couponAction=CREATE')

La respuesta será del tipo:

Ejemplo
{
    "couponHistory": [
        {
            "transactionId": "napse_1_10_20200608105150",
            "date": "2020-06-05T18:11:00Z",
            "coupon": "1010010106479",
            "couponAction": "CREATE",
            "storeCode": "1",
            "terminalCode": "10"
        },
        {
            "transactionId": "napse_1_10_20200608105150",
            "date": "2020-06-05T18:11:00Z",
            "coupon": "1010010102945",
            "couponAction": "CREATE",
            "storeCode": "1",
            "terminalCode": "10"
        },
        {
            "transactionId": "napse_1_10_20200608105150",
            "date": "2020-06-05T18:11:00Z",
            "coupon": "1010010109418",
            "couponAction": "CREATE",
            "storeCode": "1",
            "terminalCode": "10"
        },
        {
            "transactionId": "napse_1_10_20200608105250",
            "date": "2020-06-05T18:21:30Z",
            "coupon": "1010010102891",
            "couponAction": "CREATE",
            "storeCode": "1",
            "terminalCode": "10"
        }
    ]
}


Servicios REST - Consulta de Estado de Cupón


PROMO expone un servicio que permite consultar el estado de cupones a la BBDD utilizando como parámetros el Id de cliente, Id de la compañía, el tipo de acción y el rango de fechas (Fecha_desde y Fecha_hasta) y como respuesta se obtienen los movimientos asociados a dicho cupón.

La Url para acceder al servicio es: 

couponStatements
http://[server]:[port]/promo/api/rest/couponStatements


Los parámetros de entrada de la consulta son:

Propiedad Tipo de Dato Descripción
customerIdAlfanuméricoIdentificador único del cliente. Requerido
companyIdAlfanuméricoCódigo de la compañía. Requerido
actionTypestringTipo de operación que se quiere consultar. Si no se especifica, Por defecto son todas las operaciones. Los valores disponibles son: CREATE, REDEEM, VOID. Requerido
dateFromalfanuméricoFecha de Inicio en formato YYYYMMDD. Opcional
dateToalfanuméricoFecha de Final en formato YYYYMMDD. Opcional

Ej: se solicitan los cupones generados para el cliente Id = 1

y como respuesta se obtienen los datos del cupón asociado al cliente y su estado.

Respuesta:

couponStatements
[
    {
        "transactionId": "napse_napse_1_20220830120000",
        "action": "Emisión",
        "terminal": "1",
        "couponType": "cimp",
        "customerId": "1",
        "amount": "-",
        "store": "napse",
        "datetime": "30/08/2022 11:08",
        "couponCode": "116pse0018828"
    },
    {
        "transactionId": "napse_napse_1_20220830120000",
        "action": "Emisión",
        "terminal": "1",
        "couponType": "cimp",
        "customerId": "1",
        "amount": "-",
        "store": "napse",
        "datetime": "30/08/2022 11:08",
        "couponCode": "116pse0015292"
    }
]

Servicios REST – Consulta de Tarjetas

(Actualizado desde 6.5.2)

PROMO expone un servicio que permite consultar tarjetas a la BBDD utilizando solo su número de la tarjeta y como respuesta se obtienen los datos de la tarjeta en cuestión y los movimientos asociados a dicho elemento. Los datos que se devuelven son: fecha, id de transacción, tipo de operación, monto, tienda.

Para consumir este servicio se debe realizar una solicitud del tipo GET con los parámetros correspondientes a la siguiente URL: http://servidor:puerto/promo/api/rest/card


Los parámetros de entrada de la consulta son:

Propiedad

Tipo de dato

Descripción

companyIdAlfanuméricoCódigo de la compañía. Requerido
codeAlfanuméricoCódigo de la tarjeta la cual se quiere consultar. Requerido

limit

Numérico

Cantidad de registros de movimientos a retornar (default: 5) con un máximo de 100.000 por consulta. Requerido

dateFrom

Numérico

Fecha de Inicio en formato YYYYMMDD. Opcional

dateTo

Numérico

Fecha de Final en formato YYYYMMDD. Opcional

cardActionAlfanumérico

Código de Operación que se quiere consultar.  Si no se especifica code.  Por defecto son todas las operaciones. 

Los valores disponibles son: CHARGE, RECHARGE, AMOUNT_UPDATE, SALE, EXTENDED_POINTS. Opcional
timeFromNuméricoHora de Inicio en formato HHmm. Opcional
timeToNuméricoHora de Fin en formato HHmm. Opcional


Aclaración

Se pueden enviar el dateFrom y dateTo sin cargar los datos de timeFrom y timeTo, estos serán opcionales. Pero solo se utilizarán los parámetros timeFrom y timeTo si tiene cargados los parámetros de dateFrom y dateTo, caso contrario no serán utilizados.

Si se especifica un elemento de fidelidad, se retornaran los datos y movimientos asociados a dicho elemento, pudiéndose opcionalmente especificar un rango de fechas y un limite en la cantidad de movimientos.

Si no se especifica el elemento, se debe especificar un rango de fechas y se retornaran todos los movimientos de los elementos en ese rango, incluyendo en ese caso el numero del elemento que se trata.

El Formato de la Respuesta será (JSON):

Propiedad

Tipo de dato

Descripción

_id*AlfanuméricoUso Interno
amount*NuméricoSaldo Actual de la tarjeta.

code*

Alfanumérico

Número de Tarjeta

Created*

Alfanumérico

Fecha de Creación en formato ISODATE

isConsumed*

Booleano

Si ha sido consumida o no

status*Alfanumérico

Estado actual de la tarjeta

storeCode*AlfanuméricoCódigo de Tienda de generación (si aplica)
terminalCode*AlfanuméricoCódigo de terminal de generación (si aplica)
transactionId*AlfanuméricoCódigo de Transacción que la genero (si aplica)
type*AlfanuméricoTipo de Tarjeta
version*NuméricoUso Interno
cardHistoryColección

Conjunto de registros que corresponden a cada movimiento de la tarjeta, con:

  • amount: Monto del movimiento
  • card (Solo si no se consultó por una determinada): Número de tarjeta
  • cardAction: Tipo de movimiento
  • date: Fecha del movimiento (ISO DATE)
  • storeCode: Código de tienda
  • transactionId: Código de transacción.
  • Estos datos son retornados solo si se consulta por un código de tarjeta determinado.


EJEMPLO 1: se solicitan los datos de la tarjeta 1000000000001 para la compañía napse y con movimientos del 01/04/2020 al 31/04/2020 sin especificar limites con lo cual serán los 5 últimos movimientos.

(curl -X GET -H "Authorization: Bearer 8c014b30-a674-456e-bc18-29a072a7a1f8 -H "Content-type: application/json" -H "Accept: application/json" "http://localhost:8080/promo/api/rest/card?code=1000000000001&companyId=napse&dateFrom=20200401&dateTo=20200431")


El cual recibirá una respuesta del tipo:


Ejemplo
{
    "_id": "5ea975e31c8fcf4aec17953e",
    "amount": 320.0,
    "code": "1000000000001",
    "companyId": "napse",
    "created": "2020-04-29T12:41:07Z",
    "isConsumed": false,
    "status": "ENABLED",
    "storeCode": "BLC",
    "terminalCode": "001",
    "transactionId": "BLC_202004290941889",
    "type": "001",
    "version": 2,
    "cardHistory": [
        {
            "amount": "20.0",
            "cardAction": "AMOUNT_UPDATE",
            "date": "2020-04-29T12:42:26Z",
            "storeCode": null,
            "transactionId": null
        },
        {
            "amount": "300.0",
            "cardAction": "CHARGE",
            "date": "2020-04-29T12:41:07Z",
            "storeCode": null,
            "transactionId": null
        },
        {
            "amount": "0",
            "cardAction": "ACTIVATION",
            "date": "2020-04-29T12:41:07Z",
            "storeCode": null,
            "transactionId": null
        }
    ]
}


EJEMPLO 2: se solicitan todos los movimientos del 29/04/2020 al 29/04/2020 con un máximo de 100.000 movimientos.

(curl -X GET -H "Authorization: Bearer 8c014b30-a674-456e-bc18-29a072a7a1f8 -H "Content-type: application/json" -H "Accept: application/json" "http://localhost:8080/promo/api/rest/card?companyId=napse&dateFrom=20200429&dateTo=20200429&limit=100000")


El cual recibirá una respuesta del tipo:


Ejemplo
   {
    "cardHistory": [
        {
            "amount": "10.0",
            "card": "1000000000000",
            "cardAction": "AMOUNT_UPDATE",
            "date": "2020-04-29T12:42:18Z",
            "storeCode": null,
            "transactionId": null
        },
        {
            "amount": "300.0",
            "card": "1000000000000",
            "cardAction": "CHARGE",
            "date": "2020-04-29T12:02:06Z",
            "storeCode": null,
            "transactionId": null
        },
        {
            "amount": "0",
            "card": "1000000000000",
            "cardAction": "ACTIVATION",
            "date": "2020-04-29T12:02:06Z",
            "storeCode": null,
            "transactionId": null
        },
        {
            "amount": "20.0",
            "card": "1000000000001",
            "cardAction": "AMOUNT_UPDATE",
            "date": "2020-04-29T12:42:26Z",
            "storeCode": null,
            "transactionId": null
        },
        {
            "amount": "300.0",
            "card": "1000000000001",
            "cardAction": "CHARGE",
            "date": "2020-04-29T12:41:07Z",
            "storeCode": null,
            "transactionId": null
        },
        {
            "amount": "0",
            "card": "1000000000001",
            "cardAction": "ACTIVATION",
            "date": "2020-04-29T12:41:07Z",
            "storeCode": null,
            "transactionId": null
        },
        {
            "amount": "300.0",
            "card": "1000000000002",
            "cardAction": "CHARGE",
            "date": "2020-04-29T12:41:07Z",
            "storeCode": null,
            "transactionId": null
        },
        {
            "amount": "0",
            "card": "1000000000002",
            "cardAction": "ACTIVATION",
            "date": "2020-04-29T12:41:07Z",
            "storeCode": null,
            "transactionId": null
        },
        {
            "amount": "300.0",
            "card": "1000000000003",
            "cardAction": "CHARGE",
            "date": "2020-04-29T12:41:07Z",
            "storeCode": null,
            "transactionId": null
        },
        {
            "amount": "0",
            "card": "1000000000003",
            "cardAction": "ACTIVATION",
            "date": "2020-04-29T12:41:07Z",
            "storeCode": null,
            "transactionId": null
        },
        {
            "amount": "300.0",
            "card": "1000000000004",
            "cardAction": "CHARGE",
            "date": "2020-04-29T12:41:07Z",
            "storeCode": null,
            "transactionId": null
        },
        {
            "amount": "0",
            "card": "1000000000004",
            "cardAction": "ACTIVATION",
            "date": "2020-04-29T12:41:07Z",
            "storeCode": null,
            "transactionId": null
        },
        {
            "amount": "300.0",
            "card": "1000000000005",
            "cardAction": "CHARGE",
            "date": "2020-04-29T12:41:07Z",
            "storeCode": null,
            "transactionId": null
        },
        {
            "amount": "0",
            "card": "1000000000005",
            "cardAction": "ACTIVATION",
            "date": "2020-04-29T12:41:07Z",
            "storeCode": null,
            "transactionId": null
        }
    ]
}


Servicios REST – Consulta de  Estado de puntos de Tarjetas

PROMO expone un servicio que permite consultar el estado de los puntos de una tarjeta a la BBDD utilizando solo su número de la tarjeta y como respuesta se obtienen los datos del estado de los puntos de la tarjeta en cuestión y los movimientos asociados a dicha tarjeta. Los datos que se devuelven son: número y tipo de tarjeta, Id de transacción, acción realizada, tienda, fecha de la transacción, cantidad de puntos involucrados en la acción y código del cliente.

Para consumir este servicio se debe realizar una solicitud del tipo GET con los parámetros correspondientes a la siguiente URL: http://servidor:puerto/promo/api/rest/statementPoints

Los parámetros de entrada de la consulta son:

Propiedad Tipo de DatoDescripción
companyId*AlfanuméricoCódigo de la compañía. Requerido

fromDate*

Numérico

Fecha de Inicio en formato YYYYMMDD. Requerido

toDate*

Numérico

Fecha de Final en formato YYYYMMDD. Requerido

isConsume*

Booleano

Si ha sido consumida o no. Requerido

customerCode*

Alfanumérico

Identificador único del cliente. Requerido

Todos estos datos son requeridos; cuando falte alguno de ellos la aplicación enviará un mensaje como el ejemplo:

El rango de fechas no puede ser mayor a un mes:

EJ: se solicitan los datos de los puntos consumidos de la tarjeta asociada al cliente cuyo Id = 1:

El Formato de la Respuesta será (JSON):

PropiedadTipo de DatoDescripción
cardNumberAlfanuméricoNúmero de la tarjeta asociada al cliente
cardTypeCodeAlfanuméricoidentificador único de tarjeta
transactionIdNuméricoNúmero de transacción
actionAlfanuméricoAcción llevada a cabo (Otorga, Consumo)
storeCodeAlfanuméricoIdentificador único de Tienda donde se llevó a cabo la transacción
dateNuméricoFecha y hora de la transacción
amountNuméricoCant. de puntos participantes en la transacción
customerCodeAlfanuméricoIdentificador único del cliente
terminalCodeAlfanuméricoTerminal donde se realizó la transacción

La respuesta al Ej 1 es:

statementPoints
[
    {
        "cardNumber": "6000011014",
        "cardTypeCode": "10",
        "transactionId": "napse_napse_1_20220831120500",
        "action": "Consumo",
        "storeCode": "napse",
        "date": "31/08/2022 12:05",
        "amount": 200.0,
        "customerCode": "1",
        "terminalCode": "1"
    }
]



Servicios REST – Consulta de MAPAS

PROMO expone un servicio que permite consultar mapas utilizando solo el número de mapa y como respuesta se obtiene el xml del mapa de la misma forma que se obtiene por la opción de "descargar".  Como en el caso de los servicios REST previamente descriptos se necesita una authorizacion vía OAuth2.  La siguiente figura muestra el contenido del request de ejemplo:


Donde:

Operation: valor getMaps para obtener el mapa solicitado. Requerido

companyId: identificación o código de empresa la cual realiza el request. Requerido

mapNumber: Numero de mapa solicitado. Requerido


La respuesta es del tipo:

Response
<?xml version="1.0" encoding="iso-8859-1"?>
<promoCoreResponse>
	<ack>0</ack>
	<message>OK</message>
	<maps>
		<map version:="1"><?xml version="1.0" encoding="UTF-8"?>
<promo-engine start-date="14/04/2023 00:00" end-date="21/04/2023 23:59" map-version="1" suggest="not">
  <parameter key="Logging" value="true" />
  <parameter key="LogConfigurationFile" value="logrsca.xml" />
  <parameter key="LogConfigurationCategory" value="com.synthesis.promo" />
  <parameter key="Descriptors" value="descriptor.properties" />
  <parameter key="DAOConfigurationFeatures" value="com.synthesis.promo.engine.dao.ConfigurationFeatures" />
  <parameter key="EvaluationAlgorithmClass" value="com.synthesis.promo.engine.evaluation.InStepsAlgorithm" />
  <promotions>
    <promotion nro="64397700a62e432f18544f5e" name="promo 1" className="com.synthesis.promo.engine.promotion.ModularPromotion" reportParticipants="false" suggest="not">
      <sets>
        <set name="6439770da62e432f18544f62" type="item" attribute="code" comparator="Into" value="1111" />
      </sets>
      <condition type="basic" name="Exists">
        <parameter key="use-set" value="6439770da62e432f18544f62" />
      </condition>
      <benefits>
        <benefit instance="PercentageDiscount" nro="6439772ca62e432f18544f65">
          <parameter key="displayMessage" value="promo 1" />
          <parameter key="printerMessage" value="promo 1" />
          <parameter key="TLOGMessage" value="promo 1" />
          <parameter key="applicationMethod" value="resume" />
          <parameter key="prorationMethod" value="proportional" />
          <parameter key="applicationPriceType" value="original-price" />
          <parameter key="name" value="64397700a62e432f18544f5e" />
          <parameter key="percent" value="50" />
          <parameter key="unit" value="qty" />
          <parameter key="prorateBCP" value="false" />
          <applied-elements>
            <use-set name="6439770da62e432f18544f62" max="1.0" attribute="qty" />
          </applied-elements>
        </benefit>
      </benefits>
    </promotion>
  </promotions>
  <evaluation-algorithm>
    <step>
      <function name="ALL">
        <function name="SIMPLE">
          <promotion-usage name="promo 1" />
        </function>
      </function>
    </step>
  </evaluation-algorithm>
</promo-engine></map>
	</maps>
</promoCoreResponse>


Donde se observa:

ack: resultado del request, donde 0 es procesamiento correcto. (Ver códigos de respuesta ack mas arriba en este documento).

message: es el mensaje de error resultante.

maps: tag general que contiene los elementos map retornados en la respuesta.  Cada elemento map, contiene todos los elementos y tags que contiene un mapa como cuando es descargado a archivo.


Servicios REST – Precios: Servicio de Carga De Lista Cero

Se creo un Servicio Rest que permite la carga de los productos de una lista cero, El  Mismo recibe la información y será procesada de manera  asincrónica, es decir recibe la información y luego será procesada.

La Lista cero es la lista base donde se encontraran todos los precios de los productos, la misma tiene la prioridad mas baja de las listas (El motor al consultar los precios evalúa las listas existentes de prioridad de mayor a menor).

La Lista cero será enviada desde un sistema externo a promo, el proceso crea y actualiza los precios enviados.

En la consola se agrego la pantalla de Monitoreo de Importaciones. en la sección de soporte, desde esta pantalla se podrá ver el resultado de la importación,  ver la información enviada en la importación (menú contextual Contenido), el detalle de la importación mostrará el total de los registros los procesados correctamente y los que tuvieron errores, estos últimos en caso de existir se verán en la pantalla paginados o se podrá descargar los mismos en un archivo de texto. El monitor también permite el re proceso de la importaciones.

El Servicio rest deberá tener el token de oauth obtenido de 

curl -v -X POST -u my-client: -d "grant_type=password" -d "username=sender" -d "password=mate"  -d "scope=read" <promo>/oauth/token	


Donde <promo> es por ejemplo http://localhost:8080/promo


El Método es un POST a la siguiente dirección: <promo>/api/rest/priceList con el siguiente body:


{
	"companyId": "napse",
	"store": "napse",
	"items": [
		 {
		"sku": "0527-1537",
		"salePrice": 69406.77,
		"costPrice": 50942.13,
		"saleCreditPrice": 119716.68,
		"magnitudePrice": 829,
		"measuredUnit": "cm3",
		"supplierItem": "PR3",
		"supplierFinancial": "PR2",
		"supplierItemAmount": 52471,
		"supplierFinancialAmount": 53604,
		"saleWholesalePrice": 31858,
		"saleWholesaleLimit": 6081,
		"limit": 794,
		"enabledDate": "2018-12-25T10:42:25Z"
         "discountable":true,
         "manualDiscount":false
	}, 	
	{
		"sku": "66897-001",
		"salePrice": 39123.0,
		"costPrice": 10452.59,
		"saleCreditPrice": 42433.6,
		"magnitudePrice": 371,
		"measuredUnit": "kg",
		"supplierItem": "PR2",
		"supplierFinancial": "PR2",
		"supplierItemAmount": 52551,
		"supplierFinancialAmount": 21423,
		"saleWholesalePrice": 78603,
		"saleWholesaleLimit": 9691,
		"limit": 2982,
		"enabledDate": "2019-01-20T10:41:55Z"
	}
	]
}


La respuesta del mismo será en caso Ok (Http.status=200)

{
    "status": "Informacion Recibida OK",
    "description": "La lista de precios será procesada"
}


En caso de Error: (Http.status=400)

{
    "status": "companyId is Required",
    "description": "Debe enviar el campo companyId"
}
{
    "status": "companyId is Invalid",
    "description": "Debe enviar el campo companyId valido"
}

Nota: La compañía enviada en el rest debe tener el modulo de precios habilitado para que el servicio se habilite


 

Propiedad

Tipo de dato

Descripción

companyIdAlfanuméricoCódigo de la compañía. Requerido
storeAlfanuméricoCódigo de la tienda de Promo. Requerido

sku

Alfanumérico

Código del producto. Requerido

salePrice

Numérico

Precio de venta. Requerido

costPrice

Numérico

Opcional. Precio de costo

saleCreditPrice

Numérico

Precio de crédito. Requerido

magnitudePrice

Numérico

Opcional. Precio por magnitud (kilo, litro, bulto, etc.)

measuredUnit
AlfanuméricoOpcional. unidad de medida

supplierItem

Alfanumérico

Opcional. Es el código del proveedor del ítem

supplierItemAmount

Numérico

Opcional. Es el monto que el proveedor reconoce (monto del recupero)
supplierFinancialAlfanuméricoOpcional. Es el código del proveedor financiero del ítem
supplierFinancialAmount

Numérico

Opcional. Es el monto que el proveedor Financiero reconoce (monto del recupero)
saleWholesalePriceNuméricoOpcional. Precio mayorista
saleWholesaleLimit

Numérico

Opcional. Cantidad a partir de la cual aplica el precio mayorista
limit

Numérico

Opcional.(límite de unidades que se podrán vender a ese precio)

enabledDateFechaFecha que indica a partir de cuando el precio es valido (FORMATO ISO 8601 (UTC)). Requerido
discountable
BooleanoOpcional. determina si el ítem se le puede aplicar descuento.(de omitir dicho campo por default será true)
manualDiscount
BooleanoOpcional. determina si el ítem se le puede aplicar descuento Manual .(de omitir dicho campo por default será true)



El proceso de importación de la lista cero, insertara/actualizara el producto en la lista cero de la tienda, en caso de tener el campo enable_date con una fecha futura, ese precio se habilitara en el momento que sea el enable_date.

El proceso de actualización de precios para una lista cero, lockea mientras se esta procesando la actualización, en caso inesperado error no contemplado y quede lockeado, hay un configuration data que determina el tiempo en minutos de espera de un lockeo de actualización que es el siguiente (luego de ese tiempo se podrá volver a correr el proceso para esa lista cero).

ConfigurationData.readAsInteger(companyId, "prices", "priceList.lockForUpate",15)

  

Servicios REST – Próximo numero de tarjeta

PROMO expone un servicio que permita consultar, para un determinado tipo de tarjeta cual es el próximo numero  de tarjeta inactivo y sin cliente asociado.

Para los ejemplos se realizaron las consultas de tarjetas utilizando la herramienta "PostMan" de Chrome. Deberá obtenerse un nuevo Tocken (cUrl), y luego podrá realizarse la consulta de próximo numero de tarjetas (PostMan). 
El único método aceptado para realizar este pedido es POST.

Como todo servicio rest de la consola, para realizar cualquier operación será necesario utilizar un token de acceso. El mismo debe incluirse en la cabecera http Authorization, por ej.

Authorization 
Bearer fb489bee-ff9f-4a4b-905c-28c6969ef180  No olvidar el Bearer(Espacio)

curl -v -X POST -u my-client: -d "grant_type=password" -d "username=sender" -d "password=mate"  -d "scope=read" http://localhost:8080/promo/oauth/token

El cuerpo del mensaje deberá ser un xml. A continuación se detallarán las posibles peticiones y sus respuestas involucradas.


Ejemplo de Consulta por proximo numero de Tarjeta
<promoCoreRequest>
 <operation>NextCardNumber</operation>
     <params>
        <type>nominada</type>
     </params>
</promoCoreRequest>


Respuesta - Se informa el próximo numero de tarjeta
<promoCoreResponse>
  <ack>0</ack>
  <message>
    <id>2345000000002</id>
  </message>
</promoCoreResponse>


Servicios REST – IMPORTACION DE CATALOGOS

PROMO expone este nuevo servicio para brindar una alternativa en la carga/recepción de catálogos que, hasta la presente versión, podía realizarse únicamente vía archivos.  Para comprender esta sección se recomienda referirse al manejo de catálogos en el manual del usuario.

El esquema de autenticación es el mismo que en los demás servicios REST presentados aquí (ver mas arriba).

Una vez obtenido el token de acceso, el servicio puede ser invocado utilizando el método POST, desde la URL: <promo>/api/rest/catalogs


El formato general del request es:

{
 "companyId": "myCompanyId",
"catalog":"CatalogId",
"params":[      
{"param1":"param1value",
"paramN":"paramNvalue"}
],
"items": [
{.... primer item .......},
{.... otro item .......},
{.... otro item .......},
{.... otro item .......},
{.... otro item .......},
]
}


donde

CampoDescripciónTipo de Dato

companyId

  • código de Empresa
alfanumérico. Requerido

catalog

identificador del catálogoalfanumérico. Requerido
paramsParámetros que dependerán del catálogo

Listado de objetos de tipo clave, valor. Cada catalogo puede tener sus parámetros específicos, pero como valor genérico tenemos:

  • "deleteAllCollectionFirst" : "true"   Indica que antes de realizar la importación de este conjunto de registros se realice el borrado de todos los registros existentes.
    NOTA: (desde 6.5.5)
    Ejemplo: 

[...]

  "params": [
        { "deleteAllCollectionFirst": "true" }
    ],


[...]

Importante

No aplica a tarjetas de fidelidad y asignación de convenios.




itemsRegistros a importarColección de objetos dependientes de cada catálogo. Requerido


Cada uno de los ítems dependerá del catalogo en su formato, pero existe un campo común a todos:

CampoDescripciónTipo de Dato

operation

La operación a realizar sobre el elemento. Los valores posibles son:

  • I: Insertar
  • U: Actualizar
  • R: Eliminar
  • IU: (desde 6.5.5) Insertar/Actualizar: Si el registro no existe será insertado (I), si existe será actualizado (U).

    Importante

    No aplica a tarjetas de fidelidad y asignación de convenios.

    Requerido

Alfanumérico


La respuesta será del tipo:

{
    "status": "200",
    "description": "CatalogCountry",
    "detail": {
        "result": "ok",
        "detail": "Info adicional"
    }
}


donde:

CampoDescripciónTipo de DatoPosibles valores

status

código de Respuesta

alfanumérico200 (válido), 400 (errores de validación o de sintaxis json), 500 (error genérico)

description

identificador del catálogoalfanuméricoCada uno de los nombre de los catálogos importables por mensaje rest, o bien cadena vacía si no es posible obtenerlos (por ej. ante un error de sintaxis json).
detailInformación adicionalObjeto

Clave result, con los resultados posibles, es decir, ok o error.

Clave detail, con valor correspondiente al mensaje informativo de validación, error, o procesamiento válido.

Consideraciones

    1.  El número de registros por paquete (request) estará limitado a 1000 ítems para no afectar la performance y que las respuestas puedan ser procesadas.
    2.  En caso de error se informaran los registros erróneos pero los que han resultado correctos serán incorporados. Los resultados podrán visualizarse en la consola en la pantalla de Monitor de Importación.
    3.  En todos los casos se informara la cantidad total de líneas con error y las correctas. Los resultados podrán visualizarse en la consola en la pantalla de Monitor de Importación.
    4.  El proceso utiliza semáforos para evitar la concurrencia de clientes que pretendan procesar en paralelo ya que implica posibilidad de errores en las validaciones.


Los catálogos a importar son:


Para la importación de Marcas por medio del servicio REST, deberá considerarse el siguiente formato general:

Input
{
   "companyId":"napse",
   "catalog":"catalogBrand", 
   "params": [],
    "items": [
        {
            "codeType": "1",
            "name": "Nintendo",
            "operation": "I"

        },
        {
            "codeType": "2",
            "name": "Electronic Arts",
            "operation": "I"

        },
        {
            "codeType": "3",
            "name": "Activision Inc.",
            "operation": "I"

        }
          ]


}
output
{
    "status": "200",
    "description": "catalogBrand",
    "detail": {
        "result": "ok",
        "detail": "Se generó con éxito el registro de importación. Puede ver su estado correspondiente en el monitor de importación."
    }
}

Para la importación de Categoría por medio del servicio REST, deberá considerarse el siguiente formato general:

input
{
   "companyId":"napse",
   "catalog":"catalogCategory", 
   "params": [],
    "items": [
        {
            "code": "PS3G",
            "name": "PS3 Videogames",
            "familyCode": "VGCo",
            "operation": "I"

        },
        {
            "code": "AlmaCar",
            "name": "Caramelos",
            "familyCode": "AlmaDu",
            "operation": "I"

        },
        {
            "codeType": "AlmaCon",
            "name": "Confites",
            "familyCode": "AlmaDu",
            "operation": "I"

        }
          ]


}
output
{
    "status": "200",
    "description": "catalogCategory",
    "detail": {
        "result": "ok",
        "detail": "Se generó con éxito el registro de importación. Puede ver su estado correspondiente en el monitor de importación."
    }
}

Un cliente está conformado por los siguientes datos:

 Sexo (gender), Tipo de Identificación (identificationType), Tipo de Cliente (customerType), País (addressCountry), Provincia(addressState), y Ciudad (addressCity), corresponden al código de cada uno de ellos y deberán importarse previamente antes de realizar cualquier operación sobre un cliente. En el caso particular de Country, State, y City, deberán importarse en ese orden debido a que se validará que una provincia/estado esté dentro de un país, y que una ciudad esté dentro de una provincia.)


CampoTipo de datoObservaciones
codestringCorresponde al código que se le asignara al cliente en Promo. (requerido)
namestringNombre de cliente. (requerido)
lastNamestringApellido del cliente. (requerido)
genderstringGenero del cliente (en caso de "Validar catálogos relacionados al catálogo de clientes" este en "true", el dato definido en este campo deberá coincidir con alguno de los códigos de género "catalogGender" previamente cargados.) Opcional
birthDatestringFecha de nacimiento del cliente. Formato: año-mes-día siendo el año de cuatro dígitos, y el mes y el día de dos dígitos
identificationTypestringTipo de identificación del cliente. (en caso de "Validar catálogos relacionados al catálogo de clientes" este en "true", el dato definido en este campo deberá coincidir con alguno de los códigos de tipo de identificación "catalogIdType" previamente cargados.) Opcional
identifierstringNumero de identificación del cliente. (requerido)
identificationExpirationstringFecha de expiración de la identificación del cliente. Opcional
nacionalitystringNacionalidad del cliente. Opcional
emailstringe-Mail del cliente. Opcional
customerTypestringTipo de cliente (requerido) / / (en caso de "Validar catálogos relacionados al catálogo de clientes" este en "true", el dato definido en este campo deberá coincidir con alguno de los códigos de tipo cliente "catalogIdType" previamente cargados.)
addressstringDirección del cliente. Opcional
addressCountrystringPaís del cliente. (en caso de "Validar catálogos relacionados al catálogo de clientes" este en "true", el dato definido en este campo deberá coincidir con alguno de los códigos de Pais "catalogCoutry" previamente cargados.). Opcional
addressStatestringProvincia de residencia del cliente. (en caso de "Validar catálogos relacionados al catálogo de clientes" este en "true", el dato definido en este campo deberá coincidir con alguno de los códigos de Provincia "catalogState" previamente cargados.). Opcional
addressCitystringCiudad de residencia del cliente. (en caso de "Validar catálogos relacionados al catálogo de clientes" este en "true", el dato definido en este campo deberá coincidir con alguno de los códigos de Ciudad "catalogCity" previamente cargados.). Opcional
addressPostalCodestringCódigo Postal. Opcional
phonestringTeléfono. Opcional
isActivebooleanoIndicara si al momento del alta el cliente estará Activo o Inactivo. Deberá definirse como true o false. Requerido
segmentsstringSegmento/s asociado al cliente. Opcional


{
    "companyId": "napse",
    "catalog": "catalogCustomer",
    "params": [],
    "items": [{
        "operation": "I",
                "code":"949450",
                "name":"John",
                "lastName":"Promo",
                "gender":"2",
                "birthDate":"03-05-1959",
                "identificationType":"01",
                "identifier":"4688779900",
                "identificationExpiration":"31-12-2030",
                "nacionality":"Arg",
                "email":"[email protected]",
                "customerType":"111",
                "address":"Av.Livertad 123",
                "addressCountry":"100",
                "addressState":"200",
                "addressCity":"300",
                "addressPostalCode":"9999",
                "phone":"457896203",
                "isActive":"true",
                "segments":"4650"
    }]
}



Cuando desde la consola se indique que deben de Validar catálogos relacionados al catálogo de clientes, será requerida la carga de los catálogos relacionados previo a la carga del catalogo de cliente.

Se importan entonces las entidades relacionadas previo a la importación de los clientes.

Catálogo IDTYPE. Este catálogo define los tipos de documento o identificación válidos. 

{
    "companyId": "{{COMPANYID}}",
    "catalog": "CatalogIdType",
    "params": [],
    "items": [
        {
            "code": "dni",
            "description": "Documento de identidad",
            "operation": "I"
        },
        {
            "code": "le",
            "description": "Libreta de enrolamiento",
            "operation": "I"
        }
    ]
}


Catálogo GENDER. Este catálogo define los tipos de género válidos.

{
    "companyId": "{{COMPANYID}}",
    "catalog": "CatalogGender",
    "params": [],
    "items": [
        {
            "code": "M",
            "description": "Male",
            "operation": "I"
        },
        {
            "code": "F",
            "description": "Female",
            "operation": "I"
        }
    ]
}



Catálogo CUSTOMERTYPE. Este catálogo define los tipos de clientes válidos

{
    "companyId": "{{COMPANYID}}",
    "catalog": "CatalogCustomerType",
    "params": [],
    "items": [
        {
            "code": "vip",
            "description": "Cliente vip",
            "operation": "I"
        },
        {
            "code": "gold",
            "description": "Cliente gold",
            "operation": "I"
        },
        {
            "code": "silver",
            "description": "Cliente silver",
            "operation": "I"
        }
    ]
}



Catálogo COUNTRY. Este catálogo define los países válidos.

{
    "companyId": "{{COMPANYID}}",
    "catalog": "CatalogCountry",
    "params": [],
    "items": [
        {
            "code": "ar",
            "description": "Argentina",
            "operation": "I"
        },
        {
            "code": "it",
            "description": "Italia",
            "operation": "I"
        },
        {
            "code": "es",
            "description": "España",
            "operation": "I"
        }
    ]
}



Catálogo STATE. Este catálogo define las provincias válidas.

{
    "companyId": "{{COMPANYID}}",
    "catalog": "CatalogState",
    "params": [],
    "items": [
        {
            "code": "bsas",
            "description": "Buenos Aires",
            "country": "ar",
            "operation": "I"
        },
        {
            "code": "cor",
            "description": "Córdoba",
            "country": "ar",
            "operation": "I"
        }
    ]
}



Catálogo CITY. Este catálogo define las ciudades válidas

{
    "companyId": "{{COMPANYID}}",
    "catalog": "CatalogCity",
    "params": [],
    "items": [
        {
            "code": "tig",
            "description": "Tigre",
            "state": "bsas",
            "operation": "I"
        },
        {
            "code": "lm",
            "description": "Los molinos",
            "state": "cor",
            "operation": "I"
        },
        {
            "code": "sidr",
            "description": "San isidro",
            "state": "bsas",
            "operation": "I"
        }
    ]
}


Importación de nuevos clientes.

Una vez realizadas las importaciones anteriores, y considerando sus códigos, se pueden realizar altas, modificaciones, y eliminaciones de clientes.

Por ej. en este caso se dan de alta dos clientes:

{
    "companyId": "{{COMPANYID}}",
    "catalog": "CatalogCustomer",
    "params": [],
    "items": [
        {
            "code": "cod1",
            "name": "Alberto",
            "lastName": "Pérez",
            "gender": "M",
            "birthDate": "1950-01-01",
            "identificationType": "le",
            "identifier": "11112222",
            "identificationExpiration": "2050-01-01",
            "nacionality": "argentino",
            "email": "[email protected]",
            "customerType": "vip",
            "address": "diagonal 12 2233",
            "addressCountry": "ar",
            "addressState": "bsas",
            "addressCity": "tig",
            "addressPostalCode": "2222",
            "phone": "11111111",
            "isActive": "true",
            "operation": "I"
        },
        {
            "code": "cod2",
            "name": "Ángela",
            "lastName": "Gonzales",
            "gender": "F",
            "birthDate": "1960-01-01",
            "identificationType": "dni",
            "identifier": "99998888",
            "identificationExpiration": "2050-01-01",
            "nacionality": "argentina",
            "email": "[email protected]",
            "customerType": "gold",
            "address": "diagonal 50 2211",
            "addressCountry": "ar",
            "addressState": "cor",
            "addressCity": "lm",
            "addressPostalCode": "5050",
            "phone": "55555555",
            "isActive": "true",
            "operation": "I"
        }
    ]
}


Eliminación y actualización de clientes.

En el siguiente ejemplo, se elimina el primer cliente (campo operation en R) y se actualiza el segundo cliente (campo operation en U) cambiando el email y el teléfono

{
    "companyId": "{{COMPANYID}}",
    "catalog": "CatalogCustomer",
    "params": [],
    "items": [
        {
            "code": "cod1",
            "name": "Alberto",
            "lastName": "Pérez",
            "gender": "M",
            "birthDate": "1950-01-01",
            "identificationType": "le",
            "identifier": "11112222",
            "identificationExpiration": "2050-01-01",
            "nacionality": "argentino",
            "email": "[email protected]",
            "customerType": "vip",
            "address": "diagonal 12 2233",
            "addressCountry": "ar",
            "addressState": "bsas",
            "addressCity": "tig",
            "addressPostalCode": "2222",
            "phone": "11111111",
            "isActive": "true",
            "operation": "R"
        },
        {
            "code": "cod2",
            "name": "Ángela",
            "lastName": "Gonzales",
            "gender": "F",
            "birthDate": "1960-01-01",
            "identificationType": "dni",
            "identifier": "99998888",
            "identificationExpiration": "2050-01-01",
            "nacionality": "argentina",
            "email": "[email protected]",
            "customerType": "gold",
            "address": "diagonal 50 2211",
            "addressCountry": "ar",
            "addressState": "cor",
            "addressCity": "lm",
            "addressPostalCode": "5050",
            "phone": "90909090",
            "isActive": "true",
            "operation": "U"
        }
    ]
}



Para la importación de Departamentos por medio del servicio REST, deberá considerarse el siguiente formato general:

input
{
   "companyId":"napse",
   "catalog":"catalogDepartment", 
   "params": [],
    "items": [
        {
            "code": "Elec",
            "name": "Electronics",
            "operation": "I"

        },
        {
            "code": "Pack",
            "name": "Pack",
            "operation": "I"

        },
        {
            "code": "Alma",
            "name": "Almacén",
            "operation": "I"

        }
          ]


}
output
{
    "status": "200",
    "description": "catalogDepartment",
    "detail": {
        "result": "ok",
        "detail": "Se generó con éxito el registro de importación. Puede ver su estado correspondiente en el monitor de importación."
    }
}

Para la importación de Tipos de Transacción por medio del servicio REST, deberá considerarse el siguiente formato general:

input
{
   "companyId":"napse",
   "catalog":"catalogEventTransactionType", 
   "params": [],
    "items": [
        {
            "code": "BIG",
            "name": "BIG TICKET",
            "operation": "I"

        },
        {
            "code": "VEM",
            "name": "VENTA EMPLEADO",
            "operation": "I"

        },
        {
            "code": "REG",
            "name": "MESA DE REGALOS",
            "operation": "I"

        }
          ]


}

output
{
    "status": "200",
    "description": "catalogEventTransactionType",
    "detail": {
        "result": "ok",
        "detail": "Se generó con éxito el registro de importación. Puede ver su estado correspondiente en el monitor de importación."
    }
}

Para la importación de Familia por medio del servicio REST, deberá considerarse el siguiente formato general:

Input
{
   "companyId":"napse",
   "catalog":"catalogFamily", 
   "params": [],
    "items": [
        {
            "code": "Prin",
            "name": "Printers",
            "operation": "I"

        },
        {
            "code": "Lapt",
            "name": "Laptops",
            "operation": "I"

        },
        {
            "code": "DVDP",
            "name": "DVD Players",
            "operation": "I"

        }
          ]


}
output
{
    "status": "200",
    "description": "catalogFamily",
    "detail": {
        "result": "ok",
        "detail": "Se generó con éxito el registro de importación. Puede ver su estado correspondiente en el monitor de importación."
    }
}

Para la importación de Ítem por medio del servicio REST, deberá considerarse el siguiente formato general:

input
{
   "companyId":"napse",
   "catalog":"catalogItem", 
   "params": [],
    "items": [
        {
            "code": "111",
            "name": "PlayStation 4",
            "uniteprice": "1000.00",
            "level1": "Gen",
            "level2": "Cat11",
            "level3": "SubCat11",
            "level4": "1",
            "supplier": "1",
            "brand": "Consola Sony Play Station 4 Ps4 1206 500 Gb",
            "detail": "Modelo: Playstation 4 1206&nbsp",
            "detail2": "Incluye cable de alimentaci&oacute",
            "operation": "I"

        },
        {
            "code": "112",
            "name": "XBOX One",
            "uniteprice": "9900.00",
            "level1": "Gen",
            "level2": "Cat11,
            "level3": "SubCat12",
            "level4": "1",
            "supplier": "1",
            "brand": "Xbox One X 1tb, 4k", 
            "detail": "XBOX One X cuenta con reproductor 4K HDR, y te permite grabar y transmitir tus partidas en 4K 60 FPS a través de Mixer",
            "detail2": "Disfruta de tus películas favoritas gracias al reproductor Blu-ray 4K Ultra HD o disfruta de apps como NetFlix.",
            "operation": "I"

        },
        {
            "code": "113",
            "name": "Nintendo Switch",
            "uniteprice": "13300.00",
            "level1": "Gen",
            "level2": "Cat11",
            "level3": "SubCat13",
            "level4": "1",
            "supplier": "1",
            "brand": "Consola Nintendo Switch 32gb Neon",      
            "detail": "La consola Nintendo Switch está diseñada para acompañarte dondequiera que vayas, transformándose de consola para el hogar a consola portátil en un instante.",
            "detail2": "Memoria Interna 32GB de memoria NAND",
            "operation": "I"

        }
          ]


}
output
{
    "status": "200",
    "description": "catalogItem",
    "detail": {
        "result": "ok",
        "detail": "Se generó con éxito el registro de importación. Puede ver su estado correspondiente en el monitor de importación."
    }
}

Para la importación de Bancos por medio del servicio REST, deberá considerarse el siguiente formato general:

Input
{
   "companyId":"napse",
   "catalog":"catalogPaymentBank", 
   "params": [],
    "items": [
        {
            "code": "BAN",
            "name": "BANAMEX",
            "operation": "I"

        },
        {
            "code": "SAN",
            "name": "SANTANDER",
            "operation": "I"

        },
        {
            "code": "BCO",
            "name": "BANCOMER",
            "operation": "I"

        }
          ]


}
Output
{
    "status": "200",
    "description": "catalogPaymentBank",
    "detail": {
        "result": "ok",
        "detail": "Se generó con éxito el registro de importación. Puede ver su estado correspondiente en el monitor de importación."
    }
}

Para la importación de Tipos de Pago por medio del servicio REST, deberá considerarse el siguiente formato general:

Input
{
   "companyId":"napse",
   "catalog":"CatalogPaymentCode", 
   "params": [],
    "items": [
        {
            "code": "11",
            "name": "Mercado Pago",
            "operation": "I"

        },
        {
            "code": "12",
            "name": "AMERICAN EXPRESS",
            "operation": "I"

        },
        {
            "code": "13",
            "name": "BANAMEX",
            "operation": "I"

        }
          ]


}
Output
{
    "status": "200",
    "description": "CatalogPaymentCode",
    "detail": {
        "result": "ok",
        "detail": "Se generó con éxito el registro de importación. Puede ver su estado correspondiente en el monitor de importación."
    }
}

Para la importación de Prefijo por medio del servicio REST, deberá considerarse el siguiente formato general:

{
    "companyId": "napse",
    "catalog": "catalogPaymentPrefix",
    "params": [],
    "items": [
        {
            "code": "10",
            "name": "Pref A",
            "operation": "I"
        },
        {             
            "code": "11",
            "name": "Pref B",
            "operation": "I"         
        },
        {            
            "code": "12",
            "name": "Pref C",
            "operation": "I"         }
    ]
}


output
{
    "status": "200",
    "description": "catalogPaymentPrefix",
    "detail": {
        "result": "ok",
        "detail": "Se generó con éxito el registro de importación. Puede ver su estado correspondiente en el monitor de importación."
    }
}

Para la importación de Tipo de Pago por medio del servicio REST, deberá considerarse el siguiente formato general:

input
{
    "companyId": "napse",
    "catalog": "catalogPaymentType",
    "params": [],
    "items": [
        {
            "code": "EVO",
            "name": "EFECTIVO",
            "operation": "I"
        },
        {             
            "code": "TAR",
            "name": "TARJETA DE CREDITO",
            "operation": "I"         
        },
        {            
            "code": "CHE",
            "name": "CHEQUE",
            "operation": "I"         }
    ]
}
Output
{
    "status": "200",
    "description": "catalogPaymentType",
    "detail": {
        "result": "ok",
        "detail": "Se generó con éxito el registro de importación. Puede ver su estado correspondiente en el monitor de importación."
    }
}

Para la importación de Subcategoría por medio del servicio REST, deberá considerarse el siguiente formato general:

input
{
   "companyId":"napse",
   "catalog":"catalogSubCategory", 
   "params": [],
    "items": [
        {
            "code": "AlmaDes",
            "name": "Descafeinado",
            "categoryCode": "AlmaCaf",
            "operation": "I"

        },
        {
            "codeType": "AlmaIns",
            "name": "Instantaneo",
            "categoryCode": "AlmaCaf",
            "operation": "I"

        },
        {
            "codeType": "AlmaCap",
            "name": "En cápsulas",
            "categoryCode": "AlmaCaf",
            "operation": "I"

        }
          ]


}
outupt
{
    "status": "200",
    "description": "catalogSubCategory",
    "detail": {
        "result": "ok",
        "detail": "Se generó con éxito el registro de importación. Puede ver su estado correspondiente en el monitor de importación."
    }
}

Para la importación de Proveedor por medio del servicio REST, deberá considerarse el siguiente formato general:

Input
{
    "companyId": "napse",
    "catalog": "catalogSupplier",
    "params": [],
    "items": [
        {
            "code": "PR1",
            "name": "SONY",
            "operation": "I"
        },
        {             
            "code": "PR2",
            "name": "APPLE",
            "operation": "I"         
        },
        {            
            "code": "PR3",
            "name": "LACTEOS PREMIUM",
            "operation": "I"         
        }
    ]
}
input
{
    "status": "200",
    "description": "catalogSupplier",
    "detail": {
        "result": "ok",
        "detail": "Se generó con éxito el registro de importación. Puede ver su estado correspondiente en el monitor de importación."
    }
}

Para la importación de Moneda por medio del servicio REST, deberá considerarse el siguiente formato general:

imput
{
    "companyId": "napse",
    "catalog": "catalogCurrencyCode",
    "params": [],
    "items": [
        {
            "code": "1",
            "description": "Peso Argentino",
            "operation": "I"
        },
        {
            "code": "2",
            "description": "Dólar",
            "operation": "I"
        },
        {
            "code": "3",
            "description": "Euro",
            "operation": "I"
        }
    ]
}
output
{
    "status": "200",
    "description": "catalogCurrencyCode",
    "detail": {
        "result": "ok",
        "detail": "Se generó con éxito el registro de importación. Puede ver su estado correspondiente en el monitor de importación."
    }
}

Para la importación de Canje de puntos por catalogo por medio del servicio REST, deberá considerarse el siguiente formato general:

input
{
    "companyId": "napse",
    "catalog": "catalogRedeemBenefit",
    "params": [],
    "items": [
        {
            "store": "b320"
            "code": "1000",
            "points": "100",
            "discountValue": "10"
            "discountType": "perc"
            "operation": "I"
        },
        {            
            "store": "b320"
            "code": "2000",
            "points": "60",
            "discountValue": "27"
            "discountType": "fix"
            "operation": "I"         
        }
    ]
}
input
{
    "status": "200",
    "description": "catalogRedeemBenefit",
    "detail": {
        "result": "ok",
        "detail": "Se generó con éxito el registro de importación. Puede ver su estado correspondiente en el monitor de importación."
    }
}

Asignación de una tarjeta a un cliente, un convenio, y su monto.

Esta operación realiza la asignación de tarjeta, cliente, convenio, y monto. Debe existir previamente la tarjeta (activa o inactiva), un convenio activo, y el cliente, en caso de no existir, se da de alta. En relación al monto, se le puede asignar o no un operador adelante del monto; especificando el operador + suma un valor al monto que la tarjeta tiene; especificando el operador - resta saldo al monto que la tarjeta tiene; si no se pone operador reemplaza el monto que la tarjeta tiene (ver más abajo el ejemplo del campo amount).

 (Ver proceso actual de asignación de convenios).  En este caso los campos serán:

{
    "companyId": "napse",
    "catalog": "CatalogCardAssign",
    "params": [
        {
            "cardType": "tipo1"
        },
        {
            "contract": "convenio1"
        }
    ],
    "items": [
        {
            "operation": "I",
            "id": "1111000000030",
            "customer": "codCliente1",
            "amount": "90.37",
            "name": "Juan",
            "surname": "Perez",
            "gender": "hom",
            "birthDate": "19900506",
            "idType": "dni",
            "identifier": "33334444",
            "idDate": "21001005",
            "nacionality": "Argentina",
            "email": "[email protected]",
            "customerType": "gold",
            "address": "Urquiza 20",
            "country": "ar",
            "state": "bsas",
            "city": "tig",
            "postalCode": "7669",
            "phone": "2222-4444"
        }
	,{otro item.......}
	,{otro item.......}
	,{otro item.......}
	,{otro item.......}
	,{otro item.......}
	,{otro item.......}
    ]
}
CampoDescripción
params

cardType: Tipo de tarjeta a importar que será validado. Requerido

contract: código de convenio al que pertenecen estas tarjetas/clientes. Requerido

operation

I: Inserción / U: Actualización / R: Eliminación. Requerido

id

    • La tarjeta debe existir.
    • Requerido

customer

    • Si viene informado el cliente y en la DB la tarjeta no tiene un cliente asociado, se verificara si el cliente informado existe en la DB, y de ser así, se actualizara el campo con el valor informado en el archivo. Si el cliente informado, no existe en la DB, se dará de alta con los datos correspondientes al cliente (ver name inclusive en adelante).
    • Si viene informado el cliente, y en la DB la tarjeta tiene asociado el mismo cliente, queda el campo como esta.
    • Si viene informado el cliente, y en la DB la tarjeta tiene asociado otro cliente, informara en el detalle de errores que la tarjeta tiene asociado otro cliente en la DB, y no permitirá procesar ese registro.
    • Si no viene informado el cliente, informara un mensaje indicando que el campo cliente es mandatorio, y no permitirá procesar ese registro.
    • Requerido

amount

    • Numérico con decimales (string). Requerido.
    • Si se agrega un operador a la izquierda del monto, el mismo suma o resta al monto actual de la tarjeta. Para reemplazar el monto, no debe especificarse un operador.
    • Ejemplo, con tarjeta con 100 de monto:
      • +100 resulta en monto de 200.
      •  -60   resulta en monto de 40.
      •   70   resulta en monto de 70.

name

Nombre del Cliente. Cadena libre. Requerido

surname

Apellido. Cadena libre. Requerido

gender

Género. (ver valores por catálogo). Depende de los valores cargados en el catálogo a tal fin. No Requerido

birthDate

Fecha de nacimiento. Cadena en formato "yyyyMMdd".  Más Información del formato. No Requerido

idType

Tipo de identificación (ver valores por catálogo). Depende de los valores cargados en el catálogo a tal fin. Requerido

identifier

Numero de Identificación del Cliente. Requerido

idDate

Fecha de Expiración de la identificación.  Cadena en formato "yyyyMMdd".  Más Información del formato. No requerido

nacionality

Nacionalidad.  Cadena Libre. No requerido

email

Direccion de correo electrónico. Cadena libre. No requerido

customerType

Tipo de Cliente (ver valores por catálogo). Depende de los valores cargados en el catálogo a tal fin. No requerido

address

Dirección. Cadena libre. No requerido

country

País. (ver valores por catálogo). Depende de los valores cargados en el catálogo a tal fin. No requerido

state

Estado/Provincia (ver valores por Catálogo). Depende de los valores cargados en el catálogo a tal fin. No requerido

city

Ciudad (ver valores por catálogo). Depende de los valores cargados en el catálogo a tal fin. No requerido

postalCode

Código Postal. No requerido

phone

Teléfono. No requerido


Servicios REST – IMPORTACION DE SEGMENTOS

(v6.5.25 / 7.0.14) Sincrónico

Servicio Rest que opera de forma sincrónica para administrar clientes asociados a segmentos.

Una vez obtenido el token de acceso, el servicio puede ser invocado utilizando el método POST, desde la URL: <promo>/api/rest/segments

El formato general de solicitud es:

{
 "companyId": "myCompanyId",
"params":[      
	{"param1":"param1value", "paramN":"paramNvalue", ...}
],
"items": [
{.... primer item .......},
{.... otro item .......},
{.... otro item .......},
{.... otro item .......},
{.... otro item .......},
]
}

donde

CampoDescripciónTipo de Dato

companyId

  • código de Empresa
alfanumérico. Requerido
paramsParámetros extra

Listado de objetos de tipo clave, valor. Cada catalogo puede tener sus parámetros específicos, pero como valor genérico tenemos:

  • "deleteAllCollectionFirst" : "true"  
    Indica que antes de realizar la importacion de este conjunto de registros se realice el borrado de todos los registros existentes. 
  • "segmentCode": "mySegmentCode"                  
    Indica el código de segmento al cual se asocian estos "ítems".  En caso de no existir el segmento, será creado automáticamente. Es un campo requerido,  alfanumérico  y sin limitaciones de longitud.
itemsRegistros a importarColección de objetos dependientes de cada catálogo


El formato de los ítems es el siguiente:

  
CampoDescripción
operationOperación que se intenta realizar sobre el registro: "I" Insertar, "R" remover, "IU" insertar/actualizar
customerCódigo del cliente que se quiere asociar/remover respecto al segmento informado en segmentcode



Ejemplo de Envío de registro.  En este caso se envían para el segmento "ts02c", 10 registros que son 2 remociones (R), 1 Actualización/inserción (IU) y 7 Inserciones (I)


{
    "companyId": "napse",
    "params": [
        {"segmentCode": "ts02c", "deleteAllCollectionFirst":"false"}
    ],
    "items": [
        { "operation": "R", "customer": "c1" },
        { "operation": "IU", "customer": "c2" },
        { "operation": "R", "customer": "c3" },
        { "operation": "I", "customer": "c4" },
        { "operation": "I", "customer": "c5" },
        { "operation": "I", "customer": "c6" },
        { "operation": "I", "customer": "c7" },
        { "operation": "I", "customer": "c8" },
        { "operation": "I", "customer": "c9" },
        { "operation": "I", "customer": "c0" }    
    ]
}




El formato general de  respuesta es:

{
    "status": 200,
    "description": "customerSegment",
    "detail": {
        "result": "ok",
        "detail": "",
        "updated": 0,
        "ignored": 0,
        "inserted": 0,
        "removed": 0,
        "errors": 0,
        "processed": 0,
        "errorDetails": [
            {
                "rec": 1,
                "customer": "mycustomer",
                "msg": "my error message"
            },
            ...
        ]
    }
}

donde

CampoDescripciónTipo de Dato

status

  • código de respuesta
200 indica que ha sido procesada correctamente.
description

Descripción general indicando que se trata

de customerSegment.


detailDetalle del proceso
detail.resultResultado general del procesook indicando proceso realizado
detail.detailMensaje detallado respecto al procesovacío en el caso de ok
detail.updatedcantidad de ítems actualizados
detail.ignoredcantidad de ítems ignorados
detail.insertedcantidad de ítems agregados
detail.removedcantidad de ítems removidos
detail.errorscantidad de ítems erróneos
detail.processedcantidad de ítems procesados
errorDetailsDetalle de cada registro con error.

rec: numero de registro en la solicitud

customer: código de cliente correspondiente

msg: mensaje informativo del error.


Ejemplo de respuesta.  Aquí se observa status 200 indicando que se ha procesado el request, donde en este caso se han actualizado 1 registro, existen 9 errores sobre un total de 10 registros procesados.  Por otra parte errorDetails nos indica cada uno de los 9 que han tenido error.


{
    "status": 200,
    "description": "customerSegment",
    "detail": {
        "result": "ok",
        "detail": "",
        "updated": 1,
        "ignored": 0,
        "inserted": 0,
        "removed": 0,
        "errors": 9,
        "processed": 10,
        "errorDetails": [
            {
                "rec": 1,
                "customer": "c1",
                "msg": "not found"
            },
            {
                "rec": 3,
                "customer": "c3",
                "msg": "not found"
            },
            {
                "rec": 4,
                "customer": "c4",
                "msg": "already exists"
            },
            {
                "rec": 5,
                "customer": "c5",
                "msg": "already exists"
            },
            {
                "rec": 6,
                "customer": "c6",
                "msg": "already exists"
            },
            {
                "rec": 7,
                "customer": "c7",
                "msg": "already exists"
            },
            {
                "rec": 8,
                "customer": "c8",
                "msg": "already exists"
            },
            {
                "rec": 9,
                "customer": "c9",
                "msg": "already exists"
            },
            {
                "rec": 10,
                "customer": "c0",
                "msg": "already exists"
            }
        ]
    }
}







Consejos prácticos

Interacción con el Motor de Promociones


Si bien el motor de promociones puede ser utilizado de muchas formas, se recomienda realizar un envío único que contenga todos los elementos de la transacción, solicitando en su encabezado la apertura de una nueva sesión, la evaluación del ticket enviado y que envíe una respuesta para esa evaluación.
Esto permitirá un uso más eficiente de los recursos, tanto de procesamiento y memoria, como de canal de comunicaciones.
Si por algún motivo (limitaciones técnicas, estándares, etc.) no pudiese realizarse el envío de un único mensaje, como segunda opción es posible el envío de los elementos en más de un mensaje (pudiendo utilizar hasta un mensaje por cada elemento a agregar), pidiendo la apertura de una nueva sesión en el primer mensaje de envío correspondiente a la transacción, y solicitando la evaluación del ticket al final de la misma. Para asegurarse del envío exitoso de cada elemento es posible solicitar un mensaje de confirmación (utilizando response en el encabezado), pero sin pedir la evaluación.
Esta última forma de interactuar es algo menos eficiente que la anterior, dado que requiere un mayor tiempo de utilización del canal de comunicaciones y de la memoria donde se encuentre funcionando el Motor de Promociones.
También podría expirar la sesión abierta en el Motor, obligando a un reenvío del ticket como se indica en ". Envío de mensaje único
Como se menciona anteriormente, la política de envío recomendada es la de utilizar un único mensaje que contenga todos los ítems. A continuación se presenta una enumeración paso a paso del envío y evaluación en único mensaje.

  1. Crear un mensaje único que contenga
    1. el encabezado
      1. Configurar que se espera respuesta (utilizando el atributo response).
      2. Configurar que el Motor debe calcular las promociones (utilizando el atributo evaluate).
      3. Configurar si se inicia un nuevo ticket (borrar el contexto asociado a la sesión, utilizando el atributo init-tck)
    2. el cuerpo
      1. todos los artículos de la transacción, según el formato establecido.
      2. todos los eventos de la transacción, según el formato establecido.
      3. todos los clientes de la transacción, según el formato establecido.
      4. todos los medio de pago de la transacción, según el formato establecido.
      5. todos los cupones de la transacción, según el formato establecido.
  2. Enviar el mensaje utilizando el protocolo de comunicación correspondiente.
  3. Recibir la respuesta a la petición realizada. Dicha respuesta poseerá todas las promociones con sus respectivos beneficios, tal como se describe en "Engine Response". En caso de que el atributo ack del encabezado de respuesta sea distinto a 0, dirigirse a Valores del Atributo "ACK" y realizar la acción recomendada.


Manejo de sesiones


Como se mencionó con anterioridad, el Motor de Promociones es capaz de manejar múltiples sesiones, lo cual le permite atender diversas transacciones paralelamente. Cada sesión utiliza una cierta cantidad de memoria física del computador, por lo cuál no sería conveniente la creación de muchas sesiones excepto que el Motor esté atendiendo varios terminales y esté funcionando en un computador con las prestaciones adecuadas (ver Manual de instalación).
De esta forma, en caso de estar interactuando una sola terminal continuamente con el motor sería conveniente utilizar siempre la misma sesión y cada vez que se requiere borrar todo contenido de la sesión hacerlo por medio del atributo init-tck del encabezado.
Por otro lado, y debido a la naturaleza humana de la interacción del ingreso de artículos al punto de venta, si se está enviando el ticket al Motor de Promociones en varios mensajes puede que pase el tiempo de expiración de sesión. Como se describe en "Sesiones", de suceder esto el Motor de Promociones eliminará la sesión junto con todos los elementos que contenga y ante un requerimiento de la terminal donde se realiza la transacción informará que la sesión de esa transacción espiró (utilizando el atributo ack del encabezado del mensaje de respuesta). En estos casos debe recordarse abrir una nueva sesión utilizando atributo init-tck del encabezado envíos y reenviar todos los elementos que se habían ingresado hasta el momento. Luego será posible continuar con el funcionamiento normal.

Implementación de ítems aplicados


En esta sección se darán algunos lineamientos útiles a tener en cuenta al momento de interpretar los ítems aplicados dependiendo del beneficio al que pertenezcan.

Ítems aplicados en beneficios monetarios


Los artículos aplicados por un beneficio monetario son los artículos sobre los cuales debe realizarse el descuento informado por el Motor de Promociones. De esta forma, la implementación más simple es la de descontar en forma directa el monto informado por el atributo value al ítem informado por seq. El atributo qty de cada elemento indicará la cantidad total a descontar, por lo que será necesario distribuir (a criterio del implementador) el monto asignado a value entre la cantidad de ítems informada en qty. En caso de informarse una magnitud (atributo magnitude), el monto se descontará a dicha magnitud.

Ítems aplicados en beneficios no monetarios


Para el caso particular de los beneficios no monetarios, los artículos aplicados de éstos podrán ser interpretados como lo considere conveniente quien sea encargado de la integración entre el punto de venta y el Motor de Promociones. Por ejemplo, los artículos aplicados de un beneficio de plan de pagos (PaymentPlanBenefit) podrían ser interpretados como los artículos sobre los cuales se permite el plan de pago informado.
En el caso particular de FactorLoyaltyBenefit con integraciones anteriores a PROMO 5.2 (donde se incluye la administracion de saldos en la consola), la implementación recomendada es la de multiplicar el factor (atributo factor) informado por la suma de los montos (atributo unitprice) de los ítems aplicados, cada uno de ellos multiplicados por la cantidad informada por qty:
Pt = factor x Σ(unitPrice x qty)
Siendo Pt la cantidad total de puntos, dinero, millas, etc. a otorgar y Σ(unitPrice x qty) la sumatoria de los precios unitarios de los elementos aplicados, multiplicados por la cantidad correspondiente informada en <apply>.
Si no se informasen aplicados (algo que es posible para beneficios no monetarios), pueden aplicarse los puntos, dinero, millas, etc. a todo el ticket.
Para el resto de los beneficios no monetarios, los elementos aplicados pueden ser considerados meramente informativos.



  • Sem rótulos