无法在 Safari 上的 IndexedDB 中存储 Blob 类型
Unable to store Blob types in IndexedDB on Safari
我在 Safari 版本 10.1.2 上的 IndexedDB 中存储 blob 时遇到问题(在 IOS 上也面临同样的问题)。
我正在使用 angular2-indexeddb 模块包装器,但是 - 我不认为这是模块本身的问题。我的代码在 Chrome 中运行良好,但是当尝试将 blob 对象放入 Safari indexedDb 时,记录始终显示为 'null'(请参阅 FileData 字段):
我尝试了各种不同的 blob 文件(音频、视频、html),它们总是显示为 'null'。插入此记录时,IndexedDb 未返回(可见)错误。
据我了解 - Safari 应该支持 blob。我在想这个问题可能与 blob 的创建方式有关?也就是说,也许 Safari 不喜欢 blob 数据?
下面是我的代码示例(我没有在这里包含太多,所以如果需要更多信息,请告诉我):
// create blob:
const aFileParts = ['<a id="a"><b id="b">foo!</b></a>'];
const oMyBlob = new Blob(aFileParts, {type : 'text/html'});
console.log('blob type' + oMyBlob.type); // outputs as 'text/html'
// initialize my indexeddb store:
return this.initializeStores().then(() => {
// add 'oMyBlob' to the FileData data store:
return this.db.add('FileData',
{ FileName: 'foo', FileData: oMyBlob, FileType: 'audio' }).then(() => {
// Success
console.log('added ' + 'foo' + ' to FileData store.');
// Get the file from the FileData store
return this.db.getByIndex('FileData', 'FileName', 'foo').then((record) => {
return Promise.resolve();
});
}, (error) => {
console.log(error);
this.handleError(error)
return Promise.reject(error);
});
}, (error) => {
this.handleError(error);
return Promise.reject(error);
});
作为旁注 - 我可以毫无问题地将此数据存储为 Safari IndexedDB 中的 ArrayBuffer。问题是当我从数据库中检索它时,我必须将它转换回 blob(所需的额外处理能力并不理想)。
非常感谢任何帮助。
所以我设法找到了问题的原因。创建我的商店时,我引用了一个不正确的索引(主要是因为我正在学习在线教程)
const objectDataStore = evt.currentTarget.result.createObjectStore(
'FileData', { keyPath: 'id', autoIncrement: true });
密钥路径 'id' 在我的商店中不存在。这导致了保存 blob 时出现问题(奇怪的是没有报告错误......而且它似乎没有在 chrome 上引起问题)。
正确代码:
const objectDataStore = evt.currentTarget.result.createObjectStore(
'FileData', { keyPath: 'FileName', autoIncrement: true });
'FileName' 是我的商店对象中 属性 的名称。这现在解决了桌面 safari 上的问题。所以这里的教训是确保KeyPath是正确的。
但是,我现在面临一个新问题。在 IOS Safari 上,blob 无法保留到 indexedDb。我收到以下错误:
error: DOMError {name: "UnknownError", message: "An unknown error occurred within Indexed Database."}
因此 IOS Safari 上的 indexedDb 似乎不支持 blob(我假设这是一个错误)。现在我将只存储 ArrayBuffers 而不是 blob。
是的,我可以确认在 iOS Safari 版本 11.2.6 上,IndexedDB 无法将 Blob 存储为值。
我写了一小段代码来存储字符串值,它可以工作。如果我注释掉字符串并将其替换为 Blob,使用完全相同的代码,Safari 会给出 "Unknown Error"
{姓名:"UnknownError",消息:"An unknown error occurred within Indexed Database."}
也许在存储之前尝试将 Blob 转换为 ArrayBuffer。
如果 iOS/OSX 上的 indexedDb 仍然存在问题,请不要使用 auto-incrementation,因为它是 Safari 中的错误。
我在 Safari 版本 10.1.2 上的 IndexedDB 中存储 blob 时遇到问题(在 IOS 上也面临同样的问题)。
我正在使用 angular2-indexeddb 模块包装器,但是 - 我不认为这是模块本身的问题。我的代码在 Chrome 中运行良好,但是当尝试将 blob 对象放入 Safari indexedDb 时,记录始终显示为 'null'(请参阅 FileData 字段):
我尝试了各种不同的 blob 文件(音频、视频、html),它们总是显示为 'null'。插入此记录时,IndexedDb 未返回(可见)错误。
据我了解 - Safari 应该支持 blob。我在想这个问题可能与 blob 的创建方式有关?也就是说,也许 Safari 不喜欢 blob 数据?
下面是我的代码示例(我没有在这里包含太多,所以如果需要更多信息,请告诉我):
// create blob:
const aFileParts = ['<a id="a"><b id="b">foo!</b></a>'];
const oMyBlob = new Blob(aFileParts, {type : 'text/html'});
console.log('blob type' + oMyBlob.type); // outputs as 'text/html'
// initialize my indexeddb store:
return this.initializeStores().then(() => {
// add 'oMyBlob' to the FileData data store:
return this.db.add('FileData',
{ FileName: 'foo', FileData: oMyBlob, FileType: 'audio' }).then(() => {
// Success
console.log('added ' + 'foo' + ' to FileData store.');
// Get the file from the FileData store
return this.db.getByIndex('FileData', 'FileName', 'foo').then((record) => {
return Promise.resolve();
});
}, (error) => {
console.log(error);
this.handleError(error)
return Promise.reject(error);
});
}, (error) => {
this.handleError(error);
return Promise.reject(error);
});
作为旁注 - 我可以毫无问题地将此数据存储为 Safari IndexedDB 中的 ArrayBuffer。问题是当我从数据库中检索它时,我必须将它转换回 blob(所需的额外处理能力并不理想)。
非常感谢任何帮助。
所以我设法找到了问题的原因。创建我的商店时,我引用了一个不正确的索引(主要是因为我正在学习在线教程)
const objectDataStore = evt.currentTarget.result.createObjectStore(
'FileData', { keyPath: 'id', autoIncrement: true });
密钥路径 'id' 在我的商店中不存在。这导致了保存 blob 时出现问题(奇怪的是没有报告错误......而且它似乎没有在 chrome 上引起问题)。
正确代码:
const objectDataStore = evt.currentTarget.result.createObjectStore(
'FileData', { keyPath: 'FileName', autoIncrement: true });
'FileName' 是我的商店对象中 属性 的名称。这现在解决了桌面 safari 上的问题。所以这里的教训是确保KeyPath是正确的。
但是,我现在面临一个新问题。在 IOS Safari 上,blob 无法保留到 indexedDb。我收到以下错误:
error: DOMError {name: "UnknownError", message: "An unknown error occurred within Indexed Database."}
因此 IOS Safari 上的 indexedDb 似乎不支持 blob(我假设这是一个错误)。现在我将只存储 ArrayBuffers 而不是 blob。
是的,我可以确认在 iOS Safari 版本 11.2.6 上,IndexedDB 无法将 Blob 存储为值。
我写了一小段代码来存储字符串值,它可以工作。如果我注释掉字符串并将其替换为 Blob,使用完全相同的代码,Safari 会给出 "Unknown Error"
{姓名:"UnknownError",消息:"An unknown error occurred within Indexed Database."}
也许在存储之前尝试将 Blob 转换为 ArrayBuffer。
如果 iOS/OSX 上的 indexedDb 仍然存在问题,请不要使用 auto-incrementation,因为它是 Safari 中的错误。