How can we not receive a new message from the queue in Java rabbitmq until I have not responded to a message?

824 views Asked by At

Receive single message from the queue in RabbitMQ using java:

I'm new to RabbitMQ and was wondering of a good approach to this problem I'm mulling over. I want to create a service that subscribes to a queue and Receive only one message and receive the next one after processing.

    DeliverCallback deliverCallback = new DeliverCallback() {
            public void handle(String s, Delivery delivery) throws IOException {
                System.out.println("Tag: "+delivery.getEnvelope().getDeliveryTag());
                String message = new String(delivery.getBody(), "UTF-8");
            }
    };

   channel.basicConsume(QUEUE_NAME, false, deliverCallback, new CancelCallback() {
            public void handle(String consumerTag) throws IOException {}
   });
2

There are 2 answers

0
null On

RabbitMQ supports polling a single message from a Queue at a time, but the official document doesnt encourage this approach.

Poll the message by disabling auto acknowledgement, finally send an ack after processing.

boolean autoAck = false;
GetResponse response = channel.basicGet(queueName, autoAck);
if (response !=  null) {
    //process the message and acknowledge it
}

For more details please refer to the official document section 'Retrieving Individual Messages ("Pull API")'

https://www.rabbitmq.com/api-guide.html#getting

0
ismael On

To receive a single message from the queue, I did the following steps:

Step 1: Accept only one unack-ed message at a time:

channel.basicQos(1);

Step 2: Setting autoAck to false:

boolean autoAck = false;

Step 3: Work Queues using the Java Client

DeliverCallback deliverCallback = (consumerTag, delivery) -> {
  try {
    System.out.println("Tag: "+delivery.getEnvelope().getDeliveryTag());
    String message = new String(delivery.getBody(), "UTF-8");
  } finally {
    System.out.println(" [Message] Task Done");
    channel.basicAck(delivery.getEnvelope().getDeliveryTag(), false);
  }
};

channel.basicConsume(QUEUE_NAME, autoAck, deliverCallback, consumerTag -> { });

see: rabbitmq documentation