Accelerate the value of multicloud with collaborative DevSecOps Learn more

Get started with the IBM MQ messaging REST API

IBM MQ allows you to interact with its server objects through different interfaces or APIs. You might need to set things up as an architect, configure and maintain as an administrator or use queues, topics and subscriptions in your applications that connect to the MQ server, as an application developer.

This tutorial shows you how to use the messaging REST API in your applications so they can interact with the queue manager and its objects.

MQ has a number of APIs that applications written in different languages can use. Click through the Languages, Wire Formats and APIs slides for info on how they are connected. The Message Queue Interface or MQI is the interface that allows the most comprehensive access to MQ objects for applications.

The messaging REST API currently offers a more basic interface for interacting with queues and so can be quick and easy to get started with.

Prerequisites

  • Curl
  • Go runtime
  • Node.js runtime

Steps

  1. Set up your queue manager
  2. Configure the mqweb server
  3. Put a message on the queue
  4. Get a message from the queue
  5. Use the Swagger UI to interact with the MQ messaging REST APIs

Step 1. Set up your queue manager

Use one of the Ready, Set, Connect tutorials to set up your queue manager. Come back here and continue with the next step.

Step 2. Configure the mqweb server

Go to Getting started with the messaging REST API topic in the IBM MQ Knowledge Center to set up the MQ REST API. If you also need to set up the IBM MQ Console, check out the Getting started with the IBM MQ Console topic too.

Come back here and continue with the next step.

Step 3. Put a message on the queue

You can try out the MQ messaging REST API by using cURL. cURL is a command line tool and library for transferring data with URLs. You can install it on any platform.

Make sure that you have curl installed:

curl -V

The MQ messaging REST API expects the following basic details in the POST request that will put a message on a queue:

  • -k – This allows you to connect to a server that has a self-signed certificate, not a CA issued one.

  • -i – This option includes the response headers in the output (optional).

  • request URL in the following format: https://host:port/ibmmq/rest/v1/messaging/qmgr/your_qm_name/queue/your_queue_name/message.

    For example: https://localhost:9443/ibmmq/rest/v1/messaging/qmgr/QM1/queue/DEV.QUEUE.1/message.

  • -X – This specifies the request method.

  • -u – This is the name and password of the user that you added in the mqwebuser.xml file.

  • -H – This is the two header values, for the cross site request forgery token and the content type for the message.

  • -d – This is the data or the message payload.

Issue the cURL POST command that will put a message to a queue:

curl -i -k https://localhost:9443/ibmmq/rest/v1/messaging/qmgr/QM1/queue/DEV.QUEUE.1/message -X POST -u user:password -H "ibm-mq-rest-csrf-token: blank" -H "Content-Type: text/plain;charset=utf-8" -d "Hello World!"

You should see output like this: Output from curl command

Well done! If your output message looks like the one here, you’ve successfully used cURL to put a message to the queue. See if you can get the message off the queue by using a similar command.

Step 4. Get a message from the queue

The MQ messaging REST API expects the following basic details in the DELETE request that will destructively GET a message from a queue:

  • -k – This allows you to connect to a server that has a self-signed certificate, not a CA issued one.

  • -i – This option includes the response headers in the output (optional).

  • request URL in the following format: https://host:port/ibmmq/rest/v1/messaging/qmgr/your_qm_name/queue/your_queue_name/message.

    For example: https://localhost:9443/ibmmq/rest/v1/messaging/qmgr/QM1/queue/DEV.QUEUE.1/message.

  • -X – This specifies the request method.

  • -u – This is the name and password of the user that you added in the mqwebuser.xml file.

  • -H – This is the two header values, for the cross site request forgery token and the content type for the message.

Issue the cURL DELETE command that will destructively get a message from a queue:

curl -i -k https://localhost:9443/ibmmq/rest/v1/messaging/qmgr/QM1/queue/DEV.QUEUE.1/message -X DELETE -u user:password -H "ibm-mq-rest-csrf-token: blank"

You should see output like this: Output from curl command

Well done! If your output message looks like the one here, you’ve successfully used cURL to get your message from the queue.

Step 5. Use the Swagger UI to interact with the MQ messaging REST APIs

The mqweb server provides an option for switching on the API Discovery feature.

When the mqweb server is set up and running, the .xml file that you configured in section 3 contains the line inside the featureManager tags:

<featureManager>
<feature>apiDiscovery-1.0</feature>
</featureManager>

You can now use the Swagger documentation by:

  • Pointing your browser to: https://host:port/ibm/api/explorer

    Then, use the Swagger UI to interact with the REST APIs. You can put and get messages from the “messaging REST API” and see the queue depth change in the MQ Console for the queue DEV.QUEUE.1.

  • Pointing your browser to: https://host:port/ibm/api/docs

    Then, retrieve a Swagger 2 document that describes the whole REST API.

Explore sample applications that use the REST API

You can explore these examples:

  • Go example
  • Node.js example using the HTTPS module
  • Node.js example using the Promise module

For all three sample applications, the queue manager that the application looks to communicate with is running in IBM Cloud. The default SSL HTTP port for queue managers running in IBM Cloud is 9443. A user can specify a different port, but if no port is available, the default port will be used.

Go example that uses the MQ messaging REST API

In this example, the put and get calls are wrapped in Go functions.

The request URL for the queue manager, qmURL, is constructed to include the host, port, the default path for the messaging REST API, queue manager name, and queue name.

The request is then created, the message type is set and additional parameters that we used in our cURL calls earlier are added; the CSRF token, the content type and user and password for authentication.

The sender and receiver samples that are a part of this application pass on the correct MQ parameters to this method and the REST call is constructed and sent.

func mqRestCall(qm QueueManager, q Queue, verb string, msg Message, queryParams string) (statusCode int, body []byte, err error) {

if qm.Port == "" {
    qm.Port = "9443"
}

qmURL := "https://" + qm.Host + ":" + qm.Port + "/ibmmq/rest/v1/messaging/qmgr/" + qm.Name + "/queue/" + q.Name + "/message"
if queryParams != "" {
    qmURL = qmURL + queryParams
}

// allow self-signed certs. Only required in dev.
tr := &http.Transport{
    TLSClientConfig: &tls.Config{InsecureSkipVerify: true},
}
client := &http.Client{Transport: tr}

//    client := &http.Client{}
msgByteSlice := []byte(msg.Message)
req, err := http.NewRequest(verb, qmURL, bytes.NewBuffer(msgByteSlice))
if err != nil {
    fmt.Printf("Error preparing rest call. Error: %v", err)
    return statusCode, body, err
}

if msg.MsgType == "" {
    msg.MsgType = "application/json"
}
req.Header.Add("ibm-mq-rest-csrf-token", "anyvalue")
req.Header.Add("Content-Type", msg.MsgType)
req.SetBasicAuth(qm.Username, qm.Password)

resp, err := client.Do(req)

Node.js example using HTTPS module

In this Node.js example, available in our github repository, we put and get a message with the help of a basic HTTPS module.

Set up variables to include the HTTPS module, the base URI for the rest call, user and password for the Liberty server and MQ, queue manager and queue name:

// Use the inbuilt HTTPS module. Though there are simplified alternatives
var https=require('https')

// All the admin REST calls start from this point
var apiBase="/ibmmq/rest/v1/"

// Who am I
var username="app"
var password="_APP_PASSWORD_"

var queue="DEV.QUEUE.1"
var qMgr ="QM1"

Set up the GET call with basic details that the MQ messaging REST API needs to authenticate the request:

// Use basic authentication - pass userid/password on every request
// Could use alternatives with the LTPA token after a call to the /login API
var options = {
  hostname:"localhost",
  port:9443,
  method:'GET',
  headers: {
    'Authorization': 'Basic ' + new Buffer(username + ':' + password).toString('base64'),
    'Content-Type' : 'text/plain',
// Need this header for POST operations even if it has no content
    'ibm-mq-rest-csrf-token' : ''
   }
}

Construct the request path from the declared variables:

// Construct the full API path from the base for a particular request
                options.path = apiBase + "messaging/qmgr/" + qMgr + "/queue/" + queue + "/message"

Put the message:

putMessage()

///////////////////////////////////////////////////////
function putMessage() {
  // And call the operation
  options.method = 'POST'
  var request = https.request(options,(response) => {
    console.log('POST   statusCode : ', response.statusCode);
    response.setEncoding('utf8');

    response.on('data',function(cbresponse) {
       console.log('POST response: ',cbresponse);
    });

    // Once the message has been successfully put, try to get it again
    response.on('end', function() {
        getMessage();
    });
  });

  request.on('error', function (e) {
    console.log('problem with request: ' + e);
  });

  var msg = "Hello world at " + new Date()

  request.write(msg)
  request.end();
}

Get the message:

function getMessage() {
// Call the operation
options.method = 'DELETE'
var request = https.request(options,(response) => {
  console.log('DELETE statusCode : ', response.statusCode);
  response.setEncoding('utf8');
  response.on('data',function(cbresponse) {
     console.log('Message is <%s>',cbresponse);
  });
});

Make sure you have Node installed. From the directory with your mq-rest-node-https.js sample, run:

node mq-rest-node-https.js

You should see output like this: Output from Node.js HTTPS example

Node.js example with Promise module

This Node.js example, available in our github repository, shows you how to use JavaScript promises so the put and get can be used in the right sequence.

// Define the function to be used when putting a message. The
// function returns a Promise so it can be used in sequence
// before the retrieval.
const putMessage = function(msg) {
  return new Promise((resolve,reject) =>  {
    options.method = 'POST';

    // Create the request and aggregate any returned data
    var request = https.request(options,(response) => {
      if (response.statusCode < 200 || response.statusCode > 299) {
        var errMsg = util.format("POST failed.\nStatusCode: %d\nStatusMessage: \n",response.statusCode, response.statusMessage);
        reject(new Error(errMsg));

      } else {
        console.log('POST   statusCode: ' + response.statusCode);
      }
      var body = '';
      response.on('data',(chunk) => body +=chunk);
      response.on('end', () => resolve());
    });

    request.on('error', (error) => reject(error));
    // Send the message contents
    request.write(msg);
    request.end();
  });
};

// Define a function used to retrieve a message. Use
// a Promise to control when it's ready to print the
// contents.
const getMessage = function() {
  return new Promise((resolve,reject) => {
    options.method = 'DELETE';

    // Create the request and aggregate any returned data
    var request = https.request(options,(response) => {
      if (response.statusCode < 200 || response.statusCode > 299) {
        var errMsg = util.format("DELETE failed.\nStatusCode: %d\nStatusMessage: ",response.statusCode, response.statusMessage);
        reject(new Error(errMsg));
      } else {
        console.log('DELETE statusCode: ' + response.statusCode);
      }
      var body = ''; // The message contents
      response.on('data',(chunk) => body +=chunk);
      response.on('end', () => resolve(body));
    });
    request.on('error', (error) => reject(error));
    request.end();
  });
};

// Create message contents
var msg = "Hello world at " + new Date();

// Put the message and then try to retrieve it. Using Promises
// simplifies the flow and error handling.
putMessage(msg)
  .then(()   => getMessage())
  .then(body => console.log(body))
  .catch(err => console.error(err));

Make sure you have Node installed. From the directory with your mq-rest-node-promise.js sample, run:

node mq-rest-node-promise.js

You should see output like this: Output from Node.js Promises example

Next steps

Congratulations! You can REST easy now that you’ve put and got your messages.