NAV
Mobile SDK
Android iOS

Getting Started

Midtrans mobile SDK enable merchants to accept online payments natively in their mobile apps. We provide the drop-in User interface for making transactions on all payment types supported by Midtrans. Watch the video for the default SDK example.

There are four parties involved in the payment process:

  1. Merchant Server: The merchant backend implementation
  2. Customers
  3. Midtrans Backend (Payment Processor)
  4. Midtrans Mobile SDK

Transaction flow

Transaction Flow Figure

  1. Checkout: Customer clicks the Checkout button on the Host application and the app makes a request to the Merchant Server
  2. Token request: Merchant Server makes a request to Midtrans server with Order Information.
  3. Token response: Midtrans responds with a valid transaction token to Merchant server
  4. Token response: Merchant server forwards the token to the Mobile SDK
  5. Get transaction options: Mobile SDK requests payment/merchant information based on the token
  6. Transaction options response: Mobile SDK renders the payment options and payment information to make the payment
  7. Pay: Customers selects the payment method and the payment details and clicks “Pay”
  8. Charge: Mobile SDK sends the Charge request to the Midtrans Backend for payment Processing.
  9. Charge response: Mobile SDK receives the response from Midtrans Backend and triggers the handler on Mobile App with success/failure/pending status
  10. Charge notification: Midtrans Backend sends a notification to the Merchant backend confirming the completion of transaction.

Security Aspects

The following are configurable parameters of SDK that can be used while performing transaction -

  1. Merchant server Endpoint / Base URL : URL of server to which transaction data will be sent. This will also be referred to as a merchant server.
  2. Transaction details - contains payment information like amount, order Id, payment method etc.
  3. Midtrans Client Key - token that is specified by merchant server to enable the transaction using credit card. Available on the MAP

Prerequisites

  1. Create a merchant account in MAP
  2. In MAP, setup your merchant account settings, in particular the Notification URL.
  3. Setup your merchant server. A server side implementation is required for Midtrans mobile SDK to work. You can check the server implementation reference, and walk through the API’s that you may need for implementation on your backend server.
  4. Minimum requirements:
    • AndroidSDK: Android 4.0 Ice Cream Sandwich API Level 14
    • iOS SDK: iOS 7 and Xcode 8.0

Merchant Server Implementation

Sample Project to implement Merchant Server sample merchant server.

SDK Changes

There are some changes required on merchant server to make use of the latest SDK.

Merchants need to implement the following web services for SDK to work correctly. Note the below points, accept and return Content-Type JSON

Mandatory

Create Token (Checkout) : This API proxies the request to Snap Backend. This process generates the token necessary for the secure communication between Mobile SDK and Midtrans.

Endpoint: POST on /charge

  • Add header in the request.
    • Authorization: Basic Base64(SERVER_KEY:)
  • Request will be sent to checkout / create transaction endpoint at Snap Backend.
  • Note the above request does not go to api.midtrans.com but to app.midtrans.com
    • Sandbox Endpoint: https://app.sandbox.midtrans.com/snap/v1/transactions
    • Production Endpoint: https://app.midtrans.com/snap/v1/transactions

Optional

We also additionally call a few endpoints if 1-Click or 2-Clicks is enabled :

The UserId refers to a generated UUID to associate card collection to each unique user. The mobile SDK generates this UUID during the initialization.

Store Credit Card Token

Endpoint: POST on /users/<userid>/tokens

Request Body

[
  {
      "status_code": "200",
      "cardhash": "481111-1114",
      "token_id": "481111ROMUdhBGMQhjVtEPNcsGee1114"
  },
  {
      "status_code": "200",
      "cardhash": "481111-1114",
      "token_id": "481111ROMUdhBGMQhjVtEPNcsGee1114"
  }
]

Response Code : 200 Response Body

Card is saved

List Credit Cards

Endpoint: GET on /users/<userid>/tokens

Request Body

None

Response Body

[
  {
    "token_id": "481111ROMUdhBGMQhjVtEPNcsGee1114",
    "cardhash": "481111-1114"
  },
  {
    "token_id": "481111ROMUdhBGMQhjVtEPNcsGee1114",
    "cardhash": "481111-1114"
  }
]

Supported Payment Methods

Credit/Debit Cards

Support for making payments via credit cards and or debit cards. We support Visa, Mastercard, American Express and JCB. We also support additional features like two clicks, one click, installment, and pre-authorization.

Bank Transfer

Support payment using BCA Virtual Account, Permata Virtual Account, BNI Virtual Account, and Mandiri Bill Payment.

BCA Virtual Account

BCA Virtual Account is a virtual payment method offered by Bank BCA. Users can pay using their BCA Bank account. Payment can be made through all of Bank BCA’s channels (KlikBCA, m-BCA, and ATM).

Permata Virtual Account

Permata Virtual Account is a virtual payment method facilitated by Bank Permata. Users can pay using any Indonesian Bank account. Payment can be made through ATM Bersama, Prima, or Alto ATM networks.

BNI Virtual Account

BNI Virtual Account is a virtual payment method facilitated by Bank BNI. Users can pay using any Indonesian Bank account. Payment can be made through ATM Bersama, Prima, or Alto ATM networks.

Mandiri Bill Payment

Mandiri Bill is a virtual payment method offered by Bank Mandiri. Users can pay using their Mandiri bank account. Payment can be made through all of Bank Mandiri’s channels (Internet Banking, SMS Banking & ATM).

GO-PAY

GO-PAY is an e-Wallet payment method by GO-JEK. Users will pay using the GO-JEK app.

The user flow varies when using a tablet compared to a smartphone.

When users make a purchase using GO-PAY on a tablet

  1. Users see a QR code on their tablet.
  2. Users open the GO-JEK app on their phone.
  3. Users tap the Scan QR function on the GO-JEK app.

    Scan QR menu on GO-JEK app

    Note : The Scan QR button won’t appear if your GO-PAY balance is less than Rp10,000.
  4. Users point their camera to the QR Code.
    Scan the QR using GO-JEK app on smartphone
  5. Users check their payment details on the GO-JEK app and then tap Pay.
  6. The transaction is complete and the users’ GO-PAY balance is deducted.

When users make a purchase on their smartphone

  1. Users are automatically redirected to the GO-JEK app when making purchases on their smartphone.
  2. Users finish the payment on the GO-JEK app.
  3. The transaction is complete and their GO-PAY balance is deducted.

To enable GO-PAY in Midtrans Mobile SDK, all you need to do is enable GO-PAY payment method on your Merchant Dashboard (MAP). If you want to use it explicitly by applying direct payment, please take a look at this sample code.

KlikBCA

Internet banking direct payment method by Bank BCA. User will be redirected to the KlikBCA website for payment.

BCA Klikpay

Internet banking direct payment method by Bank BCA. User will be redirected to the BCA KlikPay website for payment.

Mandiri Clickpay

Internet banking direct payment method by Bank Mandiri. User will be redirected to the Mandiri Clickpay website for payment.

CIMB Clicks

Internet banking direct payment method by Bank CIMB. User will be redirected to the CIMB Clicks website for payment.

Danamon Online Banking

Internet banking direct payment method by Bank Danamon. User will be redirected to the Danamon Online Banking website for payment.

ePay BRI

Internet banking direct payment method by Bank BRI. User will be redirected to the BRI ePay website for payment.

LINE Pay / Mandiri e-cash

E-Wallet payment method by Bank Mandiri. User will pay through their LINE PAY / Mandiri e-cash account.

Indosat Dompetku

E-Wallet payment method by Indosat. User will pay through their Indosat phone number.

Indomaret - Payment via convenience Stores

Convenience store payment method by Indomaret. User will pay through the physical Indomaret convenience store.

Kioson

Convenience store payment method by Kioson. User will pay through any physical Kioson outlet.

Gift Card Indonesia (GCI)

Gift card-based payment method by GCI. User will pay through the gift card he/she possesses.

Android SDK

This SDK provides an UI to take required information from user to execute transaction.

Sample Project to implement SDK sample project.

Latest Version

Download CircleCI

Latest Released version logs on Github release page.

Download Demo App

If you want to have a look at SDK in more convenient manner, you can download latest version of our demo app from Google Play Store. This app is using the latest version of SDK.

Get it on Google Play

Installation

Add SDK installation following into your build.gradle

Midtrans Bintray repository

repositories {
    jcenter()
        // Add the midtrans repository into the list of repositories
        maven { url "http://dl.bintray.com/pt-midtrans/maven" }
        maven { url "https://jitpack.io" }
    }

Sample SDK Sandbox Dependencies

dependencies {
    // For using the Midtrans Sandbox
    compile 'com.midtrans:uikit:1.15.0-SANDBOX' // change the number to the latest version
  }

Sample SDK Production Dependencies

dependencies {
    // For using the Midtrans Production
    compile 'com.midtrans:uikit:1.15.0' // change the number to the latest version
}

You need to add Midtrans SDK inside your app’s module build.gradle. Make sure to use the proper environment (SANDBOX / PRODUCTION)

Midtrans SDK Initialization

SdkUIFlowBuilder.init()
        .setClientKey(CLIENT_KEY) // client_key is mandatory
        .setContext(CONTEXT) // context is mandatory
        .setTransactionFinishedCallback(new TransactionFinishedCallback() {
                    @Override
                   public void onTransactionFinished(TransactionResult result) {
                       // Handle finished transaction here.
                   }
                }) // set transaction finish callback (sdk callback)
        .setMerchantBaseUrl(BASE_URL) //set merchant url (required)
        .enableLog(true) // enable sdk log (optional)
        .setColorTheme(new CustomColorTheme("#FFE51255", "#B61548", "#FFE51255")) // set theme. it will replace theme on snap theme on MAP ( optional)
        .buildSDK();

Then you need to initialize it on your activity or application class.

Note:

Differentiate Sandbox and Production in one app (Optional)

Differentiate Sandbox and Production Flavors

android {
  ...
  // Define Merchant BASE URL and CLIENT KEY for each flavors
  productFlavors {
          sandbox {
              buildConfigField "String", "BASE_URL", "\"https://merchant-url-sandbox.com/\""
              buildConfigField "String", "CLIENT_KEY", "\"VT-CLIENT-sandbox-client-key\""
          }

          production {
              buildConfigField "String", "BASE_URL", "\"https://merchant-url-production.com/\""
              buildConfigField "String", "CLIENT_KEY", "\"VT-CLIENT-production-client-key\""
         }
  }
  ...
}

// Define Midtrans SDK dependencies for each flavors
dependencies {
  ...
  sandboxCompile 'com.midtrans:uikit:1.16.0-SANDBOX' // change the version to latest one
  productionCompile 'com.midtrans:uikit:1.16.0' // change the version to latest one
  ...
}

You can support two payment environments in your app by defining two flavors in your build.gradle.

Initialize Midtrans SDK using provided base URL and client key in BuildConfig

SdkUIFlowBuilder.init()
        .setClientKey(CLIENT_KEY) // client_key is mandatory
        .setContext(CONTEXT) // context is mandatory
        .setTransactionFinishedCallback(new TransactionFinishedCallback() {
                    @Override
                   public void onTransactionFinished(TransactionResult result) {
                       // Handle finished transaction here.
                   }
                }) // set transaction finish callback (sdk callback)
        .setMerchantBaseUrl(BASE_URL) //set merchant url (required)
        .enableLog(true) // enable sdk log (optional)
        .setColorTheme(new CustomColorTheme("#FFE51255", "#B61548", "#FFE51255")) // set theme. it will replace theme on snap theme on MAP ( optional)
        .buildSDK();

Initialize your SDK using merchant BASE_URL and CLIENT_KEY provided by BuildConfig data.

Adding external card scanner (Optional)

Scan card SDK Dependencies

   //..other dependencies
   compile ('com.midtrans:scancard:1.16.0'){
      exclude module: 'uikit'
   }

We provide a plugin to integrate card.io to allow customers to read/scan the credit card/debit card information using their mobile phone camera.

You can add external card scanner using ScanCardLibrary implementation by midtrans scan card library into your app’s dependencies in build.gradle.

initialize SDK with ScanCard library

SdkUIFlowBuilder.init(...)
        // initialization for using external scancard
        .setExternalScanner(new ScanCard())
        .buildSDK();

Then, when initializing the SDK you can setExternalScanner(new ScanCard()) on SdkUIFlowBuilder

Adding Customer Detail (Optional)

Create UserDetail object

UserDetail userDetail = LocalDataHandler.readObject("user_details", UserDetail.class);
if (userDetail == null) {
    userDetail = new UserDetail();
    userDetail.setUserFullName("Budi Utomo");
    userDetail.setEmail("budi@utomo.com");
    userDetail.setPhoneNumber("08123456789");
    // set user ID as identifier of saved card (can be anything as long as unique),
    // randomly generated by SDK if not supplied
    userDetail.setUserId("budi-6789");

    ArrayList<UserAddress> userAddresses = new ArrayList<>();
    UserAddress userAddress = new UserAddress();
    userAddress.setAddress("Jalan Andalas Gang Sebelah No. 1");
    userAddress.setCity("Jakarta");
    userAddress.setAddressType(com.midtrans.sdk.corekit.core.Constants.ADDRESS_TYPE_BOTH);
    userAddress.setZipcode("12345");
    userAddress.setCountry("IDN");
    userAddresses.add(userAddress);
    userDetail.setUserAddresses(userAddresses);
    LocalDataHandler.saveObject("user_details", userDetail);
}

By default, SDK expect you to supply it with customer detail. Customer detail usually consists of first and last name, email, phone number, billing address, and shipping address. For addresses, you can set billing and shipping as one address. If you want to send customer detail to your merchant server during checkout, please create UserDetail object and supply it into SDK. During checkout, SDK will automatically look for UserDetail instance and put it in JSON request as CustomerDetail.

If you don’t want to supply customer detail at all, you can use UIKitCustomSetting to skip this process.

Installation using a wizard (or setup assistant)

Pre-condition :

Integration

Please follow below steps in order to connect with us.

  1. You need to download Devsupport AI application.
  2. Install and open the App, you should see a screen below: devsupport-ai
  3. You can either open the folder containing the Android source code, drag-and-drop the source folder, or just choose one from “Recent Projects”.
  4. In this case, please choose the previously created project, named Jual-in. Proceed it by click on Integrate icon.
  5. Type/Search for “Midtrans” (without quotes) when asked for the product you would like to integrate.
  6. Click on “Midtrans android integration
  7. Enter your Sandbox Client Key and Server Key then Proceed. If you enter wrong key combination, the app will let you know the keys are incorrect.
  8. We will be able to see the changes that Devsupport AI will implement to Android project (Jual-in). Proceed by clicking Apply changes.
  9. If everything went smooth, you will see this summary.
  10. Close the Devsupport AI and open Android project in Android Studio. Then, Android Studio will download all required dependencies that previously written by Devsupport AI. If not, please do trigger project sync.
  11. Now we have two new methods : initListener() and midpay(). All we need to do is call the midpay() method with its required parameter (email, phone number, name, and transaction amount). For example, we can trigger the method everytime we click on FAB (Floating Action Bar).
  12. Run the project.

NOTE : Before running the project, please make sure that host app (in this case Jual-in) doesn’t use action bar in its theme because it will be clash with toolbar used in Midtrans SDK. For example, we can use this config in styles.xml :

<style name="AppTheme" parent="Theme.AppCompat.Light.NoActionBar">

Let Us Know Your Thoughts

Is our wizard (or setup assistant, using Devsupport AI) helpful? Do you have any feedback? Please share your feedback here.

Prepare Transaction Details

TRANSACTION_ID and TOTAL_AMOUNT are required to create a transaction request for each payment.

Create Transaction Request object

TransactionRequest transactionRequest = new TransactionRequest(TRANSACTION_ID, TOTAL_AMOUNT);

Item Details

Item details are required for Mandiri Bill and BCA KlikPay payment; it is optional for other payment methods.

ItemDetails class holds information about item purchased by user. TransactionRequest takes an array list of item details.

Item Details Object

ItemDetails itemDetails1 = new ItemDetails(ITEM_ID_1, ITEM_PRICE_1, ITEM_QUANTITY_1, ITEM_NAME_1);
ItemDetails itemDetails2 = new ItemDetails(ITEM_ID_2, ITEM_PRICE_2, ITEM_QUANTITY_2, ITEM_NAME_2);

// Create array list and add above item details in it and then set it to transaction request.
ArrayList<ItemDetails> itemDetailsList = new ArrayList<>();
itemDetailsList.add(itemDetails1);
itemDetailsList.add(itemdetails2);

// Set item details into the transaction request.
transactionRequest.setItemDetails(itemDetailsList);

Note:

Bill Info

Bill Info is optional for Mandiri Bill payment only.

BillInfoModel class holds information about billing information that will be shown in billing details.

Bill Info object

BillInfoModel billInfoModel = new BillInfoModel(BILL_INFO_KEY, BILL_INFO_VALUE);
// Set the bill info on transaction details
transactionRequest.setBillInfoModel(billInfoModel);

Set Transaction Request into SDK Instance

After creating transaction request with optional fields above, you must set it into SDK instance.

Set Transaction Request into SDK instance

MidtransSDK.getInstance().setTransactionRequest(transactionRequest);

Starting Payment

Starting Payment

CreditCard creditCardOptions = new CreditCard();
// Set to true if you want to save card to Snap
creditCardOptions.setSaveCard(false);
// Set to true to save card token as `one click` token
creditCardOptions.setSecure(false);
// Set bank name when using MIGS channel
creditCardOptions.setBank(BankType.BANK_NAME);
// Set MIGS channel (ONLY for BCA, BRI and Maybank Acquiring bank)
creditCardOptions.setChannel(CreditCard.MIGS);
// Set Credit Card Options
transactionRequest.setCreditCard(creditCardOptions);
// Set transaction request into SDK instance
MidtransSDK.getInstance().setTransactionRequest(transactionRequest);

Start payment method screen

Default mode for Android SDK is showing payment method screen. This screen will show all of your available payment methods.

You can enable/disable payment methods via Snap Preferences in MAP.

Start payment method select screen

MidtransSDK.getInstance().startPaymentUiFlow(ACTIVITY_CONTEXT);

Start payment by using snap token

We provide SDK method to allow you to make payment by using snap token without initialize transaction request first. You just need to pass snap token as argument of startPaymentUiFlow method

Start payment by using snap token

MidtransSDK.getInstance().startPaymentUiFlow(ACTIVITY_CONTEXT, SNAP_TOKEN);

Acquiring Bank

We provide acquiring bank option that can be used to make payment using credit card :

If you are using bca, bri, or maybank as your acquiring bank (MIGS channel), you have to define its channel explicitly.

Acquiring Bank Configuration

CreditCard creditCardOptions = new CreditCard();
//...
// Set bank name when using MIGS channel. for example bank BRI
creditCardOptions.setBank(BankType.BRI);
// Set MIGS channel (ONLY for BCA, BRI and Maybank Acquiring bank)
creditCardOptions.setChannel(CreditCard.MIGS);
//...

iOS SDK

Latest Version

MidtransKit

Latest released version logs on Github release page.

Integration

Prequisite

Please install Cocoapods version 1.0.0. You can find the installation guide here

Instalation

Instalation - Podfile

def shared_pods
    pod 'MidtransCoreKit'
    pod 'MidtransKit'
end

target 'MyBeautifulApp' do
    shared_pods
end

Installation - install command

pod install --verbose

Integration

Integration

//AppDelegate.m
#import <MidtransKit/MidtransKit.h>

[CONFIG setClientKey:@"VT-CLIENT-sandbox-client-key"
         environment:MidtransServerEnvironmentSandbox
   merchantServerURL:@"https://merchant-url-sandbox.com"];

Once you have completed installation of MidtransKit, configure it with your clientKey, merchant server URL and server environment in your AppDelegate.h

Enable Card Scanner (using Card.IO library)

Podfile for CardIO

platform :ios, '7.0'

def shared_pods
    pod 'MidtransKit'
    pod 'MidtransKit/CardIO'
end

target 'MyBeautifulApp' do
    shared_pods
end

We provide a plugin to integrate card.io to allow customers to read/scan the credit card/debit card information using their mobile phone camera. If you want to support this external card scanner, follow these steps

Update Cocoapods

pod update --verbose

Making Transactions

Generate TransactionTokenResponse object

Generate TransactionTokenResponse

//ViewController.m
MidtransItemDetail *itemDetail =
[[MidtransItemDetail alloc] initWithItemID:@"item_id"
                                      name:@"item_name"
                                     price:item_price
                                  quantity:item_quantity];

MidtransCustomerDetails *customerDetail =
[[MidtransCustomerDetails alloc] initWithFirstName:@"user_firstname"
                                          lastName:@"user_lastname"
                                             email:@"user_email"
                                             phone:@"user_phone"
                                   shippingAddress:ship_address
                                    billingAddress:bill_address];

MidtransTransactionDetails *transactionDetail =
[[MidtransTransactionDetails alloc] initWithOrderID:@"order_id"
                                     andGrossAmount:items_gross_amount];

[[MidtransMerchantClient shared]
 requestTransactionTokenWithTransactionDetails:transactionDetail
 itemDetails:self.itemDetails
 customerDetails:customerDetail
 completion:^(MidtransTransactionTokenResponse *token, NSError *error)
 {
     if (token) {

     }
     else {

     }
 }];

To create this object, you need to prepare required objects like item object etc.

Present the MidtransUIPaymentViewController

Present payment page

MidtransUIPaymentViewController *vc = [[MidtransUIPaymentViewController alloc] initWithToken:token];
[self presentViewController:vc animated:YES completion:nil];

We provide you a MidtransUIPaymentViewController to handle all the payment. Use the generated TransactionTokenResponse as required parameter.

Get Notified

Conform with MidtransUIPaymentViewControllerDelegate

//ViewController.m

#import <MidtransKit/MidtransKit.h>

@interface ViewController () <MidtransUIPaymentViewControllerDelegate>
//other code

SDK will give callback/ delegate transaction response to host app. To be able to do so, please follow these steps:

Set the delegate

//ViewController.m

MidtransUIPaymentViewController *vc = [[MidtransUIPaymentViewController alloc] initWithToken:token];
//set the delegate
vc.paymentDelegate = self;

Implement the functions of delegate

//ViewController.m

#pragma mark - MidtransUIPaymentViewControllerDelegate

- (void)paymentViewController:(MidtransUIPaymentViewController *)viewController paymentSuccess:(MidtransTransactionResult *)result {
    NSLog(@"success: %@", result);
}

- (void)paymentViewController:(MidtransUIPaymentViewController *)viewController paymentFailed:(NSError *)error {
    [self showAlertError:error];
}

- (void)paymentViewController:(MidtransUIPaymentViewController *)viewController paymentPending:(MidtransTransactionResult *)result {
    NSLog(@"pending: %@", result);
}

- (void)paymentViewController_paymentCanceled:(MidtransUIPaymentViewController *)viewController {
    NSLog(@"canceled");
}

Custom Acquiring Bank

Config Acquiring Bank

/* available acquiring banks
MTAcquiringBankBCA,
MTAcquiringBankBRI,
MTAcquiringBankCIMB,
MTAcquiringBankMandiri,
MTAcquiringBankBNI,
MTAcquiringBankMaybank
*/

CC_CONFIG.acquiringBank = MTAcquiringBankMaybank; //ex. maybank

We already support these banks

Features

Two Clicks Payment

Two clicks feature allows you to capture the customer’s card number, expiry date, email and phone number as a TWO_CLICKS_TOKEN. For successive payments by the same customer, the TWO_CLICKS_TOKEN can be utilized to pre-fill the details. The customer just needs to fill out the cvv number to finish the payment. Please see the configuration on the example code to enable the two clicks mode.

CreditCard creditCardOptions = new CreditCard();
// Set to true if you want to save card as two click payment
creditCardOptions.setSaveCard(true);
// Set secure option to enable or disable 3DS secure
creditCardOptions.setAuthentication(CreditCard.AUTHENTICATION_TYPE_3DS);
// Set Credit Card Options
transactionRequest.setCreditCard(creditCardOptions);
// Set transaction request into SDK instance
MidtransSDK.getInstance().setTransactionRequest(transactionRequest);
CC_CONFIG.paymentType = MTCreditCardPaymentTypeTwoclick;
CC_CONFIG.saveCardEnabled = YES;

To support two clicks configuration, merchant can use both default token storage on Midtrans backend or use their server to store their customer credentials.

Using Default Token Storage

By default this SDK will use Midtrans token storage to save customer credential so you don’t need to setup anything on your backend.

Store Token on Merchant Server

Please take a look at this guide to see save card feature implementation in your own server.

Then you need to configure SDK to disable the built-in token storage.

Disable built-in token storage

SdkUIFlowBuilder.init(CONTEXT, CLIENT_KEY, BASE_URL, CALLBACK)
                    // disable built in token storage
                    .useBuiltInTokenStorage(false)
                    .buildSDK();
CC_CONFIG.paymentType = MTCreditCardPaymentTypeTwoclick;
CC_CONFIG.tokenStorageEnabled = NO;

One Click Payment

In addition to two clicks feature, SNAP also supports one click transaction which will also capture the card’s cvv. With this, customers can directly proceed to pay without input any information.

One click payment configuration

CreditCard creditCardOptions = new CreditCard();
// Set to true if you want to save card as one click
creditCardOptions.setSaveCard(true);
// Set to true to save card token as `one click` token
creditCardOptions.setAuthentication(CreditCard.AUTHENTICATION_TYPE_3DS);
// Set Credit Card Options
transactionRequest.setCreditCard(creditCardOptions);
// Set transaction request into SDK instance
MidtransSDK.getInstance().setTransactionRequest(transactionRequest);
CC_CONFIG.paymentType = MTCreditCardPaymentTypeOneclick;
CC_CONFIG.saveCardEnabled = YES;

//1-click need token storage enabled
CC_CONFIG.tokenStorageEnabled = YES;

//1-click need 3ds enabled
CC_CONFIG.secure3DEnabled = YES;

To ease card saving process, SNAP provides card token storage feature. So, merchants don’t have to store and manage credit card token by themselves. Merchants can easily integrate credit card token storage feature to SNAP by providing unique user_id that associates with customers’ account on merchant’s system, in addition to enabling credit_card.save_card flag.

SNAP will then decide to store credit card token as one click token based on two criteria:

For one click payment, you can only use the built token storage as credentials storage option.

Installment

Prerequisites

There are few things that needs to be checked before installment can be used.

  1. MID for installment must be activated (please contact support@midtrans.com to activate MID)
  2. Setup merchant server to handle checkout request. (Please see this wiki)

Provide Installment Data

Example of installment data.

"installment": {
      "required": false,
      "terms": {
        "bni": [3, 6, 12],
        "mandiri": [3, 6, 12],
        "cimb": [3],
        "bca": [3, 6, 12],
        "offline": [6, 12]
      }
    }

Complete JSON request

{
    "transaction_details": {
        "order_id": "ORDER-ID",
        "gross_amount": 10000
    },
    "credit_card": {
        "secure": true,
        "channel": "migs",
        "bank": "bca",
        "installment": {
            "required": false,
            "terms": {
                "bni": [
                    3,
                    6,
                    12
                ],
                "mandiri": [
                    3,
                    6,
                    12
                ],
                "cimb": [
                    3
                ],
                "bca": [
                    3,
                    6,
                    12
                ],
                "offline": [
                    6,
                    12
                ]
            }
        },
        "whitelist_bins": [
            "48111111",
            "41111111"
        ]
    },
    "item_details": [
        {
            "id": "ITEM1",
            "price": 10000,
            "quantity": 1,
            "name": "Midtrans Bear"
        }
    ],
    "customer_details": {
        "first_name": "TEST",
        "last_name": "MIDTRANSER",
        "email": "test@midtrans.com",
        "phone": "+628123456",
        "billing_address": {
            "first_name": "TEST",
            "last_name": "MIDTRANSER",
            "email": "test@midtrans.com",
            "phone": "081 2233 44-55",
            "address": "Sudirman",
            "city": "Jakarta",
            "postal_code": "12190",
            "country_code": "IDN"
        },
        "shipping_address": {
            "first_name": "TEST",
            "last_name": "MIDTRANSER",
            "email": "test@midtrans.com",
            "phone": "0 8128-75 7-9338",
            "address": "Sudirman",
            "city": "Jakarta",
            "postal_code": "12190",
            "country_code": "IDN"
        }
    }
}

In order to use installment in mobile SDK, merchant server must intercept mobile SDK’s request and add installment data that is sent to Midtrans backend (snap). From the Mobile side, there are no changes needed.

Optionally whitelist_bins can be used to accept only card numbers within the specified BIN numbers. (whitelist_bins is required for offline installment type)

Mobile SDK and Midtrans backend (snap) will check if the card numbers’ first n digit numbers contain one of bins available in whitelist_bins.

This installment object and whitelist bins need to be added at credit_card object when the server accepts the transaction request from mobile SDK. A full example of installment data sent to Snap is like this.

BNI Point

BNI Point is special feature for BNI Bank customers. This feature allows users to redeem their point to be applied into their credit card payments. In your app side, there’s no adjustment needed. To enabled this feature in mobile SDK you just need to contact our support team. Please have a look to the following BNI Point flow to know more about this feature.

Mandiri Fiestapoin

Mandiri Fiestapoin is special feature for Mandiri Bank customers. This feature allows users to redeem their Mandiri fiestapoin to be applied into their credit card payments. In your app side, there’s no adjustment needed. To enabled this feature in mobile SDK you just need to contact our support team.

Risk Based Authentication (RBA)

Set up RBA

CreditCard creditCard = new CreditCard();
// ....
// make set authentication to RBA
creditCard.setAuthentication(CreditCard.AUTHENTICATION_TYPE_RBA);

// Set into transaction Request
TransactionRequest transactionRequest = MidtransSDK.getInstance().getTransactionRequest();
transactionRequest.setCreditCard(creditCard);
CC_CONFIG.authenticationType = MTAuthenticationTypeRBA;

RBA is a program from VISA for merchants to be able to route each of their transactions to use 3DS MID or non-3DS based on their risk level.

Under RBA program, VISA wish to help merchants to protect their transactions without sacrificing their conversion rate due to known issues in current 3DS (delayed/unsent OTP, connection, etc).

Example: Use 3D secure if customer is using US card and did more than 3 transactions in the last 1 hour. Use non 3D Secure if customer is using Indonesia card and amount is less than 100,000.

This feature can be activated by contacting our support team. Then you need to configure the SDK to use this feature.

Pre Authorization

Set up authorize transaction

CreditCard creditCard = new CreditCard();
creditCard.setType(CardTokenRequest.TYPE_AUTHORIZE);

// Set into transaction Request
TransactionRequest transactionRequest = MidtransSDK.getInstance().getTransactionRequest();
transactionRequest.setCreditCard(creditCard);

// Set into SDK instance
MidtransSDK.getInstance().setTransactionRequest(transactionRequest());
CC_CONFIG.preauthEnabled = YES;

Pre Authorization is a feature to set the credit card transaction type into authorize. If the transaction type is authorize then the merchant needs to capture the payment in MAP. To use this feature you need to add a settings into the credit card options in transaction request.

Direct payment screen

Start Direct Payment Screen

startPaymentUiFlow(CONTEXT, PAYMENT_METHOD)

// or run the SDK by using snap token
startPaymentUiFlow(CONTEXT, PAYMENT_METHOD, SNAP_TOKEN)
// example : credit card payment
MidtransSDK.getInstance().startPaymentUiFlow(MainActivity.this, PaymentMethod.CREDIT_CARD);
// example : credit card payment
MidtransUIPaymentViewController *paymentVC =
[[MidtransUIPaymentViewController alloc] initWithToken:token
                andPaymentFeature:MidtransPaymentFeatureCreditCard];

Other PAYMENT_METHOD Possible Value

//bank transfer
PaymentMethod.BANK_TRANSFER    
//bank transfer BCA
PaymentMethod.BANK_TRANSFER_BCA
//bank transfer Mandiri
PaymentMethod.BANK_TRANSFER_MANDIRI
//bank transfer Permata
PaymentMethod.BANK_TRANSFER_PERMATA
//bank transfer BNI
PaymentMethod.BANK_TRANSFER_BNI
//bank transfer other
PaymentMethod.BANK_TRANSFER_OTHER
//GO-PAY
PaymentMethod.GO_PAY
//BCA KlikPay
PaymentMethod.BCA_KLIKPAY
//KlikBCA
PaymentMethod.KLIKBCA
//Mandiri Clickpay
PaymentMethod.MANDIRI_CLICKPAY
//Mandiri e-cash / LINE Pay
PaymentMethod.MANDIRI_ECASH
//e-Pay BRI
PaymentMethod.EPAY_BRI
//CIMB Clicks
PaymentMethod.CIMB_CLICKS
//Indomaret
PaymentMethod.INDOMARET
//Kioson
PaymentMethod.KIOSON
//Gift Card Indonesia
PaymentMethod.GIFT_CARD_INDONESIA
//Indosat Dompetku
PaymentMethod.INDOSAT_DOMPETKU
//Danamon online
PaymentMethod.DANAMON_ONLINE
typedef NS_ENUM(NSInteger, MidtransPaymentFeature) {
    MidtransPaymentFeatureCreditCard,
    MidtransPaymentFeatureBankTransfer,///va
    MidtransPaymentFeatureBankTransferBCAVA,
    MidtransPaymentFeatureBankTransferMandiriVA,
    MidtransPaymentFeatureBankTransferBNIVA,
    MidtransPaymentFeatureBankTransferPermataVA,
    MidtransPaymentFeatureBankTransferOtherVA,
    MidtransPaymentFeatureKlikBCA,
    MidtransPaymentFeatureIndomaret,
    MidtransPaymentFeatureCIMBClicks,
    MidtransPaymentFeatureCStore,
    midtranspaymentfeatureBCAKlikPay,
    MidtransPaymentFeatureMandiriEcash,
    MidtransPaymentFeatureEchannel,
    MidtransPaymentFeaturePermataVA,
    MidtransPaymentFeatureBRIEpay,
    MidtransPaymentFeatureTelkomselEcash,
    MidtransPyamentFeatureDanamonOnline,
    MidtransPaymentFeatureIndosatDompetku,
    MidtransPaymentFeatureXLTunai,
    MidtransPaymentFeatureMandiriClickPay,
    MidtransPaymentFeatureKiosON,
    MidtransPaymentFeatureGCI,
    MidtransPaymentFeatureGOPAY,
    MidtransPaymentCreditCardForm
};

Users can directly go to payment screen and skip the default payment method screen.

Note:

// -----------------------
// GO-PAY CONFIGURATION IOS
// -----------------------


<key>LSApplicationQueriesSchemes</key>
<array>
  <string>gojek</string>
</array>

We provide a method API to make direct payment for all payment methods on Android and iOS SDK.

Card Registration

Card Register Implementation

MidtransSDK.getInstance().UiCardRegistration(CONTEXT, new CardRegistrationCallback() {
                        @Override
                        public void onSuccess(CardRegistrationResponse response) {
                            String savedTokenId = response.getSavedTokenId();
                            String maskedCard = response.getMaskedCard();
                        }

                        @Override
                        public void onFailure(CardRegistrationResponse response, String reason) {
                            // Handle failure here
                        }

                        @Override
                        public void onError(Throwable error) {
                            // Handle error here
                        }
                    });
NSString *clientkey = @"your client key";
NSString *merchantServer = @"your merchant server url";
[[MidtransNetworkLogger shared] startLogging];
[CONFIG setClientKey:clientkey
         environment:MidtransServerEnvironmentSandbox
   merchantServerURL:merchantServer];

NSArray *data = [self.expiryDate.text componentsSeparatedByString:@"/"];
NSString *expMonth = [data[0] stringByReplacingOccurrencesOfString:@" " withString:@""];
NSString *expYear = [NSString stringWithFormat:@"%ld",[data[1] integerValue]+2000];

MidtransCreditCard *creditCard = [[MidtransCreditCard alloc] initWithNumber: [self.cardNumberTextFIeld.text stringByReplacingOccurrencesOfString:@" " withString:@""]  expiryMonth:expMonth expiryYear:expYear cvv:self.cvv.text];
[[MidtransClient shared] registerCreditCard:creditCard completion:^(MidtransMaskedCreditCard * _Nullable maskedCreditCard, NSError * _Nullable error) {
    if (!error) {
        [self saveCreditCardObject:maskedCreditCard];
    }
    else {
    }

}];

Card Registration is a feature to allow customers to save credit card token without doing transactions first. This feature is provided for merchants that will make API-to-API payments. To implement it, you just need to follow the sample code.

Custom Expiry

There is a feature on mobile SDK to enable custom transaction lifetime. To use this feature you need to add an ExpiryModel object into TransactionRequest.

Custom Expiry Configuration

// set expiry time
ExpiryModel expiryModel = new ExpiryModel();

// set start time
long timeInMili = System.currentTimeMillis();
// format the time
DateFormat df = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss Z");
df.setTimeZone(TimeZone.getTimeZone("Asia/Jakarta"));
// format the time as a string
String nowAsISO = df.format(new Date(time));
// set the formatted time to expiry model
expiryModel.setStartTime(Utils.getFormattedTime();
expiryModel.setDuration(1);
// set time unit
expiryModel.setUnit(ExpiryModel.UNIT_MINUTE);
//set expiry time object to transaction request
transactionRequest.setExpiry(expiryModel);
   MidtransTransactionExpire *expireTime = [[MidtransTransactionExpire alloc] initWithExpireTime:nil expireDuration:1 withUnitTime:MindtransTimeUnitTypeHour];

// and then
[[MidtransMerchantClient shared] requestTransactionTokenWithTransactionDetails:trx
                                                                       itemDetails:@[itm]
                                                                   customerDetails:cst
                                                                       customField:arrayOfCustomField
                                                                         binFilter:binFilter
                                                                blacklistBinFilter:blacklistBin
                                                             transactionExpireTime:expireTime
                                                                        completion:^(MidtransTransactionTokenResponse * _Nullable token, NSError * _Nullable error)
Parameter Description
start_time
String(255) (optional) Timestamp in yyyy-MM-dd HH:mm:ss Z format. If not specified, transaction time will be used as start time (when customer charge)
duration
Integer (required for expiry) Expiry duration
unit
String (required for expiry) Expiry unit. Options: day, hour, minute (plural term also accepted)

Custom Field

Set up custom field

TransactionRequest transactionRequest = MidtransSDK.getInstance().getTransactionRequest();
transactionRequest.setCustomField1(CUSTOM_FIELD_1);
transactionRequest.setCustomField2(CUSTOM_FIELD_2);
transactionRequest.setCustomField3(CUSTOM_FIELD_3);
MidtransSDK.getInstance().setTransactionRequest(transactionRequest);

    NSMutableArray *arrayOfCustomField = [NSMutableArray new];
    [arrayOfCustomField addObject:@{MIDTRANS_CUSTOMFIELD_1:@"custom134"}];
    [arrayOfCustomField addObject:@{MIDTRANS_CUSTOMFIELD_2:@"custom3332"}];
    [arrayOfCustomField addObject:@{MIDTRANS_CUSTOMFIELD_3:@"custom3333"}];

// and then
 [[MidtransMerchantClient shared] requestTransactionTokenWithTransactionDetails:self.transactionDetails
                                                                       itemDetails:self.itemDetails
                                                                   customerDetails:self.customerDetails
                                                                       customField:arrayOfCustomField
                                                             transactionExpireTime:nil
                                                                        completion:^(MidtransTransactionTokenResponse * _Nullable token, NSError * _Nullable error)
     {
         ...
}];

These 3 fields will be brought at payment so it will be available at MAP and a HTTP notification will be sent to the merchant.

Custom VA Number

Set up Custom VA Number

// ....
// Custom VA Number Permata Bank
TransactionRequest transactionRequest = MidtransSDK.getInstance().getTransactionRequest();
// custom va number for Permata Bank Transfer must be 10 digits
String PERMATA_VA_NUMBER = "1234512345";
// Set into transaction Request
transactionRequest.setPermataVa(new BankTransferRequestModel(PERMATA_VA_NUMBER));
// ....
// Custom VA Number BCA Bank
TransactionRequest transactionRequest = MidtransSDK.getInstance().getTransactionRequest();
// custom va number
String BCA_VA_NUMBER = "1234512345";
// Set into transaction Request
transactionRequest.setBcaVa(new BankTransferRequestModel(BCA_VA_NUMBER));
// ...

// ....
// Custom VA Number BNI Bank
TransactionRequest transactionRequest = MidtransSDK.getInstance().getTransactionRequest();
// custom va number
String BNI_VA_NUMBER = "1234512345";
// Set into transaction Request
transactionRequest.setBniVa(new BankTransferRequestModel(BNI_VA_NUMBER));
// ...

CONFIG.customBCAVANumber = @"your va string";
CONFIG.customPermataVANumber = = @"your va string";

Mobile SDK provides a feature that allows customized VA Number for the following payment methods - Permata VA (Bank Transfer) - BCA VA (Bank Transfer) - BNI VA (Bank Transfer)

Note - The Custom VA number must consist of numbers. - Custom VA Number for Permata Bank Transfer must be 10 digits

Other Bank ATM / VA Switcher

For bank transfers beside BCA, Mandiri, BNI, or Permata, Midtrans previously utilized Permata as VA processor. Recently, Midtrans adds support for BNI VA, giving the merchant flexibility to choose which one will be used for other bank transfer. The idea is when one of the processors (either BNI or Permata) is down, merchant can switches to other processor, preventing lose of the sales. In order to use this functionality, merchant should enable both BNI VA and Permata VA. The switch itself is located in Snap Preferences in MAP (Merchant Administrator Portal). In merchant app, there’s no adjustment needed. The changes will be valid for the next checkout.

Sub Company Code

Set up sub company code for BCA VA

// ....
// Transaction request
TransactionRequest transactionRequest = MidtransSDK.getInstance().getTransactionRequest();
// sub company code must be exactly 5 digits of number
String SUB_COMPANY_CODE_BCA = "12321";
// Create BcaBankTransferRequestModel object and then set the SUB_COMPANY_CODE_BCA  
BcaBankTransferRequestModel bcaRequestModel = new BcaBankTransferRequestModel();
bcaRequestModel.setSubCompanyCode(SUB_COMPANY_CODE_BCA);
// Set into transaction Request
transactionRequest.setBcaVa(bcaRequestModel);
// sub company code must be exactly 5 digits of number ex:55555
CONFIG.customBCASubcompanyCode = @“55555;

This feature allows you to pass sub company code in VA payment. The sub company code must be exactly 5 digits of number. This feature is only available on BCA VA payment method.

Custom Recipient

Set up Custom Recipient for Permata

// ....
// Custom Recipient Name for Permata Bank
TransactionRequest transactionRequest = MidtransSDK.getInstance().getTransactionRequest();
// custom recipient for Permata Bank Transfer must be 20 character at most and in uppercase
String PERMATA_RECIPIENT = "SUDARSONO";
// Create request model (you can optionally insert custom VA as method argument here)
PermataBankTransferRequestModel permataRequest = new PermataBankTransferRequestModel();
permataRequest.setRecipientName(PERMATA_RECIPIENT);
// Set into transaction Request
transactionRequest.setPermataVa(permataRequest);

Mobile SDK provides a feature that allows merchant to customize recipient name for Permata VA (Bank Transfer). The recipient name will be displayed in the ATM screen.

Note - The custom recipient name must consist of alphanumeric characters and space. No symbol allowed. - Custom recipient name for Permata Bank Transfer must be 20 characters at most, and in uppercase.

Custom Themes

Set up Custom Fonts & Theme Color

/**
 * Android custom font
 */

MidtransSDK midtransSDK = MidtransSDK.getInstance();
midtransSDK.setDefaultText("open_sans_regular.ttf");
midtransSDK.setSemiBoldText("open_sans_semibold.ttf");
midtransSDK.setBoldText("open_sans_bold.ttf")
/**
 * Android custom theme color
 */

// Create Custom Color Theme
String examplePrimary = "#ffffff";
String examplePrimaryDark = "#ffffff";
String exampleSecondary = "#ffffff";
CustomColorTheme colorTheme = new CustomColorTheme(examplePrimary, examplePrimaryDark, exampleSecondary);
// Set Theme color into SDK Builder
SdkUIFlowBuilder.init(this, BuildConfig.CLIENT_KEY, BuildConfig.BASE_URL, this)
                    .setColorTheme(colorTheme)
                    .build();
// or
// Set Theme color into Initialized SDK
MidtransSDK midtransSDK = MidtransSDK.getInstance();
midtransSDK.setColorTheme(colorTheme)
// Set Fonts & Theme color into Initialized SDK
MidtransUIFontSource fontSource =
[[MidtransUIFontSource alloc] initWithFontNameBold:font_name
                                   fontNameRegular:font_name
                                     fontNameLight:font_name];
[MidtransUIThemeManager applyCustomThemeColor:themeColor
                                    themeFont:fontSource];

Mobile SDK provide Fonts and Theme color customization.

Android Custom Themes

Android Custom Fonts

To use a custom font on Android SDK, you need to put your font files to assets directory of project and then just follow the sample code.

Notes:

Android Custom Theme color

To set custom theme in this SDK you just need to provide 3 colors:

iOS Custom Themes

We’ve created MidtransUIThemeManager to configure the theme color and font of the Midtrans payment UI.

Class MidtransUIThemeManager needs UIColor object so you need to convert your HEX or RGB to UIColor, here is a nice tool to generate UIColor code.

Note: If you didn’t configure this MidtransUIThemeManager, your theme color will follow SNAP color configuration on MAP -> SNAP settings preference.

Uikit Custom Settings

We provide Settings to handle more customizable UI in our SDK.

Skip Payment Status

Skip Payment Status

// Init custom settings
UIKitCustomSetting uisetting = new UIKitCustomSetting();
uisetting.setShowPaymentStatus(false); // hide sdk payment status
MidtransSDK.getInstance().setUIKitCustomSetting(uiKitCustomSetting);
UICONFIG.hideStatusPage = YES;

You can skip payment status provided by Midtrans SDK if you want to show your own status page.

Set Default save card options to true

Set default save card options to true

// Init custom settings
UIKitCustomSetting uisetting = new UIKitCustomSetting();
uiKitCustomSetting.setSaveCardChecked(true);
MidtransSDK.getInstance().setUIKitCustomSetting(uiKitCustomSetting);
CC_CONFIG.setDefaultCreditSaveCardEnabled = YES;

In credit card payment page, there is a checkbox to save card and it is not checked by default. You can make this checkbox checked by default by using this settings.

Skip customer detail

Skip customer detail

UIKitCustomSetting setting = MidtransSDK.getInstance().getUIKitCustomSetting();
uiKitCustomSetting.setSkipCustomerDetailsPages(true);
MidtransSDK.getInstance().setUIKitCustomSetting(setting);

On the first SDK usage, user are required to fill in customer details to make a payment. This setting is only for Android SDK due to the iOS SDK not having built-in customer details pages. You can skip this screen if you want by using UIKitCustomSetting.

Add customer contact in credit card form

Add customer contact in credit card form

UIKitCustomSetting setting = MidtransSDK.getInstance().getUIKitCustomSetting();
uiKitCustomSetting.setShowEmailInCcForm(true);
MidtransSDK.getInstance().setUIKitCustomSetting(setting);

If you want to show additional fields for customer contact (phone number and / or email), you can use this option. SDK will automatically display additional fields. Please note that both fields are optional.

To use this feature, please make sure you have installed our latest SDK.

Enable Auto Read OTP (Android Only)

Enable Auto Read SMS OTP

// Init custom settings
UIKitCustomSetting uisetting = new UIKitCustomSetting();
// enable auto read SMS
uiKitCustomSetting.setEnableAutoReadSms(true);
// set custom setting to SDK
MidtransSDK.getInstance().setUIKitCustomSetting(uiKitCustomSetting);

There is an option to enable auto read OTP for credit card payments. You can enable this option by using the following settings.

Bin Promo (Bin Filter)

Whitelist bin object will be like this:

"whitelist_bins": [
      "mandiri",
      "41111111"
    ]

Blacklist bin object will be like this:

"blacklist_bins": [
      "mandiri",
      "41111111"
    ]

So complete bin promo request will be like this:

{
    "transaction_details": {
        "order_id": "ORDER-ID",
        "gross_amount": 10000
    },
    "credit_card": {
        "secure": true,
        "whitelist_bins": [
            "bni",
            "459920"
        ],
          "blacklist_bins": [
            "bri",
            "410505"
          ]
    },
    "item_details": [
        {
            "id": "ITEM1",
            "price": 10000,
            "quantity": 1,
            "name": "Midtrans Bear"
        }
    ],
    "customer_details": {
        "first_name": "TEST",
        "last_name": "MIDTRANSER",
        "email": "test@midtrans.com",
        "phone": "+628123456",
        "billing_address": {
            "first_name": "TEST",
            "last_name": "MIDTRANSER",
            "email": "test@midtrans.com",
            "phone": "081 2233 44-55",
            "address": "Sudirman",
            "city": "Jakarta",
            "postal_code": "12190",
            "country_code": "IDN"
        },
        "shipping_address": {
            "first_name": "TEST",
            "last_name": "MIDTRANSER",
            "email": "test@midtrans.com",
            "phone": "0 8128-75 7-9338",
            "address": "Sudirman",
            "city": "Jakarta",
            "postal_code": "12190",
            "country_code": "IDN"
        }
    }
}

Credit card bins can be filtered by using whitelist_bins or blacklist_bins or both features. To use these features, merchant server must intercept mobile SDK’s request and add list of whitelist bin into request.

Note:

Parameter Description
whitelist_bins
Array (optional)
Allowed credit card BIN numbers. The bin value can be either a prefix (up to 8 digits) of card number or the name of a bank, in which case all the cards issued by that bank will be allowed. The supported bank names are bni bca mandiri cimb bri and maybank. Default: allow all cards
blacklist_bins
Array (optional)
A list of credit card BIN numbers that cannot be used for the transaction. The bin value can be either a prefix (up to 8 digits) of card number or the name of a bank, in which case all the cards issued by that bank will be denied. The supported bank names are bni bca mandiri cimb bri and maybank. Default: allow all cards

Testing Credentials

Here is a list of dummy transaction credentials that can be used for transactions in the Sandbox Environment.

Credit Card

General Testing Card Number

Normal Transaction

VISA Description
No Authentication
Merchant disables 3DS
Accept Transaction: 4011 1111 1111 1112
Challenge by FDS Transaction: 4111 1111 1111 1111
Denied by FDS Transaction: 4211 1111 1111 1110
Denied by Bank Transaction: 4311 1111 1111 1119
MASTERCARD Description
No Authentication
Merchant disables 3DS
Accept Transaction: 5481 1611 1111 1081
Challenge by FDS Transaction: 5110 1111 1111 1119
Denied by FDS Transaction: 5210 1111 1111 1118
Denied by Bank Transaction: 5310 1111 1111 1117

3D Secure Transaction

VISA Description
Full Authentication
Cardholder is 3DS ready
Accept Transaction: 4811 1111 1111 1114
Denied by Bank Transaction: 4911 1111 1111 1113
Attempted Authentication
Cardholder is not enrolled for 3DS
Accept Transaction: 4411 1111 1111 1118
Challenge by FDS Transaction: 4511 1111 1111 1117
Denied by FDS Transaction: 4611 1111 1111 1116
Denied by Bank Transaction: 4711 1111 1111 1115
MASTERCARD Description
Full Authentication
Cardholder is 3DS ready
Accept Transaction: 5211 1111 1111 1117
Denied by Bank Transaction: 5111 1111 1111 1118
Attempted Authentication
Cardholder is not enrolled for 3DS
Accept Transaction: 5410 1111 1111 1116
Challenge by FDS Transaction: 5510 1111 1111 1115
Denied by FDS Transaction: 5411 1111 1111 1115
Denied by Bank Transaction: 5511 1111 1111 1114

Bank-Specific Testing Card

Accepted 3D Secure Card

Bank Card Number
Mandiri
Full Authentication 4617 0069 5974 6656
5573 3810 7219 6900
Attempted Authentication 4617 0017 4194 2101
5573 3819 9982 5417
CIMB
Full Authentication 4599 2078 8712 2414
5481 1698 1883 2479
Attempted Authentication 4599 2039 9705 2898
5481 1671 2103 2563
BNI
Full Authentication 4105 0586 8948 1467
5264 2210 3887 4659
Attempted Authentication 4105 0525 4151 2148
5264 2249 7176 1016
BCA
Full Authentication 4773 7760 5705 1650
5229 9031 3685 3172
Attempted Authentication 4773 7738 1098 1190
5229 9073 6430 3610
BRI
Full Authentication 4365 0263 3573 7199
5520 0298 7089 9100
Attempted Authentication 4365 0278 6723 2690
5520 0254 8646 8439
Maybank
Full Authentication 4055 7720 2603 6004
5520 0867 5210 2334
Attempted Authentication 4055 7713 3514 4012
5520 0867 7490 8452

Accepted Normal Card

Bank Card Number
Mandiri 4617 0030 8177 8145
5573 3899 1384 3648
Mandiri Debit 4097 6658 2970 8136
CIMB 4599 2043 5516 9092
5481 1620 3830 7406
BNI 4105 0568 6475 0672
5264 2282 3919 2765
BNI Private Label 1946 4159 8148 7684
BCA 4773 7781 0290 6680
5229 9028 2076 4661
BRI 4365 0286 6251 2583
5520 0219 0920 3008
Maybank 4055 7796 2846 0474
5520 0883 1465 3770

Denied Card

Bank Card Number
Mandiri 4617 0085 6083 1760
5573 3840 4322 4447
Mandiri Debit 4097 6676 7217 8631
CIMB 4599 2060 0973 3090
5481 1691 9178 2739
BNI 4105 0541 4854 1363
5264 2235 3013 171
BNI Private Label 1946 4102 7193 1269
BCA 4773 7752 0201 1809
5229 9034 0542 3830
BRI 4365 0286 6251 2583
5520 0219 0920 3008
Maybank 4055 7796 2846 0474
5520 0883 1465 3770

Expiry Date and CVV

Input Value
Expiry Month 01
Expiry Year 2020
CVV 123

Bank Transfer

Payment Methods Description
Permata Virtual Account midtrans will generate a dummy 16 digits Permata Virtual Account Number. To perform a test transaction, use the Permata Virtual Account Simulator
BCA Virtual Account midtrans will generate a dummy 11 digits BCA Virtual Account Number. To perform a test transaction, use the BCA Virtual Account Simulator
Mandiri Bill Payment midtrans will generate a 6 digits Payment Code to complete payment via Mandiri e-channel (Internet Banking, SMS Banking, Mandiri ATM). To perform a test transaction, use the Mandiri Bill Payment Simulator

Direct Debit

Payment Methods Description
Mandiri Clickpay Card Number: 4111 1111 1111 1111
Accept Token: 000000
Deny Token: 111111
CIMB Clicks midtrans will redirect CIMB Clicks test transaction to a payment simulator.
Success Transaction: testuser00
Failure Transaction: testuser01
ePay BRI midtrans will redirect ePay BRI test transaction to a payment simulator.
Success Transaction: testuser00
Failure Transaction: testuser03
BCA Klikpay midtrans will redirect BCA Klikpay test transaction to a payment simulator.
Klik BCA midtrans will register user id filled in KlikBCA input. To perform a test transaction, use the KlikBca Simulator

e-Wallet

Payment Methods Description
Telkomsel cash Accept Customer: 0811111111
Deny Customer: 0822222222
XL Tunai midtrans will generate a dummy XL Tunai Merchant Code and Order ID. To perform a test transaction, use the XL Tunai Simulator
Indosat Dompetku Accept number: 08123456789
Deny number: other than 08123456789
LINE Pay e-cash / mandiri e-cash Accept number: 0987654321
PIN: 12345
OTP: 12123434

Convenience Store

Payment Methods Description
Indomaret midtrans will generate a dummy Indomaret Payment Code. To perform a test transaction, use the Indomaret Simulator
Kioson midtrans will generate a dummy Kioson Payment Code. To perform a test transaction, use the Kioson Simulator

Status Codes

Goal: Understand all status codes used by API. For more inquiries, please contact us at support@midtrans.com or visit our support web page.

Status Codes used by midtrans API are categorized into 2xx, 3xx, 4xx dan 5xx.

Code 2xx

Status Description
200 Credit Card: Success. Request is successful, and transaction is successful (authorize, capture, settlement, cancel, get order, approve challenge transactions), accepted by midtrans and bank.
Other payment methods: Success. Transaction is successful/settlement.
201 Credit Card: Challenge. Transaction successfully sent to bank but the process has not been completed, need manual action from merchant to complete the transaction process. If the merchant does not perform any action until settlement time (H+1 16:00) midtrans will cancel the transaction.
Bank Transfer: Pending. Transaction successfully sent to bank but the process has not been completed by the customer. By default the transaction will expire within 24 hours.
CIMB Clicks: Pending. Transaction successfully sent to bank but the process has not been completed by the customer. By default the transaction will expire within 2 hours.
BRI ePay: Pending. Transaction successfully sent to bank but the process has not been completed by the customer. By default the transaction will expire within 2 hours.
Klik BCA: Pending. Transaction successfully sent to bank but the process has not been completed by the customer. By default the transaction will expire within 2 hours.
BCA Klikpay: Pending. Transaction successfully sent to bank but the process has not been completed by the customer. By default the transaction will expire within 2 hours.
Mandiri Bill Payment: Pending. Transaction successfully sent to bank but the process has not been completed by the customer. By default the transaction will expire within 2 hours.
XL Tunai: Pending. Transaction successfully sent to provider but the process has not been completed by the customer. By default the transaction will expire within 2 hours.
Indomaret: Pending. Transaction successfully sent to provider but the process has not been completed by the customer. By default the transaction will expire within 2 hours.
202 Credit Card: Denied. Transaction has been processed but is denied by payment provider or midtrans’ fraud detection system.
Other payment methods: Denied. Transaction has been processed but is denied by payment provider.

Code 3xx

Status Description
300 Move Permanently, current and all future requests should be directed to the new URL

Code 4xx

Status Description
400 Validation Error, merchant sent bad request data example; validation error, invalid transaction type, invalid credit card format, etc.
401 Access denied due to unauthorized transaction, please check client key or server key
402 Merchant doesn’t have access for this payment type
403 The requested resource is only capable of generating content not acceptable according to the accepting headers that sent in the request
404 The requested resource is not found
405 HTTP method is not allowed
406 Duplicate order ID. Order ID has already been utilized previously
407 Expired transaction
408 Merchant sent the wrong data type
409 Merchant has sent too many transactions for the same card number
410 Merchant account is deactivated. Please contact midtrans support
411 Token id is missing, invalid, or timed out
412 Merchant cannot modify status of the transaction
413 The request cannot be processed due to malformed syntax in the request body

Code 5xx

Status Description
500 Internal Server Error
501 The feature has not finished yet, it will be available soon
502 Internal Server Error: Bank Connection Problem
503 Internal Server Error
504 Internal Server Error: Fraud detection is unavailable

Going Live With Mobile SDK

Android

To use the production version in Android, please use the production version of the library and also production client key which you can get from MAP.

Latest Corekit Production version

compile 'com.midtrans:corekit:1.15.0'

Latest Uikit Production version

compile 'com.midtrans:uikit:1.15.0'

iOS

To use the production version in iOS, please use the production environment when initializing SDK and also production client key which you can get from MAP.

Production setup in Objective-C

[CONFIG setClientKey:@"merchant clientkey"
                 environment:MidtransServerEnvironmentProduction
           merchantServerURL:@"merchant server production URL"];

Production setup in Swift

MidtransConfig.shared().setClientKey("merchant clientkey", environment: .production, merchantServerURL: "merchant server URL")

Merchant Server

To use the production version of Snap, please use the production endpoint of Snap and also production server key which you can get from MAP.

Production Endpoint: https://app.midtrans.com/snap/v1/

Frequently Asked Questions

What is a merchant server?

Midtrans Mobile SDK requires merchant to have a server-side implementation to store SERVER_KEY and make charge request. As an implementation reference, please take a look at this wiki.

What is MERCHANT_BASE_URL?

It is the URL of your merchant server (backend).

Why did I get Mixpanel token error?

This error will not happen if you use the build that we have provided on bintray. If for some reason you don’t want to use the build that we have provided, you need to add your own mixpanel token by signing up to mixpanel first.

Why did I get this error “Access denied due to unauthorized transaction, please check client or server key”?

Please check whether you have used the correct client key and server key. The keys should also match the environment such that sandbox keys are used for sandbox environment, and production keys for production. If the keys are already correct but you still get the same error, make sure you have put the correct merchant server URL (MERCHANT_BASE_URL).

Why did I get response message “Token not found” when trying to do checkout?

Please make sure you have installed correct SDK and supplied corresponding credentials. In sandbox environment, please make sure that you use sandbox keys (client key and server key) and sandbox version of SDK (the name of SDK using postfix “-SANDBOX” eg: com.midtrans:uikit:1.16.0-SANDBOX).

Why did I get a blank screen when trying to do checkout?

First, please make sure you’ve already used our latest version of SDK (at least v1.15.3). If you still face this problem, please either do one of these two solutions : (1) supply user detail to SDK, or (2) use UIKitCustomSetting. Please refer to this guide on how to do one of them.

I got error when trying to do checkout.

First, please make sure you’ve already used our latest version of SDK. Then, please examine the error log captured in Logcat or other error reporting.

If the error looks like this :

E/AndroidRuntime: FATAL EXCEPTION: main java.lang.NoSuchMethodError: No virtual method load(Ljava/lang/Integer;)Lcom/bumptech/glide/DrawableTypeRequest; in class Lcom/bumptech/glide/RequestManager; or its super classes (declaration of ‘com.bumptech.glide.RequestManager’ appears in /data/app/id.packageaplikasi.app-1/base.apk:classes3.dex)

Then rest easy as this is a known problem. Our mobile SDK uses Glide v3.7 as image loader library, so if your app uses Glide too, make sure you use the same version (or at least v3.x) to avoid this error. We still work on it to make sure in the future, no such version clashing exist anymore.

Modify base theme to avoid error

<!-- Base application theme. -->
<style name="AppTheme" parent="Theme.AppCompat.Light.DarkActionBar">
<!-- Customize your theme here. -->
<item name="colorPrimary">@color/colorPrimary</item>
<item name="colorPrimaryDark">@color/colorPrimaryDark</item>
<item name="colorAccent">@color/colorAccent</item>
<item name="windowActionBar">false</item>
<item name="windowNoTitle">true</item> </style>

If the error looks like this :

java.lang.RuntimeException: Unable to start activity ComponentInfo{com.yourcompany.appname/com.midtrans.sdk.uikit.activities.UserDetailsActivity}: java.lang.IllegalStateException: This Activity already has an action bar supplied by the window decor. Do not request Window.FEATURE_SUPPORT_ACTION_BAR and set windowActionBar to false in your theme to use a Toolbar instead.

You should have no worries. Since our mobile SDK uses Toolbar as ActionBar, you need to disable ActionBar in your app and use Toolbar instead. It requires you to modify your base theme.

For more information regarding this particular error, please refer to this Stack Overflow post.

I would like to test bank point. Is there any testing credential that I can use?

Sure. If you want to test bank point in sandbox environment, you can use this card number.

The expiry and CCV are the same like any other testing cards. Please refer to this section to see other testing credential.

How to get pdf_url ?

pdf_url is an response property that provide url to download instruction of VA payment. Here’s how to get pdf_url : String pdfUrl = transactionResponse.getPdfUrl()

Handle Async Payment

There are some async payment supported by Midtrans:

If you’re using payment methods from above list, you will not get the latest transaction status after doing the charge using the SDK. SDK only returns the pending status when doing the charge to Midtrans Payment API.

Midtrans will update the transaction status after they receive notification from bank when the transaction is really completed.

There are two ways to know the latest transaction status:

Handling HTTP Notification

In order to increase the security aspect, there are several ways to ensure that the notification received is from Midtrans.

Handle HTTP Notification (Using Veritrans PHP)

<?php

require_once('Veritrans.php');
Veritrans_Config::$isProduction = false;
Veritrans_Config::$serverKey = '<your serverkey>';
$notif = new Veritrans_Notification();

$transaction = $notif->transaction_status;
$type = $notif->payment_type;
$order_id = $notif->order_id;
$fraud = $notif->fraud_status;

if ($transaction == 'capture') {
  // For credit card transaction, we need to check whether transaction is challenge by FDS or not
  if ($type == 'credit_card'){
    if($fraud == 'challenge'){
      // TODO set payment status in merchant's database to 'Challenge by FDS'
      // TODO merchant should decide whether this transaction is authorized or not in MAP
      echo "Transaction order_id: " . $order_id ." is challenged by FDS";
      }
      else {
      // TODO set payment status in merchant's database to 'Success'
      echo "Transaction order_id: " . $order_id ." successfully captured using " . $type;
      }
    }
  }
else if ($transaction == 'settlement'){
  // TODO set payment status in merchant's database to 'Settlement'
  echo "Transaction order_id: " . $order_id ." successfully transfered using " . $type;
  }
  else if($transaction == 'pending'){
  // TODO set payment status in merchant's database to 'Pending'
  echo "Waiting customer to finish transaction order_id: " . $order_id . " using " . $type;
  }
  else if ($transaction == 'deny') {
  // TODO set payment status in merchant's database to 'Denied'
  echo "Payment using " . $type . " for transaction order_id: " . $order_id . " is denied.";
  }
  else if ($transaction == 'expire') {
  // TODO set payment status in merchant's database to 'expire'
  echo "Payment using " . $type . " for transaction order_id: " . $order_id . " is expired.";
  }
  else if ($transaction == 'cancel') {
  // TODO set payment status in merchant's database to 'Denied'
  echo "Payment using " . $type . " for transaction order_id: " . $order_id . " is canceled.";
}
?>

Challenge Response

An additional mechanism we provide to verify the content and the origin of the notification is to challenge. This can be achieved by calling the get status API. The response is the same as the notification status.

Challenge Response

Signature Key

We added signature key information in our notification. The purpose of this signature key is to validate whether the notification is originated from Midtrans or not. Should the notification not be genuine, merchants can disregard the notification. Please find on the side, the logic of the signature key and the sample code to generate signature key.

Signature Key Logic

SHA512(order_id + status_code + gross_amount + serverkey)

Sample code generate signature key

<?php
$orderId = "1111";
$statusCode = "200";
$grossAmount = "100000.00";
$serverKey = "askvnoibnosifnboseofinbofinfgbiufglnbfg";
$input = $orderId.$statusCode.$grossAmount.$serverKey;
$signature = openssl_digest($input, 'sha512');
echo "INPUT: " , $input."<br/>";
echo "SIGNATURE: " , $signature;
?>

Best Practice to Handle notification

The following are the standard types of notifications. Note different types of notifications can be added in addition to the ones below. Also new fields may be added to the existing notification, please confirm with the latest documentation for the exact fields.

Get Transaction Status

Please refer to this docs.