差不多可以看消息隊列的源碼了。 在下從gitee上找到了rocketmq的早期版本(3.2.2), 壞消息是這個2014年的項目裡沒有單元測試極少, 調試會比較困難. 好消息是這個時候的RocketMQ還沒開源多久,裡面有很多中文註釋。看起來會很舒服。

我們從Broker開始塗鴉。關於RocketMQ中每個角色的作用這裡不再陳述:

先從初始化開始:

1    public static void main(String[] args) {
2        start(createBrokerController(args));
3    }

rocketmq是從commandline啟動的,createBrokerController函數比較長, 會有很多額外的邏輯干擾你,我這裡直接說重點:

  • 讀取環境變量,沒有就用默認值。
  • 解析命令行參數。
  • 初始化配置類。
  • 打印默認配置內容。
  • 檢查NameServer地址設置是否正確。
  • 檢查broker的類型(master,slave)
  • 初始化日誌配置類。
  • 再次打印。
  • 初始化服務控制對象.
  • 最後增加一個關閉Broker時觸發的hook.

服務控制對象: Broker各個服務控制器,包括存儲層配置,配置文件版本號,消費進度存儲,Consumer連接、訂閱關係管理等等。

以上就是createBrokerController的內容,函數雖然長,但是並不複雜。

下面為start函數的內容, 在main中的start函數實際上是去委託了BrokerController去執行.

 1    public void start() throws Exception {
 2
 3        // 啟動Broker的各層服務
 4
 5        if (this.messageStore != null) {
 6            this.messageStore.start();
 7        }
 8
 9        if (this.remotingServer != null) {
10            this.remotingServer.start();
11        }
12
13        if (this.brokerOuterAPI != null) {
14            this.brokerOuterAPI.start();
15        }
16
17        if (this.pullRequestHoldService != null) {
18            this.pullRequestHoldService.start();
19        }
20
21        if (this.clientHousekeepingService != null) {
22            this.clientHousekeepingService.start();
23        }
24
25        if (this.filterServerManager != null) {
26            this.filterServerManager.start();
27        }
28
29        // 啟動時,註冊該Broker的信息到所有的NameServer
30        this.registerBrokerAll(true);
31
32        // 定時註冊Broker到Name Server
33        this.scheduledExecutorService.scheduleAtFixedRate(() -> {
34            try {
35                this.registerBrokerAll(true);
36            } catch (Exception e) {
37                log.error("registerBrokerAll Exception", e);
38            }
39        }, 1000 * 10, 1000 * 30, TimeUnit.MILLISECONDS);
40
41        if (this.brokerStatsManager != null) {
42            // 看起來就是一些數據統計線程
43            this.brokerStatsManager.start();
44        }
45
46        // 刪除多餘的Topic
47        this.addDeleteTopicTask();
48    }

整個Borker的流程差不多就是這樣.代碼裡並沒有什麼亮點說實話.