最近の研究のSpringBootサブモジュールは、今モジュールコードがにアップロードされている学習する必要がありますGitHubに、リファレンスと学習ガイドを歓迎します。
I.概要
ほとんどのアプリケーションでは(1)、メッセージ・ミドルウェアを介してサービスを強化するための非同期通信システム、スケーラビリティが切り離さ。
上記の最初の画像:登録ユーザーは、ユーザーが電子メールやSMSの登録が成功すると送信する必要があります。同期および時間のかかるを使用して図従来の方法。
上述した第2の画像は:電子メールやテキストメッセージを送信し、問題の図面を解決するために、あなたは時間を待機しているユーザーを保存するために、マルチスレッドで採用することができます。
第三の画像上:使用メッセージミドルウェアの実施形態では、書き込みテキストメッセージと送信メッセージのメッセージ・キューに、その後直ちに返されたメッセージと送信テキストメッセージの終了を待たずに、ユーザに返さ、ユーザ待ち時間を低減する、非同期背景これは、メッセージキューから適切なアクションを読み込みます。
(2)メッセージサービス2つの重要な概念
Message Agentはメッセージの送信者がメッセージ、によって引き継がメッセージ・ブローカーに送信した場合:
宛先:Message Agentは、指定された宛先に送信先のメッセージキューを主に二つの形式のメッセージの配信を保証しました:
- キュー:ピア・メッセージング
- 件名:パブリッシュ/サブスクライブ・メッセージング
(3)二つの共通メッセージサービス仕様
- JMS(Java Message Serviceの):Javaメッセージサービス - 仕様JVMベースのメッセージブローカ。ActiveMQの、HornetMQはJMSを達成することです。
- AMQP(アドバンスト・メッセージキュープロトコル):高度なメッセージキュープロトコルには、報道機関の仕様であると互換性のJMSです。達成のRabbitMQのAMQP。
二、RabbitMQの
AMQPはのオープンソース実装であります
1、コアコンセプト
- メッセージ:メッセージ・ヘッダとメッセージ本体によってメッセージ。メッセージ本体が不透明で、および任意の属性一連のメッセージヘッダには、これらの属性のようなルーティングキー(ルーティングキー)、(他のメッセージに優先相対有する)優先順位とが挙げられます。
- Publisher:消息的生产者,向交换器发布消息的客户端应用程序。
- Consumer: 消息的消费者。从消息队列中取得消息的客户端应用程序。
- Exchange: 交换器,用来接收生产者发送的消息并将这些消息路由到服务器中的队列。服务器中可能由多个消息队列。通过消息中的路由键发送到指定的消息队列。
- Queue: 消息队列,用来保存消息直到发送给消费者。是消息的容器也是消息的终点。一个消息可以投入到一个或多个队列。
- Binding: 绑定,用于消息队列和交换器之间的关联。Exchange 和 Queue的绑定可以是多对多的关系。
- Channel: 信道,多路复用连接中一条独立的双向数据流通道。信道是简历在真实的TCP连接内的虚拟连接。AMQP命令都是通过信道发送出去的。不管是发布消息、订阅消息还是接收消息,这些动作都是通过信道完成的。因为对操作系统来说建立和销毁TCP都是非常昂贵的开销。所以引入了信道的概念,以复用一条TCP连接。
- Broker:表示消息队列服务器实体
2、运行机制
运行机制其实就是核心概念中的那幅图,通过交换器将消息存放到消息队列中。Exchange分发消息时根据类型的不同分发策略也不同看,目前共有四种类型。
- direct:直连健,消息的路由键和对列的键一致时,就会将该消息存放到相应的消息队列中,也就是之前说的点对点模式。
- Fanout:每个发到Fanout类型交换器上的消息都会分到所有绑定的队列上去。Fanout不处理路由键,发送消息最快。也就是之前说的广播模式。
- Topic:可以通过模式匹配分配消息的路由键属性。
- Headers:headers匹配AMQP消息头而不是路由键,其交换器和direct交换器完全一致,但性能差很多,目前基本不用。
3.SpringBoot整合RabbitMQ
(1) 安装RabbitMQ
这里可以使用Docker安装,网上教程一大堆,就不详细介绍了。注意记得安装带有management的版本,这种版本可以利用web网页进行管理。安装完成后run的时候记得映射端口。
(2) Web界面操作RabbitMQ
- 进入web界面,地址:RabbitMQ安装的主机地址:端口号,端口号为使用docker安装RabbitMQ映射管理web的端口。默认用户名和密码都是:guest。
- 进入成功后点击Queues添加消息队列,点击Add a new queue,这里的name是路由键路由的依据。
- 点击Exchanges设置交换器,点击Add a new exchanget添加交换器。选择相应的路由类型,并绑定消息队列。这里以direct类型为例演示。
- 利用设置好的交换器和消息队列进行演示
点击publish message,进行如下的填写,publish message按钮,就可在对应的消息队列中收到消息。
然后切换到queues中,点击time消息队列,然后点击get Message。就可以获取到刚才发送给消息队列的消息。
三、SpringBoot整合RabbitMQ
整合过程 比较简单。导入相应的starter就可以,不需要我们做过多的配置,不得不佩服springboot自动配置功能的强大。
1、导入相应的starter
2、配置RabbitMQ,在application.yml文件中进行RabbitMQ的配置,这里只需指定RabbitMQ软件所在主机地址,其他的使用默认配置就可以。
3、SpringBoot操作RabbitMQ代码
通过以下代码就可以操作RabbitMQ。
@RunWith(SpringRunner.class)
@SpringBootTest
public class RabbitmqApplicationTests {
@Autowired
RabbitTemplate rabbitTemplate;
/**
* 1. 单播(点对点)
*/
@Test
public void contextLoads() {
// message需要自己构造,定制消息体内容和消息头
// rabbitTemplate.send(exchange,routeKey,message);
// Object默认当成消息体,只需要传入要发送的对象,自动序列化发送给rabbitmq
//rabbitTemplate.convertAndSend(exchange,routeKey,object);
Map<String,Object> map = new HashMap<>();
map.put("msg","这是第一个消息");
map.put("data", Arrays.asList("helloWorld",123,true));
// 对象使用默认序列化方法以后发送出去
rabbitTemplate.convertAndSend("exchange.direct","time.news",map);
}
@Test
public void test(){
Object o = rabbitTemplate.receiveAndConvert("time.news");
System.out.println(o.getClass());
System.out.println(o);
}
// 定制自己的序列化方法,进行发送。需要配置自己MessageConvert,让对象以json的数据发送出去
@Test
public void test1(){
Map<String,Object> map = new HashMap<>();
map.put("msg","这是第一个消息");
map.put("data", Arrays.asList("helloWorld",123,true));
// 对象使用默认序列化方法以后发送出去
rabbitTemplate.convertAndSend("exchange.direct","time.news",map);
}
}
4、监听消息队列
假设有这样一个需求,当消息队列中存放消息时,让程序就可以直接getMassage。SpringBoot为我们提供了@RabbitMQListener注解。
* @author Time
* @created 2019/8/27
*
*
* 注解@RabbitListener:监听一或多个个消息队列,当消息队列中存放消息,就获取消息
*/
@Service
public class RabbitMQService {
@RabbitListener(queues = {"time.news"})
public void receive(Map<String,Object> map){
System.out.println(map);
}
}
5、AmqpAdmin管理Rabbit组件,之前我们添加交换器、队列都是在web界面进行创建的,除此之外还可以利用AmqpAdmin进行管理这些组件。
// 利用AmqpAdmin管理组件
@Autowired
AmqpAdmin amqpAdmin;
@Test
public void test2(){
// 利用amqpAdmin创建交换器
amqpAdmin.declareExchange(new DirectExchange("amqp"));
// 利用amqpAdmin创建消息队列
amqpAdmin.declareQueue(new Queue("amqp.queue",true));
// 利用amqpAdmin将交换器和队列绑定
amqpAdmin.declareBinding(new Binding("amqp.queue", Binding.DestinationType.QUEUE,
"amqp","amqp",null ));
}
执行后结果
创建的交换器
创建的消息队列
将交换器和消息队列绑定