I use AMQP for my application. I want to close the connection to the consumer AMQP after all the message queues have been received. However, I don't know how to handle it. I will be very grateful and appreciated if someone help me. Thank you
var amqp = require('amqplib');
amqp.connect('amqp://localhost').then(function(conn) {
process.once('SIGINT', function() { conn.close(); });
return conn.createChannel().then(function(ch) {
var ok = ch.assertQueue('hello', {durable: false});
ok = ok.then(function(_qok) {
return ch.consume('hello', function(msg) {
console.log(" [x] Received '%s'", msg.content.toString());
}, {noAck: false});
});
return ok.then(function(_consumeOk) {
console.log(' [*] Waiting for messages. To exit press CTRL+C');
});
})
}).catch(console.warn);
conn.close() this close function will be close the connection
Related
i am following this tutorial regardign saving data to database using mqtt to mysql sensor to mysql via mqtt where i am at the app_mqtt.js part where i try to follow the exact same thing to create the js file but when i try to run it via python, it shows an error of :
File "app_mqtt.js", line 1
var mqtt = require('mqtt');
^
SyntaxError: invalid syntax
I have already the mqtt via npm i mqtt and npm install mqtt --save yet it still have such an error, i really need help in this. Thank you.
var mqtt = require('mqtt');
var Topic = '#'; //subscribe to all topics
var Broker_URL = 'mqtt://192.168.1.123';
var options = {
clientId: 'MyMQTT',
port: 1883,
keepalive : 60
};
var client = mqtt.connect(Broker_URL, options);
client.on('connect', mqtt_connect);
client.on('reconnect', mqtt_reconnect);
client.on('error', mqtt_error);
client.on('message', mqtt_messsageReceived);
client.on('close', mqtt_close);
function mqtt_connect()
{
console.log("Connecting MQTT");
client.subscribe(Topic, mqtt_subscribe);
}
function mqtt_subscribe(err, granted)
{
console.log("Subscribed to " + Topic);
if (err) {console.log(err);}
}
function mqtt_reconnect(err)
{
console.log("Reconnect MQTT");
if (err) {console.log(err);}
client = mqtt.connect(Broker_URL, options);
}
function mqtt_error(err)
{
console.log("Error!");
if (err) {console.log(err);}
}
function after_publish()
{
//do nothing
}
function mqtt_messsageReceived(topic, message, packet)
{
console.log('Topic=' + topic + ' Message=' + message);
}
function mqtt_close()
{
console.log("Close MQTT");
}
As per your code , it shows fine.
1) Try to restart the server.
2) check your code to this code
npm i mqtt --save
var mqtt = require('mqtt')
var client = mqtt.connect('mqtt://{Your connection string}')
client.on('connect', function () {
client.subscribe('presence', function (err) {
if (!err) {
client.publish('presence', 'Hello mqtt')
}
})
})
client.on('message', function (topic, message) {
// message is Buffer
console.log(message.toString())
client.end()
})
3) At last , re-install the package.
Note: If still issue , please share your code. So I can debug it.
I am trying my hand at node.js/typescript for the first time and having a bit of trouble making a consumer for a rabbit queue.
Code:
let amqp = require('amqp');
let connection = amqp.createConnection({url: "amqp://" + RABBITMQ_USER + ":" + RABBITMQ_PASSWORD + "#" + RABBITMQ_HOST + ":" + RABBITMQ_PORT + RABBITMQ_VHOST});
connection.on('ready', function() {
connection.exchange(RABBITMQ_WORKER_EXCHANGE, function (exchange) {
connection.queue(RABBITMQ_QUEUE, function (queue) {
queue.bind(exchange, function() {
queue.publish(function (message) {
console.log('subscribed to queue');
let encoded_payload = unescape(message.data);
let payload = JSON.parse(encoded_payload);
console.log('Received a message:');
console.log(payload);
})
})
})
})
})
It seems to connect to the amqp server and throws no errors but it just sits there and doesn't consume anything. Is there a step I am missing?
Any help would be greatly appreciated,
Thank you.
Here is my solution that is working based off of amqp's JS tutorial.
https://www.rabbitmq.com/tutorials/tutorial-three-javascript.html
Probably not up to TypeScript standards, feel free to correct me if there's a better way.
#!/usr/bin/env node
require('dotenv').config();
import amqp = require('amqplib/callback_api');
import db = require('./database');
amqp.connect({
protocol: process.env.RABBITMQ_PROTOCOL,
hostname: process.env.RABBITMQ_HOST,
port: process.env.RABBITMQ_PORT,
username: process.env.RABBITMQ_USER,
password: process.env.RABBITMQ_PASSWORD,
vhost: process.env.RABBITMQ_VHOST
}, function(err, conn) {
conn.createChannel(function (err, ch) {
// set exchange that is being used
ch.assertExchange(process.env.RABBITMQ_WORKER_EXCHANGE, 'direct', {durable: true});
// set queue that is being used
ch.assertQueue(process.env.RABBITMQ_QUEUE, {durable: true}, function (err, q) {
console.log(" [*] Waiting for messages in %s. To exit press CTRL+C", q.queue);
// bind the queue to the exchange
ch.bindQueue(q.queue, process.env.RABBITMQ_WORKER_EXCHANGE, '');
// consume from the queue, one message at a time.
ch.consume(q.queue, function (msg) {
console.log("Message received: %s", msg.content.toString());
//save message to db
db.store(msg.content.toString()).then(function() {
//acknowledge receipt of message to amqp
console.log("Acknowledging message");
ch.ack(msg, true);
});
}, {noAck: false});
});
});
});
import * as Amqp from "amqp-ts";
var connection = new Amqp.Connection("amqp://localhost");
var exchange = connection.declareExchange("ExchangeName");
var queue = connection.declareQueue("QueueName");
queue.bind(exchange);
queue.activateConsumer((message) => {
console.log("Message received: " + message.getContent());
});
// it is possible that the following message is not received because
// it can be sent before the queue, binding or consumer exist
var msg = new Amqp.Message("Test");
exchange.send(msg);
connection.completeConfiguration().then(() => {
// the following message will be received because
// everything you defined earlier for this connection now exists
var msg2 = new Amqp.Message("Test2");
exchange.send(msg2);
});
I enqueue my messages to Rabiitmq using the following node js code:
//enqueue.js
var amqp = require('amqplib/callback_api');
amqp.connect('amqp://localhost', function(err, conn) {
conn.createChannel(function(err, ch) {
var q = 'hello';
ch.assertQueue(q, {durable: true});
ch.sendToQueue(q, new Buffer('Msg 1'));
ch.sendToQueue(q, new Buffer('Msg 2'));
ch.sendToQueue(q, new Buffer('Msg 3'));
ch.sendToQueue(q, new Buffer('Msg 4'));
ch.sendToQueue(q, new Buffer('Msg 5'));
});
setTimeout(function() { conn.close(); process.exit(0) }, 500);
});
The enqueue process happens as intended.
Now I wish to dequeue just 1 message and for that I use this code:
//dequeue.js
var amqp = require('amqplib/callback_api');
amqp.connect('amqp://localhost', function(err, conn) {
conn.createChannel(function(err, ch) {
var q = 'hello';
ch.assertQueue(q, {durable: true});
ch.prefetch(1);
ch.consume(q, function(msg) {
console.log(" [x] Received %s", msg.content.toString());
}, {noAck: false});
});
});
As expected the output is:
[x] Received Msg 1
But Msg 1 is still in the queue and it is not dequeued. So I tried adding ch.ack(msg) after the console.log() statement in dequeue.js but instead of just 1 message getting dequeued all the messages are getting dequeued!
Please help me to dequeue just 1 message.
Set noack to true.
noAck (boolean): if true, the message will be assumed by the server to
be acknowledged (i.e., dequeued) as soon as it's been sent over the
wire. Default is false, that is, you will be expected to acknowledge
the message.
http://www.squaremobius.net/amqp.node/channel_api.html#channel_get
Or remove the noack and make sure you check that msg !== null (if you call ch.ack() on a null object, it's just going to throw a channel exception).
I'm new to message queue's and i'm trying to connect to a rabbit mq instance that was setup for me using https://github.com/squaremo/amqp.node and i'm definitely on the struggle bus.
I took the example from here and i'm trying to plug my values in and I'm getting no where.
Here's the info I was given:
Server: myserver
Queue: uinotification
username: myuser
password: mypass
Here's my attempt at using this example but I think instead of having to assert the queue i need to bind to it (i think).
Here's the docs for bindQueue: http://www.squaremobius.net/amqp.node/doc/channel_api.html#toc_39
I think i'm confused by the exchange piece.
amqp.connect('amqp://myuser:mypass#myserver').then(function(conn) {
process.once('SIGINT', function() { conn.close(); });
return conn.createChannel().then(function(ch) {
var ok = ch.assertExchange('logs', 'fanout', {durable: false});
ok = ok.then(function() {
//return ch.assertQueue('', {exclusive: true});
return ch.bindQueue('uinotification', 'logs', '');
});
/*ok = ok.then(function(qok) {
console.log('qok = ');
console.log(qok);
return ch.bindQueue(qok.queue, 'logs', '').then(function() {
return qok.queue;
});
});*/
ok = ok.then(function(queue) {
console.log('queue = ');
console.log(queue);
return ch.consume(queue, logMessage, {noAck: true});
});
return ok.then(function() {
console.log(' [*] Waiting for logs. To exit press CTRL+C');
});
function logMessage(msg) {
console.log(" [x] '%s'", msg.content.toString());
}
}).catch(function(err) {
console.error('err = '+err);
});
}).then(null, console.warn).catch(function(err) {
console.error('connect err = '+err);
});
Here's the error I get with the above code:
Channel closed by server: 404 (NOT-FOUND) with message "NOT_FOUND - no previously declared queue"
A queue has to exist before you can bind to it, thus asserting it into existence first is actually what you need to do before binding to it.
Note that the settings for the queue have to be exactly the same as the ones the queue has been first created with.
I want to send the same messages many times in a row, but i need to use a loop. When I use a loop though, no messages are sent. I am using amqp in Nodejs.
Here is the working code for sending a single messages. What should I do to send many. I have already tried just wrapping a while loop around the connection.publish part and nothing was sent.
var amqp = require('amqp');
var connection = amqp.createConnection({url: "amqp://tester:tstpsswrd#10.4.52.115:5672"});
connection.on('ready', function () {
connection.queue('my-queue', function (q) {
connection.publish('my-queue', 'hi');
});
});
I'm positive that I am doing something stupid wrong here, or maybe missing something. First time with rabbitmq.
Update, Loop example
var amqp = require('amqp');
var connection = amqp.createConnection({url: "amqp://tester:tstpsswrd#10.4.52.115:5672"});
connection.on('ready', function () {
connection.queue('my-queue', function (q) {
while(true){
connection.publish('my-queue', 'hi');
}
});
});
In practical scenario you can not and should not be having a infinite loop as such for writing to a message broker. There have to be some event based thing or a proper defined number.
Try this code you can use the for loop according to your requirement:
var amqp = require('amqp');
var connection = amqp.createConnection({ host: 'localhost', port: 5672});
connection.on('ready', function () {
for(var i=0; i<1000; i++){
var status = writeOnQueue("testing the queue"+i);
}
});
function writeOnQueue(xml){
var msg = xml;
console.log(msg);
try{
connection.exchange('test-exchange', {confirm: true},function(exchange) {
publish = exchange.publish('my-queue',msg, { mandatory: false });
console.log('sent the message success test-exchange');
return true;
});
}
catch(e){
console.log('Some error occured.'+ e);
}
}