RabbitMQ入门

1. 异步通讯简述


好处:

  • 吞吐量提升:无需等待订阅者处理完成,响应更快速
  • 故障隔离:服务没有直接调用,不存在级联失败问题
  • 调用间没有阻塞,不会造成无效的资源占用
  • 耦合度极低,每个服务都可以灵活插拔,可替换
  • 流量削峰:不管发布事件的流量波动多大,都由Broker接收,订阅者可以按照自己的速度去处理事件

缺点:

  • 架构复杂了,业务没有明显的流程线,不好管理
  • 需要依赖于Broker的可靠、安全、性能

2. 常见的消息模型


SpringAMQP是基于RabbitMQ封装的一套模板,并且还利用SpringBoot对其实现了自动装配,使用起来非常方便。

提供了三个功能:

  • 自动声明队列、交换机及其绑定关系
  • 基于注解的监听器模式,异步接收消息
  • 封装了RabbitTemplate工具,用于发送消息
2.1 SimpleQueue

在pom.xml中添加依赖

xml 复制代码
<!--AMQP依赖,包含RabbitMQ-->
<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-amqp</artifactId>
</dependency>
2.1.1消息发送

首先配置MQ得地址,在application.yml中配置

yaml 复制代码
spring:
  rabbitmq:
    host: 192.168.150.101 # 主机名
    port: 5672 # 端口
    virtual-host: / # 虚拟主机
    username: itcast # 用户名
    password: 123321 # 密码

编写生产者的代码,生产消息

java 复制代码
package cn.itcast.mq.listener;

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

@Component
public class SpringRabbitListener {

    @RabbitListener(queues = "simple.queue")
    public void listenSimpleQueueMessage(String msg) throws InterruptedException {
        System.out.println("spring 消费者接收到消息:【" + msg + "】");
    }
}

编写消费者的代码,消费消息

java 复制代码
public class SpringRabbitListener {

    @RabbitListener(queues = "simple.queue")
    public void listenSimpleQueueMessage(String msg) throws InterruptedException {
        System.out.println("spring 消费者接收到消息:【" + msg + "】");
    }
}
2.2 工作队列

简单来说就是让多个消费者绑定到一个队列,共同消费队列中的消息

当消息处理比较耗时的时候,可能生产消息的速度会远远大于消息的消费速度。长此以往,消息就会堆积越来越多,无法及时处理。

此时就可以使用work 模型,多个消费者共同处理消息处理,速度就能大大提高了。

与简单队列类似,只不过多了个消费者绑定到队列上。代码省略。

2.3 Fanout(广播队列)

生产者产生消息发送给交换机,交换机决定把消息发送给哪个队列。

广播模式下,交换机会发送给所有绑定它的队列,此处注意,每一条消息都会发给所有绑定了该交换机的队列,即一条消息会被发给多个队列

java 复制代码
import org.springframework.amqp.core.Binding;
import org.springframework.amqp.core.BindingBuilder;
import org.springframework.amqp.core.FanoutExchange;
import org.springframework.amqp.core.Queue;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

@Configuration
public class FanoutConfig {
    /**
     * 声明交换机
     * @return Fanout类型交换机
     */
    @Bean
    public FanoutExchange fanoutExchange(){
        return new FanoutExchange("it.fanout");
    }

    /**
     * 第1个队列
     */
    @Bean
    public Queue fanoutQueue1(){
        return new Queue("fanout.queue1");
    }

    /**
     * 绑定队列和交换机
     */
    @Bean
    public Binding bindingQueue1(Queue fanoutQueue1, FanoutExchange fanoutExchange){
        return BindingBuilder.bind(fanoutQueue1).to(fanoutExchange);
    }

    /**
     * 第2个队列
     */
    @Bean
    public Queue fanoutQueue2(){
        return new Queue("fanout.queue2");
    }

    /**
     * 绑定队列和交换机
     */
    @Bean
    public Binding bindingQueue2(Queue fanoutQueue2, FanoutExchange fanoutExchange){
        return BindingBuilder.bind(fanoutQueue2).to(fanoutExchange);
    }
}

消息生产和消费与之前一致。

路由与广播的区别是,交换机不是无脑发送信息给队列,而是需要对 '暗号' 只有暗号对了队列才会接收到消息。

主题与路由的区别是,主题是支持通配符,而路由是一个写死的密码。

相关推荐
彭于晏Yan1 天前
Redisson分布式锁
spring boot·redis·分布式
美好的事情能不能发生在我身上1 天前
Jmeter压测遇到的问题
java·分布式·jmeter
石逸凡1 天前
谈AI原生:本质、单体、群、分布式、数据库与计算机架构
数据库·分布式·ai-native
白露与泡影1 天前
Spring Cloud进阶--分布式权限校验OAuth2
分布式·spring cloud·wpf
风吹落叶32571 天前
redis 部署方式(分布式)
数据库·redis·分布式
qq_40999093?1 天前
消息中间件:RabbitMQ、RocketMQ、Kafka快速上手
kafka·rabbitmq·rocketmq
ghie90901 天前
基于智能算法的微网分布式电源最优调度实现配电网稳定运行
分布式
枫叶丹41 天前
【HarmonyOS 6.0】ArkData 分布式数据对象新特性:资产传输进度监听与接续传输能力深度解析
开发语言·分布式·华为·wpf·harmonyos
绿算技术2 天前
OpenClaw × GP Spark:本地智能与极速存储的终极融合
大数据·分布式·spark
孤影过客2 天前
驯服数据巨兽:Hadoop如何重塑大数据的黄金时代
大数据·hadoop·分布式