Copying/Moving a file in Azure blob storage

 I was looking through the posts on weblogs.asp.net a few days ago and spotted this one, Corrupted File when using DownloadToStream in Azure blob, in which the author does what I do and realises their silly mistake! The bit I saw that did make me question what was being done was (emphasis mine):

using (MemoryStream memoryStream = new MemoryStream())
{
    srcBlob.DownloadToStream(memoryStream);
    memoryStream.Position = 0;
    destBlob = container.GetBlockBlobReference(destBlob.Name);
    destBlob.UploadFromStream(memoryStream);
}

This reminded me of someone I worked with who, and I genuinely have no idea why they had this habit, would on occasion have cause to copy a file from one machine to another within the servers in our datacentre. For reasons only they knew, they'd perform the following steps:

  1. Download the file from Server X to their local machine (usually the desktop!)
  2. Upload the file to Server Y from their local machine

Can you perhaps see where I'm going with this? Servers in the datacentre had a nice fast, local gigabit ethernet connection between them, whereas the connection between the datacentre and the PC was a VPN over an ADSL link shared with other users in the same office. This. was. very. very. slow.

Just like it would make sense to copy the file directly from Server X to Server Y, it makes sense (surely!) to keep the file move operation (which essentially is composed, as in the original blog post, of a Copy and a Delete) entirely within Azure, or as entirely within Azure as possible. So, without further ado, here's my heavily decomposed and completley error-checking free code for moving a file in Azure blob storage, without having the bytes "come down the wire" onto the computer running the code that's initiated the copy/move (requires the WindowsAzure.Storage NuGet package):

static void Main(string[] args)
{
    var cloudStorageAccount = CloudStorageAccount.Parse(@"<connection_string_here>");

    var sourceContainer = "container1";
    var destinationContainer = "container2";
    var sourceFilename = "picture.jpg";
    var destinationFilename = "picture_in_container_2.jpg";

    var copyResult = CopyBlob(cloudStorageAccount, sourceContainer, destinationContainer, sourceFilename, destinationFilename);

    if (copyResult.Status == CopyStatus.Success)
    {
        DeleteBlob(cloudStorageAccount, sourceContainer, sourceFilename);
    }
}

private static CopyState CopyBlob(CloudStorageAccount cloudStorageAccount, string sourceContainerName, string destinationContainerName, string sourceFileName, string destinationFileName)
{
    var blobStorageClient = cloudStorageAccount.CreateCloudBlobClient();

    var sourceContainer = blobStorageClient.GetContainerReference(sourceContainerName);
    var destinationContainer = blobStorageClient.GetContainerReference(destinationContainerName);

    var sourceBlob = sourceContainer.GetBlobReference(sourceFileName);

    var destinationBlob = destinationContainer.GetBlobReference(destinationFileName);

    var result = destinationBlob.StartCopy(sourceBlob.Uri);

    var copyResult = destinationBlob.CopyState;

    return copyResult;
}

private static void DeleteBlob(CloudStorageAccount cloudStorageAccount, string containerName, string blobFileName)
{
    var blobStorageClient = cloudStorageAccount.CreateCloudBlobClient();
    var container = blobStorageClient.GetContainerReference(containerName);
    var blob = container.GetBlobReference(blobFileName);
    blob.Delete();
}

About Rob

I've been interested in computing since the day my Dad purchased his first business PC (an Amstrad PC 1640 for anyone interested) which introduced me to MS-DOS batch programming and BASIC.

My skillset has matured somewhat since then, which you'll probably see from the posts here. You can read a bit more about me on the about page of the site, or check out some of the other posts on my areas of interest.

No Comments

Add a Comment