• Time to read 4 minutes
Building with an Open Bank API Part 2

Building with an Open Bank API Part 2

This is a continuation of Part 1 here. In part 1, I wrote a wrapper to call Citibank's API. In this part of the tutorial, I call the RESTful wrapper services that I wrote in part 1 to give users an interface to see their accounts and transfer funds to external accounts.

A big news in the Fintech world this week is DBS's announcement that they now have the world's largest bank API. You can read about the launch here. There are 155 APIs that you can call for various things that you may want your app to do, like transfer funds, view account details and many others. I found several interesting API calls that Citibank didn't have. For example, in DBS's API, you could add payees directly from the API - so I can get folks to pay me without asking them to first arrange for payments through their Internet banking app. Other interesting APIs are the money management ones. I get to read how a user spends his money so if I am developing, say, a shopping app, I could base on this information to push the relevant sort of products to him. 

It is absolutely possible to add DBS to my wrapper API so that users now have access to 2 banks instead of 1 in my app. These APIs work in similar ways - OAuth authentication, redirection to the bank's login for an access token, and then using the access token to access services. So getting just one bank's API to work and you pretty much nailed them all. 

A quick stock-take for the Fintech developer in Singapore looking to integrate into banks here, here are the toys currently available for you to play with:

  1. DBS Developers
  2. Citibank Sandbox
  3. OCBC API Store

The User Interface

In my app, the user logins and gets redirected to Citibank to enter his credential. Then a list of things my app requests pops up so that he knows what he's getting himself into if he carries on. 

api_login_1.png

api_login_2.png

api_login_3.png

And then I retrieve all his deposit accounts and displays them. I also populate a drop-down menu with the external payees that he has configured in his Internet Banking Account (here's where DBS will allow me configure payees directly within my app which Citi wouldn't).

api_listaccount.png

The user chooses who to pay. This demo assumes that the user will be buying my "tokens", so he states the number of tokens he wishes to buy and then confirms it.

api_confirm_buy_0.png

Nothing changes in the deposit because everything that happens here is purely static since it is a sandbox. If I want to do this for real, I will need to go to Citibank to register myself as a partner.

The Codes

All my codes can be found in my Github account here. Just to illustrate how I did this, here are the codes I wrote to to exchange for an access token and subsequently, use it to retrieve the user's deposits and payees.

function setup(code, state){
	//now call my authorization wrapper with the code to get an access and refresh token
	var JSONObject = {
		"code": code,
		"state": state
	};

	$.ajax({
		url: "https://myserver.me/authorize/",
		type: 'POST',
		data: JSONObject,
		dataType: 'json',
		contentType: "application/x-www-form-urlencoded",
		success: function (arr) {
			if (arr.hasOwnProperty('msg')){
				$("#authorization").html("Cannot get token.");	
			}
			else {
				access_token = arr.access_token;
				refresh_token = arr.refresh_token;
				localStorage.setItem("access_token", access_token);
				localStorage.setItem("refresh_token", refresh_token);
				getaccounts(localStorage.getItem("access_token"));      
				getpayees(localStorage.getItem("access_token"));
			}
		},
		error: function () {
			alert("Server is down (setup)");
			localStorage.setItem("access_token", "");
			localStorage.setItem("refresh_token", "");
		}
	});
}

I perform an AJAX call to my authorize service by passing it the "code" that Citi gave me when the user has logged in to his account successfully earlier. I take the access token that Citi returns and use it to call getaccounts() and getpayees() which are JavaScript functions that I wrote to retrieve this user's deposit accounts and payees. Citi also returns to me a refresh token that I could use to get a new access token if the old one expires (it expires every 1800 seconds by default). I was lazy, so I didn't implement this part. Instead I just pop an error message to say that the server is down (it isn't of course).

Here's getaccounts():

function getaccounts(mytoken){
	var JSONObject = {
		"access": mytoken
	};

	$.ajax({
		url: "https://myserver.me/deposits/",
		type: 'POST',
		data: JSONObject,
		dataType: 'json',
		contentType: "application/x-www-form-urlencoded",
		success: function (arr) {
			if (arr.hasOwnProperty('msg')){
				$("#authorization").html("Cannot get account.");	
			}
			else {
				accounts = arr;
				listaccounts(accounts);
			}
		},
		error: function () {
			alert("Server is down (getaccounts)");
			localStorage.setItem("access_token", "");
			localStorage.setItem("refresh_token", "");
		}
	});
}

With the access token that Citi provides, I call my deposit service, which is my wrapper service to extract just deposits from Citi's web service that retrieves every one of this user's accounts, including deposits, insurance and investments. And then I call my JavaScript function listaccounts() to display them nicely in my web app. I could have checked if the call fails due to access token expiry and use my refresh token to get a new one. But I am lazy, and just say that server is down so that the user will just need to login again.

Here's listaccounts():

function listaccounts(accounts){
	var myhtml = "";

	var numaccounts = Object.keys(accounts).length;

	for (var name in accounts){
		var accounttype = Object.keys(accounts[name])[0];

		myhtml = "";
		myhtml += '<div class="col-md-4">';
		myhtml += '<div class="panel panel-primary">';
		myhtml += '<div class="panel-heading">' + accounts[name][accounttype].productName + '</div>';
		myhtml += '<div class="panel-body">' + format2(accounts[name][accounttype].currentBalance, "$") + '</div>';
		myhtml += '</div>';
		myhtml += '</div>';
		$("#accounts_list").append(myhtml);
	}
}

Nothing exciting here really, I construct a panel for each account, then state its name and current balance.

The rest of my codes to allow fund transfer to payees are written in the same way and are self-explanatory.

What's Next?

My motivation for exploring open bank API has been to integrate it with tokens in the blockchain. I imagined an app where you could peg token price to fiat currency and fund-transfer money in your bank to buy my tokens on the Ethereum blockchain. I am still thinking if this makes sense at all because tokens on the Ethereum blockchain are logically pegged to the price of ETH. If Ethereum cease to exist, so will my token. Risk associated with Ethereum has always been priced into the token on its platform. Thus the relationship between token price and fiat currency is loose at best. Anyway the folks at Digix has been doing this with gold.

To develop this idea further is to gain a better understanding of the ERC20 token standard which I will write about in subsequent posts.