SpringBoot高级-消息-@RabbitListener&@EnableRabbit

在实际开发中我们需要监听场景,比如我们之前举的例子,两个系统,订单系统,和我们库存系统,他们交互都是通过交互

通过消息队列,某一个人下了单以后,将订单信息放到消息队列中,库存系统要实时监听队列里的内容,一旦有新的订单进来,

库存系统就要负责相关的操作,那我们的监听怎么写呢,Spring为了简化我么开发,给我们引入了相关的注解,比如我们来举一个

例子,我来写一个BookService,就来监听book里面的内容,我怎么写呢,我就叫receive,在这方法里面呢,我们要收到book的内容,

所以我在方法的参数上,我们这个方法是通过监听消息队列,可以来写一个注解,@RabbitListener,监听MQ的,那监听哪个消息队列呢,

我们可以来写一个queues,这个queues它是一个数组的方式,

/**
 * The queues for this listener.
 * The entries can be 'queue name', 'property-placeholder keys' or 'expressions'.
 * Expression must be resolved to the queue name or {@code Queue} object.
 * Mutually exclusive with {@link #bindings()}
 * @return the queue names or expressions (SpEL) to listen to from target
 * {@link org.springframework.amqp.rabbit.listener.MessageListenerContainer}.
 */
String[] queues() default {};

我们可以监听多个消息队列,我们就来监听我们之前的china.news,我们就来监听,有内容进来,@EnableRabbit,开启基于注解的MQ
package com.learn.service;

import org.springframework.amqp.rabbit.annotation.RabbitListener;
import org.springframework.stereotype.Service;

import com.learn.bean.Book;

@Service
public class BookService {

	@RabbitListener(queues="china.news")
	public void receive(Book book) {
		System.out.println("收到消息" + book);
	}
	
}
package com.learn;

import org.springframework.amqp.rabbit.annotation.EnableRabbit;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;

/**
 * 自动配置
 * @author Leon.Sun
 *
 */
@SpringBootApplication
@EnableRabbit
public class SpringBoot02AmqpApplication {

	public static void main(String[] args) {
		// Spring应用启动起来
		SpringApplication.run(SpringBoot02AmqpApplication.class,args);
	}
	
}
有了这两个注解的配合,让@RabbitListener来监听Listener里的内容,监听消息队列的内容,我们就来启动一下这个应用,

来测试一下,只要有book信息来,我们就会收到,一启动就收到消息

收到消息Book [bookName=三国演义, author=罗贯中]

/**
 * 广播
 */
@Test
public void sendMsg() {
	rabbitTemplate.convertAndSend("exchange.fanout","",new Book("红楼梦","曹雪芹"));
}

收到消息Book [bookName=红楼梦, author=曹雪芹]

这就是我们收到消息监听来收消息,只要消息队列里有,这个我们直接序列化成Book对象,如果我们有一些定制的消息,

还想要消息头等等,写成Message类型

org.springframework.amqp.core.Message

写上Message类型以后呢,我们来写一个@RabbitListener,我们来监听china队列,我们写的Message参数,既有getBody消息的

内容,还有getMessageProperties,我们消息的头信息,我们可以重新尝试一下,我们来到这个主程序,他重新启动,来看china

里的内容,china默认已经有两个内容了,我们启动的时候都能收到,

[B@4511a7ef
MessageProperties [headers={__TypeId__=com.learn.bean.Book}, timestamp=null, messageId=null, 
userId=null,
receivedUserId=null, appId=null, clusterId=null, type=null, correlationId=null, 
correlationIdString=null,
replyTo=null, contentType=application/json, contentEncoding=UTF-8, contentLength=0, 
deliveryMode=null,
receivedDeliveryMode=PERSISTENT, expiration=null, priority=0, redelivered=false, 
receivedExchange=exchange.fanout, receivedRoutingKey=, receivedDelay=null, deliveryTag=1, 
messageCount=0,
consumerTag=amq.ctag-jmwvhNiVfS6HYqKWi5xuCw, consumerQueue=china]
[B@71e6aae7
MessageProperties [headers={__TypeId__=com.learn.bean.Book}, timestamp=null, messageId=null, 
userId=null, 
receivedUserId=null, appId=null, clusterId=null, type=null, correlationId=null, 
correlationIdString=null, 
replyTo=null, contentType=application/json, contentEncoding=UTF-8, contentLength=0, 
deliveryMode=null, 
receivedDeliveryMode=PERSISTENT, expiration=null, priority=0, redelivered=false, 
receivedExchange=exchange.fanout, receivedRoutingKey=, receivedDelay=null, 
deliveryTag=2,
 messageCount=0, consumerTag=amq.ctag-jmwvhNiVfS6HYqKWi5xuCw, consumerQueue=china]
package com.learn.service;

import org.springframework.amqp.core.Message;
import org.springframework.amqp.rabbit.annotation.RabbitListener;
import org.springframework.stereotype.Service;

import com.learn.bean.Book;

@Service
public class BookService {

	@RabbitListener(queues="china.news")
	public void receive(Book book) {
		System.out.println("收到消息" + book);
	}
	
	@RabbitListener(queues="china")
	public void receive02(Message message) {
		System.out.println(message.getBody());
		System.out.println(message.getMessageProperties());
	}
}
package com.learn;

import org.springframework.amqp.rabbit.annotation.EnableRabbit;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;

/**
 * 自动配置
 * @author Leon.Sun
 *
 */
@SpringBootApplication
@EnableRabbit
public class SpringBoot02AmqpApplication {

	public static void main(String[] args) {
		// Spring应用启动起来
		SpringApplication.run(SpringBoot02AmqpApplication.class,args);
	}
	
}
package com.learn.springboot;

import java.util.Arrays;
import java.util.HashMap;
import java.util.Map;

import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.amqp.rabbit.core.RabbitTemplate;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.test.context.junit4.SpringRunner;

import com.learn.bean.Book;

@RunWith(SpringRunner.class)
@SpringBootTest
public class SpringBootAmqpApplicationTests {
	
	@Autowired
	RabbitTemplate rabbitTemplate;
	
	/**
	 * 1.单播(点对点)
	 */
	@Test
	public void contextLoads() {
		// Message需要自己构造一个,定义消息体内容和消息头
//		rabbitTemplate.send(exchange, routingKey, message);
		
		// object默认当成消息体,只需要传入要发送的对象,自动序列化发送给rabbitmq
//		rabbitTemplate.convertAndSend(routingKey, message, messagePostProcessor);
		
		Map<String,Object> map = new HashMap<String,Object>();
		map.put("msg", "这是第一个消息");
		map.put("data", Arrays.asList("helloworld",1231,true));		
		// 对象被默认序列化以后发送出去
		rabbitTemplate.convertAndSend("exchange.direct", "china.news",new Book("西游记","吴承恩"));
	}
	
	@Test
	public void receive() {
		Object o = rabbitTemplate.receiveAndConvert("china.news");
		System.out.println(o.getClass());
		System.out.println(o);
	}
	
	/**
	 * 广播
	 */
	@Test
	public void sendMsg() {
		rabbitTemplate.convertAndSend("exchange.fanout","",new Book("红楼梦","曹雪芹"));
	}
}

 

  • 2
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
以下是Springboot集成RabbitMq@RabbitListener不自动生成队列的解决方法: 1. 确保已经定义了RabbitAdmin的Bean,并且已经将其注入到了ConnectionFactory中。可以参考如下代码: ```java @Configuration @EnableRabbit public class RabbitConfig { @Bean public RabbitAdmin rabbitAdmin(ConnectionFactory connectionFactory) { RabbitAdmin rabbitAdmin = new RabbitAdmin(connectionFactory); // 服务启动时候开启自动启动 rabbitAdmin.setAutoStartup(true); return rabbitAdmin; } @Bean public SimpleRabbitListenerContainerFactory rabbitListenerContainerFactory(ConnectionFactory connectionFactory) { SimpleRabbitListenerContainerFactory factory = new SimpleRabbitListenerContainerFactory(); factory.setConnectionFactory(connectionFactory); factory.setConcurrentConsumers(3); factory.setMaxConcurrentConsumers(10); factory.setAcknowledgeMode(AcknowledgeMode.MANUAL); return factory; } } ``` 2. 确保在@RabbitListener注解中指定了正确的队列名称。例如: ```java @RabbitListener(queues = "testQueue") public void receiveMessage(String message) { System.out.println("Received message: " + message); } ``` 3. 确保在@RabbitListener注解中指定了正确的Exchange和RoutingKey。例如: ```java @RabbitListener(bindings = @QueueBinding( value = @Queue(value = "testQueue", durable = "true"), exchange = @Exchange(value = "testExchange", type = ExchangeTypes.TOPIC), key = "testRoutingKey" )) public void receiveMessage(String message) { System.out.println("Received message: " + message); } ```
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值