現在使用rocketmq基本上都是搭載spring配合使用的,現在就以springBoot作爲演示。
1.首先先倒入所需依賴包
<dependency>
<groupId>com.alibaba.rocketmq</groupId>
<artifactId>rocketmq-client</artifactId>
<version>3.2.6</version>
</dependency>
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>fastjson</artifactId>
<version>1.2.60</version>
</dependency>
備註:這裏切記要倒入正確的fastjson包,否則會導致收發消息報錯:路由異常說該nameserver下沒有配置此topic
2.分別啓動nameserver和broker
> nohup sh bin/mqnamesrv &
> nohup sh bin/mqbroker -n localhost:9876&
備註:切記一定要先查看自身的ip,啓動broker記得查看broker日誌是否成功
broker日誌地址:~/logs/rocketmqlogs/broker.log
2019-12-02 13:53:12 INFO brokerOutApi_thread_2 - register broker[0]to name server 192.168.142.80:9876 OK
查看java程序進程,看是否有啓動namesev 和 broker
>jps
6599 RemoteMavenServer36
6743 BrokerStartup
6747 Jps
6653 Launcher
6670 NamesrvStartup
3.停止Nameserver 和 Broker服務
首先進入bin目錄會存在這麼一個服務mqshutdown,當然也存在剛剛啓動的broker和nameserver服務
所以停止nameServer 和 Broker 命令如下:
(base) bogon:rocketmq-all-4.6.0-bin-release humingming$ sh bin/mqshutdown namesrv --停止註冊發現狀態服務
The mqnamesrv(12524) is running...
Send shutdown request to mqnamesrv(12524) OK
(base) bogon:rocketmq-all-4.6.0-bin-release humingming$ sh bin/mqshutdown broker --停止broker服務
The mqbroker(12534) is running...
Send shutdown request to mqbroker(12534) OK
[3]+ Exit 143 nohup sh bin/mqnamesrv
4.編寫 生產者和消費者例子
package rocketmq.day01;
import com.alibaba.rocketmq.client.exception.MQBrokerException;
import com.alibaba.rocketmq.client.exception.MQClientException;
import com.alibaba.rocketmq.client.producer.DefaultMQProducer;
import com.alibaba.rocketmq.client.producer.SendResult;
import com.alibaba.rocketmq.common.message.Message;
import com.alibaba.rocketmq.remoting.exception.RemotingException;
import java.text.SimpleDateFormat;
import java.util.Date;
/**
* @author heian
* @create 2019-11-28-8:23 下午
* @description
*/
public class ProducerDemo {
public static void main(String[] args) throws MQClientException {
DefaultMQProducer producer = new DefaultMQProducer("unique_producer_group__name");
producer.setNamesrvAddr("192.168.142.80:9876");
producer.start();
for (int i = 0; i < 1; i++) {
Date date = new Date();
SimpleDateFormat sdf = new SimpleDateFormat();
String format = sdf.format(date);
Message message = new Message("topicName", String.valueOf(i),format.getBytes());
SendResult sendResult= new SendResult();
try {
sendResult = producer.send(message);
} catch (RemotingException |MQBrokerException | InterruptedException e) {
System.out.println("消息發送失敗:" + sendResult.getMsgId());
e.printStackTrace();
}
System.out.println("key:"+i + "消息的發送結果爲:" + sendResult.toString() + "消息ID爲:" + sendResult.getMsgId());
}
}
}
package rocketmq.day01;
import com.alibaba.rocketmq.client.consumer.DefaultMQPushConsumer;
import com.alibaba.rocketmq.client.consumer.listener.ConsumeConcurrentlyContext;
import com.alibaba.rocketmq.client.consumer.listener.ConsumeConcurrentlyStatus;
import com.alibaba.rocketmq.client.consumer.listener.MessageListenerConcurrently;
import com.alibaba.rocketmq.client.exception.MQClientException;
import com.alibaba.rocketmq.common.consumer.ConsumeFromWhere;
import com.alibaba.rocketmq.common.message.MessageExt;
import java.io.UnsupportedEncodingException;
import java.util.List;
/**
* @author heian
* @create 2019-11-28-8:51 下午
* @description
*/
public class ConsumeDemo {
public static void main(String[] args) throws MQClientException {
DefaultMQPushConsumer defaultMQPushConsumer = new DefaultMQPushConsumer("unique_consume_group_name");
defaultMQPushConsumer.setNamesrvAddr("192.168.142.80:9876");
// 設置消費地點,從最第一個進行消費(其實就是消費策略)
defaultMQPushConsumer.setConsumeFromWhere(ConsumeFromWhere.CONSUME_FROM_FIRST_OFFSET);
defaultMQPushConsumer.subscribe("topicName","*");
defaultMQPushConsumer.registerMessageListener(new MessageListenerConcurrently() {
@Override
public ConsumeConcurrentlyStatus consumeMessage(List<MessageExt> list, ConsumeConcurrentlyContext consumeConcurrentlyContext) {
byte[] body = list.get(0).getBody();
try {
String ms = new String(body,"utf-8");
System.out.println(Thread.currentThread().getName() + "監聽到消息:" + ms);
} catch (UnsupportedEncodingException e) {
e.printStackTrace();
}
return ConsumeConcurrentlyStatus.CONSUME_SUCCESS;
}
});
defaultMQPushConsumer.start();
}
}
5. 分別啓動生產者和消費者
控制檯打印信息如下:
--生產者控制檯
key:0消息的發送結果爲:SendResult [sendStatus=SEND_OK, msgId=C0A88E5000002A9F0000000000070774, messageQueue=MessageQueue [topic=topicName, brokerName=bogon, queueId=0], queueOffset=20]消息ID爲:C0A88E5000002A9F0000000000070774
--消費者控制檯
ConsumeMessageThread_1監聽到消息:19-12-2 下午2:00
備註:可以發現一則消息發送前後必須先定義
- GroupName(生產組名和消費組名)
- NameServer地址及端口(broker必須先註冊到Nmaesrv上,有點類似於nio中的serverSocketChannel.register(selector, 0)),就是服務端開啓一個通道,客戶端往通道內寫數據,服務端用selector去一對多監聽多個客戶端
- topic名稱或者更細的tags
此外:1.rocketmq讀寫隊列默認是8個,生產上配置則是按照實例數的兩倍,比如生產上有8個微服務,則一般配置16個讀寫隊列
2.消費端線程監聽默認是最大起20個線程監聽
圖形化界面管理mq集羣
對於rocketmq新手如果我們要查看消息的一些軌跡或者topic的一些信息啊,使用mqadmin命令有點不切實際(mqadmin命令),所以需要又一個類似於navicat一樣的可視化界面。
運維服務是一個springboot項目,需要從GitHub上下載地址爲:https://github.com/apache/rocketmq-externals 進入後我們需要下載這些組件到本地,我們用到的只有rocketmq-console這個項目文件夾。
- 自身你可以用idea打開看其源碼,在這個boot項目中又一個properties文件,將namesrv地址配置成自身的IP地址:rocketmq.config.namesrvAddr=localhost:9876 如果是集羣部署則 ip:9876;ip2;9876
- 將boot項目打成jar包 直接使用命令:進入到/Users/humingming/IdeaProjects/rocketmq-console 文件夾執行此命令
編譯命令:mvn clean package -Dmaven.test.skip=true(注意:不要直接使用mvn package,會提示很多錯誤)
會在boot項目中生成target文件夾並在其中生成jar文件,我們主要用到的就是此:rocketmq-console-ng-1.0.1.jar
-
切換到該jar包目錄直接運行:java -jar rocketmq-console-ng-1.0.1.jar 可以直接在idea中輸入這些命令,直接打包和運行jar包
java -jar rocketmq-console-ng-1.0.1.jar
備註:如果ip地址不對,或者端口衝突,可以在運行jar後面加個後綴
-
直接訪問運行好的jar (其實就是運行了一個sprongboot項目) http://localhost:8080/
至此,開啓我們的rocketmq 學習之旅!!!