私は非常に簡単な質問を持っています(私は願っています!)-特定のコンテナに(定義した名前の)blobが存在するかどうかを確認したいだけです。存在する場合はダウンロードし、存在しない場合は別の方法でダウンロードします。
インターチューブを検索したところ、DoesExistなどの関数があったようですが、Azure APIの多くと同様に、これは存在しないように見えます(ある場合は、非常に巧妙に偽装された名前)。
私は非常に簡単な質問を持っています(私は願っています!)-特定のコンテナに(定義した名前の)blobが存在するかどうかを確認したいだけです。存在する場合はダウンロードし、存在しない場合は別の方法でダウンロードします。
インターチューブを検索したところ、DoesExistなどの関数があったようですが、Azure APIの多くと同様に、これは存在しないように見えます(ある場合は、非常に巧妙に偽装された名前)。
回答:
新しいAPIには.Exists()関数呼び出しがあります。GetBlockBlobReference
サーバーへの呼び出しを実行しないを使用していることを確認してください。それは機能を次のように簡単にします:
public static bool BlobExistsOnCloud(CloudBlobClient client,
string containerName, string key)
{
return client.GetContainerReference(containerName)
.GetBlockBlobReference(key)
.Exists();
}
len(blob_service.list_blobs(container_name, file_name)) > 0
注:この回答は現在古くなっています。存在を確認する簡単な方法については、リチャードの回答を参照してください
いいえ、単純なものを見逃していません...新しいStorageClientライブラリでこのメソッドを適切に非表示にしました。:)
私はあなたの質問に答えるためにブログ投稿を書きました: http //blog.smarx.com/posts/testing-existence-of-a-windows-azure-blob。
短い答えは:BLOBに対してHEADリクエストを行うCloudBlob.FetchAttributes()を使用します。
OpenRead
も、空のStreamやそのようなものはスローまたは返されません。そこからダウンロードを開始したときにのみエラーが発生します。これをすべて1か所で処理する方がはるかに簡単です:)
BLOBが公開されている場合は、もちろん、HTTP HEADリクエストを送信することができます-方法を知っている無数の言語/環境/プラットフォームから-応答を確認してください。
コアAzure APIは、RESTful XMLベースのHTTPインターフェイスです。StorageClientライブラリは、それらを囲む多くの可能なラッパーの1つです。Sriram KrishnanがPythonで行った別の方法を次に示します。
http://www.sriramkrishnan.com/blog/2008/11/python-wrapper-for-windows-azure.html
また、HTTPレベルで認証する方法も示します。
StorageClientライブラリのレンズではなく、HTTP / RESTのレンズを通してAzureを見る方が好きなので、私もC#で同様のことを行いました。しばらくの間、私はExistsBlobメソッドを実装することさえ気にしていませんでした。私のブロブはすべて公開されており、HTTP HEADを実行するのは簡単でした。
例外メソッドを使用したくない場合は、judellが提案する基本的なc#バージョンを以下に示します。ただし、他の可能な応答も処理する必要があることに注意してください。
HttpWebRequest myReq = (HttpWebRequest)WebRequest.Create(url);
myReq.Method = "HEAD";
HttpWebResponse myResp = (HttpWebResponse)myReq.GetResponse();
if (myResp.StatusCode == HttpStatusCode.OK)
{
return true;
}
else
{
return false;
}
blobがパブリックで、メタデータだけが必要な場合:
HttpWebRequest request = (HttpWebRequest)WebRequest.Create(url);
request.Method = "HEAD";
string code = "";
try
{
HttpWebResponse response = (HttpWebResponse)request.GetResponse();
code = response.StatusCode.ToString();
}
catch
{
}
return code; // if "OK" blob exists
更新されたSDKでは、CloudBlobReferenceを取得したら、参照でExists()を呼び出すことができます。
http://msdn.microsoft.com/en-us/library/microsoft.windowsazure.storage.blob.cloudblockblob.exists.aspxを参照してください
これが私のやり方です。それを必要とする人のために完全なコードを示しています。
// Parse the connection string and return a reference to the storage account.
CloudStorageAccount storageAccount = CloudStorageAccount.Parse(CloudConfigurationManager.GetSetting("AzureBlobConnectionString"));
CloudBlobClient blobClient = storageAccount.CreateCloudBlobClient();
// Retrieve reference to a previously created container.
CloudBlobContainer container = blobClient.GetContainerReference("ContainerName");
// Retrieve reference to a blob named "test.csv"
CloudBlockBlob blockBlob = container.GetBlockBlobReference("test.csv");
if (blockBlob.Exists())
{
//Do your logic here.
}
ここでのほとんどの答えは技術的に正しいですが、ほとんどのコードサンプルは同期/ブロッキング呼び出しを行っています。非常に古いプラットフォームやコードベースに縛られていない限り、HTTP呼び出しは常に非同期で行う必要があり、SDKはこの場合完全にサポートします。のExistsAsync()
代わりに使用してくださいExists()
。
bool exists = await client.GetContainerReference(containerName)
.GetBlockBlobReference(key)
.ExistsAsync();
Exists()
完了するまでスレッドをブロックするという点で同期です。await ExistsAscyn()
非同期ではありません。どちらも同じ論理フローに従いますが、次のコード行は前のコードが終了するまで開始されませんが、ノンブロッキングでExistsAsync
あるため非同期になります。
他のソリューションが気に入らない場合の別のソリューションを次に示します。
Azure.Storage.Blobs NuGetパッケージのバージョン12.4.1を使用しています。
コンテナー内のすべてのblobのリストであるAzure.Pageableオブジェクトを取得します。次に、BlobItemの名前が、LINQを利用するコンテナー内の各blobのNameプロパティと等しいかどうかを確認します。(もちろん、すべてが有効な場合)
using Azure.Storage.Blobs;
using Azure.Storage.Blobs.Models;
using System.Linq;
using System.Text.RegularExpressions;
public class AzureBlobStorage
{
private BlobServiceClient _blobServiceClient;
public AzureBlobStorage(string connectionString)
{
this.ConnectionString = connectionString;
_blobServiceClient = new BlobServiceClient(this.ConnectionString);
}
public bool IsContainerNameValid(string name)
{
return Regex.IsMatch(name, "^[a-z0-9](?!.*--)[a-z0-9-]{1,61}[a-z0-9]$", RegexOptions.Singleline | RegexOptions.CultureInvariant);
}
public bool ContainerExists(string name)
{
return (IsContainerNameValid(name) ? _blobServiceClient.GetBlobContainerClient(name).Exists() : false);
}
public Azure.Pageable<BlobItem> GetBlobs(string containerName, string prefix = null)
{
try
{
return (ContainerExists(containerName) ?
_blobServiceClient.GetBlobContainerClient(containerName).GetBlobs(BlobTraits.All, BlobStates.All, prefix, default(System.Threading.CancellationToken))
: null);
}
catch
{
throw;
}
}
public bool BlobExists(string containerName, string blobName)
{
try
{
return (from b in GetBlobs(containerName)
where b.Name == blobName
select b).FirstOrDefault() != null;
}
catch
{
throw;
}
}
}
うまくいけば、これは将来の誰かを助けるでしょう。