Azure 存储 CloudBlobContainer.Exists 权限
Azure Storage CloudBlobContainer.Exists permissions
我有一个生成 SAS Uri 的进程,用于将一些文件上传到 Azure 存储。现在它正在使用旧的“Microsoft.Azure.Storage”包,因为我使用的是 Microsoft.Azure.Storage.DataMovement.dll,因为它可以轻松上传大文件。
当我在存储资源管理器中使用 SAS Uri 时,一切正常。如果我不检查容器是否存在,它也能正常工作,但进行存在检查会导致权限错误。我已经尝试为生成 SAS 的应用程序提供 IAM 角色中的所有权限,但它仍然发生。
var sasUri = @"<sas uri>";
var backupsContainer = new Microsoft.Azure.Storage.Blob.CloudBlobContainer(new Uri(sasUri));
backupsContainer.Exists();
这是给我 'This request is not authorized to perform this operation' 错误的代码片段。
我看过类似的问题:
但我没有任何防火墙规则。
我应该提一下,之前我是使用存储帐户的密钥生成 SAS 的。当我更新它而不是使用应用程序时,它就坏了。我更新了它,因为最终我希望它使用 Managed Identity 凭据。我也包含了生成 SAS 的代码
BlobSasBuilder blobSasBuilder = new BlobSasBuilder
{
BlobContainerName = ExportSASInfo.ExportContainerName,
//c for container
Resource = "c",
// Access expires in 2 hours
ExpiresOn = DateTimeOffset.UtcNow.AddHours(sasSettingsModel.SasExpirationHours)
};
//allow adding blobs
blobSasBuilder.SetPermissions(
BlobContainerSasPermissions.Read
| BlobContainerSasPermissions.Add
| BlobContainerSasPermissions.Create
| BlobContainerSasPermissions.Write
| BlobContainerSasPermissions.Delete
| BlobContainerSasPermissions.List);
string scheme = "https";
string host = $"{customerInfo.AzureStorageAccountName}.blob.core.windows.net";
string blobEndpoint = $"{scheme}://{host}";
DefaultAzureCredential azureCredential = new DefaultAzureCredential(new DefaultAzureCredentialOptions() { ExcludeVisualStudioCodeCredential = true, ExcludeVisualStudioCredential = true, ExcludeSharedTokenCacheCredential = true });
BlobServiceClient blobServiceClient = new BlobServiceClient(
serviceUri: new Uri(blobEndpoint),
credential: azureCredential);
BlobContainerClient containerClient = blobServiceClient.GetBlobContainerClient(ExportSASInfo.ExportContainerName);
await containerClient.CreateIfNotExistsAsync();
UserDelegationKey key = await blobServiceClient.GetUserDelegationKeyAsync(
startsOn: DateTimeOffset.UtcNow.AddMinutes(-5),
expiresOn: DateTimeOffset.UtcNow.AddHours(sasSettingsModel.SasExpirationHours)); var sasToken = blobSasBuilder.ToSasQueryParameters(
userDelegationKey: key,
accountName: customerInfo.AzureStorageAccountName);
BlobUriBuilder blobUriBuilder = new BlobUriBuilder(containerClient.Uri)
{
Sas = sasToken
};
return new ExportSASInfo() { sasUri = blobUriBuilder.ToUri() };
你的角色足够了,我也可以重现你的问题,因为你生成的是一个容器级别的SAS,要检查这个容器的存在,SAS需要权限来列出帐户中的所有容器,即帐户级别SAS,无论你的MSI(managed identity)和blobSasBuilder.SetPermissions()
中的权限是什么角色,它都不起作用。
在您的情况下,您使用 MSI 来验证和创建用户委托 SAS,不支持创建帐户级别的 SAS,只需使用存储帐户密钥对其进行签名即可,因此如果您想检查容器的存在,您的选择是直接使用 ExistsAsync
方法。
string blobEndpoint = string.Format("https://{0}.blob.core.windows.net","joystoragev2");
BlobServiceClient blobServiceClient = new BlobServiceClient(new Uri(blobEndpoint), new ManagedIdentityCredential());
BlobContainerClient containerClient = blobServiceClient.GetBlobContainerClient("test");
containerClient.ExistsAsync().GetAwaiter().GetResult();
注意: 在我的截图中,我像上面的代码一样用 EnvironmentCredential
in local, if you want to use MSI to auth, just replace it with ManagedIdentityCredential
测试它,还要确保你是 运行 Azure 中的代码启用了 MSI 的环境,例如网络应用程序,那么它将正常工作。
之后就可以使用SAS对容器进行操作了,比如上传大文件。
我有一个生成 SAS Uri 的进程,用于将一些文件上传到 Azure 存储。现在它正在使用旧的“Microsoft.Azure.Storage”包,因为我使用的是 Microsoft.Azure.Storage.DataMovement.dll,因为它可以轻松上传大文件。
当我在存储资源管理器中使用 SAS Uri 时,一切正常。如果我不检查容器是否存在,它也能正常工作,但进行存在检查会导致权限错误。我已经尝试为生成 SAS 的应用程序提供 IAM 角色中的所有权限,但它仍然发生。
var sasUri = @"<sas uri>";
var backupsContainer = new Microsoft.Azure.Storage.Blob.CloudBlobContainer(new Uri(sasUri));
backupsContainer.Exists();
这是给我 'This request is not authorized to perform this operation' 错误的代码片段。
我看过类似的问题:
我应该提一下,之前我是使用存储帐户的密钥生成 SAS 的。当我更新它而不是使用应用程序时,它就坏了。我更新了它,因为最终我希望它使用 Managed Identity 凭据。我也包含了生成 SAS 的代码
BlobSasBuilder blobSasBuilder = new BlobSasBuilder
{
BlobContainerName = ExportSASInfo.ExportContainerName,
//c for container
Resource = "c",
// Access expires in 2 hours
ExpiresOn = DateTimeOffset.UtcNow.AddHours(sasSettingsModel.SasExpirationHours)
};
//allow adding blobs
blobSasBuilder.SetPermissions(
BlobContainerSasPermissions.Read
| BlobContainerSasPermissions.Add
| BlobContainerSasPermissions.Create
| BlobContainerSasPermissions.Write
| BlobContainerSasPermissions.Delete
| BlobContainerSasPermissions.List);
string scheme = "https";
string host = $"{customerInfo.AzureStorageAccountName}.blob.core.windows.net";
string blobEndpoint = $"{scheme}://{host}";
DefaultAzureCredential azureCredential = new DefaultAzureCredential(new DefaultAzureCredentialOptions() { ExcludeVisualStudioCodeCredential = true, ExcludeVisualStudioCredential = true, ExcludeSharedTokenCacheCredential = true });
BlobServiceClient blobServiceClient = new BlobServiceClient(
serviceUri: new Uri(blobEndpoint),
credential: azureCredential);
BlobContainerClient containerClient = blobServiceClient.GetBlobContainerClient(ExportSASInfo.ExportContainerName);
await containerClient.CreateIfNotExistsAsync();
UserDelegationKey key = await blobServiceClient.GetUserDelegationKeyAsync(
startsOn: DateTimeOffset.UtcNow.AddMinutes(-5),
expiresOn: DateTimeOffset.UtcNow.AddHours(sasSettingsModel.SasExpirationHours)); var sasToken = blobSasBuilder.ToSasQueryParameters(
userDelegationKey: key,
accountName: customerInfo.AzureStorageAccountName);
BlobUriBuilder blobUriBuilder = new BlobUriBuilder(containerClient.Uri)
{
Sas = sasToken
};
return new ExportSASInfo() { sasUri = blobUriBuilder.ToUri() };
你的角色足够了,我也可以重现你的问题,因为你生成的是一个容器级别的SAS,要检查这个容器的存在,SAS需要权限来列出帐户中的所有容器,即帐户级别SAS,无论你的MSI(managed identity)和blobSasBuilder.SetPermissions()
中的权限是什么角色,它都不起作用。
在您的情况下,您使用 MSI 来验证和创建用户委托 SAS,不支持创建帐户级别的 SAS,只需使用存储帐户密钥对其进行签名即可,因此如果您想检查容器的存在,您的选择是直接使用 ExistsAsync
方法。
string blobEndpoint = string.Format("https://{0}.blob.core.windows.net","joystoragev2");
BlobServiceClient blobServiceClient = new BlobServiceClient(new Uri(blobEndpoint), new ManagedIdentityCredential());
BlobContainerClient containerClient = blobServiceClient.GetBlobContainerClient("test");
containerClient.ExistsAsync().GetAwaiter().GetResult();
注意: 在我的截图中,我像上面的代码一样用 EnvironmentCredential
in local, if you want to use MSI to auth, just replace it with ManagedIdentityCredential
测试它,还要确保你是 运行 Azure 中的代码启用了 MSI 的环境,例如网络应用程序,那么它将正常工作。
之后就可以使用SAS对容器进行操作了,比如上传大文件。