IndexedDB 游标 .onsuccess 作为承诺

IndexDB cursor .onsucess as a promise

首先,我找不到适合这个问题的标题 - 请随时编辑。

我有以下函数从 indexDb 中读取 objects,

loadNeededParcels = property => {
    const dbResults = [];
    var readTransaction = this.db
      .transaction("parcelData")
      .objectStore("parcelData");
    readTransaction.openCursor().onerror = e => {
      console.log("open cursor error ", e);
    };
    readTransaction.openCursor().onsuccess = e => {
      const cursor = e.target.result;
      if (cursor) {
        dbResults.push(cursor.value);
        cursor.continue();
      } else {   
        return dbResults;
      }
    };
  };

现在当我用一个简单的函数调用来调用这个函数时,例如:

console.log(loadNeededParcels('hasData'))

控制台日志是undefined。我猜这是因为该函数不等待光标完成并且 return dbResults 变量?

所以我的问题是 - 我怎样才能 re-write 这个功能作为一个承诺,或者更确切地说等待 readTransaction.openCursor().onsucess 触发?

所以预期的结果是函数实际 return 退出前从数据库中读取的值。

我正在使用游标,因为 .getAll() IE 不支持该方法。

我最终使用的一个简单的解决方案:

  loadNeededParcels = property => {
    return new Promise((resolve, reject) => {
      var readTransaction = this.db
        .transaction("parcelData")
        .objectStore("parcelData");
      readTransaction.openCursor().onerror = e => {
        reject(e);
      };
      const dbResults = [];
      readTransaction.openCursor().onsuccess = e => {
        const cursor = e.target.result;
        if (cursor) {
          dbResults.push(cursor.value);
          cursor.continue();
        } else {
          resolve(dbResults);
        }
      };
    });
  };

尝试这样的事情。不要调用 openCursor 两次,这会创建两个请求。

function loadNeededParcels(db, property) {
 return new Promise(function(resolve, reject) {
   var results = [];
   var tx = db.transaction('parcelData');
   tx.onerror = function(event) {
     reject(tx.error);
   };
   var store = tx.objectStore('parcelData');

   // Open a cursor over all items
   var request = store.openCursor();

   request.onsuccess = function(event) {
     var cursor = request.result;
     if(cursor) {
       var value = cursor.value;
       if(value) {
         // Only append defined values to the array
         results.push(cursor.value);
       }

       cursor.continue();
     } else {
       resolve(results);
     }
   };
 });
}

loadNeededParcels(db, 'hasData').then(function(results) {
  console.log('Results', results);
}).catch(function(error) {
  console.error(error);
});