Chrome扩展程序:如何在磁盘上保存文件


73

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

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

你有个主意吗?

Answers:


35

您可以使用HTML5 FileSystem功能通过Download API写入磁盘。这是将文件下载到磁盘的唯一方法,并且受到限制。

您可以看一下NPAPI插件。满足您需求的另一种方法是,只需通过XHR POST向外部网站发送请求,然后再通过另一个GET请求将文件取回,这将显示为保存文件对话框。

例如,对于我的浏览器扩展程序“我的环聊”,我创建了一个实用程序,可将照片从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上重定向我。我会看一下。谢谢你的帮助
X-冲击波

7
请注意,如果您打算将扩展程序上载到Google的画廊,则使用NPAPI会延迟发布,以使他们对其进行长时间的审查,甚至可能最终无法接受。
Max Shawabkeh,2010年

我同意马克斯。由于将进行手动检查,因此将延迟发布。最好是拥有一台外部服务器,您可以在扩展中授予访问权限,并通过POST上传数据,然后通过带有适当标头的GET取回数据。
穆罕默德·曼苏尔

是否可以将一个简短的标记词保存到本地硬盘上的文件中?
巴特洛梅耶Szałach

27

长期以来,我一直希望自己做一个chrome扩展程序来批量下载图像。但是,每次让我感到沮丧的时候,因为唯一看似适用的选择是NPAPI,Chrome和Firefox似乎都不希望再支持它了。

我建议那些仍然想实现“磁盘上保存文件”功能的人看看这篇Stackoverflow帖子,这篇帖子下面的评论对我有很大帮助。

从chrome 31+开始,chrome.downloadsAPI变得稳定了。我们可以使用它来以编程方式下载文件。如果用户未ask me before every download在Chrome设置中设置进阶选项,我们可以保存文件而不会提示用户确认!

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

    // 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);
    });

遗憾的是Event,下载完成后chrome仍然没有提供。chrome.downloads.download下载begin成功(未完成)时,将调用的回调函数

官方文档大约chrome.downloads在这里

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


1
目前尚不知道2014年的消息,但从今天开始,您可以收听onChanged带有state可告知下载状态的对象的事件(例如“完成”)。
JSmyth '16

1
@Allan,关于“我们可以在不提示用户确认的情况下保存文件”;但是,当您开始将文件写入用户计算机时,底部的“下载栏”不会打开吗?有没有办法静默地做到这一点?(例如,如果您正在后台将50个文件写入用户的计算机)
Pacerier '16

1
@Pacerier叫做下载架子,当我写下答案时,我记得我必须手动禁用架子才能显示在高级选项页面中。我进行了搜索,发现了这一点:您可能很有趣。setShelfEnabled chrome.downloads.setShelfEnabled(boolean enabled)启用或禁用与当前浏览器配置文件关联的每个窗口底部的灰色架子。只要至少一个扩展名已禁用该架子,它就会被禁用。在至少一个其他扩展名已禁用的情况下启用扩展架,将通过runtime.lastError返回错误。
艾伦·鲁恩

5

据我所知,没有办法将文件静默保存到用户的驱动器中,这就是您希望执行的操作。我认为您可以使用以下方法来一次将文件保存一次(每次提示用户):

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

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

浏览器中有本地存储选项,但据我所知,它们仅供开发人员在沙箱中使用。(例如,Gmail的离线缓存。)请参阅从谷歌最近宣布像这一个



4

Google网上商店
Github

如果这里的任何人仍然感兴趣,我做了一个扩展,它可以执行类似的操作。它使用XMLHTTPRequest来获取该对象(在本例中假定为图像),然后为其创建ObjectURL,指向该ObjectUrl的链接,然后单击虚构的链接。


1
第一链接点击404
therealprashant '17

-5

由于Javascript随处随处都可以通过网页搭便车到您的计算机,因此使其具有写入磁盘的能力将很危险。

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

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.