目录
前言
Spring Boot 支持 JMS 和 AMQP 的异步消息。JMS(Java Message Service) 即Java消息服务,是基于JVM消息代理的规范,JMS的实现有:ActiveMQ、HornetQ;AMQP(Advanced Message Queuing Protocol) 也是一个消息代理的规范,不仅兼容JMS,还支持跨语言和平台,AMQP的实现有RabbitMQ。
本篇文章就来看看Spring Boot 中如何使用 RabbitMQ。
异步消息
首先来说说什么是异步消息,异步消息主要目的是为了系统与系统之间的通信。所谓异步消息即消息发送者无需等待消息接受者的处理及返回,甚至无需关系消息是否发送成功。
在异步消息中有两个 重要的概念:消息代理(message borker)和目的地(destination),当消息发送者发送消息后,消息将由消息代理接管,消息代理保证消息传递到指定的目的地。异步消息主要有两种形式的目的地:队列(queue)和主题(topic)。队列用于点对点的消息通信;主题用于发布/订阅式的消息通信。
一、点对点式
当消息发送者发送消息,消息代理获得消息后将消息放进队列中,当有消息接受者来接受消息时,消息将从队列中取出来传递给接受者,这个时候队列就没有了这条消息。
点对点式确保的是每一条消息只有唯一的生产者和消费者,当然,这并不是说只有一个接受者可以从队列中接受消息。因为队列中有很多消息,点对点式只保证每一条消息只有唯一的生产者和消费者。
二、发布/订阅式
和点对点式不同,发布/订阅式是消息发送者发送消息到主题(topic),而多个接受者监听这个主题,此时消息发送者和接受者分别叫叫做发布者和订阅者。
Spring Boot集成RabbitMQ
一、添加依赖
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-amqp</artifactId>
</dependency>
二、配置RabbitMQ
1、在application.properties中配置RabbitMQ的连接信息,如下图。
spring.rabbitmq.host=localhost
spring.rabbitmq.port=5672
spring.rabbitmq.username=guest
spring.rabbitmq.password=guest
2、声明Exchange、Queue、Binding等信息,为了声明方便,我们提前定义好队列常量信息,如下图。
/**
* 队列常量信息
*/
public interface QueueConstants {
/**
* 消息交换
*/
String MESSAGE_EXCHANGE = "spring.boot.message.direct.exchange";
/**
* 消息队列名称
*/
String MESSAGE_QUEUE_NAME = "message.queue";
/**
* 消息路由键
*/
String MESSAGE_ROUTE_KEY = "message.send";
}
@Configuration
public class RabbitConfig {
/**
* 交换机配置
* @return
*/
@Bean
public DirectExchange addDirectExchange(){
return (DirectExchange)ExchangeBuilder.directExchange(QueueConstants.MESSAGE_EXCHANGE)
.durable(true)
.build();
}
/**
* 消息队列声明
* @return
*/
@Bean
public Queue addQueue(){
return QueueBuilder.durable(QueueConstants.MESSAGE_QUEUE_NAME).build();
}
/**
* 消息绑定
* @return
*/
@Bean
public Binding messageBinding(){
return BindingBuilder.bind(addQueue())
.to(addDirectExchange())
.with(QueueConstants.MESSAGE_ROUTE_KEY);
}
}
三、定义消息实体
/**
* 消息实体
*/
public class MessageEntity implements Serializable {
private static final long serialVersionUID = 296763681597798722L;
private String contents;
//get、set方法略
}
四、定义生产者
生产者即消息发送者,需要注入AmqpTemplate用来发送消息,如下图。
/**
* 生产者(消息发送者)
*/
@Component
public class Provider {
@Autowired
private AmqpTemplate rabbitTemplate;
/**
* 发送消息
* @param object
*/
public void send(Object object){
System.out.println("Sender : " + JSON.toJSONString(object));
this.rabbitTemplate.convertAndSend(QueueConstants.MESSAGE_EXCHANGE, QueueConstants.MESSAGE_ROUTE_KEY, object);
}
}
五、定义消费者
消费者即消息接受者,通过@RabbitListener注解定义要监听的消息队列,用@RabbitHandler定义消息处理方法。
/**
* 消费者(消息接受者)
*/
@Component
@RabbitListener(queues = QueueConstants.MESSAGE_QUEUE_NAME)
public class Receiver {
/**
* 接受消息
* @RabbitHandler会自动获取消息
* @param messageEntity
*/
@RabbitHandler
public void handler(@Payload MessageEntity messageEntity){
System.out.println("Receiver : " + JSON.toJSONString(messageEntity));
}
}
六、验证
一如既往,我们还是用web请求的方法来验证,定义Controller如下:
@RestController
@RequestMapping("/rabbitmq")
public class MessageController {
@Resource
private Provider provider;
@RequestMapping("/send")
public String send(MessageEntity message){
provider.send(message);
return "success";
}
}
验证结果如下: