生產者
本節說明 Apache RocketMQ 中生產者的概念。它也說明生產者在訊息傳遞模型中的角色、生產者屬性和相容性,以及一些使用生產者的使用注意事項。
定義
Apache RocketMQ 中的生產者是建立訊息並將其傳送至伺服器的功能性訊息傳遞實體。
生產者通常整合在業務系統中,用於將資料封裝為 Apache RocketMQ 中的訊息,並將訊息傳送至伺服器。如需有關訊息的詳細資訊,請參閱 訊息。
下列訊息傳遞元素定義在生產者端
傳輸模式:生產者可以在 API 操作中指定訊息傳輸模式。Apache RocketMQ 支援同步傳輸和非同步傳輸。
批次傳輸:生產者可以在 API 操作中指定批次傳輸。例如,可以指定一次傳送的訊息數量或大小。
交易行為:Apache RocketMQ 支援交易訊息。生產者參與交易檢查以確保交易的最終一致性。如需詳細資訊,請參閱 交易訊息。
生產者和主題具有 n 對 n 的關係。生產者可以將訊息傳送至多個主題,而主題可以接收來自多個生產者的訊息。這種多對多的關係有助於效能擴充和災難復原。
模型關係
下圖顯示了 Apache RocketMQ 訊息模型中製作人的角色。
訊息由製作人初始化並傳送至 Apache RocketMQ 伺服器。
訊息會依抵達 Apache RocketMQ 伺服器的順序,儲存在主題的指定佇列中。
消費者會根據指定的訂閱關係,從 Apache RocketMQ 伺服器取得並使用訊息。
內部屬性
用戶端 ID
定義:製作人用戶端的身分。此屬性用於區分不同的製作人。用戶端 ID 在叢集中是全球唯一的。
值:用戶端 ID 會由 Apache RocketMQ SDK 自動產生。它主要用於 O\&M 目的,例如檢視記錄檔和找出問題。用戶端 ID 無法修改。
通訊參數
(必要):用於連線至伺服器的端點。此端點用於識別叢集。
存取點必須以格式設定。我們建議您使用網域名稱,避免使用 IP 位址,以防止節點變更無法執行熱點遷移。
(選用):用戶端用於驗證的身分證明。
僅當伺服器啟用身分識別和驗證時,才需要傳輸。
- 要求逾時(選用):網路要求的逾時期間。如需有關值範圍和預設值的詳細資訊,請參閱 參數限制。
預先繫結主題清單
定義:Apache RocketMQ 製作人傳送訊息至其中之主題的清單。預先繫結主題提供以下好處
交易訊息(必要):必須為交易訊息指定預先繫結主題清單屬性。在交易訊息場景中,當製作人從錯誤中復原或重新啟動時,製作人會檢查交易訊息主題是否包含未提交的交易訊息。這可防止製作人將新訊息傳送至主題後,主題中未提交交易訊息造成的延遲。
非交易訊息(選用):伺服器會在製作人初始化期間根據預先繫結主題清單檢查目的地主題的存取權限和有效性,而不是在應用程式啟動後才執行檢查。我們建議您為非交易訊息指定預先繫結主題清單屬性。
如果未對非交易訊息指定預綁定主題清單屬性或變更目的地主題,Apache RocketMQ 會動態檢查並識別目的地主題。
限制:對於交易訊息,必須指定預綁定主題並與交易檢查器一起使用。
交易檢查器
Apache RocketMQ 使用交易訊息機制,要求生產者實作交易檢查器,以確保交易的最終一致性。如需詳細資訊,請參閱 交易訊息。
當生產者傳送交易訊息時,必須設定交易檢查器並與預綁定主題一起使用。
傳送重試原則
傳送重試原則指定生產者在訊息傳遞嘗試失敗時如何重試傳遞訊息。如需詳細資訊,請參閱 訊息傳送重試。
版本相容性
從 Apache RocketMQ 版本 5.x 開始,生產者是匿名的,且生產者群組已停用。對於 Apache RocketMQ 版本 3.x 和版本 4.x,現有的生產者群組可以停用,而不會影響您的業務。
使用注意事項
我們建議您限制個別程序上的生產者數量。
在 Apache RocketMQ 中,生產者和主題提供多對多的通訊形式。單一生產者可以將訊息傳送至多個主題。我們建議您建立並初始化您的業務場景所需的最小生產者數量,並盡可能重複使用多個生產者。例如,在需要將訊息傳遞至多個主題的場景中,您不需要為每個主題建立一個生產者。
我們建議您不要定期建立和銷毀生產者。
Apache RocketMQ 的生產者是可以重複使用的基礎資源,例如資料庫的連線池。您不需要在每次傳送訊息時建立生產者,或在傳送訊息後銷毀生產者。如果您定期建立和銷毀生產者,會在代理程式上產生大量的短連線要求。這會對您的系統造成高負載。
正確使用的範例
Producer p = ProducerBuilder.build();
for (int i =0;i<n;i++)
{
Message m= MessageBuilder.build();
p.send(m);
}
p.shutdown();
不正確使用的範例
for (int i =0;i<n;i++)
{
Producer p = ProducerBuilder.build();
Message m= MessageBuilder.build();
p.send(m);
p.shutdown();
}