How to accept payments in a mobile app: tokenization, NFC, optical scanning and other benefits in one SDK
I have already showed with the example of Android SDK how to integrate a native bank card payment wizard into a mobile app not constraining oneself to frame and WebView and not risking PCI DSS audit. Since then our SDK has expanded rather significantly and the usual card input widget for Android and iOS was complemented by the following functions:
— React Native library for Android and iOS
— customization of the layout of the card details form
— card optical scanning
— acceptance of contactless payment in Android with NFC technology
In this article, I will explain what is in general possible to implement with mobile app payments, talk about existing lifehacks and pitfalls, provide an example of demo-app code and show how to write-off a friend’s debt using NFC reader of your smartphone.
Case 1. How to link a client’s bank card to the back-end for regular debits or one-click payments
It is important to know that if your back-end is not PCI DSS certified you do not have the right to store the card number and its expiration date in your database. Therefore, prior to linking the card identifier to the client’s account, one should tokenize the card. To do so you should make the first payment via the mobile app with the participation of the client and, preferably, with 3D-Secure. For this payment, you should lock a small sum, for example, 1 unit of the currency. First, in this case 3D-secure acts as the protection for the vendor against financial claims (chargebacks) towards future recurrent charges. Second, it facilitates conversion as, for example, the transactions with Privatbank card in Ukraine cannot be executed without 3D-Secure in most cases.
So, to make a card token, one should transfer the requiredRecTokenand verification characteristics (for more details on how to make a mobile app refer to an article linked in the beginning as well as in the demo app code on github):
RequiredRecToken parameter demands to return the card token if the authorization was successful while verification states that it is not required to withdraw the funds but rather to block them and reimburse afterwards (the payment gateway performs the reimbursement automatically).
In response the payment gateway will return recToken parameters – the card token, recTokenLifeTime – token expiration period (in essence, the card expiration period) and maskedCard – masked card number that should be linked to the token in the backend to show the user later when she selects the method of payment.
Now having the card token you can at any time upon the client’s demand or when the payment is due use the token charge method via server-to-server API and withdraw the required sum.
Our statistics show that a rather significant number of card holders cannot pay via 3DSecure with a mobile device due to several reasons not related to the user herself or the payment gateway.
– the SMS may not arrive or the user loses the 3D-Secure password form switching between the SMS-application and your app, as the form opens in the WebView or the system browser
– the layout of the bank’s 3D-Secure page is shifted on the smartphone or the tablet (banks adapt these pages very rarely)
– the bank’s web-server disabled the support of unsafe TSL 1.0 protocol, which makes 3D-Secure unavailable for Android ver. <4.1
We are able to switch on/off 3D-Secure instantly at the payment gateway and if the client cannot pay we adapt to her and try to process the payment without a 3D-Secure password.
It is also important to keep in mind that if you save the tokens of one payment provider in your system, you will not be able to use them with another provider unless the providers have agreed on the tokens migration, which we have seen several times in our practice.
Case 2. Customizing the layout of the card number form
Frequently it is required to locate the fields for the card number, expiration date, and cvv2 in the order that is different from the standard layout in SDK. However, PCI DSS requirements do not allow you to simply change the card number field for a standard EditText component. We have developed the flexible layout for these purposes. Flexible layout adopts your mobile app styles and allows locating the form elements in any order and with any design at the same time preventing accidental transfer of card details to your back-end.
There are two mechanisms to set up the card details input to SDK:
CardInputView – a ready-to-use view;
CardInputLayout – only a layout wrapper to build the view in the own layout style.
In essence, CardInputView = CardInputLayout + CardNumberEdit + CardExpMmEdit + CardExpYyEdit + CardCvvEdit.
A simplified CardInputView structure in XML may be:
<com.cloudipsp.android.CardInputLayout> <com.cloudipsp.android.CardNumberEdit/> <LinearLayout android:orientation="horizontal"> <com.cloudipsp.android.CardExpMmEdit /> <com.cloudipsp.android.CardExpYyEdit /> </LinearLayout> <com.cloudipsp.android.CardCvvEdit /> <com.cloudipsp.android.CardInputLayout>
Consequently, it is possible to customize freely and locate the input elements creatively. There is only one rule to observe – each input element (CardNumberEdit,CardExpMmEdit,CardExpYyEdit,CardCvvEdit) can be used in CardInputLayout only once irrespective of the View nesting level.
Here is how it may look:
Customizing the input fields, one should keep in mind:
– cvv2 may be both 3 and 4 symbols long
– card number may be 14 to 19 symbols long
– by making fork SDK and making the changes in your own layout implementation you can reach the maximum customization with your design (this is allowed if you do not transfer the card details through your back-end). However, making the fork you lose the support of SDK updated from the gateway and integration of new features.
Frequently the card details form includes the inputs for the card holder’s name and ZIP code. In 99% of the payments within CIS, there is no practical need to do so, as only some banks in the USA, Canada, and the UK support this technology called Address Verification System. In addition, for the verification to work, both the acquirer bank and the issuing bank should support it.
Case 3. Adding the possibility to scan the card by camera and NFC
NFC scanning is implemented with the use of android-sdk-nfc and react-native-cloudipsp-nfc libraries and is available only for Android. Although Apple opened the possibility of reading RFID tags for third-party developers starting from iOS 11+, reading EMV tags of bank cards is still unavailable.
Example of demo-app with the use of NFC
Differs from usual implementation by NfcCardBridge and addition of Intent to wait for the card reading event (readCard)
Although card reading is made by NFC, the financial card authorization protocol is still the usual card not present. Thus, the card should be authorized for web payments for full operation of this function.
By making a simple app, you can use it to transfer the funds from someone’s card to your simply bringing someone’s card close to the phone. For example, this may be convenient if you have to charge your friend a small sum of money for a card debt. On the one hand, it will be efficient and convenient, on the other, rather spectacular. To use the service of transfers from one card to another one should first register at the website of Fondy payment platform and link a bank card, to which the funds will be sent in the financial settings. For security reasons, the sum that can be withdrawn via NFC without 3D-Secure cannot exceed the equivalent of $4.