【问题标题】:Chrome extension: How to save a file on diskChrome 扩展程序:如何将文件保存在磁盘上
【发布时间】:2010-01-28 11:05:25
【问题描述】:

我目前正在为 google chrome 创建一个扩展程序,它可以将所有图像或指向图像的链接保存在硬盘上。

问题是我不知道如何使用 JS 或 Google Chrome 扩展 API 将文件保存在磁盘上。

你有想法吗?

【问题讨论】:

    标签: javascript google-chrome google-chrome-extension


    【解决方案1】:

    您可以使用HTML5 FileSystem features 使用Download API 写入磁盘。这是将文件下载到磁盘的唯一方法,并且是有限的。

    你可以看看 NPAPI 插件。另一种方法是通过 XHR POST 向外部网站发送请求,然后再发送一个 GET 请求来检索文件,这将显示为保存文件对话框。

    例如,对于我的浏览器扩展My Hangouts,我创建了一个实用程序,可以将照片从 HTML5 Canvas 直接下载到磁盘。您可以在这里查看代码capture_gallery_downloader.js 执行此操作的代码是:

    var url = window.webkitURL || window.URL || window.mozURL || window.msURL;
    var a = document.createElement('a');
    a.download = 'MyHangouts-MomentCapture.jpg';
    a.href = url.createObjectURL(dataURIToBlob(data.active, 'jpg'));
    a.textContent = 'Click here to download!';
    a.dataset.downloadurl = ['jpg', a.download, a.href].join(':');
    

    如果您希望在 HTML5 中将 URI 转换为 Blob,我就是这样做的:

    /**
     * Converts the Data Image URI to a Blob.
     *
     * @param {string} dataURI base64 data image URI.
     * @param {string} mimetype the image mimetype.
     */
    var dataURIToBlob = function(dataURI, mimetype) {
      var BASE64_MARKER = ';base64,';
      var base64Index = dataURI.indexOf(BASE64_MARKER) + BASE64_MARKER.length;
      var base64 = dataURI.substring(base64Index);
      var raw = window.atob(base64);
      var rawLength = raw.length;
      var uInt8Array = new Uint8Array(rawLength);
    
      for (var i = 0; i < rawLength; ++i) {
        uInt8Array[i] = raw.charCodeAt(i);
      }
    
      var bb = new this.BlobBuilder();
      bb.append(uInt8Array.buffer);
      return bb.getBlob(mimetype);
    };
    

    然后当用户点击下载按钮后,它会使用“下载”HTML5 File API将blob URI下载到一个文件中。

    【讨论】:

    • 这不是我们第一次在 NPAPI 上重定向我。我会看看它。感谢您的帮助
    • 请注意,如果您打算将扩展程序上传到 Google 的图库,使用 NPAPI 会延迟您的发布,因为他们会进行长时间的审核,甚至可能最终不会被接受。
    • 我同意 Max 的观点。它将延迟发布,因为它将被手动审查。如果您有一个外部服务器,您可以在您的扩展程序中授予访问权限,并通过 POST 上传数据并通过 GET 使用适当的标头取回数据,那将是最好的。
    • 是否允许我在本地硬盘上的文件中保存一个简短的标记词?
    【解决方案2】:

    我一直希望为自己制作一个 chrome 扩展来批量下载图像。然而,每次我感到沮丧,因为唯一看似适用的选项是 NPAPI,chrome 和 firefox 似乎都不想再支持它了。

    我建议那些仍然想实现'save-file-on-disk'功能的人看看这个Stackoverflow post,这篇文章下面的评论对我有很大帮助。

    现在自 chrome 31+ 起,chrome.downloads API 变得稳定。我们可以使用它以编程方式下载文件。如果用户没有在chrome设置中设置ask me before every download高级选项,我们可以保存文件而不提示用户确认!

    这是我使用的(在扩展程序的背景页面):

        // remember to add "permissions": ["downloads"] to manifest.json
        // this snippet is inside a onMessage() listener function
        var imgurl = "https://www.google.com.hk/images/srpr/logo11w.png";
        chrome.downloads.download({url:imgurl},function(downloadId){
            console.log("download begin, the downId is:" + downloadId);
        });
    

    虽然很可惜chrome在下载完成时仍然没有提供Eventchrome.downloads.download的回调函数在下载成功时调用begin(未完成)

    关于chrome.downloads的官方文档是here

    这不是我对解决方案的最初想法,但我在这里发布希望它可能对某人有用。

    【讨论】:

    • 不知道 2014 年的情况,但截至今天,可以收听带有 state 对象的 onChanged 事件,该对象可以告知下载状态(例如“完成”)。
    • @Allan, Re "我们可以在不提示用户确认的情况下保存文件";但是当你开始向用户的机器写入文件时,底部的“下载栏”不会打开吗?有没有办法默默地做到这一点? (例如,如果您在后台向用户的机器写入 50 个文件)
    • @Pacerier 调用下载架子,当我写答案时,我记得我必须手动禁用架子在高级选项页面中显示。我做了一些搜索,我发现了这个:你可能很有趣。setShelfEnabledchrome.downloads.setShelfEnabled(boolean enabled)启用或禁用与当前浏览器配置文件关联的每个窗口底部的灰色架子。只要至少有一个分机禁用了该架子,它就会被禁用。在至少一个其他扩展已禁用的情况下启用书架将通过 runtime.lastError 返回错误。
    【解决方案3】:

    据我所知,无法将文件静默保存到用户的驱动器,这似乎是您希望做的。我认为您可以使用以下方式要求一次保存一个文件(每次都提示用户):

    function saveAsMe (filename)
    {
    document.execCommand('SaveAs',null,filename)
    }
    

    如果您只想提示用户一次,您可以静默抓取所有图像,将它们压缩成一个包,然后让用户下载。这可能意味着对所有文件执行 XmlHttpRequest,用 Javascript 压缩它们,将它们上传到暂存区,然后询问用户是否要下载 zip 文件。听起来很荒谬,我知道。

    浏览器中有本地存储选项,但据我所知,它们仅供开发人员在沙箱内使用。 (例如,Gmail 离线缓存。)查看来自 Google 的最新公告,例如 this one

    【讨论】:

      【解决方案4】:

      考虑使用HTML5 FileSystem features,这使得使用 Javascript 写入文件成为可能。

      【讨论】:

        【解决方案5】:

        Google Webstore
        Github

        如果这里有人仍然感兴趣,我做了一个类似这样的扩展。 它使用 XMLHTTPRequest 来抓取对象,在这种情况下假定它是一个图像,然后为它创建一个 ObjectURL,一个指向该 ObjectUrl 的链接,然后单击虚构的链接。

        【讨论】:

        • 第一个链接点击 404
        【解决方案6】:

        看起来从浏览器读取和写入文件已成为可能。一些较新的基于 Chromium 的浏览器可以使用“本机文件系统 API”。这篇 2020 年的博文展示了使用 JavaScript 读取和写入本地文件系统的代码示例。

        https://blog.merzlabs.com/posts/native-file-system/

        此链接显示哪些浏览器支持本机文件系统 API。

        https://caniuse.com/native-filesystem-api

        【讨论】:

          【解决方案7】:

          由于几乎任何地方的网页都会通过 Javascript 搭便车到您的计算机,因此让它能够写入您的磁盘是很危险的。

          这是不允许的。您是否认为 Chrome 扩展程序需要用户交互?否则可能属于同一类。

          【讨论】:

            猜你喜欢
            • 1970-01-01
            • 1970-01-01
            • 2014-05-17
            • 2016-03-27
            • 1970-01-01
            • 2012-06-26
            • 2023-03-26
            • 1970-01-01
            • 1970-01-01
            相关资源
            最近更新 更多