我正在从一个 API 请求数据,该 API 需要基于名为“cursor”的自定义标头的分页记录。每次调用只能检索 100 条记录,因此我创建了一个 while 循环来执行。循环起作用......直到它不起作用为止。一旦所有记录都被分页,标题就会被删除,我的程序会出现错误:
“未找到给定的标头。”
我的数据库中不会发生任何插入操作,因为请求会一直流式传输,直到全部分页为止。
我该如何处理这个问题以使程序成功完成?
拨打的电话是:
var products = await ProcessProducts(userAndPasswordToken, BaseUrl);
被调用的任务:
private static async Task<List<Products>> ProcessProducts(string userAndPasswordToken, string BaseUrl)
{
//Construct urls
string RequestPath = string.Format("food/products");
string FullUrl = string.Format("{0}{1}", BaseUrl, RequestPath);
string CursorPath = string.Format("");
//Use GetAsync instead of GetStreamAsync unless it's mandatory for your codebase.
var response = await client.GetAsync(FullUrl);
//Extract string from the response right away
var content = await response.Content.ReadAsStringAsync();
//Pass it in instead of Steam.
var Products = Newtonsoft.Json.JsonConvert.DeserializeObject<List<Products>>(content);
//Place the header key mapped with the cursor value.
IEnumerable<string> values = response.Headers.GetValues("cursor");
// string cursor = null;
string cursor = "4146";
// cursor = values?.FirstOrDefault();
do
{
CursorPath = $"?cursor={cursor}";
if (cursor == null) CursorPath = string.Format("");
FullUrl = string.Format("{0}{1}{2}", BaseUrl, RequestPath, CursorPath);
response = await client.GetAsync(FullUrl);
content = await response.Content.ReadAsStringAsync();
var nextProducts = Newtonsoft.Json.JsonConvert.DeserializeObject<List<Products>>(content);
// add Products in the next page.
Products.AddRange(nextProducts);
values = response.Headers.GetValues("cursor");
cursor = values?.FirstOrDefault();
System.Threading.Thread.Sleep(1000);
Console.WriteLine(FullUrl);
Console.WriteLine(response);
} while (cursor != null);
return Products;
}
插入是通过 SQL 存储过程进行的:
using (SqlConnection conn = new SqlConnection(lConnString))
{
conn.Open();
using (TransactionScope ts = new TransactionScope())
{
foreach (var repo in products)
{
SqlCommand cmdIns = new SqlCommand("usp_insert_Products", conn);
cmdIns.CommandType = CommandType.StoredProcedure;
cmdIns.Parameters.AddWithValue("@ProductId", repo.ProductId.ToString() ?? (object)DBNull.Value);
cmdIns.Parameters.AddWithValue("@ProductDetailId", repo.ProductDetailId.ToString() ?? (object)DBNull.Value);
cmdIns.ExecuteNonQuery();
}
ts.Complete();
}
conn.Close();
我提供的示例代码有一个完全不同的方法,如果我无法让我的代码正常运行,我正处于转向的边缘:
示例代码
// Paging is handled by making a request and then making
// follow up requests as long as a "cursor" is returned.
string cursor = null;
do
{
var query = HttpUtility.ParseQueryString("");
query["locationId"] = "1";
query["businessDate"] = "2019-04-30";
if (cursor != null) query["cursor"] = cursor;
var fullUrl = $"{url}/{endpoint}?{query}";
_testOutputHelper.WriteLine(fullUrl);
var json = client.DownloadString(fullUrl);
results.AddRange(
JsonConvert.DeserializeObject<List<Check>>(json));
cursor = client.ResponseHeaders["cursor"];
} while (cursor != null);
}