Azure Event Grid 中的訊息佇列遙測傳輸(MQTT)保留功能確保主題的最後已知良好值被儲存,並隨時提供給新訂閱者。 這項功能可讓新的用戶端在連線時立即接收最新的訊息,不需要等候下一個發佈。 它在裝置狀態報告、控制訊號或設定資料等案例中非常有用,在這些案例中,及時存取最新訊息至關重要。
本文概述 MQTT Retain 的運作方式、計費影響、儲存體限制、訊息刪除方法和 Retain 管理考量。
帳單管理
保留發佈被視為兩個 MQTT 操作:一個用於處理訊息,另一個用於儲存。
儲存體限制
- 每個輸送量單位 (TU) 最多 640 MB 或 10,000 則保留訊息。
- 每則保留訊息的大小上限為 64 KB。
如需較大的需求,請連絡 Azure 支援。
郵件刪除
- MQTT 3.1.1:將空白酬載發佈至主題。 要設定有效期限,請聯絡 Azure 客服。
- MQTT 5.0:設定到期或傳送空白訊息以將其移除。
保留訊息 – 擷取與列出
保留訊息讓 MQTT 代理能儲存 主題上最後已知的訊息 ,讓新訂閱者能立即收到當前值,無需等待下一次發佈。 現在你可以使用以下 HTTP 管理端點:
- Retain Get:擷取特定主題的原始保留訊息主體。 訊息的元資料會透過 HTTP 標頭回傳。
- 保留清單:列舉符合主題篩選 (支援萬用字元) 的保留訊息,或使用接續權杖逐頁檢視結果。
使用這些 API 進行 可觀察性、稽核及營運工作流程 (例如支援故障排除、回填或大規模驗證裝置狀態)。
身份驗證與授權
Retain get 與 Retain List API 需要:
-
認證:
Authorization: Bearer <token>。 -
代幣受眾或範圍:使用此經紀人的 App ID URI 或本次預覽提供的資源(範例中請替換
<YOUR TOKEN HERE>)。 - RBAC:呼叫者必須擁有在命名空間上呼叫保留訊息讀取操作的權限。
要取得 Bearer 令牌,請執行以下 Azure CLI 命令:
az account get-access-token --resource=https://eventgrid.azure.net --query accessToken -o tsv
參考 API
保留 Get
GET /mqtt/retainedMessages/message?topic=<YOUR ENCODED TOPIC HERE>&api-version=2025-11-16-preview HTTP/1.1
Authorization: Bearer YOURENTRATOKEN
Host: <YOUR Event Grid MQTT BROKER URL HERE>
回應:
- 正文:原始的 MQTT 訊息負載(位元組)。
-
標頭:包含訊息元資料(名稱預覽時可能會變更):
-
x-ms-mqtt-topic保留訊息的主題。 -
x-ms-mqtt-qos:QoS 等級(0 或 1)。 -
x-ms-mqtt-size:完整的 MQTT 訊息大小(位元組)。 -
x-ms-mqtt-expiry:若設定為 ISO 8601,則為過期時間戳記。 -
x-ms-mqtt-last-modified:最後修改時間戳記(ISO 8601)。
-
保留名單
GET /mqtt/retainedMessages?topicFilter=<YOUR ENCODED TOPIC FILTER HERE>&continuationToken=<MUTUALLY EXCLUSIVE WITH TOPIC FILTER>&maxResults=<1-100>&api-version=2025-11-16-preview HTTP/1.1
Authorization: Bearer YOURENTRATOKEN
Host: <YOUR Event Grid MQTT BROKER URL HERE>
-
topicFilter支援萬用卡(例如,factory/+/state, sensors/#)。 -
continuationToken與 topicFilter 互斥。 用它從上一頁繼續。 -
maxResults限制頁面大小(1–100)。
回應(JSON):
{
"nextLink": "<NULL OR URL HERE>",
"retainedMessages": [
{
"topic": "<SOME TOPIC>",
"qos": "<SOME QOS>",
"size": "<FULL MQTT MESSAGE SIZE>",
"expiry": "<TIME STAMP>",
"lastModifiedTime": "<TIME STAMP>"
}
]
}
範例
URL 編碼範例
- 主題:
factory/line1/cell17/state- 編碼:
factory%2Fline1%2Fcell17%2Fstate
- 編碼:
- 篩選:
factory/line1/+/state- 編碼:
factory%2Fline1%2F%2B%2Fstate
- 編碼:
保留 Get - cURL 範例
BROKER="<YOUR BROKER URL HERE>" # e.g. contoso.westus.ts.eventgrid.azure.net
ENTRATOKEN="<YOUR TOKEN HERE>"
TOPIC_ENC="factory%2Fline1%2Fcell17%2Fstate"
curl -i \
-H "Authorization: Bearer $ENTRATOKEN" \
"https://$BROKER/mqtt/retainedMessages/message?topic=$TOPIC_ENC&api-version=2025-11-16-preview"
範例回應:
HTTP/1.1 200 OK
x-ms-mqtt-topic: factory/line1/cell17/state
x-ms-mqtt-qos: 1
x-ms-mqtt-size: 42
x-ms-mqtt-expiry: 2025-11-16T08:13:05Z
x-ms-mqtt-last-modified: 2025-11-16T07:59:41Z
content-type: application/octet-stream
{"state":"READY","tempC":25.1,"ts":"2025-11-16T07:59:40Z"}
保留列表與主題過濾器 - curl 範例
BROKER="<YOUR BROKER URL HERE>"
ENTRATOKEN="<YOUR TOKEN HERE>"
FILTER_ENC="factory%2Fline1%2F%2B%2Fstate"
curl -sS \
-H "Authorization: Bearer $ENTRATOKEN" \
"https://$BROKER/mqtt/retainedMessages?topicFilter=$FILTER_ENC&maxResults=50&api-version=2025-11-16-preview"
範例回應:
{
"nextLink": null,
"retainedMessages": [
{
"topic": "factory/line1/cell17/state",
"qos": 1,
"size": 42,
"expiry": "2025-11-16T08:13:05Z",
"lastModifiedTime": "2025-11-16T07:59:41Z"
},
{
"topic": "factory/line1/cell18/state",
"qos": 1,
"size": 41,
"expiry": null,
"lastModifiedTime": "2025-11-16T07:55:02Z"
}
]
}
保留清單與接續權杖 - curl 範例
NEXT_LINK="<PASTE NEXTLINK FROM PRIOR CALL>"
curl -sS -H "Authorization: Bearer $ENTRATOKEN" "$NEXT_LINK"
行為、極限與表現
- 最大結果範圍:每頁1–100。
-
主題篩選器:支援標準 MQTT 萬用字元
+,且#(以 URL 編碼)。 - 有效載荷大小:以原始位元組回傳(無 JSON 包裝)。
- 標頭:在 Get 中提供單一來源的中繼資料,不要期待有 JSON 封套。
- 分頁:遵循 nextLink,直到變成 null 為止。 不要把 topicFilter 和 continuationToken 混在一起。
- 節流:可能適用標準平台限制 (429)。 使用具輪詢的重試。
錯誤處理和疑難排解
- 400 錯誤要求:主題或 topicFilter 格式錯誤或缺失;同時提供 topicFilter 與 continuationToken。
- 401 未授權:token 無效或已過期,或受眾不正確。
- 403 禁止:呼叫者未取得命名空間權限。
- 404 未找到:指定主題無保留訊息。
- 409 衝突:請求違反預覽限制。
- 429 太多要求:受到節流;遵循 Retry-After。
- 5xx:短暫服務錯誤;用指數式後退重試。
備註
- 請確認主題精確(區分大小寫)且正確進行 URL 編碼。
- 確認你要求的經紀人的對象或範圍是正確的。