然后我将它应用到我的场景中。
我编写了一个工具,用于将数据从合作伙伴上传到Azure blob存储,然后由一些内部团队使用: YYYY-MM(容器) (DD-GUID)(前缀) File1.zip File2.zip ......
我为每个容器创建了2个策略: 1.只为合作伙伴写,这样他们只能写blob而不能写任何其他内容。 2.列出并阅读我们的内部团队,以便他们可以列出并阅读(下载)容器中的所有blob。
我的想法是,我可以简单地将正确的政策交给正确的收件人;但是,我的实现并不像我预期的那样有效。
我使用以下方法为每个容器创建了2个策略,当然每个策略都有正确的权限:
static void CreateSharedAccessPolicy(CloudBlobClient blobClient, CloudBlobContainer container, string policyName)
{
//Create a new stored access policy and define its constraints.
SharedAccessBlobPolicy sharedPolicy = new SharedAccessBlobPolicy()
{
SharedAccessExpiryTime = DateTime.UtcNow.AddHours(10),
Permissions = SharedAccessBlobPermissions.Read | SharedAccessBlobPermissions.Write | SharedAccessBlobPermissions.List
};
//Get the container's existing permissions.
BlobContainerPermissions permissions = new BlobContainerPermissions();
//Add the new policy to the container's permissions.
permissions.SharedAccessPolicies.Clear();
permissions.SharedAccessPolicies.Add(policyName, sharedPolicy);
container.SetPermissions(permissions);
}
我首先创建了只写策略,然后创建了读取和列表策略。我观察到的是第一个策略似乎不起作用,一切都得到了403 Forbidden,对于第二个策略,唯一有效的是List blob但不是Read(我试图下载blob但得到了404没找到。)
好像我错过了一些非常基本的东西。你能帮助我看看我的方法有什么问题吗?
我用来测试容器权限的代码,我还注意到容器上的读取权限并不像Azure文档中提到的那样真正起作用。在这里,我试图找到一种简单的方法来简单地为人们提供存储的访问策略,以便他们可以列出并下载容器中的所有blob,而不是为每个blob文件提供签名:
static void UseContainerSAS(string sas) { //尝试使用提供的SAS执行容器操作。
//Return a reference to the container using the SAS URI.
CloudBlobContainer container = new CloudBlobContainer(new Uri(sas));
//Create a list to store blob URIs returned by a listing operation on the container.
List<Uri> blobUris = new List<Uri>();
try
{
//Write operation: write a new blob to the container.
CloudBlockBlob blob = container.GetBlockBlobReference("blobCreatedViaSAS.txt");
string blobContent = "This blob was created with a shared access signature granting write permissions to the container. ";
MemoryStream msWrite = new MemoryStream(Encoding.UTF8.GetBytes(blobContent));
msWrite.Position = 0;
using (msWrite)
{
blob.UploadFromStream(msWrite);
}
Console.WriteLine("Write operation succeeded for SAS " + sas);
Console.WriteLine();
}
catch (StorageException e)
{
Console.WriteLine("Write operation failed for SAS " + sas);
Console.WriteLine("Additional error information: " + e.Message);
Console.WriteLine();
}
try
{
//List operation: List the blobs in the container, including the one just added.
foreach (ICloudBlob blobListing in container.ListBlobs())
{
blobUris.Add(blobListing.Uri);
}
Console.WriteLine("List operation succeeded for SAS " + sas);
Console.WriteLine();
}
catch (StorageException e)
{
Console.WriteLine("List operation failed for SAS " + sas);
Console.WriteLine("Additional error information: " + e.Message);
Console.WriteLine();
}
try
{
CloudBlockBlob blob = container.GetBlockBlobReference(blobUris[0].ToString());
MemoryStream msRead = new MemoryStream();
msRead.Position = 0;
using (msRead)
{
blob.DownloadToStream(msRead);
Console.WriteLine(msRead.Length);
}
Console.WriteLine("Read operation succeeded for SAS " + sas);
Console.WriteLine();
}
catch (StorageException e)
{
Console.WriteLine("Read operation failed for SAS " + sas);
Console.WriteLine("Additional error information: " + e.Message);
Console.WriteLine();
}
Console.WriteLine();
try
{
//Delete operation: Delete a blob in the container.
CloudBlockBlob blob = container.GetBlockBlobReference(blobUris[0].ToString());
blob.Delete();
Console.WriteLine("Delete operation succeeded for SAS " + sas);
Console.WriteLine();
}
catch (StorageException e)
{
Console.WriteLine("Delete operation failed for SAS " + sas);
Console.WriteLine("Additional error information: " + e.Message);
Console.WriteLine();
}
}
答案 0 :(得分:7)
实际上,后一种操作会删除您在第一次操作中所做的操作。为避免这种情况,您应该阅读容器的现有权限,添加新权限,然后将权限设置回容器。
以下是正确的代码示例:
static void CreateSharedAccessPolicy(CloudBlobClient blobClient, CloudBlobContainer container, string policyName)
{
//Create a new stored access policy and define its constraints.
SharedAccessBlobPolicy sharedPolicy = new SharedAccessBlobPolicy()
{
SharedAccessExpiryTime = DateTime.UtcNow.AddHours(10),
Permissions = SharedAccessBlobPermissions.Read | SharedAccessBlobPermissions.Write | SharedAccessBlobPermissions.List
};
//Get the container's existing permissions.
BlobContainerPermissions permissions = container.GetPermissions();
//Add the new policy to the container's permissions.
permissions.SharedAccessPolicies.Add(policyName, sharedPolicy);
container.SetPermissions(permissions);
}
由于您在阅读blob时遇到404错误的原因,请分享您按策略创建SAS的代码以及如何使用创建的SAS读取blob以便我可以帮助解决问题。
以下是用于创建SAS并使用它来读取blob的代码示例:(您可以直接将stdout中的URL复制并粘贴到浏览器中进行试用)
var permissions = container.GetPermissions();
var policy = new SharedAccessBlobPolicy
{
Permissions = SharedAccessBlobPermissions.Read,
SharedAccessExpiryTime = DateTime.UtcNow.AddYears(1),
};
string policyName = "read";
permissions.SharedAccessPolicies.Add(policyName, policy);
container.SetPermissions(permissions);
string sas = container.GetSharedAccessSignature(null, policyName);
var blobs = container.ListBlobs(null, true);
Console.WriteLine("SAS = {0}", sas);
Console.WriteLine("Blobs URLs with SAS:");
foreach (var blob in blobs)
{
Console.WriteLine(blob.Uri.ToString() + sas);
}