RocketMQ消费者主动拉取消息示例

RocketMQ消息发送基本示例(推送消费者)-CSDN博客

RocketMQ消费者主动去Broker上拉取消息

第一种    消费者主动拉模式

package com.example.rocketmqdemo.simple;

import org.apache.rocketmq.client.consumer.DefaultMQPullConsumer;
import org.apache.rocketmq.client.consumer.PullResult;
import org.apache.rocketmq.client.consumer.store.ReadOffsetType;
import org.apache.rocketmq.client.exception.MQBrokerException;
import org.apache.rocketmq.client.exception.MQClientException;
import org.apache.rocketmq.common.message.MessageQueue;
import org.apache.rocketmq.remoting.exception.RemotingException;

import java.util.HashSet;
import java.util.Set;

/**
 * 消费者主动去Broker拉取消息
 * @author hrui
 * @date 2024/7/31 23:42
 */
public class PullConsumer {

    public static void main(String[] args) {
        //创建一个DefaultMQPullConsumer实例,指定消费者组名为"PullConsumer"
        DefaultMQPullConsumer consumer = new DefaultMQPullConsumer("PullConsumer");
        //设置NameServer地址,RocketMQ客户端通过NameServer获取Broker的路由信息
        consumer.setNamesrvAddr("xxx.xxx.xxx:9876");
        try {
            // 指定消费者订阅的主题集合
            Set<String> topics = new HashSet<>();
            topics.add("TopicTest");
            topics.add("Topic1");
            consumer.setRegisterTopics(topics);

            //启动消费者实例
            consumer.start();

            //添加关闭钩子,当JVM退出时调用
//            Runtime.getRuntime().addShutdownHook(new Thread(() -> {
//                System.out.println("Shutdown hook executed. Closing consumer.");
//                //优雅地关闭消费者实例,释放资源
//                consumer.shutdown();
//            }));

            //无限循环,持续拉取消息
            while (true) {
                //遍历每个订阅的主题
                consumer.getRegisterTopics().forEach(topic -> {
                    try {
                        //获取订阅主题的消息队列集合
                        Set<MessageQueue> messageQueues = consumer.fetchSubscribeMessageQueues(topic);

                        //遍历每个消息队列
                        messageQueues.forEach(messageQueue -> {
                            try {
                                //获取当前队列的消费偏移量
                                long offset = consumer.getOffsetStore().readOffset(messageQueue, ReadOffsetType.READ_FROM_MEMORY);
                                if (offset < 0) {
                                    offset = consumer.getOffsetStore().readOffset(messageQueue, ReadOffsetType.READ_FROM_STORE);
                                }
                                if (offset < 0) {
                                    offset = consumer.maxOffset(messageQueue);
                                }
                                if (offset < 0) {
                                    offset = 0;
                                }

                                //从Broker中拉取消息
                                PullResult pullResult = consumer.pull(messageQueue, "*", offset, 32);
                                switch (pullResult.getPullStatus()) {
                                    case FOUND:
                                        System.out.println("拉取到消息");
                                        pullResult.getMsgFoundList().forEach(msg -> {
                                            System.out.println(msg);
                                        });
                                        //更新消费偏移量
                                        consumer.updateConsumeOffset(messageQueue, pullResult.getNextBeginOffset());
                                        break;
                                    case NO_NEW_MSG:
                                        System.out.println("没有新消息");
                                        break;
                                    case NO_MATCHED_MSG:
                                        System.out.println("没有匹配的消息");
                                        break;
                                    case OFFSET_ILLEGAL:
                                        System.out.println("偏移量不合法");
                                }
                            } catch (MQClientException | RemotingException | MQBrokerException | InterruptedException e) {
                                e.printStackTrace();
                            }
                        });
                    } catch (MQClientException e) {
                        e.printStackTrace();
                    }
                });
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}

第二种   消费者主动随机获取消息模式(随机获取一个队列(Queue)消息)

package com.example.rocketmqdemo.simple;

import org.apache.rocketmq.client.consumer.DefaultLitePullConsumer;
import org.apache.rocketmq.common.message.MessageExt;

import java.util.List;

/**
 * 拉模式:随机获取一个队列(Queue)消息
 * @author hrui
 * @date 2024/8/1 0:20
 */
public class LitePullConsumer {
    public static void main(String[] args) {
        //创建一个DefaultLitePullConsumer实例,指定消费者组名为"group1"
        DefaultLitePullConsumer consumer = new DefaultLitePullConsumer("group1");
        //设置NameServer地址,RocketMQ客户端通过NameServer获取Broker的路由信息
        consumer.setNamesrvAddr("xxx.xxx.xxx:9876");

        try {
            //订阅指定的主题和标签,这里使用"*"表示订阅所有标签
            consumer.subscribe("Topic1", "*");
            //启动消费者实例
            consumer.start();
            //无限循环,持续拉取消息
            while(true){
                //从Broker拉取消息,poll方法会返回一个包含MessageExt对象的列表
                List<MessageExt> msgs = consumer.poll();
                //遍历拉取到的消息并进行处理
                if(msgs.size()==0){
                    System.out.println("没有消息");
                }else{
                    msgs.forEach(msg -> {//不会遍历size 0的
                        System.out.println("消息消费成功_"+msg);
                    });
                }

            }
        }catch (Exception e){
            e.printStackTrace();
        }
    }
}

拉模式-指定获取一个Queue消息

package com.example.rocketmqdemo.simple;

import org.apache.rocketmq.client.consumer.DefaultLitePullConsumer;
import org.apache.rocketmq.common.message.MessageExt;
import org.apache.rocketmq.common.message.MessageQueue;

import java.util.ArrayList;
import java.util.Collection;
import java.util.List;

/**
 * 拉模式-指定获取一个Queue消息
 * 使用DefaultLitePullConsumer实现拉取模式的消息消费
 * 该消费者会持续从指定的队列拉取消息
 *
 * @date 2024/8/1 0:48
 */
public class LitePullConsumerAssign {
    public static void main(String[] args) {
        //创建一个DefaultLitePullConsumer实例,指定消费者组名为"group1"
        DefaultLitePullConsumer consumer = new DefaultLitePullConsumer("group1");
        //设置NameServer地址,RocketMQ客户端通过NameServer获取Broker的路由信息
        consumer.setNamesrvAddr("xxx.xxx.xxx:9876");

        try {
            //启动消费者
            consumer.start();
            //获取指定主题的消息队列
            Collection<MessageQueue> messageQueues = consumer.fetchMessageQueues("Topic1");
            //将消息队列转换为列表形式
            ArrayList<MessageQueue> messageQueuesList = new ArrayList<>(messageQueues);
            //指定消费者从特定的队列拉取消息
            consumer.assign(messageQueuesList);
            //删除seek以防止重复消费
            consumer.seek(messageQueuesList.get(0), 10);

            while (true) {
                //拉取消息,poll方法会返回一个包含MessageExt对象的列表
                List<MessageExt> messageExtList = consumer.poll();
                //遍历拉取到的消息并进行处理
                messageExtList.forEach(messageExt -> {
                    System.out.println("消息消费成功: " + new String(messageExt.getBody()));
                    //你可以在这里添加自定义的消息处理逻辑,例如解析消息内容、存储到数据库等
                });
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

hrui0706

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值