Skip to main content

Cryptographic Functions

Hash, encode, and sign data securely within your formulas.

sha512()

Generate a SHA-512 hash of the input string.

Syntax

sha512(input)

Parameters

ParameterTypeRequiredDescription
inputstringYesString to hash

Returns

Returns a lowercase hexadecimal SHA-512 hash string (128 characters).

Examples

Basic Hashing

var hash = sha512('my sensitive data');
console.log(hash);
// Output: 64-byte hex string (128 characters)

Hash Password (for comparison, not storage)

var inputPassword = context.password;
var hashedInput = sha512(inputPassword);

// Compare with stored hash
if (hashedInput === context.storedHash) {
return { authenticated: true };
} else {
return { authenticated: false };
}

Generate Unique Identifier

var uniqueId = sha512(
context.accountNumber +
context.timestamp +
context.randomSeed
);

return {
transactionId: uniqueId.substring(0, 32) // Use first 32 chars
};

Data Integrity Check

var data = JSON.stringify(context.transactionData);
var checksum = sha512(data);

return {
data: context.transactionData,
checksum: checksum,
timestamp: new Date().toISOString()
};

Use Cases

  • Generate checksums for data integrity
  • Create unique identifiers
  • Hash-based deduplication
  • Verify data hasn't been tampered with

Security Note

SHA-512 is a one-way cryptographic hash function. The original input cannot be derived from the hash. For password storage, use dedicated password hashing functions (bcrypt, Argon2, etc.) instead of raw SHA-512.


hmacSha256()

Generate an HMAC-SHA256 signature using a secret key.

Syntax

hmacSha256(secretKey, data)

Parameters

ParameterTypeRequiredDescription
secretKeystringYesSecret key used for signing
datastringYesData to sign

Returns

Returns a lowercase hexadecimal HMAC-SHA256 signature string (64 characters).

Examples

Sign API Request

var apiKey = $.secure.get('PAYMENT_API_KEY');
var apiSecret = $.secure.get('PAYMENT_API_SECRET');

var requestData = JSON.stringify({
amount: context.amount,
accountNumber: context.accountNumber,
timestamp: Date.now()
});

var signature = hmacSha256(apiSecret, requestData);

var response = doCmd('CallExternalAPI', {
url: 'https://api.paymentgateway.com/pay',
headers: {
'X-API-Key': apiKey,
'X-Signature': signature,
'Content-Type': 'application/json'
},
body: requestData
});

return response;

Webhook Verification

// Verify incoming webhook signature
var receivedSignature = context.headers['X-Webhook-Signature'];
var webhookSecret = $.secure.get('WEBHOOK_SECRET');

var payload = context.body;
var expectedSignature = hmacSha256(webhookSecret, payload);

if (receivedSignature === expectedSignature) {
// Signature valid - process webhook
return processWebhook(payload);
} else {
// Signature invalid - reject request
throw new Error('Invalid webhook signature');
}

Generate Secure Token

var tokenData = JSON.stringify({
userId: context.userId,
expiresAt: Date.now() + (3600 * 1000), // 1 hour
permissions: ['read', 'write']
});

var secret = $.secure.get('TOKEN_SECRET');
var signature = hmacSha256(secret, tokenData);

var secureToken = base64Encode(tokenData) + '.' + signature;

return {
token: secureToken,
expiresIn: 3600
};

Two-Way Data Integrity

// Sender side
var data = JSON.stringify(context.transferData);
var sharedSecret = $.secure.get('TRANSFER_SECRET');
var signature = hmacSha256(sharedSecret, data);

var package = {
data: base64Encode(data),
signature: signature
};

// Send package to receiver

// Receiver side (in another command)
var receivedData = base64Decode(context.package.data);
var receivedSignature = context.package.signature;
var secret = $.secure.get('TRANSFER_SECRET');

var expectedSignature = hmacSha256(secret, receivedData);

if (receivedSignature === expectedSignature) {
var transferData = JSON.parse(receivedData);
return processTransfer(transferData);
} else {
throw new Error('Data integrity check failed');
}

Use Cases

  • Sign API requests for authentication
  • Verify webhook signatures
  • Generate secure tokens
  • Ensure message integrity
  • Implement challenge-response authentication

Security Note

HMAC provides both authentication and integrity. The secret key must be kept secure and never transmitted or logged.


base64Encode()

Encode a string to Base64 format.

Syntax

base64Encode(input)

Parameters

ParameterTypeRequiredDescription
inputstringYesString to encode

Returns

Returns a Base64-encoded string.

Examples

Encode Credentials

var username = context.username;
var password = context.password;

var credentials = base64Encode(username + ':' + password);

var response = doCmd('CallExternalAPI', {
url: 'https://api.example.com/endpoint',
headers: {
'Authorization': 'Basic ' + credentials
}
});

return response;

Encode JSON Data

var data = {
accountNumber: context.accountNumber,
amount: context.amount,
timestamp: Date.now()
};

var encoded = base64Encode(JSON.stringify(data));

return {
encodedPayload: encoded
};

Safe URL Parameters

var queryData = base64Encode(JSON.stringify({
accountId: context.accountId,
filters: context.filters
}));

var url = 'https://reports.bank.com/generate?data=' + queryData;

return { reportUrl: url };

Use Cases

  • Encode credentials for Basic Authentication
  • Safely transmit binary data as text
  • Create URL-safe data representations
  • Encode data for storage or transmission

base64Decode()

Decode a Base64-encoded string.

Syntax

base64Decode(encodedInput)

Parameters

ParameterTypeRequiredDescription
encodedInputstringYesBase64-encoded string

Returns

Returns the decoded string.

Examples

Decode Credentials

var authHeader = context.headers['Authorization'];
// Expected format: "Basic base64credentials"

var encodedCredentials = authHeader.replace('Basic ', '');
var decoded = base64Decode(encodedCredentials);

var parts = decoded.split(':');
var username = parts[0];
var password = parts[1];

// Validate credentials
return validateCredentials(username, password);

Decode Payload

var encoded = context.encodedPayload;
var decoded = base64Decode(encoded);
var data = JSON.parse(decoded);

return {
accountNumber: data.accountNumber,
amount: data.amount
};

Decode and Verify Token

var tokenParts = context.token.split('.');
var encodedData = tokenParts[0];
var signature = tokenParts[1];

var decodedData = base64Decode(encodedData);
var tokenData = JSON.parse(decodedData);

// Verify signature
var secret = $.secure.get('TOKEN_SECRET');
var expectedSignature = hmacSha256(secret, decodedData);

if (signature !== expectedSignature) {
throw new Error('Invalid token signature');
}

// Check expiration
if (tokenData.expiresAt < Date.now()) {
throw new Error('Token expired');
}

return {
valid: true,
userId: tokenData.userId,
permissions: tokenData.permissions
};

Use Cases

  • Decode Basic Authentication headers
  • Receive base64-encoded data
  • Parse encoded URL parameters
  • Decode binary data transmitted as text

Complete Example: Secure API Integration

Signed Request with Authentication

// Step 1: Get credentials
var apiKey = $.secure.get('EXTERNAL_API_KEY');
var apiSecret = $.secure.get('EXTERNAL_API_SECRET');

if (!apiKey || !apiSecret) {
throw new Error('API credentials not configured');
}

// Step 2: Prepare request data
var timestamp = Date.now().toString();
var requestData = JSON.stringify({
accountNumber: context.accountNumber,
amount: context.amount,
currency: 'USD',
timestamp: timestamp
});

// Step 3: Generate signature
var signatureInput = timestamp + requestData;
var signature = hmacSha256(apiSecret, signatureInput);

// Step 4: Compute checksum
var checksum = sha512(requestData);

// Step 5: Make API call
var response = doCmd('CallExternalAPI', {
url: 'https://api.paymentprocessor.com/transaction',
method: 'POST',
headers: {
'X-API-Key': apiKey,
'X-Timestamp': timestamp,
'X-Signature': signature,
'X-Checksum': checksum,
'Content-Type': 'application/json'
},
body: requestData
});

// Step 6: Cache the result
$.cache.set('transaction_' + response.transactionId, response, 300);

return {
success: true,
transactionId: response.transactionId,
status: response.status
};

Webhook Signature Verification

function verifyWebhook(payload, receivedSignature) {
var webhookSecret = $.secure.get('WEBHOOK_SECRET');

if (!webhookSecret) {
throw new Error('Webhook secret not configured');
}

var expectedSignature = hmacSha256(webhookSecret, payload);

if (receivedSignature !== expectedSignature) {
throw new Error('Invalid webhook signature');
}

return true;
}

// Main webhook handler
var payload = context.body;
var signature = context.headers['X-Webhook-Signature'];

try {
verifyWebhook(payload, signature);

var data = JSON.parse(payload);

// Process webhook
var result = doCmd('ProcessWebhookEvent', {
eventType: data.eventType,
eventData: data.data
});

return {
success: true,
message: 'Webhook processed successfully'
};

} catch (error) {
return {
success: false,
error: error.message
};
}

Best Practices

✅ Do

  1. Use HMAC for signatures when you need authentication and integrity
  2. Use SHA-512 for checksums and data integrity verification
  3. Store secrets securely using $.secure.get()
  4. Base64 encode binary data for text-based transmission
  5. Verify signatures before processing external data
  6. Use timestamps to prevent replay attacks

❌ Don't

  1. Don't use SHA-512 alone for passwords (use bcrypt/Argon2 instead)
  2. Don't log or expose secret keys or signatures
  3. Don't reuse signatures across different contexts
  4. Don't transmit secrets in API calls
  5. Don't skip signature verification for webhooks

Security Considerations

Signature Replay Prevention

var timestamp = context.timestamp;
var currentTime = Date.now();
var maxAge = 5 * 60 * 1000; // 5 minutes

if (Math.abs(currentTime - timestamp) > maxAge) {
throw new Error('Request timestamp too old or too far in the future');
}

// Verify signature with timestamp
var signature = hmacSha256(secret, timestamp + data);

Rate Limiting with Checksums

var requestChecksum = sha512(JSON.stringify(context.requestData));
var cacheKey = 'request_' + requestChecksum;

if ($.cache.exists(cacheKey)) {
throw new Error('Duplicate request detected');
}

// Mark request as processed
$.cache.set(cacheKey, true, 60); // 1 minute deduplication window

// Process request
return processRequest(context.requestData);

Common Patterns

Pattern 1: Request Signing

function signRequest(url, method, body, secret) {
var timestamp = Date.now().toString();
var signatureData = method + url + timestamp + body;
var signature = hmacSha256(secret, signatureData);

return {
timestamp: timestamp,
signature: signature
};
}

Pattern 2: Token Generation

function generateSecureToken(userId, expiresIn) {
var payload = {
userId: userId,
exp: Date.now() + (expiresIn * 1000),
nonce: sha512(Date.now() + Math.random())
};

var payloadStr = JSON.stringify(payload);
var secret = $.secure.get('TOKEN_SECRET');
var signature = hmacSha256(secret, payloadStr);

return base64Encode(payloadStr) + '.' + signature;
}

Pattern 3: Data Fingerprinting

function createFingerprint(data) {
var normalized = JSON.stringify(data, Object.keys(data).sort());
return sha512(normalized);
}

var fingerprint1 = createFingerprint(data1);
var fingerprint2 = createFingerprint(data2);

if (fingerprint1 === fingerprint2) {
console.log('Data is identical');
}

See Also