How To Build Your First C++ REST API Client
29 August 2023
This tutorial helps us understand how to access Forex data using TraderMade’s REST API with C++ programming language. Market data helps analysts and developers gain valuable insights and make informed decisions.
Getting Started
To begin with, we need to sign-up for an account with TraderMade and get our exclusive API Key to access real-time and historical Forex data. Now, we can fetch an API key to authenticate our requests. In order to learn more about real-time and historical Forex data, let us have a look at the REST API documentation.
Let us go through a practical example to demonstrate the process. We can divide the process into several steps, such as
- Setting up the coding environment.
- Importing necessary libraries.
- Write some code.
- Debugging the code and getting results.
Setting up the coding environment
Setting-up the programming environment is essential, before jumping to the code. Now, we are ready to download a code editor or an Integrated Development Environment (IDE) and install it on the system.
Step 1: Integrated Development Environment
As C++ is easier to set up in Linux systems, we recommend downloading Ubuntu if you are not already on linux. Otherwise, you can skip Step 2. We need to download it from the official site https://ubuntu.com/download.
Step 2: Installation
The download will start automatically, giving us an ISO file.
Importing necessary libraries
A C++ library is a collection of standard functions and classes written in the core language. If you are new to C++ let’s get the GCC compiler so we can compile C++ program.
Allow us to open Ubuntu now and update the package list.
sudo apt update
If you never set a password or don't remember. Use the following command
sudo passwd
Now, we will install build-essentials on our system using this command. Build-essential packages are a form of meta-package needed to compile software.
sudo apt install build-essential
We use the following command to display information about GCC, the GNU Compiler Collection. It is a set of compilers and development tools needed to run the program.
gcc --version
We need to download two libraries here: curl and jsoncpp, and install them in the Ubuntu environment.
We are ready to install the latest version of the CURL library using this code.
sudo apt-get install libcurl4-openssl-dev
We are ready to install the latest version of the jsoncpp library with the help of this code.
sudo apt-get install libjsoncpp-dev
Let's move on to the next step:
Write some code
Now, we are entering the coding section.
The include statement helps us to include the libraries we need. It is similar to collecting all the materials needed before starting a project. These imports help us connect to the internet, request and parse data.
#include <iostream> #include <string> #include <curl/curl.h> #include <json/json.h>
The ‘namespace’ code allows us to access functions and classes from the namespace std.
using namespace std;
The WriteCallback function handles data retrieved from a web request with the help of curl library. It also helps to append data received to a string userp.
size_t WriteCallback(void *contents, size_t size, size_t nmemb, void *userp) { ((string*)userp)->append((char*)contents, size * nmemb); return size * nmemb; }
The performCurlRequest function uses the libcurl library to get data from a URL. It sets up the tool, sends the request, manages the response using the WriteCallback method, and confirms if it all went well. It gives back true if successful, otherwise false.
bool performCurlRequest(const string& url, string& response) { CURL *curl = curl_easy_init(); if (!curl) { cerr << "Failed to initialize CURL" << endl; return false; } curl_easy_setopt(curl, CURLOPT_URL, url.c_str()); curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, WriteCallback); curl_easy_setopt(curl, CURLOPT_WRITEDATA, &response); CURLcode res = curl_easy_perform(curl); curl_easy_cleanup(curl); if (res != CURLE_OK) { cerr << "curl_easy_perform() failed: " << curl_easy_strerror(res) << endl; return false; } return true; }
The function parseJsonResponse uses the JsonCpp library to try parsing a JSON response provided as a string. It uses a "JSON reader" tool to do this. If parsing works, the parsed data is saved in the given variable (parsedRoot), and the function returns true. If there's a parsing error, it shows an error message and returns false.
bool parseJsonResponse(const string& jsonResponse, Json::Value& parsedRoot) { Json::CharReaderBuilder builder; Json::CharReader *reader = builder.newCharReader(); string errs; bool parsingSuccessful = reader->parse(jsonResponse.c_str(), jsonResponse.c_str() + jsonResponse.size(), &parsedRoot, &errs); delete reader; if (!parsingSuccessful) { cerr << "Failed to parse JSON: " << errs << endl; return false; } return true; }
Now, let us take a look at the place where real action happens! The below program defines api_url and response as a string then passes this to the performCurlRequest fucntion we defined in the previous step then passes the response it receives from curl to parseJsonResponse function. The parsed JSON data is then iterated over to display the bid and ask prices for the different currency pairs and stock index.
Once we done with the parsing we clean up and release the resources libcurl library used.
int main() { string api_url = "https://marketdata.tradermade.com/api/v1/live?currency=EURUSD,GBPUSD,UK100&api_key=your_api_key"; string response; curl_global_init(CURL_GLOBAL_DEFAULT); if (performCurlRequest(api_url, response)) { Json::Value root; if (parseJsonResponse(response, root)) { const Json::Value quotes = root["quotes"]; for (const Json::Value "e : quotes) { if (quote.isMember("bid") && quote.isMember("ask")) { double bid = quote["bid"].asDouble(); double ask = quote["ask"].asDouble(); cout << "Bid: " << bid << ", Ask: " << ask << endl; } } } } curl_global_cleanup(); return 0; }
Now, we will ensure the code is error-free.
Debugging the Code and Getting Results
Now, we understand the code, we can debug, execute, and see the output.
First, save the code to the system before executing it. We are opening a new document and pasting the code into it.
We will name the file live. Any name can be used to save the file, but the cpp extension is mandatory to show the computer that we are saving a C++ file.
Now, we need to compile and execute the program.
Compilation of our code needs adding the libraries curl and jsoncpp along with the path to the jsoncpp library.
g++ -o live live.cpp -lcurl -ljsoncpp -I/usr/include/jsoncpp -L/usr/lib/x86_64-linux-gnu
We can execute our program now using the code. We use three currency pairs here: EURUSD, GBPUSD, and a CFD instrument UK100. We ask the computer to get and print these financial instrument’s “bid” and “ask” values via the REST API.
./live
Voila! You can now see the result. You have successfully requested and parsed JSON REST API using C++.
Next Steps
TraderMade’s REST API is a user-friendly tool to develop digital solutions and gain valuable insights. Please use and build awesome apps in C++ and let us know.
Forex data endpoints refer to a specific URL providing Forex data through an API. To understand endpoints better, you can get started by signing up and exploring the REST API documentation. For more assistance, please don't hesitate to contact us via live chat or email support@tradermade.com.
Here is the full program
#include <iostream> #include <string> #include <curl/curl.h> #include <json/json.h> using namespace std; // Callback function to handle curl's response size_t WriteCallback(void *contents, size_t size, size_t nmemb, void *userp) { ((string*)userp)->append((char*)contents, size * nmemb); return size * nmemb; } // Function to perform CURL request bool performCurlRequest(const string& url, string& response) { CURL *curl = curl_easy_init(); if (!curl) { cerr << "Failed to initialize CURL" << endl; return false; } curl_easy_setopt(curl, CURLOPT_URL, url.c_str()); curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, WriteCallback); curl_easy_setopt(curl, CURLOPT_WRITEDATA, &response); CURLcode res = curl_easy_perform(curl); curl_easy_cleanup(curl); if (res != CURLE_OK) { cerr << "curl_easy_perform() failed: " << curl_easy_strerror(res) << endl; return false; } return true; } // Function to parse JSON response bool parseJsonResponse(const string& jsonResponse, Json::Value& parsedRoot) { Json::CharReaderBuilder builder; Json::CharReader *reader = builder.newCharReader(); string errs; bool parsingSuccessful = reader->parse(jsonResponse.c_str(), jsonResponse.c_str() + jsonResponse.size(), &parsedRoot, &errs); delete reader; if (!parsingSuccessful) { cerr << "Failed to parse JSON: " << errs << endl; return false; } return true; } int main() { string api_url = "https://marketdata.tradermade.com/api/v1/live?currency=EURUSD,GBPUSD,UK100&api_key=api_key"; string response; curl_global_init(CURL_GLOBAL_DEFAULT); if (performCurlRequest(api_url, response)) { Json::Value root; if (parseJsonResponse(response, root)) { const Json::Value quotes = root["quotes"]; for (const Json::Value "e : quotes) { if (quote.isMember("bid") && quote.isMember("ask")) { double bid = quote["bid"].asDouble(); double ask = quote["ask"].asDouble(); cout << "Bid: " << bid << ", Ask: " << ask << endl; } } } } curl_global_cleanup(); return 0; }