

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

# DynamoDB 中的週期性付款結構描述設計
<a name="data-modeling-schema-recurring-payments"></a>

## 週期性付款商業使用案例
<a name="data-modeling-schema-recurring-payments-use-case"></a>

此使用案例將說明如何使用 DynamoDB 實作週期性付款系統。資料模型具有以下實體：*帳戶*、*訂閱*及*收據*。我們的使用案例包括以下細節：
+ 每個*帳戶*可以有多個*訂閱*
+ 需要處理下一次付款時，*訂閱*會有 `NextPaymentDate`，傳送電子郵件提醒給客戶時，則會有 `NextReminderDate`
+ 有一個代表*訂閱*的項目會儲存並在付款處理完成時更新 (平均項目大小約為 1KB，輸送量取決於*帳戶*和*訂閱*的數目)
+ *付款*處理器還會在過程中建立一張*收據*並儲存在資料表中，而且會使用 [TTL](TTL.md) 屬性將它設定為在經過一段時間後過期。

## 週期性付款實體關係圖
<a name="data-modeling-schema-recurring-payments-erd"></a>

這是我們將用於週期性付款系統結構描述設計的實體關係圖 (ERD)。

![顯示實體的週期性付款系統 ERD：帳戶、訂閱和收據。](http://docs.aws.amazon.com/zh_tw/amazondynamodb/latest/developerguide/images/DataModeling/ReoccurringPayments-1-ERD.png)


## 週期性付款系統存取模式
<a name="data-modeling-schema-recurring-payments-access-patterns"></a>

這些是我們針對週期性付款系統結構描述設計考量的存取模式。

1. `createSubscription`

1. `createReceipt`

1. `updateSubscription`

1. `getDueRemindersByDate`

1. `getDuePaymentsByDate`

1. `getSubscriptionsByAccount`

1. `getReceiptsByAccount`

## 週期性付款結構描述設計
<a name="data-modeling-schema-recurring-payments-design-evolution"></a>

通用名稱 `PK` 和 `SK` 用於金鑰屬性，以允許在相同資料表中儲存不同類型的實體，例如帳戶、訂閱和收據實體。使用者首先建立訂閱，這代表使用者同意在每個月的同一天支付一定金額來換取使用產品。使用者可以選擇要在每個月的哪一天處理付款。另外還會在處理付款之前傳送提醒。應用程式的運作方式是每天執行兩個批次任務：一個批次任務傳送當天應送出的提醒，另一個批次任務則處理當天應付的任何款項。

**步驟 1：位址存取模式 1 (`createSubscription`)**

存取模式 1 (`createSubscription`) 用於初次建立訂閱，並設定包括 `SKU`、`NextPaymentDate`、`NextReminderDate` 和 `PaymentDetails` 等詳細資訊。此步驟僅顯示具有一個訂閱的一個帳戶的資料表狀態。項目集合中可以有多個訂閱，因此這是一對多關係。

![顯示帳戶訂閱詳細資訊的資料表設計。](http://docs.aws.amazon.com/zh_tw/amazondynamodb/latest/developerguide/images/DataModeling/ReoccurringPayments-2-Step1.png)


**步驟 2：位址存取模式 2 (`createReceipt`) 和 3 (`updateSubscription`)**

存取模式 2 (`createReceipt`) 用於建立收據項目。每個月處理付款後，付款處理器會將收據寫回基礎資料表。項目集合中可以有多個收據，因此這是一對多關係。付款處理器也會更新訂閱項目 (存取模式 3 (`updateSubscription`)) 以更新下個月的 `NextReminderDate` 或 `NextPaymentDate`。

![收據詳細資訊和訂閱項目更新，以顯示下一個訂閱提醒日期。](http://docs.aws.amazon.com/zh_tw/amazondynamodb/latest/developerguide/images/DataModeling/ReoccurringPayments-3-Step2.png)


**步驟 3：位址存取模式 4 (`getDueRemindersByDate`)**

應用程式會分批處理當天的付款提醒。因此，應用程式需要存取不同維度的訂閱：日期，而非帳戶。這是一個很好的[全域次要索引 (GSI)](GSI.md) 使用案例。在此步驟中，我們會新增索引 `GSI-1`，它會使用 `NextReminderDate` 作為 GSI 分割區索引鍵。我們不需要複寫所有項目。這個 GSI 是[稀疏索引](data-modeling-blocks.md#data-modeling-blocks-sparse-index)，因此不會複寫收據項目。我們也不需要對應所有的屬性，只需要包括屬性的子集。下方影像顯示了 `GSI-1` 的結構描述，它提供了應用程式傳送提醒電子郵件所需的資訊。

![包含電子郵件地址等詳細資訊的 GSI-1 結構描述，應用程式需要傳送提醒電子郵件。](http://docs.aws.amazon.com/zh_tw/amazondynamodb/latest/developerguide/images/DataModeling/ReoccurringPayments-4-Step3.png)


**步驟 4：位址存取模式 5 (`getDuePaymentsByDate`)**

應用程式會分批處理當天的付款，採取與處理提醒相同的方式。我們會在此步驟中新增 `GSI-2`，它會使用 `NextPaymentDate` 作為 GSI 分割區索引鍵。我們不需要複寫所有項目。這個 GSI 是稀疏索引，因為不會複寫收據項目。下方影像顯示了 `GSI-2` 的結構描述。

![GSI-2 結構描述包含處理付款的詳細資訊。NextPaymentDate 是 GSI-2 的分割區索引鍵。](http://docs.aws.amazon.com/zh_tw/amazondynamodb/latest/developerguide/images/DataModeling/ReoccurringPayments-5-Step4.png)


**步驟 5：位址存取模式 6 (`getSubscriptionsByAccount`) 和 7 (`getReceiptsByAccount`)**

應用程式會在基礎資料表上使用[查詢](Query.md)來鎖定帳戶識別碼 (`PK`) 為目標，以擷取帳戶的所有訂閱，並使用範圍運算子取得 `SK` 開頭為「SUB\#」的所有項目。應用程式也可以使用相同的查詢結構來擷取所有收據，方法是使用範圍運算子來取得 `SK` 開頭為「REC\#」的所有項目。這樣就能滿足存取模式 6 (`getSubscriptionsByAccount`) 和 7 (`getReceiptsByAccount`)。應用程式使用這些存取模式讓使用者看見過去六個月內自己目前的訂閱及過去的收據。在此步驟中，我們不會變更資料表結構描述，而且可以在下面看到我們如何單獨鎖定存取模式 6 (`getSubscriptionsByAccount`) 中的訂閱項目。

![基礎資料表的查詢操作結果。其中會顯示特定帳戶的訂閱。](http://docs.aws.amazon.com/zh_tw/amazondynamodb/latest/developerguide/images/DataModeling/ReoccurringPayments-6-Step5.png)


下表摘要整理了所有存取模式，以及結構描述設計處理這些模式的方式：


| 存取模式 | 基礎資料表/GSI/LSI | 作業 | 分割區索引鍵值 | 排序索引鍵值 | 
| --- | --- | --- | --- | --- | 
| createSubscription | 基礎資料表 | PutItem | ACC\#account\_id | SUB\#<SUBID>\#SKU<SKUID> | 
| createReceipt | 基礎資料表 | PutItem | ACC\#account\_id | REC\#<RecieptDate>\#SKU<SKUID> | 
| updateSubscription | 基礎資料表 | UpdateItem | ACC\#account\_id | SUB\#<SUBID>\#SKU<SKUID> | 
| getDueRemindersByDate | GSI-1 | Query | <NextReminderDate> |  | 
| getDuePaymentsByDate | GSI-2 | Query | <NextPaymentDate> |  | 
| getSubscriptionsByAccount | 基礎資料表 | Query | ACC\#account\_id | SK begins\_with “SUB\#” | 
| getReceiptsByAccount | 基礎資料表 | Query | ACC\#account\_id | SK begins\_with “REC\#” | 

## 週期性付款最終結構描述
<a name="data-modeling-schema-recurring-payments-final-schema"></a>

以下是最終結構描述設計。若要將此結構描述設計下載為 JSON 檔案，請參閱 GitHub 上的 [DynamoDB 範例](https://github.com/aws-samples/aws-dynamodb-examples/blob/master/schema_design/SchemaExamples/ReocurringPayments/ReocurringPaymentsSchema.json)。

**基礎資料表**

![顯示帳戶資訊及其訂閱和收據詳細資訊的基礎資料表設計。](http://docs.aws.amazon.com/zh_tw/amazondynamodb/latest/developerguide/images/DataModeling/ReoccurringPayments-7-Base.png)


**GSI-1**

![包含電子郵件地址和 NextPaymentDate 等訂閱詳細資訊的 GSI-1 結構描述。](http://docs.aws.amazon.com/zh_tw/amazondynamodb/latest/developerguide/images/DataModeling/ReoccurringPayments-8-GSI1.png)


**GSI-2**

![包含 PaymentAmount 和 PaymentDay 等付款詳細資訊的 GSI-2 結構描述。](http://docs.aws.amazon.com/zh_tw/amazondynamodb/latest/developerguide/images/DataModeling/ReoccurringPayments-9-GSI2.png)


## 使用 NoSQL Workbench 與此結構描述設計
<a name="data-modeling-schema-recurring-payments-nosql"></a>

您可以將此最終結構描述匯入 [NoSQL Workbench](workbench.md)，這是為 DynamoDB 提供資料建模、資料視覺化，和查詢開發功能的視覺化工具，以進一步探索和編輯新專案。請依照下列步驟以開始使用：

1. 下載 NoSQL Workbench。如需詳細資訊，請參閱[下載 DynamoDB 專用 NoSQL Workbench](workbench.settingup.md)。

1. 下載上面列出的 JSON 結構描述檔案，該檔案已經是 NoSQL Workbench 模型格式。

1. 將 JSON 結構描述檔案匯入到 NoSQL Workbench。如需詳細資訊，請參閱[匯入現有的資料模型](workbench.Modeler.ImportExisting.md)。

1. 一旦您匯入到 NOSQL Workbench 後，便可以編輯資料模型。如需詳細資訊，請參閱[編輯現有的資料模型](workbench.Modeler.Edit.md)。