Anne
Anne

Reputation: 101

Streaming a blob from Azure storage - Cannot access a closed Stream

I am using asp.net webforms.

I have pdfs in Azure storage that I need to process. I am using PDFJet library in order to do that.

I would like to stream the pdf without downloading it as I have to process a large number of pdfs.

I am using the following function to stream the pdfs from Azure:

public MemoryStream DownloadToMemoryStream(DTO.BlobUpload b)
{
    CloudStorageAccount storageAccount = Conn.SNString(b.OrgID);
    CloudBlobClient blobClient = storageAccount.CreateCloudBlobClient();
    CloudBlobContainer container = blobClient.GetContainerReference(b.Container);
    CloudBlockBlob blob = container.GetBlockBlobReference(b.FileName);
    var sasToken = blob.GetSharedAccessSignature(new SharedAccessBlobPolicy()
    {
        Permissions = SharedAccessBlobPermissions.Read,
        SharedAccessExpiryTime = DateTime.UtcNow.AddMinutes(10),//assuming the blob can be downloaded in 10 miinutes
    }, new SharedAccessBlobHeaders()
    {
        ContentDisposition = "attachment; filename=file-name"
    });
    using (MemoryStream ms = new MemoryStream())
    {
        blob.DownloadToStream(ms);
        return ms;
    }

}

And in the aspx.cs page the following code to read the pdf stream:

BufferedStream pdfScript = new BufferedStream(new FileStream(ScriptPath + Script, FileMode.Open));

SortedDictionary<Int32, PDFobj> objects = pdfFinalScript.Read(pdfScript);

However I get the error message: Cannot access a closed Stream

If I download the pdf to disk, this is the function I use, this work but it is not practical:

blockBlob.DownloadToFile(b.LocalPath + b.FileName, FileMode.Create);

BufferedStream pdfScript = new BufferedStream(new FileStream(ScriptPath + Script, FileMode.Open));

Thank you for your help.

Upvotes: 2

Views: 2713

Answers (1)

Tom Sun
Tom Sun

Reputation: 24549

Cannot access a closed Stream

According to error information, it indicates that you need to reset stream position.

Please have a try to reset the stream position before return it. blob.DownloadToStream(ms); ms.Position = 0; //add this code return ms;

Updated:

ms was closed if out of using section. So please have a try to use the following code.

MemoryStream stream = new MemoryStream();
using (MemoryStream ms = new MemoryStream())
{
  blob.DownloadToStream(ms);
  ms.Position = 0
  ms.CopyTo(stream);
  stream.Position = 0;
  return stream;
}

Upvotes: 6

Related Questions