Spring Boot RabbitMq 并发与限流

概述


电商中秒杀请求,属于瞬间大流量,同一时刻会有大量的请求涌入到系统中,可能导致系统挂掉。应付这种瞬间大流量的其中一种方式,便是利用消息队列

1、利用消息队列先进先出的特性,将请求进行削峰;
2、控制好消费端的消费速度,进行必要的限流。

在消费端,要做到上面提到的第2点,在Spring Boot RabbitMQ中只需要利用@RabbitListener注解,做一些简单配置就可以了。


一个listener对应多个consumer


默认情况一下,一个listener对应一个consumer,如果想对应多个,有两种方式。

方式一:直接在application.yml文件中配置

spring:
  rabbitmq:
    listener:
      simple:
        concurrency: 5
        max-concurrency: 10

这个是个全局配置,应用里的任何队列对应的listener都至少有5个consumer,但是千万别这么做,因为一般情况下,一个listener对应一个consumer是够用的。只是针对部分场景,才需要一对多。

 

方式二:直接在@RabbitListener上配置

@Component
public class SpringBootMsqConsumer {
    @RabbitListener(queues = "spring-boot-direct-queue",concurrency = "5-10")
    public void receive(Message message) {
        System.out.println("receive message:" + new String(message.getBody()));
    }
}

利用@RabbitListener中的concurrency属性进行指定就行。例如上面的

concurrency = “5-10”

就表示最小5个,最大10个consumer。启动消费端应用后,找到spring-boot-direct-queue这个队列的consumer,会发现有5个。

Spring Boot RabbitMq 并发与限流_第1张图片

这5个消费者都可以从spring-boot-direct-queue这个队列中获取消息,加快队列中消息的消费速度,提高吞吐量。


限流


我们经过压测,来判断consumer的消费能力,如果单位时间内,consumer到达的消息太多,也可能把消费者压垮。
得到压测数据后,可以在@RabbitListener中配置prefetch count

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

@Component
public class SpringBootMsqConsumer {
    @RabbitListener(queues = "spring-boot-direct-queue",concurrency = "5-10",containerFactory = "mqConsumerlistenerContainer")
    public void receive(Message message) {
        System.out.println("receive message:" + new String(message.getBody()));
    }
}

只需要在@RabbitListener中,用containerFactory指定一个监听器工厂类就行。这里用的是:

containerFactory = “mqConsumerlistenerContainer”

定义监听器工厂类很简单。

import org.springframework.amqp.rabbit.config.SimpleRabbitListenerContainerFactory;
import org.springframework.amqp.rabbit.connection.CachingConnectionFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

@Configuration
public class RabbitMqConfig {

    @Autowired
    private CachingConnectionFactory connectionFactory;

    @Bean(name = "mqConsumerlistenerContainer")
    public SimpleRabbitListenerContainerFactory mqConsumerlistenerContainer(){
        SimpleRabbitListenerContainerFactory factory = new SimpleRabbitListenerContainerFactory();
        factory.setConnectionFactory(connectionFactory);
        factory.setPrefetchCount(50);
        return factory;
    }
}

上面有一句factory.setPrefetchCount(50);,就是用于设置prefetch count的,启动后,会在spring-boot-direct-queue队列的consumer中体现出来。
Spring Boot RabbitMq 并发与限流_第2张图片
配置成功后,consumer单位时间内接收到消息就是50条。


你可能感兴趣的:(#,RabbitMQ)