RabbitMQ(7)Java Client - Topics

本文探讨了RabbitMQ中主题交换(Topic Exchange)的概念及其使用方式。通过示例代码展示了如何配置主题交换并实现消息的精确路由。此外,还介绍了通配符'*'和'#'的使用方法。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

RabbitMQ(7)Java Client - Topics

Although using the direct exchange improved our system, it still has limitations - it can't do routing based on multiple criteria.

We want to subscribe to not only logs based on severity, but also based on the source which emitted the log.

Severity info/warn/critical
Facility auth/cron/kern

Topic exchange
For topic exchange, routing_key must be a list of words.

The binding key must also be in the same form. The logic behind the topic exchange is similar to a direct one. A message sent with a particular rouing key will be delivered to all the queues that are bound with a matching binding key.

* (star) can substitute for exactly one word.
#(hash) can substitute for zero or more words.

We plan our routing key like this '<speed>.<colour>.<species>'.
Q1 "*.orange.*" is interested in all the orange animals
Q2 "*.*.rabbit" and "lazy.#" wants to hear everything about rabbits, and everything about lazy animals.

All come together
package com.sillycat.easytalker.rabbitmq.topic;

import com.rabbitmq.client.Channel;
import com.rabbitmq.client.Connection;
import com.rabbitmq.client.ConnectionFactory;

public class EmitLogTopic {

private static final String EXCHANGE_NAME = "topic_logs";

private final static String SERVER_HOST = "localhost";

public static void main(String[] argv) {
Connection connection = null;
Channel channel = null;

try {
ConnectionFactory factory = new ConnectionFactory();
factory.setHost(SERVER_HOST);
connection = factory.newConnection();
channel = connection.createChannel();

channel.exchangeDeclare(EXCHANGE_NAME, "topic");

channel.basicPublish(EXCHANGE_NAME, "bird.white.fly", null,
"fly bird, haha.".getBytes());
channel.basicPublish(EXCHANGE_NAME, "bird.black.walk", null,
"walking cock!".getBytes());
channel.basicPublish(EXCHANGE_NAME, "lazy.black.sleep", null,
"sleep warm!".getBytes());
channel.basicPublish(EXCHANGE_NAME, "fast.white.rabbit", null,
"running fast rabbit!".getBytes());

} catch (Exception e) {
e.printStackTrace();
} finally {
if (connection != null) {
try {
connection.close();
} catch (Exception ignore) {
}
}
}
}

}

package com.sillycat.easytalker.rabbitmq.topic;

import com.rabbitmq.client.Channel;
import com.rabbitmq.client.Connection;
import com.rabbitmq.client.ConnectionFactory;
import com.rabbitmq.client.QueueingConsumer;

public class ReceiveLogsTopic1 {

private static final String EXCHANGE_NAME = "topic_logs";

private final static String SERVER_HOST = "rd.digby.com";

public static void main(String[] argv) {
Connection connection = null;
Channel channel = null;
try {
ConnectionFactory factory = new ConnectionFactory();
factory.setHost(SERVER_HOST);
connection = factory.newConnection();
channel = connection.createChannel();

channel.exchangeDeclare(EXCHANGE_NAME, "topic");

String queueName = channel.queueDeclare().getQueue();

channel.queueBind(queueName, EXCHANGE_NAME, "lazy.#");

System.out
.println(" [*] Waiting for messages. To exit press CTRL+C");
QueueingConsumer consumer = new QueueingConsumer(channel);
channel.basicConsume(queueName, true, consumer);
while (true) {
QueueingConsumer.Delivery delivery = consumer.nextDelivery();
String message = new String(delivery.getBody());
String routingKey = delivery.getEnvelope().getRoutingKey();
System.out.println(" [x] Received '" + routingKey + "':'"
+ message + "'");
}
} catch (Exception e) {
e.printStackTrace();
} finally {
if (connection != null) {
try {
connection.close();
} catch (Exception ignore) {
}
}
}
}
}

ReceiveLogsTopic1 will receive all lazy animals. The only difference from ReceiveLogsTopic2 to ReceiveLogsTopic1 is as follow:
channel.queueBind(queueName, EXCHANGE_NAME, "*.white.*");

And ReceiveLogsTopic2 will focus on all the white colour animals.

references:
http://www.rabbitmq.com/tutorials/tutorial-five-java.html
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值