1、配置文件

1、yml配置文件

rocketmq: #mq配置
producer:
iseffect: true
type: default # (transaction,default) transaction:TransactionMQProducer; default:DefaultMQProducer
groupName: testzjlGroup
topicName: test_topic
namesrvAddr: 192.168.244.128:9876
consumer:
iseffect: true
type: default # (transaction,default) transaction:TransactionMQProducer; default:DefaultMQProducer
groupName: testzjlGroup
topicName: test_topic
namesrvAddr: 192.168.244.128:9876

2、对应的java类

package com.gofun.customer.mq;

import org.springframework.boot.context.properties.ConfigurationProperties;

@ConfigurationProperties(prefix = "rocketmq.producer")
public class RocketMqProducerProperties { private Boolean iseffect;
private String type;
private String groupName;
private String topicName;
private String namesrvAddr; public Boolean getIseffect() {
return iseffect;
} public void setIseffect(Boolean iseffect) {
this.iseffect = iseffect;
} public String getType() {
return type;
} public void setType(String type) {
this.type = type;
} public String getGroupName() {
return groupName;
} public void setGroupName(String groupName) {
this.groupName = groupName;
} public String getTopicName() {
return topicName;
} public void setTopicName(String topicName) {
this.topicName = topicName;
} public String getNamesrvAddr() {
return namesrvAddr;
} public void setNamesrvAddr(String namesrvAddr) {
this.namesrvAddr = namesrvAddr;
}
}

2、DefaultMQProducer生产者

1、生产者配置

package com.gofun.customer.mq;

import org.apache.rocketmq.client.exception.MQClientException;
import org.apache.rocketmq.client.producer.DefaultMQProducer;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
import org.springframework.boot.context.properties.EnableConfigurationProperties;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration; @Configuration
@EnableConfigurationProperties(RocketMqProducerProperties.class)
@ConditionalOnProperty(prefix = "rocketmq.producer", name = "iseffect", havingValue = "true")
public class RocketMqConfig {
@Autowired
private RocketMqProducerProperties rocketMqProperties; @Bean
@ConditionalOnProperty(prefix = "rocketmq.producer", name = "type", havingValue = "default")
public DefaultMQProducer defaultMQProducer() throws MQClientException {
DefaultMQProducer defaultMQProducer = new DefaultMQProducer(rocketMqProperties.getGroupName());
defaultMQProducer.setNamesrvAddr(rocketMqProperties.getNamesrvAddr());
defaultMQProducer.setVipChannelEnabled(false);
defaultMQProducer.setRetryTimesWhenSendAsyncFailed(10);
defaultMQProducer.start();
return defaultMQProducer;
} }
  1. 启动应用创建生产者
  2. 使用配置文件为RocketMqProducerProperties类
  3. 配置文件iseffect = true时生效该配置
  4. 配置文件 type=default 时生效 DefaultMQProducer 生产者

2、生产者工具类

package com.gofun.customer.mq;

import com.alibaba.fastjson.JSON;
import org.apache.rocketmq.client.producer.DefaultMQProducer;
import org.apache.rocketmq.client.producer.SendResult;
import org.apache.rocketmq.common.message.Message;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component; @Component
public class RocketMqProducer {
@Autowired
private DefaultMQProducer defaultMQProducer;
@Autowired
private RocketMqProducerProperties rocketMqProperties; public SendResult send(String topic, String tag, Object obj) {
String body = null;
if(obj == null){
return null;
}
if(obj instanceof String){
body = (String) obj;
}else{
body = JSON.toJSONString(obj);
}
Message msg = new Message(topic, tag, body.getBytes());
SendResult sendResult = null;
try {
sendResult = defaultMQProducer.send(msg);
} catch (Exception e) {
}
return sendResult;
} /**
* 延时消息
* @param topic
* @param tag
* @param obj
* @param delayTimeLevel 1s 5s 10s 30s 1m 2m 3m 4m 5m 6m 7m 8m 9m 10m 20m 30m 1h 2h
* 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18
* @return
*/
public SendResult send(String topic, String tag, Object obj,int delayTimeLevel) {
String body = null;
if(obj == null){
return null;
}
if(obj instanceof String){
body = (String) obj;
}else{
body = JSON.toJSONString(obj);
}
Message msg = new Message(topic, tag, body.getBytes());
msg.setDelayTimeLevel(delayTimeLevel);
SendResult sendResult = null;
try {
sendResult = defaultMQProducer.send(msg);
} catch (Exception e) {
}
return sendResult;
} public SendResult send(String tag, Object obj) {
return send(rocketMqProperties.getTopicName(), tag, obj);
} }

3、生产者发送消息

1、引入工具类调用 发送方法

@Autowired
private RocketMqProducer rocketMqProducer;
rocketMqProducer.send("testTag","测试mq发送消息。。。。");

4、问题

注意:
  1. mq设置autoCreateTopicEnable=false时需要手动创建topic
  2. 启动后后台一直报打印日志如:closeChannel: close the connection to remote address[] result: true  说明namesrvAddr 的ip 或 端口号配置错误
  3. 启动后后台一直报打印日志如:closeChannel: close the connection to remote address[192.168.244.128:9876] result: true  可能是jar包错误
  4. 要引入fastjson的jar包

3、消费者

1、DefaultMQPullConsumer 消费者

private static final Map<MessageQueue,Long> OFFSE_TABLE = new HashMap<MessageQueue,Long>();

    public void testDefaultMQPullConsumer() throws MQClientException {
DefaultMQPullConsumer consumer = new DefaultMQPullConsumer(rocketMqConsumerProperties.getGroupName());
consumer.setNamesrvAddr("192.168.244.128:9876;192.168.244.130:9876");
consumer.start();
// 从指定topic中拉取所有消息队列
Set<MessageQueue> mqs = consumer.fetchSubscribeMessageQueues("order-topic");
for(MessageQueue mq:mqs){
try {
// 获取消息的offset,指定从store中获取
long offset = consumer.fetchConsumeOffset(mq,true);
System.out.println("consumer from the queue:"+mq+":"+offset);
while(true){
PullResult pullResult = consumer.pullBlockIfNotFound(mq, null, getMessageQueueOffset(mq), 32);
putMessageQueueOffset(mq,pullResult.getNextBeginOffset());
switch(pullResult.getPullStatus()){
case FOUND:
List<MessageExt> messageExtList = pullResult.getMsgFoundList();
for (MessageExt m : messageExtList) {
System.out.println(new String(m.getBody()));
}
break;
case NO_MATCHED_MSG:
break;
case NO_NEW_MSG:
break;
case OFFSET_ILLEGAL:
break;
}
}
} catch (Exception e) {
e.printStackTrace();
}
}
consumer.shutdown();
} // 保存上次消费的消息下标
private static void putMessageQueueOffset(MessageQueue mq, long nextBeginOffset) {
OFFSE_TABLE.put(mq, nextBeginOffset);
} // 获取上次消费的消息的下标
private static Long getMessageQueueOffset(MessageQueue mq) {
Long offset = OFFSE_TABLE.get(mq);
if(offset != null){
return offset;
}
return 0l;
}

2、DefaultMQPushConsumer 消费者模板方法

RocketMqConsumerProperties 配置类 参见 消费者配置类。

package com.gofun.customer.mq;

import org.apache.rocketmq.client.consumer.DefaultMQPushConsumer;
import org.apache.rocketmq.client.consumer.listener.ConsumeConcurrentlyContext;
import org.apache.rocketmq.client.consumer.listener.ConsumeConcurrentlyStatus;
import org.apache.rocketmq.client.consumer.listener.MessageListenerConcurrently;
import org.apache.rocketmq.client.exception.MQClientException;
import org.apache.rocketmq.common.message.MessageExt;
import org.springframework.beans.factory.annotation.Autowired; import java.util.List; public abstract class RocketMqDefaultConsumer {
@Autowired
private RocketMqConsumerProperties rocketMqConsumerProperties; public void listener(String topic, String tag) throws MQClientException {
DefaultMQPushConsumer consumer = new DefaultMQPushConsumer(rocketMqConsumerProperties.getGroupName());
consumer.setNamesrvAddr(rocketMqConsumerProperties.getNamesrvAddr());
consumer.subscribe(topic, tag);
// 开启内部类实现监听
// consumer.registerMessageListener((MessageListenerConcurrently) (list, consumeConcurrentlyContext) -> RocketMqDefaultConsumer.this.dealBody(list));
consumer.registerMessageListener(new MessageListenerConcurrently() {
@Override
public ConsumeConcurrentlyStatus consumeMessage(List<MessageExt> list, ConsumeConcurrentlyContext consumeConcurrentlyContext) {
return RocketMqDefaultConsumer.this.dealBody(list);
}
});
consumer.start();
} // 处理body的业务
public abstract ConsumeConcurrentlyStatus dealBody(List<MessageExt> msgs);
}
  1. 消费者需要继承此抽象类
  2. 传入topic 和 tag,添加监听, 开启消费者
  3. 定义抽象函数处理消息,实现类需要自已实现处理函数内容

3、DefaultMQPushConsumer 消费者实现

package com.gofun.customer.controller.test;

import com.gofun.customer.mq.RocketMqDefaultConsumer;
import org.apache.rocketmq.client.consumer.listener.ConsumeConcurrentlyStatus;
import org.apache.rocketmq.common.message.MessageExt;
import org.springframework.beans.factory.InitializingBean;
import org.springframework.stereotype.Component;
import org.springframework.util.CollectionUtils; import java.util.List; @Component
public class TestConsumer extends RocketMqDefaultConsumer implements InitializingBean {
private final String testtopic = "test_topic";
private final String testflag = "testTag"; @Override
public void afterPropertiesSet() throws Exception {
super.listener(testtopic, testflag);
} @Override
public ConsumeConcurrentlyStatus dealBody(List<MessageExt> msgs) {
if (!CollectionUtils.isEmpty(msgs)) {
for (MessageExt msg : msgs) {
byte[] body = msg.getBody();
String s = new String(body);
System.out.println("这是rocketmq消费者消费的消息:"+s);
}
}
return ConsumeConcurrentlyStatus.CONSUME_SUCCESS;
} }
  1. 继承模板类定义自己的topic和tag
  2. 实现处理消息的方法
  3. 实现接口InitializingBean ,加载完成自动调用 afterPropertiesSet方法,父类模板添加监听

3、消费模式

在RocketMQ中,可以理解为没有ActiveMQ的createQueue()和createTopic()的用法,也就是并没有P2P和Pub/Sub类似的概念。RocketMQ不遵循JMS规范,而是使用了一套自定义的机制。可以理解为RocketMQ都是基于Pub/Sub发布订阅模式的,

在此基础上提供了集群消息和广播消息两种消息模式,可通过消费端方法consumer.setMessageModel()进行设置。

集群消息——MessageModel.CLUSTERING

这方方式可以实现类似ActiveMQ负载均衡客户端的功能,同一个ConsumerGroup下的所有Consumer已负载均衡的方式消费消息。比较特殊的是,这种方式可以支持生产端先发送消息到Broker,消费端再订阅主题进行消费,比较灵活。RocketMQ默认为该模式。

广播消息——MessageModel.BROADCASTING

在这种模式下,生产端发送到Topic下的消息,会被订阅了该Topic的所有Consumer消费,即使它们处于同一个ConsumerGroup。

原文链接:https://blog.csdn.net/weixin_34452850/article/details/82754419

3、顺序消息

SendResult sendResult = producer.send(msg, new MessageQueueSelector() {
@Override
public MessageQueue select(List<MessageQueue> mqs, Message msg, Object arg) {
Integer id = (Integer) arg;
int index = id % mqs.size();
return mqs.get(index);
}
}, orderId);

参考https://www.jianshu.com/p/5260a2739d80

springboot整合RocketMq(非事务)的更多相关文章

  1. SpringBoot(17)---SpringBoot整合RocketMQ

    SpringBoot整合RocketMQ 上篇博客讲解了服务器集群部署RocketMQ 博客地址:RocketMQ(2)---Docker部署RocketMQ集群 这篇在上篇搭建好的基础上,将Spri ...

  2. Springboot整合RocketMQ解决分布式事务

    直接上代码: 代码结构如下: 依次贴出相关类: DataSource1Config: package com.example.demo.config;import org.apache.ibatis. ...

  3. MongoDB与SpringBoot整合(支持事务)

    1.创建SpringBoot工程,选择 Web.MonogDB 依赖,pom如下: <parent> <groupId>org.springframework.boot< ...

  4. SpringBoot整合RocketMQ

    1.RocketMQ的下载与配置 到官网选择想要的版本下载即可,https://rocketmq.apache.org/release_notes/ 下载速度会比较慢,这里提供目前最新版本4.9.3的 ...

  5. SpringBoot - 集成RocketMQ实现延迟消息队列

    目录 前言 环境 具体实现 前言 RocketMQ是阿里巴巴在2012年开源的分布式消息中间件,记录下SpringBoot整合RocketMQ的方式,RocketMQ的安装可以查看:Windows下安 ...

  6. 【SpringBoot】数据库操作之整合Mybaties和事务讲解

    ========================8.数据库操作之整合Mybaties和事务讲解 ================================ 1.SpringBoot2.x持久化数 ...

  7. SpringBoot整合Mybatis【非注解版】

    接上文:SpringBoot整合Mybatis[注解版] 一.项目创建 新建一个工程 ​ 选择Spring Initializr,配置JDK版本 ​ 输入项目名 ​ 选择构建web项目所需的state ...

  8. SpringBoot系列七:SpringBoot 整合 MyBatis(配置 druid 数据源、配置 MyBatis、事务控制、druid 监控)

    1.概念:SpringBoot 整合 MyBatis 2.背景 SpringBoot 得到最终效果是一个简化到极致的 WEB 开发,但是只要牵扯到 WEB 开发,就绝对不可能缺少数据层操作,所有的开发 ...

  9. @Transactional(事务讲解)和springboot 整合事务

    概述 事务在编程中分为两种:声明式事务处理和编程式事务处理 编程式事务处理:编码方式实现事务管理,常与模版类TransactionTemplate(推荐使用) 在业务代码中实现事务. 可知编程式事务每 ...

随机推荐

  1. opencv图像的基本操作3

    1.获取像素并修改 读取一副图像,根据像素的行和列的坐标获取它的像素值,对于RGB图像而言,返回RGB的值,对于灰度图则返回灰度值 import cv2 import numpy img = cv2. ...

  2. 服务器修改静态ip

    ifconfig,看当前网卡名字 设置 ip地址,子网掩码 ,广播地址 ifconfig eth1 172.16.11.25 netmask 255.255.255.0 broadcast 172.1 ...

  3. Nginx动静分离基本概述

    Nginx动静分离基本概述 动静分离,通过中间将动静分离和静态请求进行分离: 通过中间件将动态请求和静态请求分离,可以建上不必要的请求消耗,同时能减少请求的延时. 通过中间件将动态请求和静态请求分离, ...

  4. shell input value from console

    echo "Please enter some input: " read input_variable echo "You entered: $input_variab ...

  5. java while循环

    /* while 循环有一个标准格式,还有一个扩展格式 标准格式: while(条件表达式){ 循环体 } 扩展格式: 初始化语句; while(条件判断){ 循环体 步进表达式 } */ publi ...

  6. Linux下的Jenkins作为hub,Windows作为node节点,在Android手机上执行自动化脚本

    1.在Linux上放selenium-server-standalone-2.53.0.jar,在jar包目录下执行命令java -jar selenium-server-standalone-2.5 ...

  7. Qt + VS【无法打开xxx文件】

    在工程中右键点击属性-配置属性-VC++目录-包含目录-选择自己安装的qt路径下的头文件包含进去即可,烦人的下杠红线也随之消失.

  8. 人生苦短_我用Python_str(字符串)_001

    # 字符串 str str_1 = 'hello,selenium,888,999' # 切片/截断 # 更换大小写 upper/lower 英文字符 print(str_1.upper()) pri ...

  9. proxy-target-class="false"与proxy-target-class="true"区别

    原创转载请注明出处:https://www.cnblogs.com/agilestyle/p/11484063.html <aop:aspectj-autoproxy proxy-target- ...

  10. make编写教程(二)

    1. make中的变量 makefile中的变量就是c/c++中的宏 2. 引用其他的make文件 类似于c语言中的#include,被包含的文件会原模原样的放在当前文件的包含位置. include& ...