新建springboot项目测试rocketmq发消息

新建项目MyTestRocket

image

 

pom文件添加

 <!--mq-->
        <!-- RocketMQ Starter -->
        <dependency>
            <groupId>org.apache.rocketmq</groupId>
            <artifactId>rocketmq-spring-boot-starter</artifactId>
            <version>2.3.0</version>
        </dependency>

在config包中创建配置类 RocketMQConfig 

package com.example.mytestrocket.config;
import org.apache.rocketmq.client.producer.DefaultMQProducer;
import org.apache.rocketmq.client.producer.TransactionMQProducer;
import org.apache.rocketmq.spring.core.RocketMQTemplate;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

/**
 * @author*/
@Configuration
public class RocketMQConfig {

    @Value("${rocketmq.name-server}")
    private String nameServer;

    @Value("${rocketmq.producer.group}")
    private String producerGroup;

    @Value("${rocketmq.consumer.group}")
    private String consumerGroup;


    @Bean
    public DefaultMQProducer defaultMQProducer() {
        System.out.println("nameServer==="+nameServer);
        System.out.println("producerGroup==="+producerGroup);
        System.out.println("consumerGroup==="+consumerGroup);
        DefaultMQProducer producer = new DefaultMQProducer(producerGroup);
        producer.setNamesrvAddr(nameServer);
        // 可以根据需要设置其他参数,如超时时间、重试次数等
        // producer.setSendMsgTimeout(3000);
        // producer.setRetryTimesWhenSendFailed(2);
        return producer;
    }

    @Bean
    public RocketMQTemplate rocketMQTemplate(DefaultMQProducer producer) {
        RocketMQTemplate rocketMQTemplate = new RocketMQTemplate();
        rocketMQTemplate.setProducer(producer);
        return rocketMQTemplate;
    }

    /**
     * 事务消息生产者
     * @return
     */
    @Bean
    public TransactionMQProducer producer() {
        TransactionMQProducer producer = new TransactionMQProducer();
        producer.setProducerGroup(producerGroup);
        producer.setNamesrvAddr(nameServer);
        return producer;
    }



}

 

yaml文件配置信息

spring:
  application:
    name: MyTestRocket
server:
  port: 8088
  servlet:
    context-path: /rocketMq
# RocketMQ??
rocketmq:
  name-server: 127.0.0.1:9876
  #生产者分组
  producer:
    group: producer-group
  #消费者分组
  consumer:
    group: consumer-group

控制层代码

SendMsgController
package com.example.mytestrocket.controller;
import com.example.mytestrocket.producer.SimpleProducer;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;

/**
 * @author*/
@RestController
@RequestMapping("/sendMsg")
public class SendMsgController {
    @Autowired
    private SimpleProducer simpleProducer;
    @GetMapping("/sendSimpleMsg")
    public String sendSimpleMsg(){
        String msg = LocalDateTime.now().format(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss"))+"发送个简单消息";
        //发送异步消息
        simpleProducer.sendMessage("test-topic",msg);
        //发送同步消息
        simpleProducer.sendSyncMessage("test-topic","同步消息"+msg);
        return "发送成功";
    }
}

生产者

SimpleProducer
package com.example.mytestrocket.producer;
import com.alibaba.fastjson.JSON;
import com.example.mytestrocket.producer.vo.Order;
import com.example.mytestrocket.producer.vo.UserAddMoneyDTO;
import com.example.mytestrocket.vo.MyMessage;
import org.apache.rocketmq.client.producer.SendResult;
import org.apache.rocketmq.client.producer.TransactionMQProducer;
import org.apache.rocketmq.spring.core.RocketMQTemplate;
import org.apache.rocketmq.spring.support.RocketMQHeaders;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.messaging.support.MessageBuilder;
import org.springframework.stereotype.Component;

import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
import java.util.UUID;

/**
 * @author 50649
 */
@Component
public class SimpleProducer {

    @Autowired
    private RocketMQTemplate rocketMQTemplate;


    /**
     * 发送简单消息
     * @param topic
     * @param message
     */
    public void sendMessage(String topic, String message) {
        System.out.println("发送简单消息入参topic==:"+topic);
        for(int i=0;i<6;i++){
            String targetMsg = message+i;
            System.out.println("发送简单消息入参targetMsg==:"+targetMsg);
            rocketMQTemplate.convertAndSend(topic, targetMsg);

        }

    }

    /**
     * 发送同步消息
     * @param topic
     * @param message
     */
    public void sendSyncMessage(String topic, String message) {
        System.out.println("同步消息发送简单消息入参topic==:"+topic);
        for(int i=0;i<1;i++){
            message = message+i;
            System.out.println("同步消息发送简单消息入参message==:"+message);
            SendResult result = rocketMQTemplate.syncSend(topic, message);
            System.out.println("result=="+result);
        }

    }

    /**
     * 发送对象消息
     * @param topic
     * @param user
     */
    public void sendObjectMessage(String topic, MyMessage user) {
        System.out.println("发送对象消息topic==="+topic);
        System.out.println("发送对象消息user==="+user);
        rocketMQTemplate.convertAndSend(topic,JSON.toJSONString(user));
    }

    /**
     * 发送带tag消息
     * @param topic
     * @param tag
     * @param message
     */
    public void sendMessageWithTag(String topic, String tag, String message) {
        System.out.println("发送带tag消息topic=="+topic);
        System.out.println("发送带tag消息tag=="+tag);
        System.out.println("发送带tag消息message=="+message);
        rocketMQTemplate.convertAndSend(topic + ":" + tag, message);
    }

    /**
     * 发送延迟消息
     * @param topic
     * @param message
     */
    public void sendDelayMessage(String topic,String message){
        System.out.println("发送延迟消息topic=="+topic);
        System.out.println("发送延迟消息message=="+message);
        // 构建消息
        org.springframework.messaging.Message<String> messageInfo = MessageBuilder.withPayload(message)
                .build();
        //发送延迟消息(5分钟对应延迟级别9)
        // 参数含义:topic, message, 发送超时时间(毫秒), 延迟级别
        // 设置超时时间为3000毫秒:cite[8]
        SendResult sendResult = rocketMQTemplate.syncSend(topic, messageInfo, 3000, 9);

        System.out.println("延迟消息发送成功,消息ID: " + sendResult.getMsgId());
    }

    /**
     * 发送同步顺序消息
     * @param topic
     * @param message
     * @param hashKey 一般指订单id或者产品id
     */

    public void sendSyncOrderlyMessage(String topic,String message,String hashKey){
        System.out.println("发送同步顺序消息topic=="+topic+"message=="+message+"hashKey=="+hashKey);
        for(int i=0;i<5;i++){
            String targetMsg = message+i;
            String targetHashKey = hashKey+i;
            rocketMQTemplate.syncSendOrderly(topic,targetMsg,targetHashKey);
        }

    }

    /**
     * 发送事务消息
     */
    public void sendMessageInTransaction(String topic) {
        //实际订单数据根据自己业务需求获取
        Order order = new Order();
        order.setAmount("100");
        order.setAccountCode("code2025");
        String message = LocalDateTime.now().format(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss")) + "测试事务消息";
        order.setMessage(message);
        order.setId(UUID.randomUUID().toString());
        //业务逻辑
        String transactionId = UUID.randomUUID().toString();
        rocketMQTemplate.sendMessageInTransaction(
                // 目标Topic
                topic,
                MessageBuilder.withPayload(
                                // 消息体
                                JSON.toJSONString(UserAddMoneyDTO.builder()
                                        .userCode(order.getAccountCode())
                                        .amount(order.getAmount())
                                        .message(order.getMessage())
                                        .build())

                        )
                        // 通常设置事务ID
                        .setHeader(RocketMQHeaders.TRANSACTION_ID, transactionId)
                        // 其他自定义头信息
                        .setHeader("order_id", order.getId())
                        .build(),
                // 可选参数,会传递给事务监听器
                order
        );
    }
}

实体类

package com.example.mytestrocket.producer.vo;

import lombok.Data;

/**
 * @author*/
@Data
public class Order {
    private String id;

    private String accountCode;

    private String amount;

    private String message;
}
package com.example.mytestrocket.producer.vo;

import lombok.Builder;
import lombok.Data;

/**
 * @author*/
@Data
@Builder
public class UserAddMoneyDTO {
    private String userCode;
    private String amount;
    private String message;

}

 

 

 

 

消费者

SimpleConsumer 
package com.example.mytestrocket.service.consumer;
import org.apache.rocketmq.spring.annotation.RocketMQMessageListener;
import org.apache.rocketmq.spring.core.RocketMQListener;
import org.springframework.stereotype.Component;

/**
 * @author 
 * 消费简单消息
 */

@Component
@RocketMQMessageListener(topic = "test-topic", consumerGroup = "${rocketmq.consumer.group}")
public class SimpleConsumer implements RocketMQListener<String> {
    @Override
    public void onMessage(String message) {
        System.out.println("消费消息开始>>>>>>>>>>>>>>");
        System.out.println("消费简单消息Received message: " + message);
    }
}
TagConsumer (使用@Component注解或者@Service注解都可以,主要是是让容器管理)
package com.example.mytestrocket.service.consumer;

import org.apache.rocketmq.spring.annotation.RocketMQMessageListener;
import org.apache.rocketmq.spring.core.RocketMQListener;
import org.springframework.stereotype.Service;

/**
 * 消费tag消息
 * @author*/
@Service
@RocketMQMessageListener(topic = "tag-topic", selectorExpression = "tagA", consumerGroup = "tag-consumer-group")
public class TagConsumer implements RocketMQListener<String> {

    @Override
    public void onMessage(String message) {
        System.out.println("Received tag message: " + message);
    }
}
UserConsumer (使用@Component注解或者@Service注解都可以,主要是是让容器管理)
**
* @author
* 消费对象消息
*/
@Service
@RocketMQMessageListener(topic = "user-topic", consumerGroup = "user-consumer-group")
public class UserConsumer implements RocketMQListener<String> {

@Override
public void onMessage(String user) {
System.out.println("消费对象消息Received user: " + user);
}
}

 

DelayConsumer
package com.example.mytestrocket.service.consumer;
import org.apache.rocketmq.spring.annotation.RocketMQMessageListener;
import org.apache.rocketmq.spring.core.RocketMQListener;
import org.springframework.stereotype.Service;

import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;

/**
 * @author 
 * 延迟消费消息
 */
@Service
@RocketMQMessageListener(topic = "delay-topic", consumerGroup = "delay-consumer-group")
public class DelayConsumer implements RocketMQListener<String> {
    @Override
    public void onMessage(String message) {
        String time = LocalDateTime.now().format(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss"));
        System.out.println("延迟消费消息开始time=="+time);
        System.out.println("延迟消费消息Received message: " + message);
    }
}

消费顺序消息

package com.example.mytestrocket.service.consumer;
import org.apache.rocketmq.spring.annotation.ConsumeMode;
import org.apache.rocketmq.spring.annotation.RocketMQMessageListener;
import org.apache.rocketmq.spring.core.RocketMQListener;
import org.springframework.stereotype.Service;
/**
 * @author 
 * 消费顺序消息
 */
@Service
@RocketMQMessageListener(topic = "orderly-topic", consumerGroup = "orderly-consumer-group",consumeMode = ConsumeMode.ORDERLY)
public class SyncOrderlyConsumer implements RocketMQListener<String> {
    @Override
    public void onMessage(String user) {
        System.out.println("消费顺序消息 Received user: " + user);
    }
}

事务消息==

事务消息监听器

package com.example.mytestrocket.service.consumer.listener;

import com.alibaba.fastjson.JSON;
import com.example.mytestrocket.producer.vo.Order;
import org.apache.rocketmq.spring.annotation.RocketMQTransactionListener;
import org.apache.rocketmq.spring.core.RocketMQLocalTransactionListener;
import org.apache.rocketmq.spring.core.RocketMQLocalTransactionState;
import org.apache.rocketmq.spring.support.RocketMQHeaders;
import org.springframework.messaging.Message;
import org.springframework.messaging.MessageHeaders;
import org.springframework.stereotype.Component;

/**
 * @author 
 * 
 */
@Component
@RocketMQTransactionListener
public class MyTransactionListener implements RocketMQLocalTransactionListener {
    /**
     * 执行本地事务
     * @param msg
     * @param arg
     * @return
     */
    @Override
    public RocketMQLocalTransactionState executeLocalTransaction(Message msg, Object arg) {
        // 从消息头或arg参数中获取事务ID和业务数据
        MessageHeaders headers = msg.getHeaders();
        String transactionId = (String) headers.get(RocketMQHeaders.TRANSACTION_ID);
        // 通常arg对象是发送消息时传入的业务参数:cite[3]:cite[4]
        Order order = (Order) arg;
        System.out.println("执行本地事务transactionId=="+transactionId);
        System.out.println("执行本地事务msg=="+ JSON.toJSONString(msg));
        System.out.println("执行本地事务order=="+order);
        try {
            // 1. 执行本地事务操作,例如删除订单、更新库存等
            // orderService.updateStatus(order.getId(), Status.INVALID);
            // 2. 如果本地事务成功,返回COMMIT
            return RocketMQLocalTransactionState.COMMIT;
        } catch (Exception e) {
            // 3. 如果本地事务失败,返回ROLLBACK
            return RocketMQLocalTransactionState.ROLLBACK;
            // 4. 如果事务状态暂时未知(如依赖第三方调用),可先返回UNKNOWN:cite[6]:cite[9]
            // return RocketMQLocalTransactionState.UNKNOWN;
        }
    }

    /**
     * 检查本地事务状态
     * @param msg
     * @return
     */
    @Override
    public RocketMQLocalTransactionState checkLocalTransaction(Message msg) {
        MessageHeaders headers = msg.getHeaders();
        String transactionId = (String) headers.get(RocketMQHeaders.TRANSACTION_ID);
        System.out.println("检查本地事务状态transactionId=="+transactionId);
        // 根据transactionId或消息内容去检查本地事务的真实执行结果:cite[3]:cite[6]
        // 例如:Order order = orderMapper.selectByTransactionId(transactionId);
        // if (order != null && order.getStatus().equals(Status.INVALID)) {
        //    return RocketMQLocalTransactionState.COMMIT;
        // } else {
        //    return RocketMQLocalTransactionState.ROLLBACK;
        // }

        // 示例:简单返回COMMIT
        return RocketMQLocalTransactionState.COMMIT;
    }

}

事务消息消费者

package com.example.mytestrocket.service.consumer;
import org.apache.rocketmq.spring.annotation.RocketMQMessageListener;
import org.apache.rocketmq.spring.core.RocketMQListener;
import org.springframework.stereotype.Component;

/**
 * @author 
 * 示例:消费事务消息
 */
@Component
@RocketMQMessageListener(topic = "transaction-topic", consumerGroup = "transaction-consumer-group")
public class YourTransactionMessageConsumer implements RocketMQListener<String> {

    @Override
    public void onMessage(String message) {
        // 1. 处理消息,例如为用户增加金额
        try {
            //userService.addMoney(userAddMoneyDTO.getUserCode(), userAddMoneyDTO.getAmount());
            System.out.println("消费事务消息message=="+ message);
            // 2. 消费成功(默认自动ACK)
        } catch (Exception e) {
            // 3. 处理异常,根据业务决定是否重试:cite[6]
            // 如果抛出异常,消息会根据重试策略重新投递
            throw new RuntimeException("Consumption failed, requeue the message", e);
        }
    }
}

 

posted @ 2025-09-02 11:12  红尘沙漏  阅读(17)  评论(0)    收藏  举报