如何保护 azure blob 存储 url 不被任何使用开发人员工具的人检索
Posted
技术标签:
【中文标题】如何保护 azure blob 存储 url 不被任何使用开发人员工具的人检索【英文标题】:How to protect the azure blob storage urls from being retrieved by anyone using developer tools 【发布时间】:2018-11-03 14:23:19 【问题描述】:我必须将图像/视频保存在 azure blob 中,然后在我的网站中使用它们。在做了一些研究之后,我发现你必须在 href 标记中包含 blob url,才能从 azure 中检索图像/视频。
但是,任何人都可以打开站点页面并获取该 blob 网址并滥用它。该站点还具有用户身份验证,因此只有在登录后用户才能在站点页面上看到该图像/视频。
还有其他方法可以从 azure 中检索 blob 吗?或者在开发人员工具中公开可见网址的任何其他解决方案?
我目前正在使用带有 Visual Studio 的 azure 模拟器。
【问题讨论】:
有几种方法可以解决这个问题。一种是不让 Blob 公开可用,而是通过后端服务(可能是 Azure 函数)检索它们。示例:api/images/uniquename
。另一种方法是使用共享访问密钥,该密钥仅对所需图像具有只读访问权限。
@rickvdbosch 我不确定第一种解决方案是否可行。我将不使用 blob URL,而是使用 API URL,并且仍然能够访问 blob,除非我也保护 API 调用。第二种解决方案不能完全防止这种情况,但可以通过短期 SAS 令牌和适当的 IP ACL 在很大程度上控制它。
@GauravMantri 我知道第一个解决方案有效,因为我以前用过它:) 特别是使用 Azure Functions,您可以非常快速地创建这样的后端服务。我让函数使用 Azure SDK 从 blob 存储中检索文件并将它们返回以在前端使用。
@rickvdbosch 现在你让我很好奇 :)。我认为您的解释不适合 cmets。您介意提供详细的答案吗?这将非常有帮助。
@rickvdbosch 如果您能进一步详细说明将不胜感激:)
【参考方案1】:
不确定问题是否有效,但另一种非常简单的方法可能是
-
将自定义域与您的存储端点一起使用
将您的 Blob 和容器设为私有
使用后端基础架构生成共享访问令牌,该令牌应仅在短时间内有效。
使用 SAS 生成 blob url。
如果您需要一起隐藏结构,所有步骤都可以与@rick 回答中提到的功能结合使用。
需要了解的一点是视频流需要到浏览器播放器,所以不可能有完美的方案。上面的选项也只会对访问进行时间限制。可能还有其他一些选项,例如服务器发送加密内容的消息层加密,并将在运行时解密您需要有一些自定义播放器功能,这可能会在服务器端产生更高的费用..
如果他有技能和高积极性,即使这也不会成为盗版视频的用户,但会以某种方式使其变得困难,这应该是这里的驱动点。
参考:https://docs.microsoft.com/en-us/azure/storage/common/storage-dotnet-shared-access-signature-part-1
【讨论】:
【参考方案2】:我重新创建了一个 Azure 函数,它实现了我提到的第一个场景。存储帐户内的 Blob URL 未公开,并且容器及其中的所有内容都设置为私有。由于我不知道您的身份验证方案,所以我暂时跳过了它,但您可以通过多种方式保护它。
此代码中有一些快捷方式,但您会大致了解。代码如下:
public static async Task<HttpResponseMessage> Run(
[HttpTrigger(AuthorizationLevel.Anonymous, "get", Route = "files/id")]
HttpRequest req, string id, TraceWriter log)
var account = CloudStorageAccount.Parse("UseDevelopmentStorage=true");
var client = account.CreateCloudBlobClient();
var container = client.GetContainerReference("sitecontent");
var blob = container.GetBlockBlobReference(id);
var stream = new MemoryStream();
await blob.DownloadToStreamAsync(stream);
stream.Seek(0, SeekOrigin.Begin);
HttpResponseMessage result = new HttpResponseMessage(HttpStatusCode.OK);
result.Content = new StreamContent(stream);
result.Content.Headers.ContentType =
new MediaTypeHeaderValue("application/octet-stream");
return result;
我已经通过从这样的 html 文件中引用它来测试它:
<img src="http://localhost:7071/api/files/techdays2017.jpg" />
我使用的图像是 267KB,使用 Storage Emulator 进行本地测试时,Function 的响应时间均
【讨论】:
我不确定这将如何防止误用。我可以将此 URL 放入浏览器的地址栏中,然后我就可以访问该 blob。我在这里错过了什么吗? 嗯,存储中 blob 的完整 url 不再可见,blob 不再需要公开,并且可以保护函数,因此仅在用户登录时才下载文件在。 啊...我明白你的意思了。但是,是的,这需要保护函数,否则保持 blob 私有将无济于事。 当我看到你的回答时,我们在这里也做了同样的事情 :) 非常感谢 :) 这是非常错误的答案,最简单正确的答案是使用共享访问签名,绝对不需要通过azure函数重新路由网络调用。此外,这不支持带有进度等的部分下载,并且根本不适用于从 azure blob 传递视频。以上是关于如何保护 azure blob 存储 url 不被任何使用开发人员工具的人检索的主要内容,如果未能解决你的问题,请参考以下文章
Azure Blob 存储:从 Excel 工作簿中删除密码