我尝试编写一些代码来检索图像文件(来自Wikimedia Commons),将其存储在本地然后显示。这是我的代码:
<!DOCTYPE html>
<html>
<head>
<script>
window.requestFileSystem = window.requestFileSystem || window.webkitRequestFileSystem;
function onError(e) {
console.log('Error', e);
}
var xhr = new XMLHttpRequest();
xhr.open('GET', 'http://upload.wikimedia.org/wikipedia/fr/2/26/10_francs_Mathieu_1987_F365-28_revers.jpg', true);
xhr.responseType = 'blob';
xhr.onload = function(e) {
window.requestFileSystem(PERSISTENT, 1024 * 1024, function(fs) {alert(fs.root.name);}, onError);
window.requestFileSystem(PERSISTENT, 1024 * 1024, function(fs) {
fs.root.getFile('image.jpg', {create: true}, function(fileEntry) {
fileEntry.createWriter(function(writer) {
writer.onwrite = function(e) {};
writer.onerror = function(e) {};
var blob = new Blob([xhr.response], {type: 'image/jpeg'});
writer.write(blob);
}, onError);
}, onError);
}, onError);
window.requestFileSystem(PERSISTENT, 1024 * 1024, function(fs) {
fs.root.getFile('image.jpg', {create: false}, function(fileEntry) {
fileEntry.file(function(file) {
var reader = new FileReader();
reader.onloadend = function(event) {
var img = document.createElement("img");
img.src = event.target.result;
document.body.parentNode.insertBefore(img, document.body.nextSibling);
};
reader.readAsDataURL(file);
}, onError);
}, onError);
}, onError);
};
xhr.send();
</script>
</head>
<body>
</body>
</html>
没有显示任何内容。 Chrome的控制台没有显示任何错误消息,所以我不知道为什么它不起作用。任何线索?
编辑:
我刚刚看到我实际上得到一个FileError,代码10,这意味着QUOTA_EXCEEDED_ERR,即使我使用这些参数启动我的Google Chrome:
"C:\Program Files\Google\Chrome\Application\chrome.exe" --allow-file-access-from-files --unlimited-quota-for-files
实际上,无论有没有--unlimited-quota-for-files
参数,我都会得到相同的错误,这很奇怪。但是我收到了没有--allow-file-access-from-files
答案 0 :(得分:1)
在回答您关于为什么使用“--unlimited-quota-for-files”无法启动的问题时,我认为您会混淆两件不同的事情。该参数只是删除了配额限制,它不会自动预先批准脚本,以便在未经许可的情况下篡夺沙箱中的空间。如果您使用的是“临时”文件系统请求,那么它会在没有提示的情况下分配它(请参阅我的答案末尾的链接)。
但是,正如您在需要调用requestQuota()方法时遇到的那样,Chrome将不允许在没有明确用户权限的情况下分配持久性文件系统存储。这有几个原因,但安全性最好:即如果Chrome要按需要(没有用户知识)将持久文件系统存储分配给任何要求它的脚本,那么恶意脚本可以快速轻松填充用户的硬盘驱动器,由于成千上万的物体而导致Chrome内存崩溃,并造成一般混乱。这样的漏洞也可能通过锤击内存来触发缓冲区溢出。
结论:Chrome只允许用户批准持久存储文件系统。更多来自Google:Managing HTML5 Offline Storage:Persistent storage
答案 1 :(得分:1)
如果有人发现这一点,--unlimited-quota-for-files
不再是有效标志。但是,有一个list of current chromium flags maintained here。
--unlimited-storage
将成为新的旗帜。
将每个来源的配额设置覆盖为任何应用/来源的无限存储空间。这应该仅用于测试目的。
我认为您必须更新配额请求,因为该标志没有覆盖任何内容(但我实际上并不知道该标志本身何时被弃用)。因为它没有像以前那样工作(假设您的代码之前已经工作过,或者您从教程中获得了它)我认为浏览器在配置系统上没有发生,并且超出了配额与你正在做的事情,从而抛出异常。
你得到的File Error
没有--allow-file-access-from-files
,因为如果允许浏览器在正常操作下访问这些文件会出现安全问题,因此文件错误应该是类型{ {1}}。
以下链接中的信息是旧的,但该策略类似于相关代码(标志现在是--unlimited-storage)。See this article for more details。
所有人都说,在实际应用中,配额请求是必须的,本文撰写时OP的解决方案包含正确的代码。目前,配额和fs请求的javascript如下所示:
SECURITY_ERR
答案 2 :(得分:0)
我添加了对window.webkitStorageInfo.requestQuota
的调用,现在它可以正常工作了。我无法理解为什么有必要,因为我使用--unlimited-quota-for-files
选项启动了Chrome。
这是工作代码:
<!DOCTYPE html>
<html>
<head>
<script>
window.requestFileSystem = window.requestFileSystem || window.webkitRequestFileSystem;
function onError(e) {
console.log('Error', e);
}
var xhr = new XMLHttpRequest();
xhr.open('GET', 'http://upload.wikimedia.org/wikipedia/fr/2/26/10_francs_Mathieu_1987_F365-28_revers.jpg', true);
xhr.responseType = 'blob';
xhr.onload = function(e) {
window.webkitStorageInfo.requestQuota(PERSISTENT, 1024*1024, function(grantedBytes) {
window.requestFileSystem(PERSISTENT, 1024 * 1024, function(fs) {
fs.root.getFile('image.jpg', {create: true}, function(fileEntry) {
fileEntry.createWriter(function(writer) {
writer.onwrite = function(e) {};
writer.onerror = function(e) {};
var blob = new Blob([xhr.response], {type: 'image/jpeg'});
writer.write(blob);
}, function(e) {
console.log('Error', e);
});
}, function(e) {
console.log('Error', e);
});
}, function(e) {
console.log('Error', e);
});
}, function(e) {
console.log('Error', e);
});
window.requestFileSystem(PERSISTENT, 1024 * 1024, function(fs) {
fs.root.getFile('image.jpg', {create: false}, function(fileEntry) {
fileEntry.file(function(file) {
var reader = new FileReader();
reader.onloadend = function(event) {
var img = document.createElement("img");
img.src = event.target.result;
document.body.parentNode.insertBefore(img, document.body.nextSibling);
};
reader.readAsDataURL(file);
}, function(e) {
console.log('Error', e);
});
}, function(e) {
console.log('Error', e);
});
}, function(e) {
console.log('Error', e);
});
};
xhr.send();
</script>
</head>
<body>
</body>
</html>