0
votes

This is a very contrived example of a rabbitmq app which is both producer and consumer of messages in one single main method. The problem is the code inside overridden handleDelivery method never gets executed. I use Rabbitmq dashboard and see the queue fills up and consumes. And the line in handleConsumeOk gets printed. Since I am new to rabbitmq I'm wondering if I have done something fundamentally wrong or I just got the idea of "Called when a basic.deliver is received for this consumer" wrong.

public class RabbitMain {

    public static void main(String[] args) throws IOException, TimeoutException, InterruptedException {
        Connection connection = Utils.getConnection("test");
        String payload = "hello world!";
        try (Channel channel = connection.createChannel()){
            channel.exchangeDeclare("sampleExchange", BuiltinExchangeType.TOPIC, true);
            channel.basicPublish("sampleExchange", "testKey", null, payload.getBytes());
        }

        System.out.println("Consume...");

        try (Channel channel = connection.createChannel()){
            channel.exchangeDeclare("sampleExchange", BuiltinExchangeType.TOPIC, true);
            channel.queueDeclare("testQueue", true, false, false, null);
            channel.queueBind("testQueue", "sampleExchange", "testKey");

            Consumer consumer = new DefaultConsumer(channel){
                @Override
                public void handleDelivery(String consumerTag, Envelope envelope, AMQP.BasicProperties properties, byte[] body) throws IOException {
                    String message = new String(body);
                    System.out.println("Received: " + message);
                }

                @Override
                public void handleConsumeOk(String consumerTag) {
                    System.out.println("handled consume ok");
                }
            };

            Thread.sleep(2000);

            channel.basicConsume("testQueue", true, consumer);
        }
    }
}
1
Consuming happens on another thread. When I ran the code with IntelliJ idea debugger the code works. By adding some idle time to the main thread (e.g. Thread.sleep(1000) the consuming thread had time to finish its job. I am not sure but it seems consumer thread was a daemon thread and got killed after the main thread terminated. - Hessam

1 Answers

0
votes

You publish the message to the exchnage before any queue is bound to it. RabbitMQ will discard any message it can't route to a queue.

Do

channel.queueDeclare("testQueue", true, false, false, null);
channel.queueBind("testQueue", "sampleExchange", "testKey");

before you call channel.basicPublish.