General API Information
The general request parameters are required for merchants to invoke the platform's various business APIs. The current version uses HTTP header information for requests.
Callback IP Addresses
- 54.169.54.48
- 3.0.143.201
- 52.76.5.66
Currency Unit
Rupiah (IDR)
Test Request Domain
| Parameter | Required | Details |
|---|---|---|
| API endpoint | Yes | https://test-merchant.hzpay.net/prex/ |
Production Request Domain
| Parameter | Required | Details |
|---|---|---|
| API endpoint | Yes | https://merchant.hzpay.net/prex/ |
Request Header Information
WARNING
Both request and callback include request header data
| Parameter | Required | Details |
|---|---|---|
| Content-Type | No | application/json |
| Api-Key | Yes | A unique identifier assigned to the merchant by the platform |
| Request-Id | Yes | A unique request ID provided by the merchant, suggested format: UUID, NanoID, or a string with 8-32 characters, no special symbols |
| Timestamp | Yes | Long type, the current time as the difference from UTC (January 1, 1970) in milliseconds |
| Sign | Yes | Signature used for authentication (see below for the signature calculation method) |
Signature Calculation Method
Payment Collection Signature Calculation ✅
The signature is calculated by encrypting the request body using the SHA-256 encryption algorithm.
A component is formed by concatenating the merchant's unique identifier, request body, request ID, and * timestamp* using the "&" separator.
The HMAC-SHA256 is computed using the encryption key assigned to the merchant, and the encrypted result is converted to a BASE64 string.
Assume the following parameters:
- Merchant Unique Identifier (api-key): 934ns90d
- Merchant Encryption Key (api-secret): 90oa4dowox00o3cd
- Merchant Request (requestId): d123455678892238729
- Request Timestamp (timestamp): 1687227487329
- Request Body (body): As shown below
DANGER
Note: All transmitted request data must be encrypted. The body in the following encryption data is for example purposes only.
Signature Calculation Example:
public static String sha256(String body) throws Exception {
MessageDigest messageDigest = MessageDigest.getInstance("SHA-256");
byte[] hash = messageDigest.digest(body.getBytes("UTF-8"));
return Base64.getEncoder().encodeToString(hash);
}
public static String hmacSha256(String component, String secret) throws Exception {
byte[] decodedKey = secret.getBytes(StandardCharsets.UTF_8);
SecretKey originalKey = new SecretKeySpec(decodedKey, 0, decodedKey.length, "HmacSHA256");
Mac hmacSha256 = Mac.getInstance("HmacSHA256");
hmacSha256.init(originalKey);
hmacSha256.update(component.getBytes(StandardCharsets.UTF_8));
byte[] HmacSha256DigestBytes = hmacSha256.doFinal();
return Base64.getEncoder().encodeToString(HmacSha256DigestBytes);
}
String body = {"order":{"amount":10000,"callback":"http://yourdomain.com/callback_success","id":"9bddcb4114b24aceb49daa506b7b406d"}};
String component = Api-Key={yourApiKey}&Body-Hash={sha256(body)}&Request-Id={requestId}&Timestamp={timestamp};
String api-secret = 90oa4dowox00o3cd;
String sign = hmacSha256(component, api-secret);<?php
function sha256($str) {
return base64_encode(hash('sha256', $str, true));
}
function hmacSha256($component, $secret) {
return base64_encode(hash_hmac('sha256', $component, utf8_decode($secret), true));
}
$body = '{"order":{"amount":10000,"callback":"http://yourdomain.com/callback_success", "id":"9bddcb4114b24aceb49daa506b7b406d"}}';
$bodyHash = sha256($body);
$component = "Api-Key=934ns90d&Body-Hash=" . $bodyHash . "&Request-Id=123455678892238729&Timestamp=1687227487329";
$sign = hmacSha256($component, "90oa4dowox00o3cd");using System;
using System.Collections.Generic;
using System.Security.Cryptography;
using System.Text;
class Program
{
static void Main() {
string body = "{\"order\":{\"amount\":10000,\"callback\":\"http://yourdomain.com/callback_success\",\"id\":\"9bddcb4114b24aceb49daa506b7b406d\"}}";
string component = $"Api-Key=934ns90d&Body-Hash={Sha256(body)}&Request-Id=123455678892238729&Timestamp=1687227487329";
string sign = HmacSha256(component, "90oa4dowox00o3cd");
}
static string Sha256(string str) {
using (SHA256 sha256 = SHA256.Create()) {
byte[] hashBytes = sha256.ComputeHash(Encoding.UTF8.GetBytes(str));
return Convert.ToBase64String(hashBytes);
}
}
static string HmacSha256(string component, string secret) {
using (HMACSHA256 hmac = new HMACSHA256(Encoding.UTF8.GetBytes(secret))) {
byte[] hashBytes = hmac.ComputeHash(Encoding.UTF8.GetBytes(component));
return Convert.ToBase64String(hashBytes);
}
}
}import hashlib
import hmac
import base64
def sha256(data):
return base64.b64encode(hashlib.sha256(data.encode('utf-8')).digest()).decode('utf-8')
def hmac_sha256(data, key):
return base64.b64encode(hmac.new(key.encode('utf-8'), data.encode('utf-8'), hashlib.sha256).digest()).decode('utf-8')
api_key = "ABCDWER12"
request_id = "123455678892238729"
timestamp = 1687227487329
body = '{"order":{"amount":10000,"callback":"http://yourdomain.com/callback_success","id":"9bddcb4114b24aceb49daa506b7b406d"}}'
api_secret = "AEKRIU1254838DJK"
signature = hmac_sha256(f"Api-Key={api_key}&Body-Hash={sha256(body)}&Request-Id={request_id}&Timestamp={timestamp}", api_secret)Payment Disbursement Signature Calculation ✅
The signature is calculated by encrypting the APIKey, Request ID, Timestamp, and APISecret (merchant's encryption key) using the AES encryption algorithm.
The encrypted result is then converted to a BASE64 string.
Assume the following parameters:
- APIKey: M12345
- APISecret: abcdef1234567890
- Request ID: 11223344-5566-7788-9900-abcdabcdabcd
- Timestamp: 1687227487329
Signature Calculation Example:
import javax.crypto.Cipher;
import javax.crypto.spec.SecretKeySpec;
import org.apache.commons.codec.binary.Base64;
public static String encrypt(String valueToEnc, String encKey) throws Exception {
SecretKeySpec key = new SecretKeySpec(encKey.getBytes(), "AES");
Cipher c = Cipher.getInstance("AES");
c.init(Cipher.ENCRYPT_MODE, key);
return Base64.encodeBase64String(c.doFinal(valueToEnc.getBytes()));
}
public static void main(String[] args) throws Exception {
String valueToEnc = "M12345" + "11223344-5566-7788-9900-abcdabcdabcd" + "1687227487329";
String encKey = "abcdef1234567890";
String sign = encrypt(valueToEnc, encKey);
}<?php
$apiKey = "M12345";
$requestId = "11223344-5566-7788-9900-abcdabcdabcd";
$timestamp = "1687227487329";
$valueToEnc = $apiKey . $requestId . $timestamp;
$encKey = "abcdef1234567890";
$encValue = openssl_encrypt($valueToEnc, "aes-128-ecb", $encKey, OPENSSL_RAW_DATA);
$encValueBase64 = base64_encode($encValue);
echo $encValueBase64;
?>using System;
using System.Security.Cryptography;
using System.Text;
class Program {
public static void Main() {
string valueToEnc = "M12345" + "11223344-5566-7788-9900-abcdabcdabcd" + "168722748732
9";
string encKey = "abcdef1234567890";
using (Aes aes = Aes.Create()) {
aes.Key = Encoding.UTF8.GetBytes(encKey);
aes.Mode = CipherMode.ECB;
aes.Padding = PaddingMode.PKCS7;
ICryptoTransform encryptor = aes.CreateEncryptor();
byte[] encValue = encryptor.TransformFinalBlock(Encoding.UTF8.GetBytes(valueToEnc), 0, valueToEnc.Length);
Console.WriteLine(Convert.ToBase64String(encValue));
}
}
}from Crypto.Cipher import AES
from Crypto.Util.Padding import pad
import base64
def encrypt(value_to_enc, enc_key):
cipher = AES.new(enc_key.encode('utf-8'), AES.MODE_ECB)
padded_value_to_enc = pad(value_to_enc.encode('utf-8'), AES.block_size)
enc_value = cipher.encrypt(padded_value_to_enc)
return base64.b64encode(enc_value).decode('utf-8')
value_to_enc = "M12345" + "11223344-5566-7788-9900-abcdabcdabcd" + "1687227487329"
enc_key = "abcdef1234567890"
print(encrypt(value_to_enc, enc_key))General Response
When the payment platform receives a request, whether the processing is successful or not, a general status message with the following content will be returned.
Payment Collection General Status
{
"status": 1,
"data": {}
}Payment Collection Status Codes
| Code | Description | Possible Reasons |
|---|---|---|
| 1 | Success | Success |
| Other | Failure | Failure |
Payment Disbursement General Status
{
"status": 1,
"message": "PROCESSING SUCCESS",
"data": {}
}Payment Disbursement Status Codes
| Code | Description | Possible Reasons |
|---|---|---|
| 0 | PROCESSING FAILED | Failure due to undetermined external causes |
| 1 | PROCESSING SUCCESS | Processing successful |
| 10 | IP ILLEGAL | The requester's IP address is illegal or unregistered |
| 11 | IDENTITY ERROR | Identity verification failed |
| 12 | PARAMETER FORMAT ERROR | Incorrect parameter format, invalid JSON data |
| 13 | NECESSARY PARAMETER MISSING | Missing required parameters |
| 14 | ORDER_ID REPEAT | Duplicate transaction ID |
| 15 | BANK_ID ERROR | Incorrect bank code for disbursement |
| 20 | REQUEST REJECTED | Request was rejected due to frequent or restricted access |
| 21 | PROCESSING TIMEOUT | Processing timed out |
| 23 | LOW BALANCE | Insufficient balance |
| 24 | ORDER NOT EXIST | Order not exist |
| 99 | UNKNOWN ERROR | Unknown platform error |