Summary
After registering the HMAC, this documentation provides instructions for generating an HMAC (Hash-based Message Authentication Code) using various programming languages such as JavaScript (Postman), Python, Java, JavaScript (Node.js), C#, and PHP. HMAC is required for utilizing the PIX Cash in and PIX Cash out endpoints, ensuring data integrity and authenticity in HTTP requests. Properly configuring a script that formats the JSON payload correctly is essential for consistently generating HMACs.
HMAC authentication is a robust method to safeguard your API endpoints. It ensures data integrity and restricts access to authorized clients only. By implementing HMAC authentication, you can enhance the security of your API, confidently share your services globally, and keep malicious actors at bay.
Script Functionality
The script can be divided into several steps. Below is a detailed description of each step along with implementations in various programming languages:
1. Importing the crypto-js Module
This command imports the crypto-js library, which is used to perform cryptographic operations such as HMAC generation.
const crypto = require('crypto-js');
import hmac
import hashlib
import javax.crypto.Mac;
import javax.crypto.spec.SecretKeySpec;
const crypto = require('crypto');
using System.Security.Cryptography;
// No need to import any additional library for HMAC in PHP
2. 'generateHMAC' Function
This function takes two parameters:
- jsonData: The request body in JSON format.
- secretKey: The secret key used to generate the HMAC.
The function uses the HmacSHA512 method from the crypto-js library to generate the HMAC SHA-512 and returns the result in hexadecimal format.
function generateHMAC(jsonData, secretKey) {
const hmacSHA512 = crypto.HmacSHA512(jsonData, secretKey);
return hmacSHA512.toString(crypto.enc.Hex);
}
def generate_hmac(json_data, secret_key):
hmac_obj = hmac.new(secret_key.encode(), json_data.encode(), hashlib.sha512)
return hmac_obj.hexdigest()
public static String generateHMAC(String jsonData, String secretKey) throws Exception {
Mac sha512_HMAC = Mac.getInstance("HmacSHA512");
SecretKeySpec keySpec = new SecretKeySpec(secretKey.getBytes(StandardCharsets.UTF_8), "HmacSHA512");
sha512_HMAC.init(keySpec);
byte[] hmacBytes = sha512_HMAC.doFinal(jsonData.getBytes(StandardCharsets.UTF_8));
return bytesToHex(hmacBytes);
}
private static String bytesToHex(byte[] bytes) {
Formatter formatter = new Formatter();
for (byte b : bytes) {
formatter.format("%02x", b);
}
return formatter.toString();
}
function generateHMAC(jsonData, secretKey) {
const hmac = crypto.createHmac('sha512', secretKey);
hmac.update(jsonData);
return hmac.digest('hex');
}
static string GenerateHMAC(string jsonData, string secretKey) {
using (var hmacsha512 = new HMACSHA512(Encoding.UTF8.GetBytes(secretKey))) {
byte[] hashmessage = hmacsha512.ComputeHash(Encoding.UTF8.GetBytes(jsonData));
return BitConverter.ToString(hashmessage).Replace("-", "").ToLower();
}
}
function generateHMAC($jsonData, $secretKey) {
return hash_hmac('sha512', $jsonData, $secretKey);
}
3. Retrieving the Request Body
This command retrieves the request body as a raw string.
let payload = pm.request.body.raw;
payload = '{"key1": "value1", "key2": "value2"}' # Example request body
String payload = "{\"key1\":\"value1\",\"key2\":\"value2\"}"; // Example request body
let payload = '{"key1": "value1", "key2": "value2"}'; // Example request body
string payload = "{\"key1\":\"value1\",\"key2\":\"value2\"}"; // Example request body
$payload = '{"key1":"value1","key2":"value2"}'; // Example request body
4. Parsing the JSON
This command converts the raw JSON string into a JavaScript object.
let jsonObj = JSON.parse(payload);
import json
json_obj = json.loads(payload)
import org.json.JSONObject;
JSONObject jsonObj = new JSONObject(payload);
let jsonObj = JSON.parse(payload);
using Newtonsoft.Json.Linq;
JObject jsonObj = JObject.Parse(payload);
$jsonObj = json_decode($payload, true);
5. Converting the Object Back to a JSON String
Here, the JavaScript object is converted back to a JSON string without formatting (no indentation).
payload = JSON.stringify(jsonObj);
payload = json.dumps(json_obj, separators=(',', ':'))
payload = jsonObj.toString();
payload = JSON.stringify(jsonObj);
payload = jsonObj.ToString(Newtonsoft.Json.Formatting.None);
$payload = json_encode($jsonObj, JSON_UNESCAPED_SLASHES);
6. Removing Unnecessary Spaces
This command removes unnecessary spaces after colons and commas in the JSON string. This is important to ensure the HMAC is generated consistently, regardless of the original JSON formatting.
payload = payload.replace(/:\s/g, ':').replace(/,\s/g, ',');
payload = payload.replace(': ', ':').replace(', ', ',')
payload = payload.replaceAll(":\\s", ":").replaceAll(",\\s", ",");
payload = payload.replace(/:\s/g, ':').replace(/,\s/g, ',');
payload = payload.Replace(": ", ":").Replace(", ", ",");
$payload = str_replace(array(': ', ', '), array(':', ','), $payload);
7. Retrieving the Secret Key
This is where the secret key used to generate the HMAC is defined. This key is the same one generated and sent to the email [email protected] in step: Register HMAC
Note: Only after registering the HMAC key will it be possible to complete this step
const secretKey = "edcb3xxxxf248b744653f052b22cexxxx8d87ad2b2777xxxx35f33d27be6xxxx";
secret_key = "edcb3xxxxf248b744653f052b22cexxxx8d87ad2b2777xxxx35f33d27be6xxxx"
String secretKey = "edcb3xxxxf248b744653f052b22cexxxx8d87ad2b2777xxxx35f33d27be6xxxx";edcb3xxxxf248b744653f052b22cexxxx8d87ad2b2777xxxx35f33d27be6xxxx
const secretKey = "edcb3xxxxf248b744653f052b22cexxxx8d87ad2b2777xxxx35f33d27be6xxxx";
string secretKey = "edcb3xxxxf248b744653f052b22cexxxx8d87ad2b2777xxxx35f33d27be6xxxx";
$secretKey = "edcb3xxxxf248b744653f052b22cexxxx8d87ad2b2777xxxx35f33d27be6xxxx";
Best practices: To ensure the security of the secret key used to generate the HMAC, it is crucial to avoid including it directly in the code. Instead, it is recommended to retrieve it from a secure source, such as environment variables or some form of secret management. Below are examples of how to do this securely in each language:
// Get the secret key from Postman environment variables
const secretKey = pm.environment.get('secret_key');
// In Postman, it is a best practice to store sensitive information like secret keys in environment variables. You can set these variables in the Postman interface and retrieve them securely in your scripts.
# Get the secret key from environment variables
import os
secret_key = os.getenv('SECRET_KEY')
# In Python, use the os module to retrieve the secret key from environment variables. This method ensures that sensitive information is not hardcoded and can be managed securely.
// Get the secret key from environment variables
String secretKey = System.getenv("SECRET_KEY");
// In Java, use the System.getenv method to retrieve the secret key from environment variables. This approach keeps the secret key secure and separate from the codebase.
// Get the secret key from environment variables
const secretKey = process.env.SECRET_KEY;
// In Node.js, use the process.env object to retrieve the secret key from environment variables. This practice helps maintain the security of sensitive information.
// Get the secret key from environment variables
string secretKey = Environment.GetEnvironmentVariable("SECRET_KEY");
// In C#, use the Environment.GetEnvironmentVariable method to retrieve the secret key from environment variables. This approach ensures that sensitive information is handled securely.
// Get the secret key from environment variables
$secretKey = getenv('SECRET_KEY');
// In PHP, use the getenv function to retrieve the secret key from environment variables. This practice helps secure sensitive information by keeping it out of the codebase.
8. Generating the HMAC
This command calls the generateHMAC function with the formatted request body and secret key, storing the generated HMAC in the hmac variable.
const hmac = generateHMAC(payload, secretKey);
hmac_result = generate_hmac(payload, secret_key)
String hmacResult = generateHMAC(payload, secretKey);
const hmac = generateHMAC(payload, secretKey);
string hmac = GenerateHMAC(payload, secretKey);
$hmac = generateHMAC($payload, $secretKey);
9. Storing the HMAC in an Environment Variable
This command stores the generated HMAC in an environment variable named 'generated_hmac', which can be used in other parts.
pm.collectionVariables.set('generated_hmac', hmac);
// This command stores the generated HMAC in an environment variable named generated_hmac, which can be used in other parts of the Postman collection.
import os
# Assuming you are using some configuration or environment management package
os.environ['GENERATED_HMAC'] = hmac
// This example uses System properties as an analogy to environment variables
System.setProperty("generated_hmac", hmac);
process.env.GENERATED_HMAC = hmac;
// This command stores the generated HMAC in an environment variable named GENERATED_HMAC.
// Setting an environment variable in C# (note: it will only persist for the current process)
Environment.SetEnvironmentVariable("GENERATED_HMAC", hmac);
// Setting an environment variable in PHP
putenv("GENERATED_HMAC=$hmac");
10. Storing the HMAC in an Environment Variable
This command logs the generated HMAC for debugging purposes.
console.log('Generated HMAC:', hmac);
print('Generated HMAC:', hmac_result)
System.out.println("Generated HMAC: " + hmacResult);
console.log('Generated HMAC:', hmac);
Console.WriteLine("Generated HMAC: " + hmac);
echo "Generated HMAC: " . $hmac;
Complete Script Examples
JavaScript (Postman)
// Function to generate HMAC
function generateHMAC(jsonData, secretKey) {
const crypto = require('crypto-js');
const hmacSHA512 = crypto.HmacSHA512(jsonData, secretKey);
return hmacSHA512.toString(crypto.enc.Hex);
}
// Get the request body
let payload = pm.request.body.raw;
// Parse the JSON string
let jsonObj = JSON.parse(payload);
// Convert back to a JSON string without pretty-printing
payload = JSON.stringify(jsonObj);
// Replace ": " with ":" and ", " with ","
payload = payload.replace(/:\s/g, ':').replace(/,\s/g, ',');
// Get the secret key (you need to set this in your environment variables)
const secretKey = "edcb3xxxxf248b744653f052b22cexxxx8d87ad2b2777xxxx35f33d27be6xxxx";
// Generate the HMAC
const hmac = generateHMAC(payload, secretKey);
// Set the HMAC in an environment variable for later use
pm.collectionVariables.set('generated_hmac', hmac);
console.log('Generated HMAC:', hmac);
Python
import hashlib
import hmac
import json
def gera_hash(json_data, chave_secreta):
chave_secreta = chave_secreta.encode('utf-8')
hmac_sha512 = hmac.new(chave_secreta, json_data, hashlib.sha512)
chave_hmac = hmac_sha512.hexdigest()
return chave_hmac
# Get the request body (assuming it's a JSON string)
payload = '{"key1": "value1", "key2": "value2"}'
payload_json_str = json.dumps(payload, ensure_ascii=False)
payload_json_str = payload_json_str.replace(": ", ":")
payload_json_str = payload_json_str.replace(", ", ",").encode('utf-8')
hmacresult = gera_hash(payload_json_str, "7a3edd380d2356bcb5f4bb1ff3a25f918cfb11e83c2eb468f967457037e43949")
print("Generated HMAC:", hmacresult)
Java
import javax.crypto.Mac;
import javax.crypto.spec.SecretKeySpec;
import java.nio.charset.StandardCharsets;
import java.security.MessageDigest;
import java.util.Formatter;
public class HMACGenerator {
public static String generateHMAC(String jsonData, String secretKey) throws Exception {
Mac sha512_HMAC = Mac.getInstance("HmacSHA512");
SecretKeySpec keySpec = new SecretKeySpec(secretKey.getBytes(StandardCharsets.UTF_8), "HmacSHA512");
sha512_HMAC.init(keySpec);
byte[] hmacBytes = sha512_HMAC.doFinal(jsonData.getBytes(StandardCharsets.UTF_8));
return bytesToHex(hmacBytes);
}
private static String bytesToHex(byte[] bytes) {
Formatter formatter = new Formatter();
for (byte b : bytes) {
formatter.format("%02x", b);
}
return formatter.toString();
}
public static void main(String[] args) throws Exception {
String payload = "{\"key1\":\"value1\",\"key2\":\"value2\"}";
// Secret key
String secretKey = "edcb3xxxxf248b744653f052b22cexxxx8d87ad2b2777xxxx35f33d27be6xxxx";
// Generate the HMAC
String hmacResult = generateHMAC(payload, secretKey);
System.out.println("Generated HMAC: " + hmacResult);
}
}
JavaScript (Node.js)
const crypto = require('crypto');
function generateHMAC(jsonData, secretKey) {
const hmac = crypto.createHmac('sha512', secretKey);
hmac.update(jsonData);
return hmac.digest('hex');
}
// Get the request body
let payload = '{"key1": "value1", "key2": "value2"}';
// Parse the JSON string
let jsonObj = JSON.parse(payload);
// Convert back to a JSON string without pretty-printing
payload = JSON.stringify(jsonObj);
// Replace ": " with ":" and ", " with ","
payload = payload.replace(/:\s/g, ':').replace(/,\s/g, ',');
// Secret key
const secretKey = "edcb3xxxxf248b744653f052b22cexxxx8d87ad2b2777xxxx35f33d27be6xxxx";
// Generate the HMAC
const hmac = generateHMAC(payload, secretKey);
console.log('Generated HMAC:', hmac);
C#
using System;
using System.Security.Cryptography;
using System.Text;
using Newtonsoft.Json;
using Newtonsoft.Json.Linq;
class Program
{
static void Main()
{
string payload = "{\"key1\":\"value1\",\"key2\":\"value2\"}";
// Parse the JSON string
JObject jsonObj = JObject.Parse(payload);
// Convert back to a JSON string without pretty-printing
payload = JsonConvert.SerializeObject(jsonObj, Formatting.None);
// Secret key
string secretKey = "edcb3xxxxf248b744653f052b22cexxxx8d87ad2b2777xxxx35f33d27be6xxxx";
// Generate the HMAC
string hmac = GenerateHMAC(payload, secretKey);
Console.WriteLine("Generated HMAC: " + hmac);
}
static string GenerateHMAC(string jsonData, string secretKey)
{
using (var hmacsha512 = new HMACSHA512(Encoding.UTF8.GetBytes(secretKey)))
{
byte[] hashmessage = hmacsha512.ComputeHash(Encoding.UTF8.GetBytes(jsonData));
return BitConverter.ToString(hashmessage).Replace("-", "").ToLower();
}
}
}
PHP
<?php
function generateHMAC($jsonData, $secretKey) {
return hash_hmac('sha512', $jsonData, $secretKey);
}
// Get the request body
$payload = '{"key1":"value1","key2":"value2"}';
// Decode and encode JSON to remove pretty-printing
$jsonObj = json_decode($payload, true);
$payload = json_encode($jsonObj, JSON_UNESCAPED_SLASHES);
// Secret key
$secretKey = "edcb3xxxxf248b744653f052b22cexxxx8d87ad2b2777xxxx35f33d27be6xxxx";
// Generate the HMAC
$hmac = generateHMAC($payload, $secretKey);
echo "Generated HMAC: " . $hmac;
?>