I have answered to a question on Stackoverflow where Andy struggled to cancel a Stream copy to file operation using the Universal .NET Framework:
Apparently, cancelling the cts CancelOperation token had not the expected behavior.
await httpResponseContent.Content.WriteToStreamAsync(streamToWrite.AsOutputStream()).AsTask(cts, progressDownload);
So I suggested to do it another way using a chunks-based stream reading and writing. So I provided this code which has been tested and accepted:
async Task Download(Uri uriToWork, CancellationToken cts, IProgress<int> progress) {
using(HttpClient httpClient = new HttpClient()) {
var chunkSize = 1024;
var buffer = new byte[chunkSize];
int count = 0;
string fileToWrite = Path.GetTempFileName();
using(var inputStream = await httpClient.GetInputStreamAsync(uriToWork)) {
using(var streamToRead = inputStream.AsStreamForRead()) {
using(Stream streamToWrite = File.OpenWrite(fileToWrite)) {
int size;
while((size = await streamToRead.ReadAsync(buffer, 0, chunkSize, cts).ConfigureAwait(false)) > 0) {
count += size;
await Dispatcher.RunAsync(CoreDispatcherPriority.Normal, () => progress.Report(count));
// progress.Report(count);
await streamToWrite.WriteAsync(buffer, 0, size, cts).ConfigureAwait(false);
}
}
}
}
}
}
Although it works, I am not that familiar with the Universal .NET and I am not sure this code is optimal. A casual .NET solution would be shorter.
I am very sensitive about code quality and canonicity and I wonder whether some parts of this code are redundant and can be removed, and I would like it to match the most "Universal .NET" oriented as possible.