IndexedDB代码整理

147 阅读1分钟


//第一步,调用indexedDB.open(),并传入要打开的数据库。
//根据数据库请求成功与否,在实例上添加onerror和onsuccess事件处理程序
let request, db, version = 1;
request = indexedDB.open("admin", version);
request.onerror = (error) => alert(`Failed to open: ${ebent.target.errorCode}`);
request.onsucess = (event) => { 
    db = event.target.result;
    //并发问题
    db.onversionchange=()=>db.close();
 };


//如果数据库版本与期待的不一样,那可能需要创建对象存储。(对象存储键为username属性)
request.onupgradeneeded = (event) => {
    const db = event.target.result;
    //如果存在则删除当前objectStore。测试的时候可以这样做
    //当这样会在每次执行时间处理程序时删除已有数据
    if (db.objectStoreNames.contains("users")) {
        db.deleteObjectStore("users")
    };//如果存在则删除当前objectStore
    db.createObjectStore("users", { keyPath: "username" });
}; //keyPath属性表示应该作用键的存储对象的属性名


//创建了对象存储之后,剩下所有的操作都是要通过事务完成的。事务要通过调用数据库对象的transaction()方法创建
let transaction = db.transaction("users", "readwrite");
//let transaction = db.transaction("users");
//let transaction = db.transaction(["users","anotherStore"]);
//要修改访问模式,可以传入第二个参数 readonly readwrite versionchage
transaction.onerror = (event) => { }
transaction.oncomplete = (event) => { }
//因为一个事务可以完成任意多个请求,使用事务对象本身也有事件处理程序:onerrorhe oncomplete


//有了事务的引用,就可以使用objectStore()方法并传入对象存储的名称以访问特定的存储对象。然后可以使用add()put()方法添加更新对象,get取得对象,delete删除对象,clear清除所有对象。
const store = transaction.objectStore("users"),
    requestGet = store.get("007");
requestGet.onerror = (event) => alert();
requestGet.onsucess = (event) => alter(event.targer.result.firstName);



//拿到了对象存储的引用后,就可以使用add()put()写入数据了。
//当存在同名键时,add会导致错误,input会简单重写
//可以吧add想象成插入新值,put想象成更新值。
for (let user of users) {
    store.ass(user);
}//简单插入
//想验证请求是否成功,可以吧请求对象保存到一个变量,然后为他添加onerror和onsuccess事件处理程序:
let requestAdd, requests = [];
for (let user of users) {
    requestAdd = store.ass(user);
    requestAdd.onerror = () => {
        //处理错误
    };
    requestAdd.onsucess = () => {
        //处理成功
    };
    requests.push(requestAdd);
}

//如果想获取多条数据,则需要在事务中创建一个游标。游标是一个指向结果集的指针。
//需要在对象存储上调用openCursor()方法创建游标
//const requestCursor = store.openCursor();

//使用键范围可以让游标更容易管理
//使用only()方法并传入想要获取的值
//const onlyRange = IDBKeyRange.only("007");
//定义了范围之后,把它传给openCursor()方法就可以得到位于该范围的游标值
const range = IDBKeyRange.bound("007", "ace");

//openCursor()方法实际上可以接受两个参数,第一个是IDBKeyRange的实例,第二个是表示方向的字符串
//默认为next,还有nextunique,prev,prevunique
const requestCursor = store.openCursor(range, "nextunique");//跳过重复的项
requestCursor.onerror = (event) => alert();
//requestCursor.onsucess = (event) => alter(event.targer.result.firstName);


//在调用onsucess事件处理程序时,可通过event.target.result访问对象存储中的下一条记录。
//这个记录中保存着IDBCursor的实例或null,这个实例有几个属性
//direction:字符串常量,表示游标前进的方向
//key:对象的关键字
//value:实际的对象
//primaryKey:游标使用的键
//continue(key):移动到下一条记录
//advance(count):移动到指定count记录
requestCursor.onsucess = (event => {
    const cursor = event.target.result;//获取IDBCursor实例
    let value, updateRequest;
    if (cursor) {//永远要判断,如果有实例则执行
        if (cursor.key == "foo") {
            value = cursor.value;//获取当前对象
            value.password = "magic!";//更新密码
            updataRequest = cursor.updata(value);//请求保存更新后的对象
            updataRequest.onerror = () => { };
            updateRequest.onsucess = () => { };
        };
        cursor.continue();//移动到下一条记录
    } else {
        console.log("Done!");
    }
});
//调用cursor.continue()会出发另一个请求,并再次调用onsucess事件处理程序;


//对于某些数据集,可能需要为对象存储指定多个键。
//要创建新索引,首先要取得对象的引用,然后调用createIndex()
//const index=store.createIndex("username","username",{unique:true});
//第一个参数是索引的名称,第二个参数是索引属性的名称,第三个参数是包含键unique的options对象。
//这个选项中的unique应该必须指定,表示这个键是否在所有记录中唯一。
//索引返回的是IDBIndex实例,它非常像存储对象,可以使用openCursor()方法,只是result.key是索引键不是主键
//也可以使openKeyCursor()方法创建特殊游标,只返回每条记录的主键,接收参数与openCursor()方法一样
//只是event.reuslt.key是索引键,且event.result.value是主键而不是整个记录
const index=store.index("username");
requestIndex=index.openKeyCursor();
requestIndex.onerror=()=>{};
requestIndex.onsucess=(event)=>{
    //event.reuslt.key是索引键,event.result.value是主键
}
//可以使用get()方法,并传入索引键通过索引取得单条记录
requestIndexGet=index.get("007");
//如果想只取得给定索引的主键,使用getKey()方法

requestIndexGetKey=index.getKey("007");
requestIndexGetKey.onsucess=(event)=>{
    //event.reuslt.key是索引键,event.result.value是主键
}
//这个时候onsuccess事件处理程序中,event.target.result.value中是用户ID
//任何时候都可以使用IDBIndex对象下列属性取得索引的相关信息
//name,keyPath,objectStore,unique
const indexNames=store.indexNames;
for (let indexName in indexNames){
    const index=store.index(indexName);
    console.log(`Index name:${index.name}
    Keypath: ${index.keyPath}
    Unique: ${index.unique}`)
};
//删除索引
store.delateIndex("username");