我正在尝试使用index.openCursor(此处提供keyRange.only或keyRange.bound)使用 autoIncrement:true 创建的表上的索引访问一个或多个记录。我尝试过多种变化但没有成功。有人可以使用以下代码作为模板向我展示一个工作示例:
window.indexedDB = window.indexedDB || window.webkitIndexedDB
|| window.mozIndexedDB || window.msIndexedDB;
var ixDb;
var ixDbIndexTest = function () {
//Open or create the requested IndexedDB Database
var ixDbRequest = window.indexedDB.open("testDBindexes", 2);
ixDbRequest.onupgradeneeded = function (e) {
ixDb = ixDbRequest.result || e.currentTarget.result;
objectStore =
ixDb.createObjectStore("demoOS",
{ keyPath: "id", autoIncrement: true });
objectStore.createIndex("ixdemo", "Field1",
{ unique: false, multiEntry: false });
//define new dummy record
var newRecord = {};
newRecord.Field1 = "222";
newRecord.Field2 = "333";
newRecord.Field3 = "444";
var request = objectStore.add(newRecord);
request.onsuccess = function (e) {
var index = objectStore.index('ixdemo');
var range = IDBKeyRange.only("222");
var cursorRequest = index.openCursor(range);
cursorRequest.onsuccess = function(e) {
var cursor = cursorRequest.result || e.result;
alert(cursor.value);
cursor.continue();
}
}
};
};
window.onload = ixDbIndexTest;
更新 我修改了演示脚本,以便在仍然使用setVersion的Firefox和较旧的Chrome版本中运行。但是,您需要为Chrome添加其他版本检查逻辑,因为每次脚本运行时当前逻辑都会运行setVersion。
window.indexedDB = window.indexedDB || window.webkitIndexedDB
|| window.mozIndexedDB || window.msIndexedDB;
window.IDBTransaction = window.IDBTransaction || window.webkitIDBTransaction
|| window.mozIDBTransaction || window.msIDBTransaction;
window.IDBKeyRange = window.IDBKeyRange || window.webkitIDBKeyRange ||
window.mozIDBKeyRange || window.msIDBKeyRange;
var ixDb;
var ixDbIndexTest = function () {
//Open or create the requested IndexedDB Database
var ixDbRequest = window.indexedDB.open("testDBindexes", 1);
ixDbRequest.onsuccess = function(e) {
ixDb = ixDbRequest.result || e.currentTarget.result;
if (typeof ixDb.setVersion === "function") {
ixDbVersionRequest = ixDb.setVersion(1);
ixDbVersionRequest.onsuccess = function (e) {
indexTest();
};
}
else {
ixDbRequest.onupgradeneeded = function (e) {
indexTest();
};
}
}
};
window.onload = ixDbIndexTest;
function indexTest() {
var objectStore = ixDb.createObjectStore("demoOS",
{ keyPath: "id", autoIncrement: true });
objectStore.createIndex("ixdemo", "Field1",
{ unique: false, multiEntry: false });
//define new record with users input
var newRecord = {};
newRecord.Field1 = "222";
newRecord.Field2 = "333";
newRecord.Field3 = "444";
var request = objectStore.add(newRecord);
request.onsuccess = function (e) {
var index = objectStore.index('ixdemo');
var range = IDBKeyRange.only("222");
var cursorRequest = index.openCursor();
cursorRequest.onsuccess = function(e) {
var cursor = cursorRequest.result || e.result;
if(cursor) {
alert(JSON.stringify(cursor.value));
cursor.continue();
}
}
}
}
答案 0 :(得分:4)
出现错误消息Type Error: cursor is undefined
,因为您正在使用游标而不检查它是否已定义。因此,当cursor.continue()
告诉IndexedDB去获取数据库中的下一个对象时,光标将耗尽实际存在的唯一对象后将被取消定义。
所以你应该做this之类的事情。在您的代码中,它看起来像:
cursorRequest.onsuccess = function(e) {
var cursor = cursorRequest.result || e.result;
if (cursor) {
alert(cursor.value);
cursor.continue();
}
}
另外,如果您知道自己只是在寻找一个对象(比如使用IDBKeyRange.only
时),则可以省略cursor.continue()
部分:
cursorRequest.onsuccess = function(e) {
var cursor = cursorRequest.result || e.result;
alert(cursor.value);
}
关于你的问题对于Chrome,我无法帮助你,因为到目前为止我只专注于Firefox。我建议您尝试Chrome的最新开发版本,它实际上支持onupgradeneeded
以及各种其他更新,但在我的测试中,它仍然非常错误,在Firefox中运行的代码可能会在Chrome中失败。如果这不是一个紧急的项目,那么等待一段时间让Chrome稳定下来你可能会更好。
答案 1 :(得分:0)
在onupgardeneeded事件中,您无法添加记录。
在改变之后,必须重新打开数据库以获取新的objectStore架构。所以会有两个开放
目前的Chrome是,我认为仍旧旧标准,setVersion,onupgardeneeded永远不会打电话。
newRecord必须具有keyPath'id',否则您不应在创建对象库时指定keyPath。