直接从浏览器将文件上传到 Azure Blob 存储?

Posted

技术标签:

【中文标题】直接从浏览器将文件上传到 Azure Blob 存储?【英文标题】:Upload file to Azure Blob Storage directly from browser? 【发布时间】:2013-03-18 05:31:58 【问题描述】:

是否可以创建一个 html 表单以允许 Web 用户直接将文件上传到 azure blob 存储而不使用其他服务器作为中介? S3 和 GAW blobstore 都允许这样做,但我找不到对 azure blob 存储的任何支持。

【问题讨论】:

【参考方案1】:

请查看这些博客文章,了解如何将文件直接从浏览器上传到 Blob 存储:

http://coderead.wordpress.com/2012/11/21/uploading-files-directly-to-blob-storage-from-the-browser/

http://gauravmantri.com/2013/02/16/uploading-large-files-in-windows-azure-blob-storage-using-shared-access-signature-html-and-javascript

第二篇文章(由我撰写)使用 HTML 5 File API,因此不适用于所有浏览器。

基本思想是为 blob 容器创建一个Shared Access Signature (SAS)。 SAS 应该有Write 权限。由于 Windows Azure Blob 存储尚不支持 CORS(Amazon S3 和 Google 都支持),因此您需要将 HTML 页面托管在希望用户上传文件的 Blob 存储中。然后就可以使用 jQuery 的 Ajax 功能了。

【讨论】:

更新:Azure 现在supports CORS。 顺便说一句,您可能想更新您的博客文章...如果您尝试手动设置请求的内容长度标头,浏览器会抛出错误。 在此过程中解决了其他几个问题(启用 CORS 很痛苦!),我发现显然您需要示例中不存在的授权标头。 @RonLugge 感谢 Ron 对Content-Length 标题的评论。我已经相应地更新了我的帖子。我认为您不需要授权标头,因为您使用的是包含必要授权信息的共享访问签名。 所以事实证明你是对的,问题是我的身份验证标头从我的常规应用程序逻辑中“泄漏”了。 (哎呀)。一旦我从这个特定的调用中手动删除标题,我就会转到关于cannot convert object to primitive value 的类型错误——有什么想法吗? (好吧,我想这可能是关于我如何删除标题......我只是喜欢编程,是的,是的......)【参考方案2】:

2019 年 11 月编辑

现在可以参考官方文档了:

Azure Storage JavaScript Client Library Sample for Blob Operations Azure Storage client library for JavaScript

初步回答

有一个New Azure Storage JavaScript client library for browsers (Preview)。

这篇文章的所有内容均来自上面的原始文章

用于 Azure 存储的 JavaScript 客户端库支持使用 Blob、表、队列和文件等存储服务的许多 Web 开发场景,并且与现代浏览器兼容 新的浏览器 JavaScript 客户端库支持最新 REST API 版本 2016-05-31 中可用的所有存储功能,因为它是使用适用于 Node.js 的 Azure 存储客户端库通过 Browserify 构建的

我们强烈建议使用 SAS tokens 对 Azure 存储进行身份验证,因为 JavaScript 客户端库会在浏览器中向用户公开身份验证令牌。强烈建议使用范围和时间有限的 SAS 令牌。在理想的 Web 应用程序中,预计后端应用程序将在用户登录时对其进行身份验证,然后将 SAS 令牌提供给客户端以授权访问存储帐户。这消除了使用帐户密钥进行身份验证的需要。查看我们的 Github 存储库中的 Azure Function sample,它会根据 HTTP POST 请求生成 SAS 令牌。

代码示例:

    在您的 HTML 代码中插入以下脚本标签。确保 JavaScript 文件位于同一文件夹中。

    <script src="azure-storage.common.js"></script/>
    <script src="azure-storage.blob.js"></script/>
    

    现在让我们在页面中添加一些项目以启动传输。在 BODY 标签内添加以下标签。请注意,该按钮在单击时会调用 uploadBlobFromText 方法。我们将在下一步定义此方法。

    <input type="text" id="text" name="text" value="Hello World!" />
    <button id="upload-button" onclick="uploadBlobFromText()">Upload</button>
    

    到目前为止,我们已经包含了客户端库并添加了 HTML 代码,以向用户显示文本输入和启动传输的按钮。当用户点击上传按钮时,uploadBlobFromText 将被调用。现在让我们定义它:

    <script>
    function uploadBlobFromText() 
        // your account and SAS information
        var sasKey ="....";
        var blobUri = "http://<accountname>.blob.core.windows.net";
        var blobService = AzureStorage.createBlobServiceWithSas(blobUri, sasKey).withFilter(new AzureStorage.ExponentialRetryPolicyFilter());
        var text = document.getElementById('text');
        var btn = document.getElementById("upload-button");
        blobService.createBlockBlobFromText('mycontainer', 'myblob', text.value,  function(error, result, response)
            if (error) 
                alert('Upload filed, open browser console for more detailed info.');
                console.log(error);
             else 
                alert('Upload successfully!');
            
        );
    
    </script>
    

【讨论】:

【参考方案3】:

现在 Windows Azure 存储服务支持 CORS,您可以这样做。您可以在此处查看公告:Windows Azure Storage Release - Introducing CORS, JSON, Minute Metrics, and More。

我有一个简单的例子来说明这个场景:http://www.contentmaster.com/azure/windows-azure-storage-cors/

该示例展示了如何使用 jQuery.ajax 从私有 blob 直接上传和下载。此示例仍然需要一个服务器组件来生成共享访问签名:这避免了在客户端代码中公开存储帐户密钥的需要。

【讨论】:

contentmaster.com/azure/windows-azure-storage-cors这个链接是404。【参考方案4】:

我写了一篇blog 帖子,其中有一个关于如何做到这一点的示例,code is at GitHub

它基于Gaurav Mantris post,并通过在 Blob 存储本身上托管 JavaScript 来工作。

【讨论】:

您的博文不再可见 :( 不,很抱歉,这是 8 年前的事了,我不再为托管它的公司工作。代码仍在 GitHub 中,但它已经有 8 年历史了......【参考方案5】:

您可以使用 HTML5 File API、AJAX 和 MVC 3 构建强大的文件上传控件,以安全可靠地将大文件上传到 Windows Azure blob 存储,并提供监控操作进度和操作取消。解决方案如下:

    接受并处理用户上传的文件的客户端 JavaScript。 处理由 JavaScript 发送的文件块的服务器端代码。 调用 JavaScript 的客户端 UI。

在此处获取示例代码:Reliable Uploads to Windows Azure Blob Storage via an HTML5 Control

【讨论】:

本文使用 Web 服务器作为中介,使用自定义 Javascript 分块方法将块中继到 Azure。它可能很漂亮,但不适合这个问题。

以上是关于直接从浏览器将文件上传到 Azure Blob 存储?的主要内容,如果未能解决你的问题,请参考以下文章

将文件从浏览器上传到 Azure Blob 存储,无需 SAS 密钥

直接从前端将数据上传到 Azure Blob 存储时的安全问题

从 SFTP 服务器将文件上传到 Azure 存储 Blob

当文件上传到 azure 文件共享时,如何添加触发器以将文件从 azure 文件共享移动到 azure blob?

恢复文件从用户的机器上传到 Azure Blob 存储和从 Azure Blob 下载文件到用户的机器在 Typescript(angular) 从浏览器

将文件从 Azure 存储 blob 移动到 Ftp 服务器