Html HTML5 File API 从服务器下载文件并将其保存在沙箱中
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/13752984/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
HTML5 File API downloading file from server and saving it in sandbox
提问by Mamadum
I'm trying to understand HTML5 API. I'm designing the web application where the browser client need to download multiple files from server; user will perform something with the downloaded files and the application than need to save the state on user hard-rive. I understand that the browser can save these files only to its sandbox which is fine as long as the user can retrieve those files on the second time he starts the application. Should I use BlobBuilder or FileSaver? I'm a bit lost here.
我正在尝试了解 HTML5 API。我正在设计浏览器客户端需要从服务器下载多个文件的 Web 应用程序;用户将对下载的文件和应用程序执行一些操作,而不需要在用户硬盘上保存状态。我知道浏览器只能将这些文件保存到它的沙箱中,只要用户可以在第二次启动应用程序时检索这些文件就可以了。我应该使用 BlobBuilder 还是 FileSaver?我有点迷失在这里。
回答by mayconbordin
I'm going to show you how to download files with the XMLHttpRequest Level 2and save them with the FileSystem APIor with the FileSaver interface.
我将向您展示如何使用XMLHttpRequest Level 2下载文件并使用FileSystem API或FileSaver 接口保存它们。
Downloading Files
下载文件
To download a file you will use the XMLHttpRequest Level 2 (aka XHR2), which supports cross-origin requests, uploading progress events, and uploading/downloading of binary data. In the post "New Tricks in XMLHttpRequest2" there's plenty of examples of use of XHR2.
要下载文件,您将使用 XMLHttpRequest Level 2(又名 XHR2),它支持跨源请求、上传进度事件和上传/下载二进制数据。在“ XMLHttpRequest2 中的新技巧”一文中,有大量使用 XHR2 的示例。
To download a file as a blob all you have do to is specify the responseType
to "blob". You can also use the types "text", "arraybuffer" or "document". The function below downloads the file in the url
and sends it to the success
callback:
要将文件下载为 blob,您只需指定responseType
“blob”即可。您还可以使用“text”、“arraybuffer”或“document”类型。下面的函数下载 中的文件url
并将其发送到success
回调:
function downloadFile(url, success) {
var xhr = new XMLHttpRequest();
xhr.open('GET', url, true);
xhr.responseType = "blob";
xhr.onreadystatechange = function () {
if (xhr.readyState == 4) {
if (success) success(xhr.response);
}
};
xhr.send(null);
}
The success
callback will receive as argument an instance of Blob that can be later modified and saved and/or uploaded to a server.
该success
回调将收到的参数,可以在以后修改和保存和/或上传到服务器的Blob的一个实例。
Saving Files with the FileSystem API
使用 FileSystem API 保存文件
As the Can i use...site points outthere aren't many browsers with support to the FileSystem API. For Firefox there's an explanationfor the lack of support. So, you will have to use Chrome to do this.
正如Can i use...站点指出的那样,支持 FileSystem API 的浏览器并不多。对于 Firefox,有一个缺乏支持的解释。因此,您必须使用 Chrome 来执行此操作。
First you will have to request a storage space, it can be either temporary or persistent. You will probably want to have a persistent storage, in this case you will have request a quota of storage space upfront (some facts):
首先,您必须请求一个存储空间,它可以是临时的,也可以是持久的。您可能希望拥有一个持久存储,在这种情况下,您需要预先请求一个存储空间配额(一些事实):
window.requestFileSystem = window.requestFileSystem || window.webkitRequestFileSystem;
window.storageInfo = window.storageInfo || window.webkitStorageInfo;
// Request access to the file system
var fileSystem = null // DOMFileSystem instance
, fsType = PERSISTENT // PERSISTENT vs. TEMPORARY storage
, fsSize = 10 * 1024 * 1024 // size (bytes) of needed space
;
window.storageInfo.requestQuota(fsType, fsSize, function(gb) {
window.requestFileSystem(fsType, gb, function(fs) {
fileSystem = fs;
}, errorHandler);
}, errorHandler);
Now that you have access to the file system you can save and read files from it. The function below can save a blob in the specified path into the file system:
现在您可以访问文件系统,您可以从中保存和读取文件。下面的函数可以将指定路径中的 blob 保存到文件系统中:
function saveFile(data, path) {
if (!fileSystem) return;
fileSystem.root.getFile(path, {create: true}, function(fileEntry) {
fileEntry.createWriter(function(writer) {
writer.write(data);
}, errorHandler);
}, errorHandler);
}
And to read a file by its path:
并通过其路径读取文件:
function readFile(path, success) {
fileSystem.root.getFile(path, {}, function(fileEntry) {
fileEntry.file(function(file) {
var reader = new FileReader();
reader.onloadend = function(e) {
if (success) success(this.result);
};
reader.readAsText(file);
}, errorHandler);
}, errorHandler);
}
In addition to the readAsText
method, according to the FileReader APIyou can call readAsArrayBuffer
and readAsDataURL
.
除了readAsText
方法之外,根据FileReader API,您可以调用readAsArrayBuffer
和readAsDataURL
。
Using the FileSaver
使用文件保护程序
The post "Saving Generated Files on Client-Side" explains very well the use of this API. Some browsers may need the FileSaver.jsin order to have the saveAs
interface.
“在客户端保存生成的文件”一文很好地解释了这个 API 的使用。某些浏览器可能需要FileSaver.js才能拥有该saveAs
界面。
If you use it together with the downloadFile
function, you could have something like this:
如果你把它和downloadFile
函数一起使用,你可能会有这样的事情:
downloadFile('image.png', function(blob) {
saveAs(blob, "image.png");
});
Of course it would make more sense if the user could visualize the image, manipulate it and then save it in his drive.
当然,如果用户可以对图像进行可视化、操作,然后将其保存在他的驱动器中,那会更有意义。
Error Handler
错误处理程序
Just to fulfill the example:
只是为了完成这个例子:
function errorHandler(e) {
var msg = '';
switch (e.code) {
case FileError.QUOTA_EXCEEDED_ERR:
msg = 'QUOTA_EXCEEDED_ERR';
break;
case FileError.NOT_FOUND_ERR:
msg = 'NOT_FOUND_ERR';
break;
case FileError.SECURITY_ERR:
msg = 'SECURITY_ERR';
break;
case FileError.INVALID_MODIFICATION_ERR:
msg = 'INVALID_MODIFICATION_ERR';
break;
case FileError.INVALID_STATE_ERR:
msg = 'INVALID_STATE_ERR';
break;
default:
msg = 'Unknown Error';
break;
};
console.log('Error: ' + msg);
}
Useful links
有用的链接
回答by Trunal Bhanse
If you only support HTML5 browsers, there's a "download" attribute you can use. More details here : http://updates.html5rocks.com/2011/08/Downloading-resources-in-HTML5-a-download
如果您只支持 HTML5 浏览器,则可以使用“下载”属性。更多细节在这里:http: //updates.html5rocks.com/2011/08/Downloading-resources-in-HTML5-a-download
回答by Martin Rode
My trick is to simply append IFRAMEs with a "src" attribute pointing to your multiple downloads. The server site should send the files with a "disposition: attachment" header and then the client will try to store the file locally. The only "problem" is that the IFRAMEs will stay in your DOM tree as debris until the user leaves or reloads the page. Make the IFRAME invisible (e.g. width=0; height=0;) and you are ready to go! All browsers.
我的技巧是简单地将 IFRAME 附加到指向您的多个下载的“src”属性。服务器站点应该发送带有“处置:附件”标头的文件,然后客户端将尝试将文件存储在本地。唯一的“问题”是 IFRAME 将作为碎片留在您的 DOM 树中,直到用户离开或重新加载页面。使 IFRAME 不可见(例如,宽度=0;高度=0;),您就可以开始了!所有浏览器。