*加入依赖
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-amqp</artifactId>
</dependency>
在application.yml中加入
spring:
rabbitmq:
addresses: localhost:5672
username: root
password: root
添加RabbitMQConfig配置类
@Configuration
public class RabbitMQConfig {
@Autowired
private ConnectionFactory connectionFactory;
@Bean
public RabbitAdmin rabbitAdmin(ConnectionFactory connectionFactory) {
return new RabbitAdmin(connectionFactory);
}
@Bean
public MessageConverter messageConverter() {
return new Jackson2JsonMessageConverter();
}
@Bean
@Scope(ConfigurableBeanFactory.SCOPE_PROTOTYPE)
public RabbitTemplate rabbitTemplate(ConnectionFactory connectionFactory, MessageConverter messageConverter) {
RabbitTemplate rabbitTemplate = new RabbitTemplate(connectionFactory);
rabbitTemplate.setMessageConverter(messageConverter);
return rabbitTemplate;
}
//在此可以定义交换机
@Bean
TopicExchange topicExchange(RabbitAdmin rabbitAdmin) {
TopicExchange topicExchange = new TopicExchange(RabbitMQCode.Exchange.DF_TOPIC.getCode());
rabbitAdmin.declareExchange(topicExchange);
logger.info("主题型交换机bean实例化");
return topicExchange;
}
@Bean
DirectExchange directExchange(RabbitAdmin rabbitAdmin) {
DirectExchange directExchange = new DirectExchange(RabbitMQCode.Exchange.DF_DIRECT.getCode());
rabbitAdmin.declareExchange(directExchange);
logger.info("直连型交换机bean实例化");
return directExchange;
}
//在此可以定义队列
@Bean
Queue queueReceive(RabbitAdmin rabbitAdmin) {
Queue queue = new Queue(RabbitMQCode.Queue.DF_RECEIVE.getCode(), true, false, false, queueArguments());
rabbitAdmin.declareQueue(queue);
logger.info("接收队列实例化完成");
return queue;
}
@Bean
Queue queueResolve(RabbitAdmin rabbitAdmin) {
Queue queue = new Queue(RabbitMQCode.Queue.DF_RESOLVE.getCode(), true, false, false, queueArguments());
rabbitAdmin.declareQueue(queue);
logger.info("解析队列实例化完成");
return queue;
}
//在此处完成队列和交换机绑定
@Bean
Binding bindingQueueReceive(Queue queueReceive, DirectExchange directExchange, RabbitAdmin rabbitAdmin) {
Binding binding = BindingBuilder.bind(queueReceive).to(directExchange).with(RabbitMQCode.RoutingKey.DF_RECEIVE_KEY.getCode());
rabbitAdmin.declareBinding(binding);
logger.info("接收队列与直连型交换机绑定完成");
return binding;
}
@Bean
Binding bindingQueueResolve(Queue queueResolve, DirectExchange directExchange, RabbitAdmin rabbitAdmin) {
Binding binding = BindingBuilder.bind(queueResolve).to(directExchange).with(RabbitMQCode.RoutingKey.DF_RESOLVE_KEY.getCode());
rabbitAdmin.declareBinding(binding);
logger.info("解析队列与直连型交换机绑定完成");
return binding;
}
RabbitAdmin
mq的消息流程如下
该类封装了对 RabbitMQ 的管理操作
- 定义删除交换机
rabbitAdmin.declareExchange(exchange);
rabbitAdmin.deleteExchange(exchange);
- 定义删除队列
rabbitAdmin.declareQueue(queue);
rabbitAdmin.deleteQueue(queue);
//将队列中的消息全消费掉
rabbitAdmin.purgeQueue("info",false);
//定义binding
Binding binding = BindingBuilder.bind(queue).to(exchange).with(routingKey);
rabbitAdmin.declareBinding(binding);
rabbitAdmin.removeBinding(binding);
-exchange
在rabbitmq中,exchange有4个类型:direct,topic,fanout,header。
RabbitTemplate
Spring AMQP 提供了 RabbitTemplate 来简化 RabbitMQ 发送和接收消息操作
设置 RabbitTemplate 的默认交换器、默认路由键、默认队列
发送消息
send (自定义消息 Message)
Message message = new Message("hello".getBytes(),new MessageProperties());
// 发送消息到默认的交换器,默认的路由键
rabbitTemplate.send(message);
// 发送消息到指定的交换器,指定的路由键
rabbitTemplate.send("direct.exchange","key.1",message);
// 发送消息到指定的交换器,指定的路由键
rabbitTemplate.send("direct.exchange","key.1",message,new CorrelationData(UUID.randomUUID().toString()));
convertAndSend(自动 Java 对象包装成 Message 对象,Java 对象需要实现 Serializable 序列化接口)
User user = new User("linyuan");
// 发送消息到默认的交换器,默认的路由键
rabbitTemplate.convertAndSend(user);
// 发送消息到指定的交换器,指定的路由键,设置消息 ID
rabbitTemplate.convertAndSend("direct.exchange","key.1",user,new CorrelationData(UUID.randomUUID().toString()));
// 发送消息到指定的交换器,指定的路由键,在消息转换完成后,通过 MessagePostProcessor 来添加属性
rabbitTemplate.convertAndSend("direct.exchange","key.1",user,mes -> {
mes.getMessageProperties().setDeliveryMode(MessageDeliveryMode.NON_PERSISTENT);
return mes;
});
接收消息
receive(返回 Message 对象)
// 接收来自指定队列的消息,并设置超时时间
Message msg = rabbitTemplate.receive("debug",2000l);
receiveAndConvert(将返回 Message 转换成 Java 对象)
User user = (User) rabbitTemplate.receiveAndConvert();
或者利用注解监听mq消息
设置sender类
@Component
@Slf4j
public class MySender implements RabbitTemplate.ConfirmCallback, RabbitTemplate.ReturnCallback {
private RabbitTemplate rabbitTemplate;
@Autowired
public MySender(RabbitTemplate rabbitTemplate) {
this.rabbitTemplate = rabbitTemplate;
this.rabbitTemplate.setConfirmCallback(this);
this.rabbitTemplate.setReturnCallback(this);
}
@Override
public void confirm(CorrelationData correlationData, boolean ack, String cause) {
log.debug("消息唯一标识:"+correlationData);
log.debug("确认结果:"+ack);
log.debug("失败原因:"+cause);
}
private boolean sendMessage(String desPath) {
try {
CorrelationData correlationData = new CorrelationData(desPath);
this.rabbitTemplate.convertAndSend(RabbitMQCode.Exchange.DF_DIRECT.getCode(),
RabbitMQCode.RoutingKey.DF_PROCESS_KEY.getCode() , desPath,
message -> {message.getMessageProperties().setPriority(MessageUtil.parseMQPriority(desPath));
return message;
},
correlationData);
return true;
} catch (Exception e) {
log.error(e.getMessage(),e);
return false;
}
}
@Override
public void returnedMessage(Message message, int replyCode, String replyText, String exchange, String routingKey) {
log.error(message.getMessageProperties().getCorrelationId() + " 发送失败");
}
}
在客户端监听队列消息
@RabbitListener(queues = "df.receive")
@RabbitHandler
public void onMessage(Message message, String path,
Channel channel) throws Exception {
logger.info("onMessage path:" + path);
}