本文只针对通配符/主题模式(Topic Exchange)的使用。
一、生产者端的队列/交换器配置:
这里只有生产者客户端需要配置,消费者端可无需配置。
@Configuration
public class TopicRabbitConfig {
/**
* 创建队列
* @return
*/
@Bean
public Queue firstQueue() {
return new Queue("TopicFirstQueue", true);
}
/**
* 创建队列
* @return
*/
@Bean
public Queue secondQueue() {
return new Queue("TopicSecondQueue", true);
}
/**
* 创建 Topic交换器
* @return
*/
@Bean
public TopicExchange CustomTopicExchange() {
return new TopicExchange("CustomTopicExchange");
}
/**
* 将交换器与队列绑定,设定匹配键
* @return
*/
@Bean
public Binding bindingFirst() {
return BindingBuilder.bind(firstQueue()).to(CustomTopicExchange()).with("custom.topic.#");
}
/**
* 将交换器与队列绑定,设定匹配键
* @return
*/
@Bean
public Binding bindingSecond() {
return BindingBuilder.bind(secondQueue()).to(CustomTopicExchange()).with("custom.topic.second");
}
}
二、消费者端的监听消费:
@Component
public class TopicConsumer {
@RabbitListener(queues = "TopicFirstQueue")
public void process(Map message) {
System.out.println("[consumer-1]从队列[TopicFirstQueue]中收到消息:" + message.toString());
}
@RabbitListener(queues = "TopicSecondQueue")
public void process1(Map message) {
System.out.println("[consumer-2]从队列[TopicSecondQueue]中收到消息:" + message.toString());
}
}
三、发送消息到队列:
下面只是调试样例,不涉及业务。
@RequestMapping("/producer")
@RestController
public class ProducerController {
@Autowired
private RabbitTemplate rabbitTemplate;
@GetMapping("topic/send/{type}")
public String sendTopicMessage(@PathVariable String type) {
int i = 0;
while(i < 10000) {
HashMap<String, Object> map = new HashMap<>();
map.put("message_id", UUID.randomUUID());
map.put("message_msg", "这是一条消息数据");
map.put("message_num", ++i);
map.put("message_created_time", new Date());
map.put("routing_key", "custom.topic." + type);
rabbitTemplate.convertAndSend("CustomTopicExchange", "custom.topic." + type, map);
}
return "【topic】发送成功";
}
}
使用Postman进行模拟消息发送。
当发送 routingKey为custom.topic.second 的信息到指定交换器,交换器根据 routingKey 寻找与之匹配绑定队列,若匹配多个队列则转发到各个队列中。这里匹配 bindingKey 为 custom.topic.second 和通配符匹配的 custom.topic.# 的两个队列中。
当发送 routingKey 不为custom.topic.second,但前缀为 custom.topic. 的信息到指定交换器,交换器根据 routingKey 只能匹配 bindingKey为 custom.topic.# 的绑定队列中。