![](/img/trans.png)
[英]How to write an IAsyncEnumerable function so that cleanup code always executes
[英]How to use SqlBulkCopy to write an IAsyncEnumerable
我有以下方法返回IAsyncEnumerable<T>
:
async IAsyncEnumerable<T> RunReport()
{
var handler = new HttpClientHandler();
var client = new HttpClient(handler);
client.BaseAddress = new Uri("");
client.DefaultRequestHeaders.Accept.Clear();
client.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json"));
var settings = new JsonSerializerSettings();
var jsonFormatter = new JsonMediaTypeFormatter() { SerializerSettings = settings };
var requestMessage = new HttpRequestMessage(HttpMethod.Get, "api/controler");
var response = await client.SendAsync(requestMessage);
response.EnsureSuccessStatusCode();
using (var stream = await response.Content.ReadAsStreamAsync())
{
using (var reader = new StreamReader(stream))
{
while (!reader.EndOfStream)
{
var linesJson = await reader.ReadLineAsync();
var line = JsonConvert.DeserializeObject<List<T>>(linesJson, jsonFormatter.SerializerSettings);
foreach (var line in lines)
yield return line;
}
}
}
}
我想使用SqlBulkCopy
的WriteToServerAsync
方法將該結果流傳輸到數據庫,但無法弄清楚如何將其轉換為IDataReader
或WriteToServerAsync
的重載列表中的任何其他類型。
如果性能合理,我願意使用批量復制以外的其他東西。
使用此處的示例,我想出了一個 IDataReader,它采用 IAsyncEnumerable,並實現接口的適當部分。
public class GenericDataReader<T> : IDataReader where T : class
{
private readonly IAsyncEnumerator<T> _asychEnumerator;
private readonly List<FieldInfo> _fields = new List<FieldInfo>();
public GenericDataReader(IAsyncEnumerable<T> asyncEnumerable)
{
_asychEnumerator = asyncEnumerable.GetAsyncEnumerator();
foreach (FieldInfo fieldinfo in typeof(T).GetFields(BindingFlags.Instance | BindingFlags.Public))
{
_fields.Add(fieldinfo);
}
}
public int FieldCount => _fields.Count;
public void Dispose() { Close(); }
public bool Read()
{
return _asycEnumerator.MoveNextAsync().Result;
}
public async void Close(){ await _asychEnumerator.DisposeAsync(); }
public Type GetFieldType(int i){ return _fields[i].FieldType; }
public string GetName(int i) { return _fields[i].Name; }
public object GetValue(int i){ return _fields[i].GetValue(_asychEnumerator.Current); }
}
我仍在研究這個例子,但對 Read() 方法的實現有點了解。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.