0

I have created a Blazor Server Project in .NET6. In my project I need to upload files mostly exe files to the azure container. Here is the code:

// Get the file from file picker
var file = e.Files.FirstOrDefault();    

BlobServiceClient blobServiceClient = new BlobServiceClient(connectionString);

// Get or create the container in azure
BlobContainerClient blobContainer = blobServiceClient.GetBlobContainerClient("uploadfiles");
var containerResponse = await blobContainer.CreateIfNotExistsAsync();

if (containerResponse != null && containerResponse.GetRawResponse().Status == 201)
{
    await blobContainer.SetAccessPolicyAsync(Azure.Storage.Blobs.Models.PublicAccessType.Blob);
}

// Create the blob in container
BlobClient blobClient = blobContainer.GetBlobClient(file.Name);

//Read file contents
using var stream = file.OpenReadStream();

using (var memoryStream = new MemoryStream())
{
    await stream.CopyToAsync(memoryStream);
    byte[] fileBytes = memoryStream.ToArray();
    
    BinaryData uploadData = new BinaryData(fileBytes);

    Response<BlobContentInfo> uploadResponse = await blobClient.UploadAsync(uploadData, true);
}

Now the problem is, I can upload small sized file to the container. But when comes to large file, for example 5 MB, I can't upload the file to the container. It says the below error:

Supplied file with size 5275768 bytes exceeds the maximum of 512000 bytes.

Now one solution could be making smaller chunks. But in that case I am not sure the file will be corrupted or not.

Can anyone help me by providing any solution.

mnu-nasir
  • 1,642
  • 5
  • 30
  • 62

2 Answers2

2

I have followed the below articles and post in the stackoverflow.

https://www.andrewhoefling.com/Blog/Post/uploading-large-files-to-azure-blob-storage-in-c-sharp

https://github.com/Azure-Developer-Support/CodeRepository/blob/master/Storage/Dotnet/UploadBlockBlob.cs

https://stackoverflow.com/a/58741171/765766

Finally wrote the code which solved my problem. Here is the full code:

var container = new BlobContainerClient(connectionString, "uploadfiles");
var createResponse = await container.CreateIfNotExistsAsync();

if (createResponse != null && createResponse.GetRawResponse().Status == 201)
{
    await container.SetAccessPolicyAsync(PublicAccessType.Blob);
}

BlockBlobClient blobClient = container.GetBlockBlobClient(file.Name);
var deleteResponse = await blobClient.DeleteIfExistsAsync(DeleteSnapshotsOption.IncludeSnapshots);

byte[] fileBytes;

// Read file to memory stream
using var stream = file.OpenReadStream(long.MaxValue);
using (var memoryStream = new MemoryStream())
{
    await stream.CopyToAsync(memoryStream);
    fileBytes = memoryStream.ToArray();
}

// Prepare chunks of the file
const int pageSizeInBytes = 1000000;
long prevLastByte = 0;
long bytesRemain = file.Size;
int blockNumber = 0;

HashSet<string> blocklist = new HashSet<string>();

do
{
    blockNumber++;

    long bytesToCopy = Math.Min(bytesRemain, pageSizeInBytes);
    byte[] bytesToSend = new byte[bytesToCopy];

    Array.Copy(fileBytes, prevLastByte, bytesToSend, 0, bytesToCopy);
    prevLastByte += bytesToCopy;
    bytesRemain -= bytesToCopy;

    string blockId = $"{blockNumber:0000000}";
    string base64BlockId = Convert.ToBase64String(Encoding.UTF8.GetBytes(blockId));
    
    var stageResponse = blobClient.StageBlock(base64BlockId, new MemoryStream(bytesToSend));
    var responseInfo = stageResponse.GetRawResponse();

    blocklist.Add(base64BlockId);           
}
while (bytesRemain > 0);

var contentResponse = blobClient.CommitBlockList(blocklist);
mnu-nasir
  • 1,642
  • 5
  • 30
  • 62
1

I came across a process of putting the file into pieces and uploading them as blocks.

Found it here https://stackoverflow.com/a/58741171/765766

Sebastian
  • 64
  • 1
  • 7