[Azure] C# + Microsoft.Azure.Cosmos.Table v1+ Azure Storage Table - 使用 ExecuteQuerySegmented 取得資料

2021-01-13

前幾篇文章,我都是用 CloudTable.ExecuteQuery 來查詢,但是這用得好好的為何 SDK 有出一個 ExecuteQuerySegmented ,原因是因為,如果當你一次要執行的查詢非常大量的時候,假設撈回來是兩萬,但是當 Azure Table 那邊準備兩萬資料傳輸回來,這容易造成 timeout ,所以這時候就是要用 ExecuteQuerySegmented ,但是請記得她一次回來最大的量就是 1000




前置作業 首先你要 安裝 nuget https://www.nuget.org/packages/Microsoft.Azure.Cosmos.Table ,這邊我撰寫案例是用 .net core 3.1;在 Azure Portal  開一個 儲存體帳戶,並且在左側的存取金鑰中拿到 Connection String.



之前文章我把一萬筆資料寫入 分別 Age 1~ 10,000 ,這案例我是撈出 >100 && <=2000 的資料,分別印出來到底撈取了幾次(多少分頁)跟總筆數,案例我是每 500  做一次撈取。

var tableClient = CloudStorageAccount.Parse(_ConnectionString).CreateCloudTableClient(new TableClientConfiguration()); var table = tableClient.GetTableReference("table1"); string pkFilter = new TableQuery<User>() .Where(TableQuery.GenerateFilterCondition("PartitionKey", QueryComparisons.Equal, "CLASSA")).FilterString; string ageGreaterFilter = new TableQuery<User>() .Where(TableQuery.GenerateFilterConditionForInt("Age", QueryComparisons.GreaterThan, 100)).FilterString; string ageLessequalFilter = new TableQuery<User>() .Where(TableQuery.GenerateFilterConditionForInt("Age", QueryComparisons.LessThanOrEqual, 2000)).FilterString; string combineAgeFilter = TableQuery.CombineFilters(ageGreaterFilter, TableOperators.And, ageLessequalFilter); string combinePKAndAgeFilter = TableQuery.CombineFilters(pkFilter, TableOperators.And, combineAgeFilter); TableQuery<User> query = new TableQuery<User>().Where(combinePKAndAgeFilter); //只選擇固定欄位回來 query.SelectColumns = new List<string>(); query.SelectColumns.Add("Age"); query.OrderByDesc("Age"); //Max:1000 //超過 1000 會有 Exception. //One of the request inputs is not valid. query.TakeCount = 500; TableContinuationToken token = null; //紀錄資料總數 var allCount = 0; //記錄分頁數 var segmentCount = 0; do { TableQuerySegment<User> segment = table.ExecuteQuerySegmented(query, token); if (segment.Results.Count > 0) { segmentCount++; Console.WriteLine(); Console.WriteLine("Segment Page {0}", segmentCount); } token = segment.ContinuationToken; foreach (User entity in segment) { Console.WriteLine("\t Data: {0},{1},Age:{2}", entity.PartitionKey, entity.RowKey, entity.Age); allCount++; } Console.WriteLine(); } while (token != null); Console.WriteLine("Segment Page Count:" + segmentCount); Console.WriteLine("All Data Count:" + allCount);


Result:
Segment Page Count:4
All Data Count:1900


這中間只有一個比較特別的觀念就是當 TableContinuationToken 不是 null 就是一直做下去,至於能不能在 Azure Table 那邊先排列好呢 ? 當然是 不支援 !! ,請使用 CosmosDB 吧 :)


當麻許的碎念筆記 2014 | Donma Hsu Design.