Archiv

Posts Tagged ‘Blob’

Optimistic Concurrency im Windows Azure Blob Storage

15. Oktober 2012 Hinterlasse einen Kommentar

imageBei Azure Blob Storage denkt man sofort an große Dateien wie z. B. VHDs oder Filmmaterial.

Der Blob Storage bietet jedoch eine sehr einfache Möglichkeit um kleinere Datendateien wie z. B. Konfigurationen, XML Daten oder persistierte Objekte abzuspeichern.

Verwendet man den Blob Storage um Applikationsdaten zu speichern, kommt man sehr schnell auf die Problemstellung wie man gemeinsamen Zugriff von mehreren Instanzen bzw. Usern auf die Dateien regelt. Der Blob Storage liefert hier einen einfach zu integrierenden Mechanismus der für “Optimistic Concurrency” Implementationen verwendet werden kann.

Auslesen E-Tag Property

Beim Lesen oder bei der Erzeugung eines Blob kann über das Object Properties (Typ: Microsoft.WindowsAzure.StorageClient.BlobProperties) der BlobReference das Property ETag ausgelesen werden.

 

string eTag = "";
string containerName = "BlobContainer".ToLower();
string blobName = String.Concat(containerName, @"/DataInBlob");
string connectionString = "UseDevelopmentStorage=true”;

CloudStorageAccount cloudStorageAccount = CloudStorageAccount.Parse(connectionString);
CloudBlobClient cloudBlobClient = cloudStorageAccount.CreateCloudBlobClient();
cloudBlobClient.RetryPolicy = RetryPolicies.Retry(5, TimeSpan.FromSeconds(1));
CloudBlockBlob cloudBlockBlob = cloudBlobClient.GetBlockBlobReference(blobName);
eTag = cloudBlockBlob.Properties.ETag;

 

ETag ist ein Read-Only Property welche eine spezifische Version des Blob eindeutig identifiziert. Der Wert wird vom Azure Storage System bei jedem Update bzw. bei der Anlage eines Blobs neu vergeben.

 

Verwendung E-Tag Property beim Upload

Verwendet man nun den Wert des ETag bei einem Update kann einfach geprüft werden, dass das Blob noch im Originalzustand ist und nicht von jemand anderem zwischenzeitlich geändert worden ist.

string eTag = "";
string containerName = "BlobContainer".ToLower();
string blobName = String.Concat(containerName, @"/DataInBlob");
string connectionString = "UseDevelopmentStorage=true”;

CloudStorageAccount cloudStorageAccount = CloudStorageAccount.Parse(connectionString);
CloudBlobClient cloudBlobClient = cloudStorageAccount.CreateCloudBlobClient();
cloudBlobClient.RetryPolicy = RetryPolicies.Retry(5, TimeSpan.FromSeconds(1));
CloudBlockBlob cloudBlockBlob = cloudBlobClient.GetBlockBlobReference(blobName);
eTag = cloudBlockBlob.Properties.ETag;

cloudBlockBlob.UploadText("Upload Will Work!");

try
{
    cloudBlockBlob.UploadText("Upload Will Fail", Encoding.ASCII, new BlobRequestOptions()
    {
        AccessCondition = AccessCondition.IfMatch(eTag)
    });

}
catch (StorageClientException exception)
{
    if (exception.ErrorCode == StorageErrorCode.ConditionFailed)
    {
        throw new System.Data.DBConcurrencyException()
        {
            Source = "Blob Storage"
        };
    }
    throw;
}

Im obigen Beispiel wird der erste Upload mit dem Textinhalt “Upload Will Work” ohne weitere Prüfung durchgeführt. Dadurch ändert sich im Blob Storage das ETag des Blobs.

Beim zweiten Upload im obigen Beispiel wird der Upload unter Verwendung des ursprünglichen ETag durchgeführt (siehe AccessCondition.IfMatch(eTag)). Dies führt zu einer Exception die im weiteren Verlauf für das Erkennen und Auslösen einer DBConcurrencyException() verwendet werden kann.

Kategorien:Azure Schlagwörter: , , ,