【问题标题】:JavaScript: How to pass and reset an incremental value to IndexedDB store get method?JavaScript:如何将增量值传递和重置到 IndexedDB 存储获取方法?
【发布时间】:2015-10-14 18:37:06
【问题描述】:

以下代码将参数变量nextId传递给IndexedDBStore get方法,如果传递的参数与记录的键匹配,则返回相应的记录。

最初我创建了另一个将所有记录放入数组的方法,然后我返回了数组长度。然而,我的循环只是得到了它应该得到的最后一个值。

代码如下: 注意:这个方法getEmployeeCount() 保存数组长度,使用如下:

    var something;
    for ( var i = 1; i <= getEmployeeCount(); i ++ )  {
        something = i;
    }

实验工作代码

function displaySingleRecord() {

    var output = document.getElementById( 'display' );
    output.textContent = "";

    var store = getObjectStore(DB_STORE_NAME, 'readwrite');

    var  nextId = incre ++;
    var request = store.get(nextId.toString());

    request.onerror = function(e) {
        dbStatusMessage('Cannot Retrieve data.', 1);
    };

    request.onsuccess = function(e) {

        output.innerHTML = '<b>Employee ID:</b> '  + request.result.employeeId  + ' <br> ' +
                           '<b>First Name:</b>  '  + request.result.firstName   + ' <br> ' +
                           '<b>Last Name:</b>   '  + request.result.lastName    + ' <br> ' +
                           '<b>Email:</b>       '  + request.result.email       + ' <br> ' +
                           '<b>Department:</b>  '  + request.result.department;
    };
}

当记录到达末尾或最后一条记录时,如何将增量重置为 1。我尝试使用 p 标签的输出,但没有用。

if ( output.textContent === '')
     doReset;

更新: 工作解决方案:

我面临的主要问题之一是从光标中获取总记录,而不是使用此数字作为阈值来重置增量过程。以下步骤说明了我为获得有效的解决方案所做的工作:

第一步: 我使用hidden field 来保存增量值并将其返回给执行增量的方法:我还添加了两个按钮:nextprev

HTML:

<!--Hidden Field-->
<input id="currentValue" value="0" type="hidden" />

<a id="next" href="/">Next</a>
<a id="prev" href="/">Previous</a>

<!--Output value here-->
<p id="output"></p>

接下来,我需要从数据存储中获取总记录:我通过在 getTotalRecordCount 方法中获取数组的长度来做到这一点。 请记住,当我们增加时,我们需要知道是否已经到达终点,这样我们就不会单击下一步并看到空结果,我们只需重置为一个。注意:我们将记录数组传递给回调以避免IndexedDB 异步架构问题:

从商店获取总记录的方法:

function getTotalRecordCount(callback) {

    var IDBOpenRequest = indexedDB.open(Database.Name, Database.Version);

    IDBOpenRequest.onerror = function () {
        dbStatusMessage('Database failed to open.', 1000);
    };

    IDBOpenRequest.onsuccess = function (e) {

        var objectStore = getObjectStore(Database.Store.USGeological, 
            Database.ReadWrite, e.target.result);

        var record = [];
        var cursorRequest = objectStore.openCursor();

        cursorRequest.onsuccess = function (e) {
            var cursor = e.target.result;
            if (cursor) {
                record.push(cursor.value);
                cursor.continue();
            } else {

                callback(record);
            }
        };

        e.target.result.close();
    };
}

接下来:我们从getNextId方法的回调中访问记录数组。

代码:

function getNextId(val) {

    getTotalRecordCount(function (record){

    // Get initial or current value from hidden field.    
    var currentValue = document.getElementById('currentValue');

    var newValue = parseInt(currentValue.value,10) + val;

    // Use the record array from the callbck, pass it's length.
    // IMPORTANT: If our current position or count is greater 
    // than array length we go back to 1.   

    if (newValue > parseInt(record.length) || newValue <= 0) {
        newValue = 1;
    }

        currentValue.value = newValue;
        getRecordByRotatingId(newValue);

    });
}

最后:我们将结果显示到屏幕上:这段代码只是将增量值传递给get method,并根据当前id显示数据:

注意:这是开发代码,我没有使用所有的回调事件,例如:在 try catch 中我故意不使用 catch 块中的 e.message。

   function getRecordByRotatingId(value) {

        var output = document.getElementById('output');
        output.textContent = "";

        var IDBOpenRequest = indexedDB.open(Database.Name, Database.Version);

        IDBOpenRequest.onerror = function () {
            dbStatusMessage('Database failed to open.', 1000);
        };

        IDBOpenRequest.onsuccess = function (e) {

            var objectStore = getObjectStore(Database.Store.USGeological,
                Database.ReadOnly, e.target.result);

            var request = objectStore.get(value);

            request.onsuccess = function () {

                try {

                    output.innerHTML = '<b>State ID:</b> ' + 
                        request.result.StateId +  ' <br> ' +
                        '<b>State:</b>  ' + request.result.StateName + 
                        ' <br> ' + '<b>Abbreviation:</b>   ' + 
                        request.result.StateAbbreviation;

                } catch (e) {

                    dbStatusMessage('Data does not exist.', 1000);
                }
            };

            request.onerror = function () {
                dbStatusMessage('Data does not exist.', 1000);
            };

            e.target.result.close();
        };
}

此代码在具有大数据结果集的生产中会产生性能影响,这是因为每次单击下一个或上一个时它都会调用游标。我们可以将总记录数放入内存(本地存储)并在每次加载页面时更新。

更新: 在我上面的初始更新之后,我发现您还可以使用索引计数方法获取对象存储中的总记录: 有了这个,我将方法合并为一个方法:

IDBIndex.count()

function getRecordByNextId(val) {

    var IDBOpenRequest = indexedDB.open(Database.Name, Database.Version);

    IDBOpenRequest.onerror = function () {
        dbStatusMessage('Database failed to open.', 1000);
    };

    IDBOpenRequest.onsuccess = function (e) {

        var output = document.getElementById('output');
        output.textContent = "";

        var objectStore = getObjectStore(Database.Store.USGeological,
            Database.ReadOnly, e.target.result);

        var myIndex = objectStore.index('StateName');
        var request = myIndex.count();

        request.onsuccess = function () {

            var currentValue = document.getElementById('currentValue');
            var newValue = parseInt(currentValue.value, 10) + val;

           if (newValue > parseInt(request.result) || newValue <= 0) {
                newValue = 1;
            }

            currentValue.value = newValue;

            var dataRequest = objectStore.get(parseInt(currentValue.value));

            dataRequest.onsuccess = function (e) {

                output.innerHTML = '<b>State ID:</b> ' + dataRequest.result.StateId
                    + ' <br> ' + '<b>State:</b>  ' + dataRequest.result.StateName +
                    ' <br> ' + '<b>Abbreviation:</b>   ' +
                    dataRequest.result.StateAbbreviation;
            };
        };


        e.target.result.close();
    };
}

【问题讨论】:

  • 您的问题不是特别清楚,因为您将数据库操作与输出逻辑混合在一起。您是否试图检测何时达到最后一条记录?如果是这样:当您访问不存在的记录时,即当您遍历所有记录时,request.result 将是未定义的值。这假定您的记录具有连续的 ID(没有间隙),并且您没有实际未定义值的记录(不寻常但允许)。在这些情况下,您可能想要使用游标,即使您不调用 continue()。

标签: javascript indexeddb


【解决方案1】:

嗯,我觉得你的问题不是很清楚,但也许这只是我。如果我完全理解您,也许我可以建议您执行以下操作:

function iterateEmployees(db) {
  var tx = db.transaction(DB_STORE_NAME);
  var store = tx.objectStore(DB_STORE_NAME);
  var request = store.openCursor();
  request.onsuccess = function(event) {
    var cursor = event.target.result;
    if(cursor) {
      var employee = cursor.value;
      printEmployeeDetails(employee);
      cursor.continue(); // advance the cursor by 1
    } else {
      // no more employees, or no employees found at all
      doSomethingAfterListingEmployees();
    }
  };
}

function printEmployeeDetails(employee) {
  output.innerHTML += '<p>Id: ' + employee.employeeId + '</p>' +
    'etc ...';
}

编辑,阅读您的评论后,您可能想做的是了解 cursor.advance。见https://developer.mozilla.org/en-US/docs/Web/API/IDBCursor/advance。您可以做的是每次用户单击按钮时打开一个光标,然后每次用户单击按钮时增加一个计数器。

【讨论】:

  • 简而言之,我只是尝试在单击按钮时单独显示数据。下一条记录基于增量参数显示,这就是为什么我使用get 方法,然后传递一个值。当我使用您的代码时,光标直接移动到数据的末尾。除非使用警报方法,否则它不会根据需要逐步执行。同样,我只是试图在用户单击时显示每条记录。最好是我想前进和后退。非常感谢。
猜你喜欢
  • 2023-03-07
  • 2019-10-18
  • 1970-01-01
  • 2016-06-16
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2023-03-13
  • 1970-01-01
相关资源
最近更新 更多