Express Servers communicating through RabbitMQ

Express Servers communicating through RabbitMQ


WHAT IS RABBITMQ?

RabbitMQ is?a message broker . It gives your applications a common platform to send and receive messages, and your messages a safe place to live until received. You can use it for caching, realtime updates etc.

Pre-requisites:

  • Basics of Nodejs
  • Basics of Docker

HOW TO SETUP RABBITMQ IN WINDOWS:

You can download the rabbitMQ server in your machine, then install and run to use it locally. Another method is that we can pull the docker image and use it. Following are steps to run the rabbitMQ docker image:

  1. Pull the docker image:

docker pull rabbitmq:3-management        

2. Run the image to use it, do specify the name of it when running it:

docker run -d -p 15672:15672 -p 5672:5672 --name [your-name] rabbitmq:3-management        

3. Check is it running or not:

docker images        

Above command will give the following list

No alt text provided for this image

Default port for rabbitMQ is 15672, so on running the url 'https://localhost:15672' it will render the GUI for RabbitMQ Management. It will ask for username and password, for guest user both the username and password is "guest". Here you can monitor all the connections, channels and queues.

ARCHITECTURE DIAGRAM:

The flow of the communication will be like this. Producer will send the message to the queue. Consumer will be listening throughout the queue. As the queue got the message, consumer will extract it.

No alt text provided for this image

To implement this architecture, we need 3 simple steps which are mentioned below:

STEP 1:

Lets configure the two express servers. One named as Producer and other named as Consumer.

Install the rabbitmq package in both servers with following command.

npm i?amqplib        

Make a connection to the rabbitmq server as following on both the nodejs servers:

const mq = require('amqplib/callback_api')
l
let queue = "myMsg"


//rabbitmq connection
mq.connect({
? ? username: process.env.USERNAME,
? ? password: process.env.PASSWORD
}, (err, con) => {
? ? if (err)
? ? ? ? throw err


? ? //create channel
? ? con.createChannel((err, channel) => {
? ? ? ? if (err)
? ? ? ? ? ? throw err;


? ? ? ? //create queue,if not exist
? ? ? ? channel.assertQueue(queue, {
? ? ? ? ? ? durable: false
? ? ? ? })
? ? ? ? 
? ? })
}))        

STEP 2:

Now move to producer server and make a function to publish the message to the queue. And assign the channel to any variable to access it in the function. Now the connection file of producer will look like this:

**/Production server

const mq = require('amqplib/callback_api')
let myChannel = null;
let queue = "myMsg"


//rabbitmq connection
mq.connect({
? ? username: process.env.USERNAME,
? ? password: process.env.PASSWORD
},
 (err, con) => {
? ? if (err)
? ? ? ? throw err


? ? //create channel
? ? con.createChannel((err, channel) => {
? ? ? ? if (err)
? ? ? ? ? ? throw err;


? ? ? ? //create queue,if not exist
? ? ? ? channel.assertQueue(queue, {
? ? ? ? ? ? durable: false
? ? ? ? })
? ? ? ? myChannel = channel
? ? })
})


//send the msg to the consumer
const publishToQueue = async (data) => {
? ? 
? ? //send data to the queue
? ? myChannel.sendToQueue(queue, Buffer.from(data))
}


module.exports = { publishToQueue }

        

Now configure a route in server.js for publishing a message to the queue.

**/Production server

//route to send the msg to the queue
app.get("/send/:msg", async (req, res) => {
? ? try {
? ? ? ? await publishToQueue(req.params.msg);
? ? ? ? return res.status(200).json({ msg: "Send to the queue" })
? ? } catch (err) {
? ? ? ? 
? ? ? ? return res.status(400).json(err)
? ? }


})
        

STEP 3:

Lets configure the consumer now, which will listen to the queue and console the message. 'noAck' option is set to false as for now on testing I dont want the data to be lost after recieved. But for production it should set to be true, so that data should be cleared from queue as soon as it is recieved.

**/Consumer server

//listening to the queue
? channel.consume(queue, function (msg) {
? ? ? console.log("[Publisher]:", msg.content.toString());
?}, {
? ? ? noAck: false
? });
        

Finally both the Production and consumer are set. Run both servers and hit the API from producer server to publish a message. In consumer server, you can see the same message which you have send through API.

WHY I USED RABBITMQ?

I had two scenarios which is covered through rabbitMQ.

  1. I dont want to loose data, even when the server is down so I send the data to the server through queue means rabbitMQ. So even if server is down, my data will stay there and as soon as server reconnects, data will be saved to the database.
  2. I want realtime update of any change happens in database because application involves calculations and I cant depend on webpage refresh rate.

CONCLUSION:

RabbitMQ is easy to use and good for mid-level applications. We have more brokers like Apache, Redis etc and they have their own pros and cons. For my scenario, rabbitMQ looks better choice so it also depends on the use case. For complete code, checkout this repo, and share the use case for which you have used it.

Thanks for reading!

要查看或添加评论,请登录

Wajiha Abid的更多文章

  • phonenumbers library in python

    phonenumbers library in python

    Get different requirements daily, so the recent requirement I got was to extract the carriers of phone numbers…

    1 条评论
  • Google Sheet API with Nodejs

    Google Sheet API with Nodejs

    Google sheet is a platform where you can maintain your spreadsheet and can share with other people. Changes are tracked…

社区洞察

其他会员也浏览了