Postman and RPG-XML Suite IBM i Web Services

RPG, JSON, and REST: How to Test IBM i Web Services

Using Postman + RPG-XML Suite

Every day, RPG shops use REST IBM i web services to communicate with their clients. However, their software options are often limited to open source tools written in C or Java, with even fewer solutions available in RPG. What’s worse is that of the options available, none can compose, transmit, and parse web service data in a single package of RPG subprocedures except for one – and that’s where RPG-XML Suite comes in. 

RPG-XML Suite is a web API toolkit containing dozens of subprocedures and utilities to help RPG developers with everyday tasks. In other words, it lets you compose and parse XML & JSON, and transmit SOAP & REST web service data. Furthermore, RPG-XML Suite clears common web service hurdles, such as encoding, CCSID conversion, encryption, and text-conversion. Read below to see what RPG-XML Suite can do.

RPG-XML Suite - XML & JSON, SOAP & REST
RPG-XML Suite lets you easily communicate with IBM i web services in a variety of ways.

IBM i (or AS400/ iSeries) REST web services are everywhere these days. As such, this article will highlight RPG-XML Suite’s commonly used REST features, and will parallel these features using the Postman web service testing tool. Overall, this blog post:

  1. Describes how restful IBM i web services function.
  2. Creates HTTP GET and POST REST calls in Postman using JSON.
  3. Demonstrates how to perform similar calls in RPGLE with RPG-XML Suite.

Table of Contents

Restful Web Services

What are they?

To begin, restful is an extension of the acronym REST, which itself stands for REpresentational State Transfer. In this context, “REST” is a set of rules or standards used when following HTTP/HTTPS protocols. By following a REST architecture, programs can transmit text, XML, and JSON data to an API endpoint (a communication touchpoint between an API and a server), and get a response back in turn.

How do they work?

Servers communicate with REST web services via four HTTP methods: POST, GET, PUT/PATCH, and DELETE, with GET and POST being the most common. These methods strongly parallel the so-called CRUD operations used in relational database applications. Note the CRUD operations below, which create, read, update, or delete a resource’s data, as well as their HTTP counterparts.

CRUD Operations and their Equivalent HTTP Methods
The CRUD options for Create, Read, Update, and Delete strongly parallel the HTTP Methods of POST, GET, PUT, and DELETE.

Of those mentioned, this post focuses specifically on GET and POST HTTP Methods. Typically, GET requests are used to gather information in a read-only fashion. POST requests, on the other hand, are used when sending sensitive information, like passwords or authorization keys.

A quick mention on SOAP web services

Comparisons of REST vs. SOAP
SOAP and REST Methods each offers benefits above the other, with REST web services becoming more popular over time.

While most web services use REST APIs, many will use another protocol instead: SOAP, which stands for Simple Object Access Protocol. Some differences between the two are that SOAP:

  1. Is only XML-compatible.
  2. Can communicate over HTTP, SMTP, & FTP.
  3. Is restricted to POST requests.
  4. Is more verbose thus requiring more resources.

REST, on the other hand:

  1. Can handle many data formats such as XML, JSON, CSV, and more.
  2. Is restricted to HTTP communication.
  3. Can perform a wide range of HTTP Methods.
  4. Is lightweight by comparison.

With that in mind, neither REST nor SOAP is strictly “better” than the other. However, covering both is beyond the scope of this article. If you are interested in offering or consuming RPG SOAP web services on your IBM i, go to the RPG-XML Suite documentation site for more info.

GET Requests

Each HTTP Method has its own rules. For example, making an HTTP GET request requires two particular pieces of information, and an optional third:

GET Request Requirements
GET Requests always require a Request Method and Target URL, and optionally require Query String Parameters.

The first piece, or Request Method, describes how information is requested, while the second piece, or Target URL, describes where it’s being requested from. The optional third piece, or Query String Parameter, tells the web service what a request is looking for by passing in parameters formed as “key=value” pairs.

GET Requests in Postman & RPG

Postman

This article will use Postman, a free API testing tool, to make GET and POST requests. The team over at Postman has included some great documentation on making REST HTTP requests here.

In this example, Postman is making a GET request to the Target URL:
https://postman-echo.com/get?foo1=bar1&foo2=bar2. The image below includes the Query String Parameters foo1=bar1 and foo2=bar2:

GET Requirements in Postman
Calling an example GET request in Postman.

After sending the request parameters, the API at postman-echo.com sends back a response body. This body contains JSON objects such as the query string parameters (“args”), default header information (“headers”), and Target URL (“url”), as shown below:

Postman GET Response Data
Sample GET Request data that Postman echoed back.
RPG-XML Suite

You can make RPG GET requests by using RPG-XML Suite’s RXS_Transmit() subprocedure. Other than standard program code (declarations, control-options, etc), these three lines accomplish the same task as in Postman:

  1. TransmitDS.HTTPMethod = RXS_HTTP_METHOD_GET;
  2. TransmitDS.URI = ‘https://postman-echo.com/get?foo1=bar1&foo2=bar2’;
  3. Response = RXS_Transmit( *Omit : TransmitDS );

To explain, line 1 declares the HTTP Request Method, while line 2 declares the Target URL and Query String Parameters. Line 3 assigns response JSON from the RXS_Transmit() call to the Response variable.

It’s really that easy. RPG-XML Suite’s web service subprocedures are all built into one convenient toolkit, saving you from the time and stress that comes with being an RPG web service developer. RPG-XML Suite simplifies your RPGLE REST web service infrastructure. If you have a business need in mind, contact the RPG-XML Suite sales team here for a free proof of concept.

"...RPG-XML Suite simplifies your RPGLE REST web service infrastructure."

With a proof of concept, the RPG-XML Suite development team builds out a program based on your use case. This can cover a wide range of scenarios, such as:

Along with the proof of concept, you will get a free trial license of RPG-XML Suite for 30 days or longer, depending on your needs. Drop the team a line and see how RXS can help you.

Would you like to try out RPG-XML Suite? 

Request a free proof of concept by clicking the button below.

POST Requests

When working with REST IBM i web services, it’s common to need more than just a GET request to fetch data. Users may need POST requests too when updating resources. The examples below describe some common POST requirements.

How are POST Requests Different?

Like a GET request, POST requests require an HTTP Request Method and Target URL. However, unlike a GET request, a POST request typically does not include Query String Parameters, and includes a Request Body instead.

POST Request Requirements
POST Requests always require a Request Method and Target URL, and typically a Request Body, and almost never require Query String Parameters.

Content-Type Headers

A POST Request Body often includes a special “Content-Type” header describing its format. This header tells the client server what data is being sent and how to interpret it. Some of the most common Content-Type headers used in restful web services include:

  1. application/x-www-form-urlencoded
  2. application/json
  3. multipart/form-data

The first and default Content-Type header, application/x-www-form-urlencoded, is similar to the Query String Parameters sent in a GET request. However, instead of being sent through the URL, the Query String Parameters are sent through a Request Body. The application/json header specifies that JSON request data is being sent (though not in a file format). The third common header, multipart/form-data, is used when sending large amounts of binary data, files like PDFs or CSVs, and non-ASCII files.

Content-Type Headers for POST
Content-Type Headers describe a Request Body's format.

Content-Type Header - application/x-www-form-urlencoded

Postman

As it is one of the most common Content-Type headers, this first example of sending a POST request will use the application/x-www-form-urlencoded header.

To create the test request within Postman, first specify the HTTP Request Method and Target URL in the request bar. Next, select the x-www-form-urlencoded Content-Type header as shown below. Finally, make sure to include the “foo:bar” key:value pairs:

x-www-form-urlencoded Content-Type Header
Making a POST request, along with an x-www-form-urlencoded Content-Type Header.

After clicking the “Send” button, Postman makes the POST request and gets a JSON-formatted Response Body back. Notice below that unlike the GET request, the “args” object echoed back is now empty. Furthermore, instead of being specified as a Query String Parameter, the parameters are now being specified in a “form” object.  Also, note that the Content-Type header on line 15 is specified in the “content-type” object. Finally, note the echoed JSON from the postman-echo.com endpoint.

x-www-form-urlencoded Postman response
Sample x-www-form-urlencoded POST Response data that Postman echoed back.
RPG-XML Suite

The RPG-XML Suite code required to perform the Postman equivalent of an application/x-www-form-urlencoded HTTP request is relatively simple. Program declarations aside, these steps show how to create a similar call:

  1. URLEncodeDS.EncodeDecode = RXS_ENCODE;
  2. bar1Encoded = RXS_Convert( %Trim( bar1 ) : URLEncodeDS );
  3. bar2Encoded = RXS_Convert( %Trim( bar2 ) : URLEncodeDS );
  4. Request = ‘foo1=’ + %Trim( bar1Encoded )
  5.         + ‘&foo2=’ + %Trim( bar2Encoded );
  6. TransmitDS.HTTPMethod = RXS_HTTP_METHOD_POST;
  7. TransmitDS.URI = ‘https://postman-echo.com/post’;
  8. TransmitDS.HeaderContentType = ‘application/x-www-form-urlencoded’;
  9. Response = RXS_Transmit( Request : TransmitDS );

In this example code:

  • Lines 1-5 perform URL encoding via RXS_Convert() and BIFs,
  • Lines 6-8 assign the HTTP call requirements to the “TransmitDS” data structure,
  • Line 9 transmits the POST request and assigns the response to “Response”.
  • Lastly, it’s worth noting that the URL encoding performed via RXS_Convert() in lines 2-3 reformats unsafe characters, while the %Trim() BIFs in lines 2-5 remove space characters from the URL (as URLs can’t contain spaces).  

Content-Type Header - application/json

Postman

This next example shows how to send JSON along with the application/json Content-Type header. Assume the same Target URL is being called. To enter request data, first select “raw”, then “JSON” as shown below. From there, enter JSON data in the text editor.

Content-Type header application/json
Making a POST request, along with an application/json Content-Type Header.

After clicking the “Send” button, Postman echoes back JSON-formatted response data. Note that the “args” and “form” objects below are empty, while the “data” object is filled. This is because the Content-Type header application/json is being used instead to specify a raw JSON Body as its contents. Also notice the echoed response data sent back to Postman once again.

application/json Postman Response
Sample application/json POST Response data that Postman echoed back.
RPG-XML Suite

Program declarations aside, RPG-XML Suite accomplishes the same application/json request as the Postman example above:

  1. Request = ‘{“foo1”:”bar1”;“foo2”:”bar2”}’;
  2. TransmitDS.HTTPMethod = RXS_HTTP_METHOD_POST;
  3. TransmitDS.URI = ‘https://postman-echo.com/post’;
  4. TransmitDS.HeaderContentType = ‘application/json’;
  5. Response = RXS_Transmit( Request : TransmitDS );

In this example code:

  • Line 1 declares the JSON Request Body, with all of its whitespace removed.
  • Lines 2 and 3 assign the HTTP Method and Target URL to an HTTP-configured data structure.
  • Line 4 specifies the POST request’s Content-Type header as application/json in the data structure.
  • Line 5 calls the RXS_Transmit() subprocedure, which has the “Request” variable as the first parameter, and the “TransmitDS” data structure as the second parameter. This call to RXS_Transmit() then assigns the response JSON to the “Response” variable.

Content-Type Header - multipart/form-data

Postman

This last example involves transmitting a multipart/form-data Content-Type header along with a file, here named “jsonData.json”. Following below, select form-data, specify the key as “File”, name the Key, and select a file (you can create your own “jsonData.json” file first).

Content-Type header application/form-data
Making a POST request, along with an application/form-data Content-Type Header.

After clicking the “Send” button, Postman echoes back a JSON response. Notice that the “args”, “data”, and “form” objects below are all empty, while the “files” object contains information on the  “jsonData.json” file. This is because a multipart/form-data Content-Type header was specified, which is often used to send files. Also, notice the empty (null) “json” object:

application/form-data Postman Response
Sample application/form-data POST Response data that Postman echoed back.
RPG-XML Suite

RPG-XML Suite makes it easy to transmit files requiring the multipart/form-data Content-Type header. With declarations aside, the example below is of an RXS program transmitting an IFS JSON file via POST:

  1. TransmitDS.RequestStmf = ‘/tmp/jsonData.json’;
  2. TransmitDS.HTTPMethod = RXS_HTTP_METHOD_POST;
  3. TransmitDS.URI = ‘https://postman-echo.com/post’;
  4. TransmitDS.HeaderContentType = ‘multipart/form-data’;
  5. TransmitDS.LogFile = ‘/tmp/transmitLog.txt’;
  6. RXS_Transmit( *Omit : TransmitDS );

In the example:

  • Line 1 specifies the IFS path pointing to the transmitted “jsonData.json” file. 
  • Lines 2 and 3 represent the HTTP Request Method and Target URL, respectively. 
  • Line 4 designates multipart/form-data as the Content-Type header. 
  • Line 5 creates a log file containing transmission information.
  • Line 6 makes an RXS_Transmit() call, populating TransmitDS.LogFile in the process.

Summary

IBM i web services are crucial to the world’s digital infrastructure – businesses make HTTP calls every day by logging into websites, updating inventory, or ordering lunch. However, many RPG shops struggle to easily consume web services from their IBM i’s. It’s not that there aren’t options out there – the issue is that many of those options require a Java or C-based solution. Oftentimes, shops have to cobble together multiple non-RPG options to take care of their XML, JSON, SOAP, and REST needs.

That’s where RPG-XML Suite comes in. Between the RXS_Transmit() subprocedure for consuming web services and the RXS Router utility for offering them, RPG-XML Suite’s thoroughly documented toolkit helps you take care of all things web services in RPG.

RPG-XML Suite List of Features Graphic
RPG-XML Suite connects you to IBM i web services around the globe. Contact us for a free proof of concept today!

RPG-XML Suite has an established presence in the IBM i community, and you can try it with a free, no commitment proof of concept. After describing your business needs to us, the RXS development team can then build out your RPG-XML Suite program and provide you with a trial license key. Click the button below and try out the industry’s top RPG web service toolkit.

RPG-XML Suite – Web Services Simplified

Request a free proof of concept by clicking the button below.