RabbitMQ入門_09_TTL

參考資料:https://www.rabbitmq.com/ttl.htmlhtml

A. 爲隊列設置消息TTL

TTL 是 Time-To-Live 的縮寫,指的是存活時間。RabbitMQ 能夠爲每個隊列設置其內部消息的 TTL。ui

gordon.study.rabbitmq.ttl.TestPerQueueMsgTtlcode

Map<String, Object> args = new HashMap<String, Object>();
        args.put("x-message-ttl", 5000);
        consumerChannel.queueDeclare(QUEUE_NAME, false, false, true, args);

如上,只要給隊列設置 x-message-ttl 參數,就設定了該隊列全部消息的存活時間。時間單位是毫秒,值必須大於等於零(等於零的狀況比較複雜,之後再分析)。htm

RabbitMQ 保證死消息(在隊列中的時間超過設定的TTL時間)不會被消費者得到,同時會盡快刪除死消息。rabbitmq

消息不會在消費者的緩衝區中過時,也就是說,只要隊列在消息過時前將消息推送給消費者,消費者就必定能處理到這條消息。隊列

從新入隊(例如被取消確認或信道關閉)的消息的過時時間保留初始值,即不刷新過時時間。

資源

B. 爲單條消息設置TTL

也能夠爲每一條消息設置存活時間。get

AMQP.BasicProperties properties = new AMQP.BasicProperties.Builder().expiration("500").build();
            senderChannel.basicPublish("", QUEUE_NAME, properties, message.getBytes("UTF-8"));

AMQP.BasicProperties 在當前版本使用 Builder 模式建立實例,在此,咱們經過設置 expiration 的值來設置消息存活時間爲 500 毫秒。it

當兩種消息 TTL 都被設置時,時間短的 TTL 設置生效。io

爲消息設置 TTL 有一個問題:RabbitMQ 只對處於隊列頭部的消息判斷是否過時(即不會掃描隊列),因此,極可能隊列中已存在死消息,可是隊列並不知情。這會影響隊列統計數據的正確性,妨礙隊列及時釋放資源。

實驗發現,RabbitMQ 對隊列頭部消息的 TTL 掃描是自發的,即便沒有 Consumer 鏈接在隊列上,過時消息也會被正確的移除。這種行爲對兩種消息TTL 都成立。

C. 隊列TTL

經過設置隊列TTL,若是指定時間內隊列沒被使用,則隊列自動被刪除。

Map<String, Object> args = new HashMap<String, Object>();
        args.put("x-expires", 5000);
        consumerChannel.queueDeclare(QUEUE_NAME, false, false, true, args);

隊列未被使用指未發生如下行爲:

  • 隊列沒有被從新申明
  • 沒有 basicGet 操做發生
  • 沒有 Consumer 鏈接在隊列上(哪怕隊列一直沒有消息)

特別的,就算一直有消息進入隊列,也不算隊列在被使用

RabbitMQ 保證未被使用的隊列必定不會在指定的過時時間內被刪除,可是不保證能及時刪除(試驗代碼中刪除很及時),只能保證在 RabbitMQ 重啓後必定已經刪除。

過時時間單位也是毫秒,可是與消息TTL 不一樣在於,隊列TTL 值必須大於零。

相關文章
相關標籤/搜索