Page tree
Skip to end of metadata
Go to start of metadata

El apartado describe el uso del parámetro notification_url dentro de los pagos y suscripciones.

Descripción

Al momento de registrar un pago o una suscripción en la plataforma de Pay per TIC se tiene la posibilidad de utilizar el parámetro url_notification, este permite la recepción de notificaciones de cambio de dicho pago o suscripción.


Modelo de Notificación

Al momento de enviar una notificación el sistema realiza un POST a la url informada con un modelo de dato como el siguiente

Notificación de un pago:

Payment Notification
{
  "type" : "debit",
  "validation" : false,
  "review" : false,
  "id" : "554ecb4a-aec5-439f-b506-9a22215e0746",
  "external_transaction_id" : "c189ad3d-f5e7-4d33-a92e-09adcb9273ed",
  "collector_id" : "999",
  "collector_detail" : {
    "name" : "PRUEBA"
  },
  "notification_url" : "http://127.0.0.1:9999/notifications",
  "form_url" : "http://localhost:8180/formularios/v2/pagos/554ecb4a-aec5-439f-b506-9a22215e0746",
  "details" : [ {
    "amount" : 1.0,
    "external_reference" : "123",
    "concept_id" : "prueba",
    "concept_description" : "Concepto de prueba"
  } ],
  "currency_id" : "ARS",
  "payment_methods" : [ {
    "amount" : 1.0,
    "media_payment_id" : 9,
    "media_payment_detail" : "VISA CREDIT",
    "last_four_digits" : "0010",
    "first_six_digits" : "450799",
    "installments" : 1,
    "authorization_code" : "191780",
    "gateway" : {
      "establishment_number" : "PRUEBA",
      "transaction_id" : "4021606",
      "batch_number" : "1",
      "ticket_number" : "1533",
      "ppt_owner" : false
    },
    "payment_method_id" : 0
  } ],
  "final_amount" : 1.0,
  "status" : "approved",
  "status_detail" : "APROBADA - Autorizada - MOP GPAY: -1 - Aprobada",
  "request_date" : "2019-08-06T14:58:25-0300",
  "due_date" : "2019-08-06T14:58:25-0300",
  "last_due_date" : "2019-08-06T14:58:25-0300",
  "process_date" : "2019-08-06T14:58:25-0300",
  "paid_date" : "2019-08-06T14:58:25-0300",
  "accreditation_date" : "2019-08-06T14:58:25-0300",
  "last_update_date" : "2019-08-06T14:58:25-0300",
  "metadata" : {
    "parametro_1" : "valor_de_prueba"
  },
  "source" : {
    "id" : "ee84ca67-5f90-4ca9-b587-37afce6ecc14",
    "name" : "system-test",
    "type" : "system"
  }
}


Notificación de una suscripción:

Subscription Notification
{
  "type" : "subscription",
  "validation" : false,
  "review" : false,
  "source" : {
    "id" : "4450b7c2-58c6-4f38-b8ab-69b8d4761a7f",
    "name" : "system-test",
    "type" : "collector"
  },
  "id" : "a16d59ca-b974-4f9c-a17a-37721705688d",
  "collector_id" : "999",
  "collector_detail" : {
    "name" : "PRUEBA"
  },
  "notification_url" : "http://127.0.0.1:9980/notifications",
  "detail" : {
    "amount" : 1.0,
    "external_reference" : "344",
    "concept_id" : "44",
    "concept_description" : "Concepto de prueba"
  },
  "currency_id" : "ARS",
  "payment_method" : {
    "media_payment_id" : 9,
    "media_payment_detail" : "VISA CREDIT",
    "last_four_digits" : "0010",
    "first_six_digits" : "450799"
  },
  "payer" : {
    "name" : "Prueba",
    "email" : "prueba@paypertic.com",
    "external_reference" : "664",
    "identification" : {
      "type" : "DNI_ARG",
      "number" : "99999999",
      "country" : "ARG"
    }
  },
  "amount" : 1.0,
  "status" : "active",
  "request_date" : "2019-08-06T15:35:04-0300",
  "due_day" : 25,
  "last_update_date" : "2019-08-06T15:35:05-0300",
  "recurrence" : "monthly",
  "periods" : 30
}


Encriptación

Es posible enviar notificaciones en forma encriptada. Para esto se usaran tres tipos de llaves, una simétrica, una privada y una pública.

  • Llave simétrica: esta es la llave que se usara para encriptar la notificación y la cual se enviara junto con la misma. Nota: al momento de ejecutar esta acción se utiliza el algoritmo default de cifrado AES de java. Este utiliza AES-256-ECB.
  • Llave privada: esta llave se usara para encriptar la llave simétrica. Esta estará configurada en el comercio.
  • Llave publica: esta llave se usara para desencriptar la llave simétrica del lado del cliente. Se creara junto con la privada y sera proveída para su uso. 

La notificación se encriptara con la llave simétrica. La llave simétrica se encriptara con la llave privada. Se envía al cliente la notificación junto con la llave simétrica, ambos encriptados.

El cliente deberá desencriptar primero la lleve simétrica utilizando la llave publica, y luego con esta deberá desencriptar la notificación.

Se recibirá un body en el request como el siguiente:

El secret_key es la llave simétrica encriptada por la llave privada configurada en el comercio.

El payload es la notificación encriptada con la llave simétrica.


body
{
	secret_key:"ka8lPU+YudBbupb8UsjIviBBU2aQWHyLKZcOCjb9ENFNbftyfI50LrxroqwEixvSH97ZnN53yeUqd/LyGpaTuwna1aZQLQgKWg+G/Y3eKE0iRH1IyVNUdomndoKTlGY27w+5VoMpDlhWiQ3o8aDHzb5rVTNgz+dbUZsD5ot/vqeZmNv1Z4y6eEjpebc6X6wmHOkRUA+qVNak10oFRVycdapU0JzbaNGTFP9OzeCXDa/jMSxnBvqsmnv57PNhVKKd6T2jvMI01tPHj7iqqI+uNXRKuS7t47rFrLkG6YBwmr8FnWcryTiEE1LzoIMIgX9xBSPoYV3IodRw9dJ6BFvySw==",
	payload:"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"
}


Para desencriptar la notificación se deberá seguir el siguiente ejemplo (código en lenguaje java):


Decrypt Notification
public String decryptNotification(String body){
	
	// Convierto el body a un objeto
    PayloadNotification payloadNotification = JacksonConfigurationProvider.JacksonObjectMapper.get().readValue(body, PayloadNotification.class);

    String secretKey = payloadNotification.getSecretKey();
    String payload = payloadNotification.getPayload();

	// Obtengo la llave publica
    String publicKey = getPublicKey();


	// Desencripto la llave simétrica con la llave publica
    String simetricKey = decryptWithPublicKey(secretKey,publicKey);

	// Desencripto la notificación con la llave simétrica
    String notificationDecrypt = decryptSymmetric(payload,simetricKey);

	return notificationDecrypt;
}	


private String decryptWithPublicKey(String inputStr, String publicKey) {
    try {
        PublicKey pKey = getPublicKey(publicKey);
        Cipher cipher = Cipher.getInstance("RSA");
        cipher.init(Cipher.DECRYPT_MODE, pKey);

        return new String(cipher.doFinal(Base64.getDecoder().decode(inputStr.getBytes())));
    } catch (NoSuchAlgorithmException | InvalidKeySpecException | BadPaddingException | NoSuchPaddingException
            | InvalidKeyException | IllegalBlockSizeException | IOException | ArrayIndexOutOfBoundsException e) {
        //error
    }
}

private PublicKey getPublicKey(String publicKey) throws NoSuchAlgorithmException, InvalidKeySpecException, IOException {
    publicKey = publicKey.replaceAll("\\n", "").replace("-----BEGIN PUBLIC KEY-----", "").replace("-----END PUBLIC KEY-----", "");

    X509EncodedKeySpec keySpec = new X509EncodedKeySpec(Base64.getDecoder().decode(publicKey));
    KeyFactory keyFactory = KeyFactory.getInstance("RSA");
    return keyFactory.generatePublic(keySpec);
}


private String decryptSymmetric(String value,String secretKey) {
    try {
        Cipher c = Cipher.getInstance("AES");
        c.init(Cipher.DECRYPT_MODE, generateSecretKey(secretKey));
        return new String(c.doFinal(Base64.getDecoder().decode(value)));
    } catch(Exception e) {
        //error
    }
}

private Key generateSecretKey(String secKey) {
    return new SecretKeySpec(secKey.getBytes(), "AES");
}


Para el ejemplo se usaron los siguientes datos:

Llave simétrica: 5q0++mJ1AJZdzHzSkfV2+VtGg9u9BFmq

Llave publica:

-----BEGIN PUBLIC KEY-----
MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAp2L2AqxGt0ROiCRbBKWH
wJU7ye28DwHRMaZeq0zP9laf8qJ3Vt9uN6gCytgpWd+u7gVmgg1B0+YUiRTOWSUE
aaSew0hgs1gK8f0rcFj4CmETl+DTE/Qbgu/zOo1LycD5Mm/Vj3kErTRqd9bqJu0n
XJOXDGgyX4KcUQYzZcBTr3wKLPuaSKbcq2V6x1z1WrGFLOMgLaGIqHgVoc8PD1xm
3pDtslsbZvpIUx+z1lEK0IrCa0WwIOThjMzzzE4iXS0pfvCOiRejsUFoEKn7yphw
izIgdcgW8ljCHQjjyvHnWT3kOlG8RFDRpEyRbEngW+Cxm3xf5y7BKNYzWTdBGaHL
4QIDAQAB
-----END PUBLIC KEY-----


Llave privada:

-----BEGIN PRIVATE KEY-----
MIIEvgIBADANBgkqhkiG9w0BAQEFAASCBKgwggSkAgEAAoIBAQCnYvYCrEa3RE6I
JFsEpYfAlTvJ7bwPAdExpl6rTM/2Vp/yondW3243qALK2ClZ367uBWaCDUHT5hSJ
FM5ZJQRppJ7DSGCzWArx/StwWPgKYROX4NMT9BuC7/M6jUvJwPkyb9WPeQStNGp3
1uom7Sdck5cMaDJfgpxRBjNlwFOvfAos+5pIptyrZXrHXPVasYUs4yAtoYioeBWh
zw8PXGbekO2yWxtm+khTH7PWUQrQisJrRbAg5OGMzPPMTiJdLSl+8I6JF6OxQWgQ
qfvKmHCLMiB1yBbyWMIdCOPK8edZPeQ6UbxEUNGkTJFsSeBb4LGbfF/nLsEo1jNZ
N0EZocvhAgMBAAECggEADSakR297mth+Bwo8MHBE6yeOa/4GoXM2GV2F4JWHXUZP
CMQk9ilVwn+rwH4dOZduafr4o80g1+IiyOZek/hpkVdCtfsQxeZr7blDWW9UBZS8
8ljSnKW4J6BsjrQdOTu1GHZa5AvRBz6wArxa5zYIuqhJ3Mqu8nwThfYjwaHLsWS/
3gcL9xgE2R9sHkB5PtdlR6PoTCC8wNQdxeAW9w+Y1ekUznaIS2v9Ybu/zP9Gvlac
JS8wYLKjt/OSo/VV6rZ3I2MLFbZdPWsG5WDumkWvoQ61sKk97cB+pT0sK0/OVT7X
YxYZ90rtTA7y1+Ot1PIdrJk34VLmHs5cXIUZCwcwAQKBgQDbuG0cV9gBzSVty/WC
hqLPU1/dCEgiXXaGqKi0+fNu5VFcIAGqo803QwAu08z8KQ7PALLzseL0CDeny5Wn
Lbxqi69luuvsUd2w6jI7uGDVR9c6uZ/OpsI23zC98cAN1+0rNskTgtamkXgWV1VP
rc3wkeFqYl2vb5sbfjNVFjVNYQKBgQDDBmKKj+hdBhxkAWP+RdS7kMPy8sis3W7o
tyFwDTpv9/WzgJVDhVyoK8KRwBaXGcTp1LSQ/EGyH/BNROK/fviIw7b38b8u9Meu
+e27otVq5l1lV/ppqBfKvsXuPTq3mDoRw8VDaPvarf0nwwsNPkJae5CxeiNhfIzr
3FW6/BqOgQKBgQDEe8Im7G8f/UIRU6jy1k9Vs6swT62h/Y52kPB9FmAYtTzyczTK
Uby8RFAvj/vpKxYxCuD8iAD6VTbf+HCVlZK+fLeW83byV6s1/9h4C0OctqfDvico
d3uJ8kD2Ou+R8ZwHXvClYAVv4vpOkD6cCEL3dJzts5Uvw1AjX9GrrzZvQQKBgQCH
4YT7AfVmCwHw878VxNXJsb21Ik+LkeTao+3aQn060ksQvEBDgUHjskmof2u976hx
O1BrzDaBwxsM2zgZMIA92g87heYs80PFuEFZgMSt7L+aAshooUOicXU63tJwZNHg
2sQwiY8g+CTwdUbX/U8B+CICZhUMsVkGZMgetdRTAQKBgH2kTrUiSMV7U3HN1DPk
5aidlhLL2OTuOW/nS67WPLk4TqRyKpZbUyl2VgDfQ5dpHzpoDqSynyE7z8MvV3At
9XLsHk+HDoPalvB37DqhACRdoDwEKPCCQ1wwFBDpKue4zetoV6wTTjPr+S5Z9SAb
SlcaOoCS2A9BWs4ctFzwZerS
-----END PRIVATE KEY-----


Pago de prueba:

Payment test
{
  "type" : "debit",
  "validation" : false,
  "review" : false,
  "id" : "554ecb4a-aec5-439f-b506-9a22215e0746",
  "external_transaction_id" : "c189ad3d-f5e7-4d33-a92e-09adcb9273ed",
  "collector_id" : "999",
  "collector_detail" : {
    "name" : "PRUEBA"
  },
  "notification_url" : "http://127.0.0.1:9999/notifications",
  "form_url" : "http://localhost:8180/formularios/v2/pagos/554ecb4a-aec5-439f-b506-9a22215e0746",
  "details" : [ {
    "amount" : 1.0,
    "external_reference" : "123",
    "concept_id" : "prueba",
    "concept_description" : "Concepto de prueba"
  } ],
  "currency_id" : "ARS",
  "payment_methods" : [ {
    "amount" : 1.0,
    "media_payment_id" : 9,
    "media_payment_detail" : "VISA CREDIT",
    "last_four_digits" : "0010",
    "first_six_digits" : "450799",
    "installments" : 1,
    "authorization_code" : "191780",
    "gateway" : {
      "establishment_number" : "PRUEBA",
      "transaction_id" : "4021606",
      "batch_number" : "1",
      "ticket_number" : "1533",
      "ppt_owner" : false
    },
    "payment_method_id" : 0
  } ],
  "final_amount" : 1.0,
  "status" : "approved",
  "status_detail" : "APROBADA - Autorizada - MOP GPAY: -1 - Aprobada",
  "request_date" : "2019-08-06T14:58:25-0300",
  "due_date" : "2019-08-06T14:58:25-0300",
  "last_due_date" : "2019-08-06T14:58:25-0300",
  "process_date" : "2019-08-06T14:58:25-0300",
  "paid_date" : "2019-08-06T14:58:25-0300",
  "accreditation_date" : "2019-08-06T14:58:25-0300",
  "last_update_date" : "2019-08-06T14:58:25-0300",
  "metadata" : {
    "parametro_1" : "valor_de_prueba"
  },
  "source" : {
    "id" : "ee84ca67-5f90-4ca9-b587-37afce6ecc14",
    "name" : "system-test",
    "type" : "system"
  }
}
  • No labels