rabbitmq单向ssl认证配置与最佳实践(适用于各大云厂商)

背景

这里后补直接上代码

最佳实践

主要从两个方面保证消息不丢失

RabbitMQ方面

  1. 创建队列时开启持久化
  2. 创建交换器时开启持久化
  3. 创建镜像队列(可选)
  4. 开启延迟队列(可选)

代码层面

  1. 开启生产者到交换器回调参数
  2. 开启交换器到队列回调参数
  3. 开启消费者手动ack
  4. 注意消费端打印日志,考虑手动补偿(可选)

实现代码

RabbitMQ配置文件

java 复制代码
package com.jndj.core.config;

import com.rabbitmq.client.ConnectionFactory;
import org.springframework.amqp.core.AcknowledgeMode;
import org.springframework.amqp.core.Message;
import org.springframework.amqp.rabbit.config.SimpleRabbitListenerContainerFactory;
import org.springframework.amqp.rabbit.connection.CachingConnectionFactory;
import org.springframework.amqp.rabbit.connection.CorrelationData;
import org.springframework.amqp.rabbit.core.RabbitTemplate;
import org.springframework.amqp.support.converter.Jackson2JsonMessageConverter;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

import java.security.KeyManagementException;
import java.security.NoSuchAlgorithmException;


@Configuration
@EnableAutoConfiguration
public class RabbitMQAutoConfiguration {

    @Value("${spring.rabbitmq.host}")
    public String rmHost;

    @Value("${spring.rabbitmq.port}")
    public int rmPort;

    @Value("${spring.rabbitmq.username}")
    public String rmUsername;

    @Value("${spring.rabbitmq.password}")
    public String rmPassword;

    @Value("${spring.rabbitmq.virtual-host}")
    public String virtualHost;

    @Bean
    public CachingConnectionFactory connectionFactory() throws NoSuchAlgorithmException, KeyManagementException {
        ConnectionFactory rabbitConnectionFactory = new ConnectionFactory();
        rabbitConnectionFactory.setHost(rmHost);
        rabbitConnectionFactory.setPort(rmPort);
        rabbitConnectionFactory.setUsername(rmUsername);
        rabbitConnectionFactory.setPassword(rmPassword);
        rabbitConnectionFactory.setVirtualHost(virtualHost);
        rabbitConnectionFactory.useSslProtocol();
        CachingConnectionFactory cachingConnectionFactory = new CachingConnectionFactory(rabbitConnectionFactory);
        cachingConnectionFactory.setPublisherReturns(true);
        cachingConnectionFactory.setPublisherConfirms(true);
        return cachingConnectionFactory;
    }

    @Bean
    public RabbitTemplate rabbitTemplate(CachingConnectionFactory connectionFactory) {
        RabbitTemplate rabbitTemplate = new RabbitTemplate();
        rabbitTemplate.setConnectionFactory(connectionFactory);
        rabbitTemplate.setMandatory(true);
        rabbitTemplate.setConfirmCallback(new RabbitTemplate.ConfirmCallback() {
            @Override
            public void confirm(CorrelationData correlationData, boolean ack, String cause) {
                System.out.println("ConfirmCallback:     " + "相关数据:" + correlationData);
                System.out.println("ConfirmCallback:     " + "确认情况:" + ack);
                System.out.println("ConfirmCallback:     " + "原因:" + cause);
            }
        });
        rabbitTemplate.setReturnCallback(new RabbitTemplate.ReturnCallback() {
            @Override
            public void returnedMessage(Message message, int replyCode, String replyText, String exchange, String routingKey) {
                System.out.println("ReturnCallback:     " + "消息:" + message);
                System.out.println("ReturnCallback:     " + "回应码:" + replyCode);
                System.out.println("ReturnCallback:     " + "回应信息:" + replyText);
                System.out.println("ReturnCallback:     " + "交换机:" + exchange);
                System.out.println("ReturnCallback:     " + "路由键:" + routingKey);
            }
        });
        rabbitTemplate.setMessageConverter(new Jackson2JsonMessageConverter());
        return rabbitTemplate;
    }

    @Bean
    public SimpleRabbitListenerContainerFactory rabbitListenerContainerFactory(CachingConnectionFactory connectionFactory) {
        SimpleRabbitListenerContainerFactory factory = new SimpleRabbitListenerContainerFactory();
        factory.setConnectionFactory(connectionFactory);
        factory.setAcknowledgeMode(AcknowledgeMode.MANUAL);
        return factory;
    }

}

生产者

java 复制代码
    public AjaxResult insertStuResults(@RequestBody MyoResults model) {
        try {
            rabbitTemplate.convertAndSend(RabbitMQConstant.EX_STU_RESULTS_MANUAL, RabbitMQConstant.Q_STU_RESULTS_MANUAL, model);
            return AjaxResult.success("上送成功");
        } catch (Exception e) {
            return AjaxResult.error(e.getMessage());
        }
    }

消费者

java 复制代码
    @RabbitListener(queues = RabbitMQConstant.Q_STU_RESULTS_MANUAL)
    @RabbitHandler
    public void getManualMsg(Message message, Channel channel) throws IOException {
        String jsonString = new String(message.getBody(), StandardCharsets.UTF_8);
        ObjectMapper objectMapper = new ObjectMapper();
        MyoResults model = objectMapper.readValue(jsonString, MyoResults.class);
        iStuResultsService.insertMongodb(model);
        channel.basicAck(message.getMessageProperties().getDeliveryTag(), false);
    }
相关推荐
Geek-Chow14 小时前
ALB SSL policy conflict (AWS Load Balancer Controller)
网络协议·ssl·aws
过期动态17 小时前
【LeetCode 热题 100】找到字符串中所有字母异位词
java·数据结构·算法·leetcode·职场和发展·rabbitmq
GlobalSign数字证书1 天前
自动化时代,如何高效部署SSL证书?
运维·自动化·ssl
YDS8293 天前
大营销平台 —— 活动SKU库存扣减业务及其一致性处理
java·spring boot·redis·rabbitmq·ddd
霸道流氓气质3 天前
Kiro 中配置 RabbitMQ MCP Server 指南
分布式·rabbitmq·ruby
quweiie3 天前
tp8使用rabbitMQ消息队列的示例
消息队列·rabbitmq·thinkphp消息队列
六点_dn3 天前
RabbitMQ学习笔记-定义与作用
笔记·学习·rabbitmq
山顶夕景4 天前
【MAE】音频自监督训练Masked Autoencoders that Listen
音视频·ssl·多模态·自监督·mae
froyoisle5 天前
阿里云免费 SSL 证书申请及配置
服务器·阿里云·ssl·网站
VX_186 天前
域名SSL证书监测平台
网络·网络协议·ssl