Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

ReadAsync get data from buffer

Tags:

c#

I've been banging my head around this for some while (and know it's something silly).

I'm downloading files with a ProgressBar which shows fine, but how do I get the data from the ReadAsync Stream to save?

public static readonly int BufferSize = 4096;
int receivedBytes = 0;
int totalBytes = 0;
WebClient client = new WebClient();
byte[] result;

using (var stream = await client.OpenReadTaskAsync(urlToDownload))
{
  byte[] buffer = new byte[BufferSize];
  totalBytes = Int32.Parse(client.ResponseHeaders[HttpResponseHeader.ContentLength]);

  for (;;)
  {
    result = new byte[stream.Length];
    int bytesRead = await stream.ReadAsync(buffer, 0, buffer.Length);
    if (bytesRead == 0)
    {
      await Task.Yield();
      break;
    }

    receivedBytes += bytesRead;
    if (progessReporter != null)
    {
      DownloadBytesProgress args = 
                 new DownloadBytesProgress(urlToDownload, receivedBytes, totalBytes);
      progessReporter.Report(args);
    }
  }
}

I was trying via the result var, but that is obviously wrong. I'd appreciate any pointers on this long Sunday afternoon.

like image 299
John Sourcer Avatar asked Aug 03 '14 13:08

John Sourcer


2 Answers

The content that was downloaded is inside your byte[] buffer variable:

int bytesRead = await stream.ReadAsync(buffer, 0, buffer.Length);

From Stream.ReadAsync:

buffer:

Type: System.Byte[] The buffer to write the data into.

You never use your result variable at all. Not sure why its there.

Edit

So the problem is how to read the full content of your stream. You can do the following:

public static readonly int BufferSize = 4096;
int receivedBytes = 0;
WebClient client = new WebClient();

using (var stream = await client.OpenReadTaskAsync(urlToDownload))
using (MemoryStream ms = new MemoryStream())
{
    var buffer = new byte[BufferSize];
    int read = 0;
    totalBytes = Int32.Parse(client.ResponseHeaders[HttpResponseHeader.ContentLength]);

    while ((read = await stream.ReadAsync(buffer, 0, buffer.Length)) > 0)
    {
        ms.Write(buffer, 0, read);

        receivedBytes += read;
        if (progessReporter != null)
        {
           DownloadBytesProgress args = 
             new DownloadBytesProgress(urlToDownload, receivedBytes, totalBytes);

           progessReporter.Report(args);
         }
    }
    return ms.ToArray();
  }
}
like image 87
Yuval Itzchakov Avatar answered Oct 14 '22 13:10

Yuval Itzchakov


The data you read should be in the buffer array. Actually the beginning bytesRead bytes of the array. Check ReadAsync method on MSDN.

like image 42
Gildor Avatar answered Oct 14 '22 14:10

Gildor