To integrate with Stripe, make sure you have the Stripe key and register with the Payment Gateway. See Payment Gateway to register.
Environment | BASE_URL |
Staging | https://payment-hub.bnlstg.com |
Production | https://paymenthub.bookandlink.com |
# | Feature | Support |
1 | Return to specific URL after success or failed to pay | NO |
2 | Tokenize credit card | YES |
3 | Tokenize 3ds credit card | YES |
The following is a list of available currencies supported by the Stripe Payment Gateway.
Stripe uses the chosen language to localize invoice emails and PDFs, receipt emails and PDFs, and credit note PDFs. The selected language will not be used on the payment link page.
Stripe didn't allows to present hosted payment links via html iframe. Below a screenshots of the hosted payment link from Stripe.
Refunds are used to return funds to clients for invoices that have paid status. Stripe makes it possible to process full refunds and partial refunds, as well as check the status of refunds.
Transaction Webhook is used to obtain real-time transaction data when an invoice is paid, refund and payment failed. Adding hooks can be done via the stripe dashboard → https://dashboard.stripe.com/test/webhooks
To implemented Payment Hub Invoice Hook, please adding Payment Hub endpoint as invoice.paid, charge.expired, charge.failed, charge.refunded hook event name.
Webhook Value:
BASE_URL/api/v1/hook/stripe
Tokenize is used to generate tokens based on the user's credit card. Later this token can be used to make payments or charge transactions.
In Payment Hub, this endpoint can be used specifically to create tokens only, or automatically charge transactions.
We recommend that this process be carried out directly from the client page so that the customer's credit card credentials do not pass through your server. This process can be done with your public token or client token as the Authorization header. For the security of your account, use a public token if this process is done via client side.
POST: BASE_URL/api/v1/transactions/token
curl --location 'BASE_URL/api/v1/transactions/token' \
--header 'Accept: application/json' \
--header 'Authorization: Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9' \
--header 'Content-Type: application/json' \
--data '{
"payment_vendor": "65f3b208559e33aa146f7dca",
"credit_card" : {
"account_name" : "John Doe",
"account_number" : "3530111333300000",
"exp_month" : "12",
"exp_year" : 2040,
"cvn" : "123",
"email" : "dev@bookandlink.com",
"phone" : "081xxxxxxxxxxxx"
}
}'
<html>
<body>
<button onclick="generateToken()">Generate Token</button>
</body>
<script>
async function generateToken() {
var public_key = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9";
const token = await fetch('BASE_URL/api/v1/transactions/token', {
method: 'POST',
headers: {
'Content-Type': 'application/json',
'Authorization': `Bearer ${public_key}`,
},
body: JSON.stringify({
"payment_vendor": "65f3b208559e33aa146f7dca",
"credit_card" : {
"account_name" : "Test Card",
"account_number": "3530111333300000",
"exp_month" : "12",
"exp_year" : 2040,
"cvn" : "123",
"email" : "dev@bookandlink.com",
"phone" : "081xxxxxxxxxxxx"
}
})
}).then(r => r.json())
console.log(token);
}
</script>
</html>
Field | Descriptions | Type |
---|---|---|
payment_vendor | Your payment gateway ID to use. | text |
credit_card.account_name | Customer credit card account name | text |
credit_card.account_number | Customer credit card account number | text |
credit_card.exp_month | Customer credit card expired account month | text |
credit_card.exp_year | Customer credit card expired account year | number |
credit_card.cvn | 3 digit of credit card CVN | text |
credit_card.email | Customer email | text |
credit_card.phone | Customer phone number | text |
{
"success": true,
"message": "Tokenize successfully",
"data": {
"token": "tok_1QOxafF7o6utiGeADUlGCxsa",
"status": "verified",
"transaction": null
}
}
POST: BASE_URL/api/v1/transactions/token
curl --location 'BASE_URL/api/v1/transactions/token' \
--header 'Accept: application/json' \
--header 'Authorization: Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9' \
--header 'Content-Type: application/json' \
--data '{
"payment_vendor": "65f3b208559e33aa146f7dca",
"credit_card" : {
"account_name" : "John Doe",
"account_number" : "4000000000001091",
"exp_month" : "12",
"exp_year" : 2040,
"cvn" : "123",
"email" : "dev@bookandlink.com",
"phone" : "081xxxxxxxxxxxx"
},
"transaction_detail" : {
"merchant_ref_code": "84b88501",
"amount": 100000,
"service_charge": 0,
"description": "Invoice 84b88501",
"currency" : "IDR",
"first_name": "",
"last_name": "",
"mobile": "",
"email": "",
"send_email" : true,
"webhook_url": "https://clientpage.io/webhook/84b88501"
}
}'
<html>
<body>
<button onclick="generateToken()">Generate Token</button>
</body>
<script>
async function generateToken() {
var public_key = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9";
const token = await fetch('BASE_URL/api/v1/transactions/token', {
method: 'POST',
headers: {
'Content-Type': 'application/json',
'Authorization': `Bearer ${public_key}`,
},
body: JSON.stringify({
"payment_vendor": "65f3b208559e33aa146f7dca",
"credit_card" : {
"account_name" : "John Doe",
"account_number" : "4000000000001091",
"exp_month" : "12",
"exp_year" : 2040,
"cvn" : "123",
"email" : "dev@bookandlink.com",
"phone" : "+6281xxxxxxxxxxxx"
},
"transaction_detail" : {
"merchant_ref_code": "84b88501",
"amount": 100000,
"service_charge": 0,
"description": "Invoice 84b88501",
"currency" : "IDR",
"first_name": "",
"last_name": "",
"mobile": "",
"email": "",
"send_email" : true,
"webhook_url": "https://clientpage.io/webhook/84b88501"
}
})
}).then(r => r.json())
console.log(token);
}
</script>
</html>
Field | Descriptions | Type |
---|---|---|
payment_vendor | Your payment gateway ID to use | text |
credit_card.account_name | Customer credit card account name | text |
credit_card.account_number | Customer credit card account number | text |
credit_card.exp_month | Customer credit card expired account month | text |
credit_card.exp_year | Customer credit card expired account year | number |
credit_card.cvn | 3 digit of credit card CVN | text |
credit_card.email | Customer email | text |
credit_card.phone | Customer phone | text |
transaction_detail.merchant_ref_code | This is likely a reference code or identifier assigned by the merchant to uniquely identify a particular transaction. It helps in tracking and managing transactions. | mandatory | unique |
transaction_detail.amount | Represents the monetary value of the transaction, indicating the total amount involved in the payment. | mandatory | decimal |
transaction_detail.service_charge | Refers to any additional charges or fees associated with the service. This could include transaction fees or service charges imposed by the payment processing system. | mandatory | decimal |
transaction_detail.description | Provides a brief description or comment related to the transaction. It could include details about the purpose of the payment or any other relevant information. | mandatory | text |
transaction_detail.first_name | Typically the first name of the person involved in the transaction. This could be the first name of the payer or recipient, depending on the context. | optional | text |
transaction_detail.last_name | Typically the last name of the person involved in the transaction. This could be the first name of the payer or recipient, depending on the context. | optional | text |
transaction_detail.mobile | Represents the mobile phone number associated with the transaction. It might be used for notifications or communication related to the payment. | optional | text |
transaction_detail.email | The email address associated with the transaction. Similar to the mobile number, it could be used for communication and transaction-related notifications. | conditional | text Note: required for Stripe and Reddot |
transaction_detail.currency | Indicates the currency in which the transaction is conducted. It specifies the monetary unit, such as USD (U.S. Dollar) or EUR (Euro). Each payment merchant has available currency. To get the available currency, you can check based on Vendor Payment Gateway you used on this transaction. | mandatory | text |
transaction_detail.send_email | Indicate whether this payment link will be sent to the customer via email or not | bool |
transaction_detail.webhook_url * | A URL provided by the merchant where real-time updates or notifications about the transaction status can be sent. Webhooks are often used for automated communication. Once transaction has an update on payment status, Payment Hub will send a signal to this Webhook. You can provide the merchant_ref_code to this webhook URL parameter. When this webhook is called, you can retrieve the transaction status based on merchant_ref_code to get the latest transaction status. | optional | text | GET |
{
"success": true,
"message": "Tokenize and Charge Successfully",
"data": {
"token": "65d419718e2268001799cd87",
"status": "verified",
"transaction": {
"ID": "65d4197150dab0e83598a14b",
"ClientId": "65d2ab05d469920aee62896f",
"Description": "Invoice 84b88501",
"FirstName": "",
"LastName": "",
"Amount": 100000,
"ServiceCharge": 0,
"Mobile": "",
"Currency": "IDR",
"Email": "",
"PaymentMethod": null,
"PaymentVendor": "65f3b208559e33aa146f7dca",
"Status": "paid",
"Total": 100000,
"MerchantRefCode": "84b88501",
"WebhookUrl": "https://clientpage.io/webhook/84b88501",
"PaymentFailReason": "",
"Lang": "",
"SendEmail": true,
"Enable3dSecure": false,
"PaymentLinkType": "",
"ExpiredAt": "0001-01-01T00:00:00Z",
"CreatedAt": "2024-02-20T03:16:01.184Z",
"UpdatedAt": "2024-02-20T03:16:05.429Z",
"VendorId": "",
"VendorOrderId": "",
"VendorPaymentId": "65d419756449350015255ab2",
"VendorPaidAt": "2024-02-20T03:16:05.429Z",
"VendorPaymentChannel": "VISA",
"VendorPaymentMethod": "CREDIT_CARD",
"Refunds": null
}
}
}
Field | Descriptions | type |
---|---|---|
token | Represent the generated token from credit card | text |
status | Represent the token status from merchant. It can be "review", "verified", "failed", "fraud", "skipped", "skipped", "used" | text |
transaction | Represent the transaction that has been charge. Will return null if create token only | object |
Error Code | Message | Description |
---|---|---|
401 | Unauthorized | The client token was invalid |
400 | Validation failed | Inputs are failing validation. The errors field contains details about which fields are violating validation. |
500 | Server went wrong | An internal error occurred |
This endpoint is specifically used to generate 3D secure tokens. This endpoint will provide the one time use token, status and verify URL.
We recommend that this process be carried out directly from the client page so that the customer's credit card credentials do not pass through your server. This process can be done with your public token or client token as the Authorization header. For the security of your account, use a public token if this process is done via client side.
POST: BASE_URL/api/v1/transactions/token/3ds
Server side example
curl --location 'BASE_URL/api/v1/transactions/token/3ds' \
--header 'Accept: application/json' \
--header 'Authorization: Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9' \
--header 'Content-Type: application/json' \
--data '{
"payment_vendor": "65f3b208559e33aa146f7dca",
"credit_card" : {
"account_name" : "John Doe",
"account_number" : "3530111333300000",
"exp_month" : "12",
"exp_year" : 2040,
"cvn" : "123",
"email" : "dev@bookandlink.com",
"phone" : "+6281xxxxxxxxxxxx"
},
"amount" : 10000,
"currency" : "IDR",
"return_url" : "https://example.com/complete"
}'
Client Side Example
<html>
<body>
<button onclick="generateToken()">Generate Token</button>
</body>
<script>
async function generateToken() {
var public_key = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9";
const token = await fetch('BASE_URL/api/v1/transactions/token/3ds', {
method: 'POST',
headers: {
'Content-Type': 'application/json',
'Authorization': `Bearer ${public_key}`,
},
body: JSON.stringify({
"payment_vendor": "65f3b208559e33aa146f7dca",
"credit_card" : {
"account_name" : "John Doe",
"account_number" : "3530111333300000",
"exp_month" : "12",
"exp_year" : 2040,
"cvn" : "123",
"email" : "dev@bookandlink.com",
"phone" : "+6281xxxxxxxxxxxx"
},
"amount" : 10000,
"currency" : "IDR",
"return_url" : "https://example.com/complete"
})
}).then(r => r.json())
console.log(token);
}
</script>
</html>
Field | Descriptions | Type |
---|---|---|
payment_vendor | Your payment gateway ID to use | text |
credit_card.account_name | Customer credit card account name | text |
credit_card.account_number | Customer credit card account number | text |
credit_card.exp_month | Customer credit card expired account month | text |
credit_card.exp_year | Customer credit card expired account year | number |
credit_card.cvn | 3 digit of credit card CVN | text |
credit_card.email | Customer email | text |
credit_card.phone | Customer phone | text |
amount | Amount to charge | number |
currency | Indicates the currency in which the transaction is conducted. | text |
return_url | The URL to redirect the user to after a user successfully verify their credit card token | text |
{
"success": true,
"message": "Tokenize successfully",
"data": {
"token": "pi_3QOxeSF7o6utiGeA2Wjzgz0F",
"status": "review",
"auth_url": "https://hooks.stripe.com/3d_secure_2/hosted?merchant=acct_1OCzfbF7o6utiGeA&payment_intent=pi_3QOxeSF7o6utiGeA2Wjzgz0F&payment_intent_client_secret=pi_3QOxeSF7o6utiGeA2Wjzgz0F_secret_H6UZ31Uj3P2qS7XGulQ778qKf&publishable_key=pk_test_51OCzfbF7o6utiGeAopWCeFg30JZckLPFnopAV35R2ZD2CLsEfeeqYjLS2j1gtBDgZ47zsqa7saUaIUxh5nddkJzX00YFkUcCoj&source=payatt_3QOxeSF7o6utiGeA21SHipMl"
}
}
Field | Descriptions | type |
---|---|---|
token | Represent the generated token from credit card | text |
status | Represent the token status from merchant. It can be "review", "verified", "failed", "fraud", "skipped", "skipped", or "used" | text |
auth_url | If the status was review, client can be redirected to this URL to verify the token before charge. ' | text |
Error Code | Message | Description |
---|---|---|
401 | Unauthorized | The client token was invalid |
400 | Validation failed | Inputs are failing validation. The errors field contains details about which fields are violating validation. |
500 | Server went wrong | An internal error occurred |
This endpoint allow you to check the status of token.
GET: BASE_URL
/api/v1/transactions/token
curl --location --request GET 'BASE_URL/api/v1/transactions/token' \
--header 'Accept: application/json' \
--header 'Authorization: Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.GV-Wei86FcFsdWz8wXMgzyBx06zaQLAUTMK4k-QUrz8' \
--header 'Content-Type: application/json' \
--data '{
"payment_vendor": "65f3eadc9d311dea1a9f1ff8",
"token" : "65d434c1644935001525604c"
}'
{
"success": true,
"message": "Token check result",
"data": {
"chargeable": false,
"description": "The token you requested was in review",
"status": "review",
"token": "65d434c1644935001525604c"
}
}
Field | Descriptions | type |
---|---|---|
chargeable | Indicate the token is available to charge or not | boolean |
description | Indicate the description of token state | text |
status | Represent the token status from merchant. It can be "review", "verified", "failed", "fraud", "skipped", "skipped", or "used" | text |
token | Echo back the token from your payload | text |
If you don't want to automatically charge generated tokens, you can charge them manually via this endpoint.
POST: BASE_URL/api/v1/transactions/charge
curl --location 'BASE_URL/api/v1/transactions/charge' \
--header 'Accept: application/json' \
--header 'Authorization: Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9' \
--header 'Content-Type: application/json' \
--data '{
"payment_vendor" : "65f3b208559e33aa146f7dca",
"token" : "65d434c1644935001525604c",
"transaction_detail" : {
"merchant_ref_code": "TEST_STG-500000007",
"amount": 200000,
"service_charge": 0,
"description": "Invoice TEST_STG-500000007",
"currency": "IDR",
"first_name": "",
"last_name": "",
"mobile": "",
"email": "",
"payment_method" : "",
"lang": "",
"send_email" : true,
"webhook_url": "https://payku.bnlstg.com/hook/payment/TEST_STG-500000007"
}
}'
Field | Descriptions | type |
---|---|---|
payment_vendor | Your payment gateway ID to use | text |
token | Credit card token that has been generated from create token endpoint. | text |
transaction_detail | Detailed transaction information that you want to charge | object |
This endpoint will create payment to current transaction based on merchant_ref_code
and will echo back the paid transaction data.
{
"success": true,
"message": "Charge Credit Card Successfully",
"data": {
"token": "65d434c1644935001525604c",
"transaction": {
"ID": "65d4197150dab0e83598a14b",
"ClientId": "65d2ab05d469920aee62896f",
"Description": "Invoice 84b88501",
"FirstName": "",
"LastName": "",
"Amount": 100000,
"ServiceCharge": 0,
"Mobile": "",
"Currency": "IDR",
"Email": "",
"PaymentMethod": null,
"PaymentVendor": "65f3b208559e33aa146f7dca",
"Status": "paid",
"Total": 100000,
"MerchantRefCode": "84b88501",
"WebhookUrl": "https://clientpage.io/webhook/84b88501",
"PaymentFailReason": "",
"Lang": "",
"SendEmail": true,
"Enable3dSecure": false,
"PaymentLinkType": "",
"ExpiredAt": "0001-01-01T00:00:00Z",
"CreatedAt": "2024-02-20T03:16:01.184Z",
"UpdatedAt": "2024-02-20T03:16:05.429Z",
"VendorId": "",
"VendorOrderId": "",
"VendorPaymentId": "65d419756449350015255ab2",
"VendorPaidAt": "2024-02-20T03:16:05.429Z",
"VendorPaymentChannel": "VISA",
"VendorPaymentMethod": "CREDIT_CARD",
"Refunds": null
}
}
}
Error Code | Message | Description |
---|---|---|
401 | Unauthorized | The client token was invalid |
400 | Validation failed | Inputs are failing validation. The errors field contains details about which fields are violating validation. |
500 | Server went wrong | An internal error occurred |