我有一个非常简单的问题(我希望!) - 我只想知道特定容器中是否存在blob(具有我定义的名称)。如果确实存在,我会下载它,如果没有,那么我会做其他事情。
我已经对intertubes进行了一些搜索,显然曾经有一个名为DoesExist的函数或类似的东西......但是就像许多Azure API一样,这似乎不再存在(或者如果它是,有一个非常巧妙伪装的名字)。
答案 0 :(得分:187)
新API具有.Exists()函数调用。只需确保使用GetBlockBlobReference
,它不会执行对服务器的调用。它使功能像以下一样简单:
public static bool BlobExistsOnCloud(CloudBlobClient client,
string containerName, string key)
{
return client.GetContainerReference(containerName)
.GetBlockBlobReference(key)
.Exists();
}
答案 1 :(得分:49)
注意:此答案现已过时。请参阅理查德的答案,以便检查存在的简便方法
不,你不会错过一些简单的东西......我们很好地将这个方法隐藏在新的StorageClient库中。 :)
我刚写了一篇博文来回答你的问题:http://blog.smarx.com/posts/testing-existence-of-a-windows-azure-blob。
简短的回答是:使用CloudBlob.FetchAttributes(),它对blob执行HEAD请求。
答案 2 :(得分:16)
看起来很蹩脚,你需要捕获一个异常来测试blob是否存在。
public static bool Exists(this CloudBlob blob)
{
try
{
blob.FetchAttributes();
return true;
}
catch (StorageClientException e)
{
if (e.ErrorCode == StorageErrorCode.ResourceNotFound)
{
return false;
}
else
{
throw;
}
}
}
答案 3 :(得分:9)
如果blob是公共的,你当然可以发送一个HTTP HEAD请求 - 来自任何知道如何做的数十种语言/环境/平台 - 并检查响应。
核心Azure API是基于REST的XML的HTTP接口。 StorageClient库是围绕它们的许多可能包装器之一。这是Sriram Krishnan在Python中做的另一个:
http://www.sriramkrishnan.com/blog/2008/11/python-wrapper-for-windows-azure.html
它还显示了如何在HTTP级别进行身份验证。
我在C#中为自己做了类似的事情,因为我更喜欢通过HTTP / REST镜头而不是通过StorageClient库的镜头看到Azure。很长一段时间,我甚至都不愿意实施ExistsBlob方法。我的所有blob都是公开的,做HTTP HEAD是微不足道的。
答案 4 :(得分:5)
新的Windows Azure存储库已包含Exist()方法。 它位于Microsoft.WindowsAzure.Storage.dll。
作为NuGet包提供
创建者:Microsoft
Id:WindowsAzure.Storage
版本:2.0.5.1
答案 5 :(得分:2)
如果你不喜欢使用异常方法,那么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;
}
答案 6 :(得分:2)
如果您不喜欢其他解决方案,那么这里是另一种解决方案:
我正在使用Azure.Storage.Blobs NuGet软件包的12.4.1版本。
我得到一个 Azure.Pageable 对象,该对象是容器中所有blob的列表。然后,我检查 BlobItem 的名称是否等于容器内每个Blob的 Name 属性,利用< strong> LINQ 。 (当然,如果一切都有效)
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;
}
}
}
希望这对以后的人有所帮助。
答案 7 :(得分:1)
使用更新的SDK,一旦您拥有CloudBlobReference,您就可以在引用上调用Exists()。
答案 8 :(得分:1)
这就是我这样做的方式。显示需要它的人的完整代码。
// 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.
}
答案 9 :(得分:1)
尽管这里的大多数答案在技术上都是正确的,但大多数代码示例仍在进行同步/阻塞调用。除非您受制于非常老的平台或代码库,否则HTTP调用应该始终异步进行,并且在这种情况下,SDK完全支持它。只需使用ExistsAsync()
而不是Exists()
。
bool exists = await client.GetContainerReference(containerName)
.GetBlockBlobReference(key)
.ExistsAsync();
答案 10 :(得分:0)
如果您的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
答案 11 :(得分:0)
借助Azure Blob存储库v12,您可以使用BlobBaseClient.Exists()/BlobBaseClient.ExistsAsync()
回答了另一个类似的问题:https://stackoverflow.com/a/63293998/4865541
答案 12 :(得分:0)
相同的Java版本(使用新的v12 SDK)
这使用共享密钥凭据授权,即帐户访问密钥。
StorageSharedKeyCredential credential = new StorageSharedKeyCredential(accountName, accountKey);
String endpoint = String.format(Locale.ROOT, "https://%s.blob.core.windows.net", accountName);
BlobServiceClient storageClient = new BlobServiceClientBuilder().credential(credential)
.endpoint(endpoint).buildClient();
BlobContainerClient container = storageClient.getBlobContainerClient(containerName)
if ( container.exists() ) {
// perform operation when container exists
}