在IndexedDB的对象库块UI中插入大量数据 [英] Inserting large quantities in IndexedDB's objectstore blocks UI
问题描述
我想在我的IndexedDB的对象库中保存一些〜35000个对象。
I want to save some ~35000 objects in my IndexedDB's objectstore. I am using below code to insert.
AddListings = function (x2j_list_new, callback) {
var transaction = db.transaction(["listings"], IDBTransaction.READ_WRITE);
var count = 0;
transaction.oncomplete = function (event) {
if (callback) {
console.log('x2jShowListing Added ' + count + '/' + x2j_list_new.length);
callback([count, x2j_list_new.length]);
}
};
transaction.onerror = function (e) {
console.log("myError: ", e);
if (callback) {
callback(false);
}
};
var store = transaction.objectStore("listings");
$.each(x2j_list_new, function (index0, item0) {
var request = store.put(item0);
request.onsuccess = function (event) {
count++;
// event.target.result
};
});
});
};
上面的代码工作正常,但循环和插入超过35000个对象会导致UI无法响应〜200秒。我想也许我可以使用WebWorkers,但IndexedDB在WebWorkers内部不可用。我试图找到一种批量插入的方式,找不到一个。任何想法如何插入大量的对象,而不会阻止用户界面?
The above code works fine, but looping and inserting over ~35000 objects makes the UI unresponsive for ~200 seconds. I thought maybe i can use WebWorkers, but IndexedDB is not available inside WebWorkers. I tried to find a way to bulk insert, couldn't find one. Any ideas of how to insert large quantities of objects without blocking the UI?
推荐答案
您现在处于正确的轨道上,但您要求浏览器在存储35,000个对象之前有机会完成存储一个。这里是代码,它在开始下一个(但使用相同的事务)之前异步地等待一个请求完成:
You're on the right track, but you're asking the browser to store 35,000 objects before it's had a chance to finish storing one. Here's code which asynchronously waits for one request to finish before starting the next (but using the same transaction):
openRequest = window.indexedDB.open("MyDatabase", 1);
openRequest.onerror = function(event) {
console.error(event);
};
openRequest.onsuccess = function (event) {
var db = openRequest.result;
db.onerror = function(event) {
// Generic error handler for all errors targeted at this database's requests
console.error(event.target);
window.alert("Database error: " + event.target.wePutrrorMessage || event.target.error.name || event.target.error || event.target.errorCode);
};
var transaction = db.transaction('item', "readwrite");
var itemStore = transaction.objectStore("item");
putNext();
function putNext() {
if (i<items.length) {
itemStore.put(items[i]).onsuccess = putNext;
++i;
} else { // complete
console.log('populate complete');
callback();
}
}
};
这篇关于在IndexedDB的对象库块UI中插入大量数据的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!