Uploading An Object As JSON To Windows Azure Blob Storage

June 24, 2012 — 15 Comments

[2015/05/13] The code in this post has been updated to work with the “Windows Azure Storage 4.4.0-preview” NuGet package

Applying the ModelCommand pattern I was able to create a command that enables us to upload a serializable object as JSON and store it in an existing Blob Container.

Working with Json.NET, which can be installed using NuGet, we are able to serialize objects and send them to the Windows Azure Blob Storage. The UploadToBlogStorageAsJson ModelCommand was created specifically to simplify this process.

To upload JSON to a Blob Storage container we first have to get the Contrainer Reference using the container name provided by the constructor parameters. Then from the Container Reference we get the Blob Reference. We then prepare the Blob Reference with the provided Metadata and Properties before uploading the JSON to Windows Azure Blob Storage.

public class UploadToBlobStorageAsJson : IModelCommand<CloudStorageAccount>
{
    private const string CONTENT_TYPE = "application/json";

    private readonly object obj;
    private readonly string containerPath;
    private readonly string blobAddressUri;
    private readonly Dictionary<string, string> metadata;

    public UploadToBlobStorageAsJson(object obj,
                                        string containerPath,
                                        string blobAddressUri,
                                        Dictionary<string, string> metadata)
    {
        this.obj = obj;
        this.containerPath = containerPath;
        this.blobAddressUri = blobAddressUri;
        this.metadata = metadata;
    }

    public void Apply(CloudStorageAccount model)
    {
        var client = model.CreateCloudBlobClient();

        var container = client.GetContainerReference(containerPath);

        if (!container.Exists())
            container.Create();

        var blobReference = container.GetBlockBlobReference(blobAddressUri);

        var blockBlob = blobReference;
        UploadToContainer(blockBlob);
    }

    private void UploadToContainer(CloudBlockBlob blockBlob)
    {
        SetBlobProperties(blockBlob);

        using (var ms = new MemoryStream())
        {
            LoadStreamWithJson(ms);
            blockBlob.UploadFromStream(ms);
        }
    }

    private void SetBlobProperties(CloudBlockBlob blobReference)
    {
        blobReference.Properties.ContentType = CONTENT_TYPE;
        foreach (var meta in metadata)
        {
            blobReference.Metadata.Add(meta.Key, meta.Value);
        }
    }

    private void LoadStreamWithJson(Stream ms)
    {
        var json = JsonConvert.SerializeObject(obj);
        StreamWriter writer = new StreamWriter(ms);
        writer.Write(json);
        writer.Flush();
        ms.Position = 0;
    }
}

Using the UploadToBlobStorageAsJson ModelCommand

The following tests have been written to demonstrate an interesting side effect of the ModelCommand. The first test shows how to instantiate a command and upload an object to Windows Azure Blob Storage. The second test is interesting because it applies the command twice, effectively reusing the command instance.

The command holds a reference to the object that it will serialize and send to the Windows Azure Blob Storage. By preserving the Command instance, we can upload the object. Then we can modify it locally and call Apply on the command to re-upload the modified object to the same Blob in Windows Azure Blob Storage.

[TestClass]
public class BlobStorageUnitTests
{
    [TestMethod]
    public void TestUploadToBlobStorage()
    {
        var obj = new
        {
            By = "Alexandre Brisebois",
            Message = "This is a test Message"
        };

        var uploadToBlobStorage = new UploadToBlobStorageAsJson(obj,
                                                "test",
                                                "testObject",
                                                new Dictionary<string, string>());

        var storageAccount = CloudStorageAccount.Parse(GetConnectionString());

        uploadToBlobStorage.Apply(storageAccount);
    }

    [TestMethod]
    public void TestUploadThenChangeThenUpload()
    {
        var obj = new
        {
            By = "Alexandre Brisebois",
            Message = "This is a test Message"
        };

        var uploadToBlobStorage = new UploadToBlobStorageAsJson(obj,
                                                "test",
                                                "testObject",
                                                new Dictionary<string, string>());

        var storageAccount = CloudStorageAccount.Parse(GetConnectionString());

        uploadToBlobStorage.Apply(storageAccount);

        obj = new
        {
            By = "Charles Brisebois",
            Message = "This is a test Message"
        };

        uploadToBlobStorage = new UploadToBlobStorageAsJson(obj,
                                                "test",
                                                "testObject",
                                                new Dictionary<string, string>());

        uploadToBlobStorage.Apply(storageAccount);
    }

    private static string GetConnectionString()
    {
        return CloudConfigurationManager.GetSetting("StorageConnectionString");
    }
}

The CloudConfigurationManager will first look for the Cloud Configurations, if it does not find them, it will then look a matching AppSetting. In this example it found the setting in the following App.Config.

<?xml version="1.0" encoding="utf-8" ?>
<configuration>
  <appSettings>
    <add key="StorageConnectionString"
         value="DefaultEndpointsProtocol=https;
                AccountName=*******;
                AccountKey=********" />
 </appSettings> 
</configuration> 

15 responses to Uploading An Object As JSON To Windows Azure Blob Storage

  1. 

    what is ModelCommand here ? is there any other work around for this ?

    Like

  2. 

    I think this code is older one can you please update the code as per new classes and methods. “CloudBlob” is also not present currently.

    Like

  3. 

    getting error “Additional information: No valid combination of account information found.” while calling this var storageAccount = CloudStorageAccount.Parse(GetConnectionString());

    Like

  4. 

    In class library I’m getting this error :(
    Value cannot be null.
    Parameter name: connectionString

    Description: An unhandled exception occurred during the execution of the current web request. Please review the stack trace for more information about the error and where it originated in the code.

    Exception Details: System.ArgumentNullException: Value cannot be null.
    Parameter name: connectionString

    my code is
    var obj = new
    {
    By = “Alexandre Brisebois”,
    Message = “This is a test Message”
    };

            var uploadToBlobStorage = new UploadToBlobStorageAsJson(obj,
                                                    "test2",
                                                    "testObject2",
                                                    new Dictionary<string, string>());
    
            var storageAccount = CloudStorageAccount.Parse(GetConnectionString());
    

    getting error at above line , please guide ? thanks a lot

    Like

  5. 

    very thankful for your quick response . how can i retrieve data from that Blob in a object. I mean If I have stored Customer data into blob, how could I retrieve data in customer object from that blob ? please guide thanks a lot :)

    Like

  6. 

    I made it like this var Details = blob.DownloadText();
    Obj = JsonConvert.DeserializeObject(Details);
    thanks

    Like

  7. 

    Hi need your help to convert list of object and stored it into blog , how can i do so?
    I mean List for one key

    Like

  8. 

    Thanks Alexandre,

    it worked well.

    Best Regards

    Like

Leave a comment

This site uses Akismet to reduce spam. Learn how your comment data is processed.