練習 - 建立新項目
回想一下,您可以使用適用於 .NET 的 Azure Cosmos DB SDK 在容器內建立項目。 針對此專案,產品容器會同時包含每個類別的個別產品項目以及特殊類別項目。 您想要在此應用程式中處理兩個案例:
- 如果類別是空的,只要個別建立該類別的項目即可。 沒有要建立的相關產品項目。
- 不過,如果類別包含相關產品,您想要同時建立類別專案和相關的產品專案。
現在,您有兩個主要需求:
- 個別建立項目做為單一作業
- 使用交易式批次建立多個相關項目
完成此練習之後,您的專案將會有邏輯,以個別或批次方式在容器中建立項目。
將個別項目新增至容器
在 Azure Cosmos DB 中,您可以建立、取代項目或將其更新插入容器。 建立項目需要項目具有唯一識別碼。 取代項目需要項目已經存在。 更新插入是兩全其美的方式,將檢查唯一識別碼,然後取代或建立項目。 對於此項目,您希望能夠多次執行應用程式而不會出錯,進而使更新插入成為明確的選擇。 針對我們的第一個項目,我們會建立沒有任何相關聯產品的類別。 在這裡,您會使用手動建立的類別來實作單一更新插入作業。
再次開啟 Program.cs 檔案。
使用下列值建立名為
goggles
的新 Category 執行個體:屬性 值 id ef7fa0f1-0e9d-4435-aaaf-a778179a94ad
categoryId gear-snow-goggles
Category goggles = new( Id: "ef7fa0f1-0e9d-4435-aaaf-a778179a94ad", CategoryId: "gear-snow-goggles" );
使用與您稍早建立 Category 執行個體
categoryId
屬性相同的值,建立新的 PartitionKey 執行個體。PartitionKey gogglesKey = new("gear-snow-goggles");
使用 UpsertItemAsync 方法來建立或取代項目,剛項目會傳入要讓項目建立的物件以及分割區索引鍵值。
Category result = await container.UpsertItemAsync(goggles, gogglesKey);
將
result
的各種屬性列印到主控台,包括:項目的唯一識別碼和項目類型。Console.WriteLine($"[New item created]:\t{result.Id}\t(Type: {result.Type})");
使用下列值建立名為
helmets
的新 Category 執行個體:屬性 值 id 91f79374-8611-4505-9c28-3bbbf1aa7df7
categoryId gear-climb-helmets
Category helmets = new( Id: "91f79374-8611-4505-9c28-3bbbf1aa7df7", CategoryId: "gear-climb-helmets" );
使用與您稍早建立 Category 執行個體
categoryId
屬性相同的值,建立新的 PartitionKey 執行個體。PartitionKey helmetsKey = new("gear-climb-helmets");
使用 UpsertItemAsync 方法來建立或取代項目。 傳入要讓項目建立的物件以及分割區索引鍵值。 傳回類型為 ItemResponse<T> 的物件。
ItemResponse<Category> response = await container.UpsertItemAsync(helmets, helmetsKey);
將各種
response
屬性列印至主控台,包括:基礎項目的唯一識別碼、基礎項目的類型,以及 RU 中的要求費用。Console.WriteLine($"[New item created]:\t{response.Resource.Id}\t(Type: {response.Resource.Type})\t(RUs: {response.RequestCharge})");
儲存 Program.cs 檔案。
將多個作業實作為交易式批次
現在,請考慮您想要建立多個產品以及類別的情節。 如果產品已建立,但類別不存在,則這些產品幾乎沒有用。 建立多個項目是一種情況,您可以使用交易將多個「點」作業組合在一起,使其全都成功或失敗為單一統合單位。 回到我們的案例,我們需要為具有一些帳篷產品的室外帳篷建立類別。 我們已經有一個沒有任何產品項目的單一類別項目。 以下是我們最終應得到的結果:
在本節中,我們會建立交易式批次,以一起建立 tents
類別和相關產品。
在 Program.cs 中,使用下列值建立名為
tents
的新 Category 執行個體:屬性 值 id 5df21ec5-813c-423e-9ee9-1a2aaead0be4
categoryId gear-camp-tents
Category tents = new( Id: "5df21ec5-813c-423e-9ee9-1a2aaead0be4", CategoryId: "gear-camp-tents" );
使用這些值建立 Product 類型的四個執行個體。
屬性 cirroa
kuloar
mammatin
nimbolo
Id e8dddee4-9f43-4d15-9b08-0d7f36adcac8
e6f87b8d-8cd7-4ade-a005-14d3e2fbd1aa
f7653468-c4b8-47c9-97ff-451ee55f4fd5
6e3b7275-57d4-4418-914d-14d1baca0979
CategoryId gear-camp-tents
gear-camp-tents
gear-camp-tents
gear-camp-tents
名稱 Cirroa Tent
Kuloar Tent
Mammatin Tent
Nimbolo Tent
價格 490.00
530.00
0.00
330.00
Archived false
false
true
false
數量 15
8
0
35
Product cirroa = new( Id: "e8dddee4-9f43-4d15-9b08-0d7f36adcac8", CategoryId: "gear-camp-tents" ){ Name = "Cirroa Tent", Price = 490.00m, Archived = false, Quantity = 15 };
Product kuloar = new( Id: "e6f87b8d-8cd7-4ade-a005-14d3e2fbd1aa", CategoryId: "gear-camp-tents" ){ Name = "Kuloar Tent", Price = 530.00m, Archived = false, Quantity = 8 };
Product mammatin = new( Id: "f7653468-c4b8-47c9-97ff-451ee55f4fd5", CategoryId: "gear-camp-tents" ){ Name = "Mammatin Tent", Price = 0.00m, Archived = true, Quantity = 0 };
Product nimbolo = new( Id: "6e3b7275-57d4-4418-914d-14d1baca0979", CategoryId: "gear-camp-tents" ){ Name = "Nimbolo Tent", Price = 330.00m, Archived = false, Quantity = 35 };
現在,使用
gear-camp-tents
值建立新的 PartitionKey 執行個體。PartitionKey tentsKey = new("gear-camp-tents");
使用
gear-camp-tents
方法,建立範圍設定為 CreateTransactionalBatch(PartitionKey) 分割區索引鍵值的新交易批次。 使用 Fluent 語法,新增五個更新插入作業,以在類別和所有相關產品的容器中建立我們需要的項目。TransactionalBatch batch = container.CreateTransactionalBatch(tentsKey) .UpsertItem<Category>(tents) .UpsertItem<Product>(cirroa) .UpsertItem<Product>(kuloar) .UpsertItem<Product>(mammatin) .UpsertItem<Product>(nimbolo);
將訊息輸出至主控台,指出我們正在啟動批次作業。
Console.WriteLine("[Batch started]");
使用
TransactionalBatch.ExecuteAsync
方法來執行批次並傳回特殊回應類型。using TransactionalBatchResponse batchResponse = await batch.ExecuteAsync();
使用 for 迴圈,逐一查看回應中的所有項目。 首先,使用您的
Item
基底類別作為泛型,將每個項目轉換成類型TransactionalBatchOperationResult
。 然後,列印回應物件的唯一識別碼和類型。for (int i = 0; i < batchResponse.Count; i++) { TransactionalBatchOperationResult<Item> batchResult = batchResponse.GetOperationResultAtIndex<Item>(i); Console.WriteLine($"[New item created]:\t{batchResult.Resource.Id}\t(Type: {batchResult.Resource.Type})"); }
將另一則訊息輸出至主控台,指出批次已完成。 在此訊息中包含整個批次的要求費用。
Console.WriteLine($"[Batch completed]:\t(RUs: {batchResponse.RequestCharge})");
儲存 Program.cs 檔案。
檢查您的工作
您的應用程式現在會建立多個項目,並設計成具有足夠的復原能力,以便多次執行而不會造成例外狀況。 在這裡,您會執行應用程式,並檢查六個新建立項目的唯一識別碼輸出。
在終端中執行 .NET 應用程式:
dotnet run
觀察執行應用程式的輸出。 輸出應該會與此處範例相符:
... [New item created]: ef7fa0f1-0e9d-4435-aaaf-a778179a94ad (Type: Category) [New item created]: 91f79374-8611-4505-9c28-3bbbf1aa7df7 (Type: Category) (RUs: 10.29) [Batch started] [New item created]: 5df21ec5-813c-423e-9ee9-1a2aaead0be4 (Type: Category) [New item created]: e8dddee4-9f43-4d15-9b08-0d7f36adcac8 (Type: Product) [New item created]: e6f87b8d-8cd7-4ade-a005-14d3e2fbd1aa (Type: Product) [New item created]: f7653468-c4b8-47c9-97ff-451ee55f4fd5 (Type: Product) [New item created]: 6e3b7275-57d4-4418-914d-14d1baca0979 (Type: Product) [Batch completed]: (RUs: 36.76)
提示
此範例輸出中顯示的 RU 可能會因您的輸出而有所不同。