

本文為英文版的機器翻譯版本，如內容有任何歧義或不一致之處，概以英文版為準。

# Amazon SNS 訊息傳遞重試
<a name="sns-message-delivery-retries"></a>

Amazon SNS 會為每個傳遞通訊協定定義*傳遞政策*。傳遞政策會定義在伺服器端發生錯誤時，Amazon SNS 重試傳遞訊息的方式 (在託管訂閱端點的系統無法使用時)。當傳遞政策用盡時，除非已將無效字母佇列附加至訂閱，否則 Amazon SNS 會停止重試傳遞並捨棄訊息。如需詳細資訊，請參閱[Amazon SNS 無效字母佇列](sns-dead-letter-queues.md)。

## 傳遞通訊協定和政策
<a name="delivery-policies-for-protocols"></a>

**注意**  
您無法變更 Amazon SNS 定義的傳遞政策，但 HTTP/S 除外。只有 HTTP/S 支援自訂政策。請參閱 [建立 HTTP/S 傳遞政策](#creating-delivery-policy)。
Amazon SNS 會將抖動套用到傳遞重試。如需詳細資訊，請參閱 *AWS 架構部落格*中的[指數退避和抖動](https://aws.amazon.com/blogs/architecture/exponential-backoff-and-jitter/)貼文。
** HTTP/S 端點的總政策重試時間不能大於 3，600 秒。這是硬性限制，無法再增加**。

[\[See the AWS documentation website for more details\]](http://docs.aws.amazon.com/zh_tw/sns/latest/dg/sns-message-delivery-retries.html)

1 對於 Firehose 通訊協定的限流錯誤，Amazon SNS 使用與客戶受管端點相同的交付政策。

## 傳遞政策階段
<a name="delivery-policy-stages"></a>

下圖顯示傳遞政策的各個階段。

![\[x y 軸圖顯示時間作為 x 值，初始交付嘗試作為 y 值。交付政策從 y 軸上的立即重試階段開始，接著 x 軸上的預退避階段、退避階段和後退避階段。\]](http://docs.aws.amazon.com/zh_tw/sns/latest/dg/images/sns-delivery-policy-phases.png)


每個傳遞政策都是由四個階段組成。

1. **立即重試階段 （無延遲）** – 此階段會在初次交付嘗試後立即發生。在此階段各次重試之間無延遲。

1. **預退避階段** – 此階段遵循立即重試階段。Amazon SNS 會先使用此階段來嘗試一組重試動作，然後再套用輪詢函數。此階段會指定重試次數和各次重試之間的延遲量。

1. **退避階段** – 此階段使用重試退避函數控制重試之間的延遲。此階段會設定最小延遲、最大延遲，以及重試輪詢函數，以定義延遲多快從最小增加到最大延遲。輪詢函數可以是算術、指數、幾何或線性類型。

1. **後退避階段** – 此階段遵循退避階段。它會指定重試次數和各次重試之間的延遲量。此為最後一個階段。

## 建立 HTTP/S 傳遞政策
<a name="creating-delivery-policy"></a>

您可以使用具有四個階段的傳遞政策來定義 Amazon SNS 如何重試將訊息傳遞至 HTTP/S 端點：*無延遲*、*預退避*、*退避*和*後退避*。此政策可讓您覆寫預設的重試設定，並自訂以符合 HTTP 伺服器的容量。

您可以在**主題**或**訂閱**層級將 HTTP/S 交付政策定義為 JSON 物件：
+ **主題層級政策** – 適用於連結至主題的所有 HTTP/S 訂閱。使用 [https://docs.aws.amazon.com/sns/latest/api/API_CreateTopic.html](https://docs.aws.amazon.com/sns/latest/api/API_CreateTopic.html)或 [https://docs.aws.amazon.com/sns/latest/api/API_SetTopicAttributes.html](https://docs.aws.amazon.com/sns/latest/api/API_SetTopicAttributes.html) API 動作來設定此政策。
+ **訂閱層級政策** – 僅適用於特定訂閱。使用 [https://docs.aws.amazon.com/sns/latest/api/API_Subscribe.html](https://docs.aws.amazon.com/sns/latest/api/API_Subscribe.html)或 [https://docs.aws.amazon.com/sns/latest/api/API_SetSubscriptionAttributes.html](https://docs.aws.amazon.com/sns/latest/api/API_SetSubscriptionAttributes.html) API 動作來設定此政策。

或者，您也可以在 CloudFormation 範本中使用 [AWS::SNS::Subscription](https://docs.aws.amazon.com/AWSCloudFormation/latest/UserGuide/aws-resource-sns-subscription.html) 資源。

您應該根據 HTTP/S 伺服器的容量自訂交付政策：
+ **所有訂閱的單一伺服器** – 如果主題中的所有 HTTP/S 訂閱都使用相同的伺服器，請將交付政策設定為主題屬性，以確保所有訂閱的一致性。
+ **訂閱的不同伺服器** – 如果訂閱以不同的伺服器為目標，請為每個訂閱建立唯一的交付政策，根據特定伺服器的容量量身打造。

您也可以在請求政策中設定 `Content-Type`標頭，以指定通知的媒體類型。根據預設，Amazon SNS 會將所有通知傳送至內容類型設為 的 HTTP/S 端點`text/plain; charset=UTF-8`。不過，您可以使用請求政策中的 [`headerContentType`](#header-content-type) 欄位覆寫此預設值。

下列 JSON 物件定義交付政策，其重試分為四個階段：

1. **無延遲階段** – 立即重試 3 次。

1. **預退避階段** – 以 1 秒的間隔重試 2 次。

1. **退避階段** – 重試 10 次，指數延遲範圍為 1 到 60 秒。

1. **後退避階段** – 以固定的 60 秒間隔重試 35 次。

Amazon SNS 在捨棄訊息之前，總共會嘗試傳遞訊息 **50 次**。若要保留所有重試後無法傳遞的訊息，請將您的訂閱設定為將無法傳遞的訊息移至無效字母佇列 (DLQ)。如需詳細資訊，請參閱[Amazon SNS 無效字母佇列](sns-dead-letter-queues.md)。

Amazon SNS 會將所有 5XX 錯誤和 429 （傳送的請求太多） 錯誤視為可重試。這些錯誤受交付政策約束。所有其他錯誤都視為永久失敗，不會嘗試重試。

**注意**  
此交付政策使用 `maxReceivesPerSecond` 屬性，將交付流量調節為每個訂閱平均每秒 10 則訊息。雖然此機制有助於防止 HTTP/S 端點因高流量而不堪負荷，但其設計目的是維持平均交付速率，並且不會強制執行嚴格的上限。偶爾可能會發生超過指定限制的交付流量峰值，特別是當您的發佈速率明顯高於限流限制時。  
當發佈 （傳入） 流量超過交付 （傳出） 速率時，可能會導致訊息積壓和更高的交付延遲。若要避免此類問題，請確定 `maxReceivesPerSecond`值符合您 HTTP/S 伺服器的容量和工作負載需求。

下列交付政策範例會將 HTTP/S 通知的預設內容類型覆寫為 `application/json`。

```
{
    "healthyRetryPolicy": {
        "minDelayTarget": 1,
        "maxDelayTarget": 60,
        "numRetries": 50,
        "numNoDelayRetries": 3,
        "numMinDelayRetries": 2,
        "numMaxDelayRetries": 35,
        "backoffFunction": "exponential"
    },
    "throttlePolicy": {
        "maxReceivesPerSecond": 10
    },
    "requestPolicy": {
        "headerContentType": "application/json"
    }
}
```

交付政策由**重試政策**、**調節政策和****請求政策**組成。交付政策中總共有 **9 個屬性**。


| 政策  | Description | 限制條件 | 
| --- | --- | --- | 
| minDelayTarget | 重試的最小延遲。**單位：**秒 | 1 到最大延遲**預設：**20 | 
| maxDelayTarget | 重試的最大延遲。**單位：**秒 | 最小延遲到 3,600**預設：**20 | 
| numRetries | 重試總數，包括立即、預先輪詢、輪詢和事後輪詢重試。 | 0 到 100**預設：**3 | 
| numNoDelayRetries | 要立即完成的重試次數，且各次重試之間毫無延遲。 | 0 或以上**預設：**0 | 
| numMinDelayRetries | 預先輪詢階段中的重試次數，且各次重試之間有指定的最小延遲。 | 0 或以上**預設：**0 | 
| numMaxDelayRetries | 事後輪詢階段中的重試次數，且各次重試之間有最大延遲。 | 0 或以上**預設：**0 | 
| backoffFunction | 重試之間的輪詢模式。 |  下列四個選項之一： [\[See the AWS documentation website for more details\]](http://docs.aws.amazon.com/zh_tw/sns/latest/dg/sns-message-delivery-retries.html) **預設值：**線性  | 
| maxReceivesPerSecond  | 每個訂閱每秒的訊息傳遞平均數量上限。 | 1 或以上**預設：**無限流 （傳遞速率無限制） | 
| headerContentType  | 傳送至 HTTP/S 端點之通知的內容類型。 |  如果未定義請求政策，則內容類型預設為 `text/plain; charset=UTF-8`。 當訂閱停用原始訊息傳遞時 (預設)，或在主題層級定義傳遞政策時，支援的標頭內容類型為 `application/json` 和 `text/plain`。 啟用訂閱的原始訊息傳遞時，支援下列內容類型： [\[See the AWS documentation website for more details\]](http://docs.aws.amazon.com/zh_tw/sns/latest/dg/sns-message-delivery-retries.html)  | 

Amazon SNS 會使用下列公式計算輪詢階段中的重試次數：

```
numRetries - numNoDelayRetries - numMinDelayRetries - numMaxDelayRetries
```

您可以使用三個參數來控制退避階段期間的重試頻率：
+ **`minDelayTarget`** – 設定退避階段中第一次重試嘗試的延遲。
+ **`maxDelayTarget`** – 設定退避階段中最後一次重試嘗試的延遲。
+ **`backoffFunction`** – 決定 Amazon SNS 用來計算第一次和最後一次重試之間所有重試嘗試延遲的演算法。您可以從四個可用的重試退避函數中進行選擇。

下圖說明不同的重試退避函數如何影響退避階段期間重試之間的延遲。用於此範例的交付政策包括下列設定：**10 次重試**、**最短延遲 5 秒**，以及**最長延遲 260 秒**。
+ **垂直軸**會顯示每次重試嘗試的延遲 （以秒為單位）。
+ **水平軸**代表重試序列，範圍從第一次到第十次嘗試。

![\[圖表顯示根據四個退避函數，重試如何延遲 10 次嘗試的進度：指數函數、算術函數、線性函數和幾何函數。每個彩色線代表函數的延遲模式：指數：快速增加，達到最大延遲最快，線性：在每次重試時穩定增加，算術和幾何：顯示中等增加，比線性更陡，但比指數更快。所有行都接近 5 秒的最小延遲，並接近第十次重試的 260 秒最大延遲。\]](http://docs.aws.amazon.com/zh_tw/sns/latest/dg/images/backoff-graph.png)
