一、RocketMQ安装:
1.Centos7系统上安装:
安装Java(x64):https://blog.csdn.net/a526001650a/article/details/104122455
(1)下载rocketmq-all-4.7.1-bin-release.zip:
https://www.apache.org/dyn/closer.cgi?path=rocketmq/4.7.1/rocketmq-all-4.7.1-bin-release.zip
(2)用Xftp上传到/usr/local目录,并输入解压命令(cd到/usr/local目录):
[root@localhost local]# yum install -y unzip zip
[root@localhost local]# unzip rocketmq-all-4.7.1-bin-release.zip
(3)修改默认内存大小(cd到/usr/local/rocketmq-all-4.7.1-bin-release/bin目录):
<1>修改runserver.sh:
[root@localhost bin]# vi runserver.sh
修改内容如下:
JAVA_OPT="${JAVA_OPT} -server -Xms128m -Xmx128m -Xmn128m -XX:MetaspaceSize=128m -XX:MaxMetaspaceSize=128m"
<2>修改 runbroker.sh :
[root@localhost bin]# vi runbroker.sh
修改内容如下:
JAVA_OPT="${JAVA_OPT} -server -Xms128m -Xmx128m -Xmn128m"
(4)修改broker服务连接IP(cd到/usr/local/rocketmq-all-4.7.1-bin-release/conf目录):
[root@localhost conf]# vi broker.conf
末尾增加内容如下:
brokerIP1=192.168.233.128
namesrvAddr=192.168.233.128:9876
brokerName=rmq_broker
(5)启动nameserver服务(cd到/usr/local/rocketmq-all-4.7.1-bin-release/bin目录):
[root@localhost bin]# ./mqnamesrv
停止服务(cd到/usr/local/rocketmq-all-4.7.1-bin-release目录):
[root@localhost rocketmq-all-4.7.1-bin-release]# sh bin/mqshutdown namesrv
(6)启动broker服务(cd到/usr/local/rocketmq-all-4.7.1-bin-release/bin目录,-n 指定nameserver服务IP和端口):
[root@localhost bin]# ./mqbroker -c /usr/local/rocketmq-all-4.7.1-bin-release/conf/broker.conf
停止服务(cd到/usr/local/rocketmq-all-4.7.1-bin-release目录):
[root@localhost rocketmq-all-4.7.1-bin-release]# sh bin/mqshutdown broker
(7)测试发消息/收消息(cd到/usr/local/rocketmq-all-4.7.1-bin-release/bin目录):
<1>发消息:
[root@localhost bin]# sh tools.sh org.apache.rocketmq.example.quickstart.Producer
<2>收消息:
[root@localhost bin]# sh tools.sh org.apache.rocketmq.example.quickstart.Consumer
2.Docker上安装RocketMQ:
(1)下载rocketmq镜像:
[root@localhost ~]# docker pull rocketmqinc/rocketmq
(2)创建运行rocketmq-namesrv容器:
[root@localhost ~]# docker run -di -p 9876:9876 --name=rmq_namesrv \
-e "JAVA_OPT_EXT=-server -Xms128m -Xmx128m -Xmn128m" \
-e "JAVA_OPTS=-Duser.home=/opt" \
rocketmqinc/rocketmq:latest
(3)创建运行rocketmq-broker容器:
[root@localhost ~]# docker run -di -p 10911:10911 -p 10909:10909 --name=rmq_broker \
-e "JAVA_OPTS=-Duser.home=/opt" \
-e "JAVA_OPT_EXT=-server -Xms128m -Xmx128m -Xmn128m" \
rocketmqinc/rocketmq:latest
(4)停止/删除rocketmq容器:
[root@localhost ~]# docker stop rmqbroker rmq_namesrv
[root@localhost ~]# docker rm rmqbroker rmq_broker
3.Docker上安装rocketmq-console界面管理工具:
(1)下载rocketmq-console镜像:
[root@localhost ~]# docker pull styletang/rocketmq-console-ng
(2)创建启动rocketmq-console容器:
[root@localhost ~]# docker run -e "JAVA_OPTS=-Drocketmq.namesrv.addr=192.168.233.128:9876 -Dcom.rocketmq.sendMessageWithVIPChannel=false" -p 8080:8080 -t styletang/rocketmq-console-ng
(3)访问rocketmq-console主页:
http://192.168.233.128:8080
二、用Java-API操作RocketMQ:
1.创建消息接方法,接收指定组-订阅名下的消息:
private static void receiveMsg() {
try {
//1.创建mygroup组
DefaultMQPushConsumer c = new DefaultMQPushConsumer("my_group"); //组名要与发消息的一样
// 集群模式
//consumer.setMessageModel(MessageModel.CLUSTERING);
// 广播模式
c.setMessageModel(MessageModel.BROADCASTING);
//2.设置mqnamesrv连接地址
c.setNamesrvAddr("192.168.233.128:9876");
//3.订阅接收my_topic的消息
c.subscribe("my_topic", "*");
c.registerMessageListener(new MessageListenerConcurrently() {
@Override
public ConsumeConcurrentlyStatus consumeMessage(List<MessageExt> msgs, ConsumeConcurrentlyContext context) {//接收消息
System.out.println("收到消息: " + msgs);
if (msgs.get(0).getReconsumeTimes() >= 2) { //重试2次后,返回成功,就不会再接收了
return ConsumeConcurrentlyStatus.CONSUME_SUCCESS;
}
return ConsumeConcurrentlyStatus.RECONSUME_LATER; //返回此值时,会重试拉消息
}
});
//4.启动
c.start();
} catch (Exception e) {
e.printStackTrace();
}
}
2.创建消息发送方法:
(1)发送普通消息:
private static void sendMsg() {
try {
//创建mygroup组
DefaultMQProducer p = new DefaultMQProducer("my_group");
//设置mqnamesrv连接地址
p.setNamesrvAddr("192.168.233.128:9876");
//设置消息发送失败时重试N次
p.setRetryTimesWhenSendFailed(2);
//启动
p.start();
//1.创建消息
Message msg = new Message("my_topic", ("发送消息").getBytes(RemotingHelper.DEFAULT_CHARSET));
//2.1 同步发送消息
SendResult result = p.send(msg);
//SendResult sendResult = producer.send(msg, 1000); //指定发送超时时间
//2.2 异步发送消息
p.send(msg, new SendCallback() {
@Override
public void onSuccess(SendResult result) {//发送成功
}
@Override
public void onException(Throwable e) {//发送失败
}
});
//3.关闭连接
p.shutdown();
} catch (Exception e) {
e.printStackTrace();
}
}
(2)发送带事务的消息:
<1>消息发送:
private static void sendTranMsg() {
try {
//创建mygroup组
TransactionMQProducer p = new TransactionMQProducer("my_group");
p.setNamesrvAddr("192.168.233.128:9876");
//设置事务监听器,TransactionListenerImpl为实现类
p.setTransactionListener(new TransactionListenerImpl());
//设置消息发送失败时重试N次
p.setRetryTimesWhenSendFailed(2);
//启动
p.start();
//1.创建消息
Message msg = new Message("my_topic", ("发送带事务的消息").getBytes(RemotingHelper.DEFAULT_CHARSET));
//2. 发送带事务的消息
p.sendMessageInTransaction(msg, null);
//3.关闭连接
p.shutdown();
} catch (Exception e) {
e.printStackTrace();
}
}
<2>事务处理类:
public class TranListenerImpl implements TransactionListener {
private static Map<String, LocalTransactionState> map = new HashMap<>();
@Override
public LocalTransactionState executeLocalTransaction(Message msg, Object arg) {//执行需要事务内的业务逻辑
try {
//1. 需要事务的具体操作代码
//...
//2.1 设置提交
map.put(msg.getTransactionId(), LocalTransactionState.COMMIT_MESSAGE); //设置提交
return LocalTransactionState.COMMIT_MESSAGE; //返回提交类别
} catch (Exception e) {
e.printStackTrace();
}
//2.2 操作异常时执行回滚
map.put(msg.getTransactionId(), LocalTransactionState.ROLLBACK_MESSAGE); //设置回滚
return LocalTransactionState.ROLLBACK_MESSAGE; //返回回滚类别
}
@Override
public LocalTransactionState checkLocalTransaction(MessageExt msg) {
return map.get(msg.getTransactionId()); //回查消息并返回
}
}
三、集成SpringBoot操作RocketMQ:
1.在工程pom.xml是配置rocketmq依赖包:
<dependencies>
<!-- 导入rocketmq依赖包 -->
<dependency>
<groupId>org.apache.rocketmq</groupId>
<artifactId>rocketmq-spring-boot-starter</artifactId>
<version>2.1.1</version>
</dependency>
<dependency>
<groupId>org.apache.rocketmq</groupId>
<artifactId>rocketmq-client</artifactId>
<version>4.7.1</version>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter</artifactId>
</dependency>
</dependencies>
2.在工程resources/application.yml中rocketmq服务器地址:
rocketmq: #配置rocketmq服务器地址,rocketmq是顶级节点,不要跟在spring下面
name-server: 192.168.233.128:9876
#连接集群方式
#name-server: 192.168.233.128:9876;192.168.233.128:9877...
producer:
group: my_group
3.创建消息接收类,接收指定组-订阅名下的消息:
@Component
@RocketMQMessageListener(consumerGroup = "my_group", //组名称
topic = "my_topic", //订阅名称
selectorExpression = "*") //my_topic订阅名称下的消息
public class MsgReceive implements RocketMQListener<String> { //消息接收类
@Override
public void onMessage(String msg) {//接收消息
System.out.println("收到消息 msg: " + msg);
}
}
4.创建消息发送类:
(1)发送普通消息:
@Component
public class MsgSendBiz { //消息发送类
@Autowired
private RocketMQTemplate rocketMQTemplate; //RocketMQ消息发送类
//1.发送普通消息
public void sendMsg(String topic, String msg) {
rocketMQTemplate.convertAndSend(topic, msg);
System.out.println("发送消息成功");
}
}
(2)发送带事务的消息:
<1>消息发送类:
@Service
public class MsgSendBiz { //消息发送类
@Autowired
private RocketMQTemplate rocketMQTemplate; //RocketMQ消息发送类
//2.发送带事务的消息
public void sendMsgInTran(String topic, String msgStr) {
Message msg = MessageBuilder.withPayload(msgStr).build();
rocketMQTemplate.sendMessageInTransaction(topic, msg, null);
System.out.println("发送带事务消息成功");
}
}
<2>事务处理类:
@RocketMQTransactionListener
public class TranListener implements RocketMQLocalTransactionListener {
private final static Map<String, RocketMQLocalTransactionState> map = new HashMap<>();
@Override
public RocketMQLocalTransactionState executeLocalTransaction(Message message, Object o) {
String transId = (String) message.getHeaders().get(RocketMQHeaders.TRANSACTION_ID);
try {
//1 具体业务操作代码
//...
//2.1 执行提交
map.put(transId, RocketMQLocalTransactionState.COMMIT); //设置提交
return RocketMQLocalTransactionState.COMMIT; //返回提交类别
} catch (Exception e) {
e.printStackTrace();
}
//2.2 操作异常时执行回滚
map.put(transId, RocketMQLocalTransactionState.ROLLBACK); //设置回滚
return RocketMQLocalTransactionState.ROLLBACK; //返回回滚类别
}
@Override
public RocketMQLocalTransactionState checkLocalTransaction(Message message) {
String transId = (String) message.getHeaders().get(RocketMQHeaders.TRANSACTION_ID);
return map.get(transId); //回查消息并返回
}
}