【问题标题】:Update indexedDB更新 indexedDB
【发布时间】:2015-02-26 20:46:53
【问题描述】:

您好,我正在尝试更新记录 indexdb。我想实现一个通用方法,允许我升级到任何字段。

为此,我有一个函数可以返回我需要的记录。

function getObjectStoreClienteDB(clave,valor){
    //Ahora recogeremos los datos de nuestro almacén "Productos"
    var transaction = db.transaction(["customers"], "readwrite");
    var objectStore = transaction.objectStore("customers");

    var index = objectStore.index(clave);
    var singleKeyRange = IDBKeyRange.only(valor);

    // To use one of the key ranges, pass it in as the first argument of openCursor()/openKeyCursor()

    return  index.openCursor(singleKeyRange);
} 

另一个更新返回的记录

function updateClienteDB(clave,valor,newvalor){
    console.log("updateClienteDB ... clave: "+clave+" valor: "+valor+" newvalor: "+newvalor);
    var objectStore = db.transaction(["customers"], "readwrite").objectStore("customers");

    request = getObjectStoreClienteDB("name",valor);

    request.onsuccess = function(event) {
      // Get the old value that we want to update
      var data = request.result;

      // update the value(s) in the object that you want to change
      if(clave=="name")
        data.name = newvalor;
       else if(clave=="email")
        data.email = newvalor;
       else if(clave=="matricula")
        data.matricula = newvalor;
       else if(clave=="telefono")
        data.telefono = newvalor;

      // Put this updated object back into the database.
      var requestUpdate = objectStore.put(data);
       requestUpdate.onerror = function(event) {
          console.log("addCliente ..."+name+" "+email +" "+ event.target.errorCode);
       };
       requestUpdate.onsuccess = function(event) {
            console.log("All done!");
       };
    };
}

在该行中: var requestUpdate = objectStore.put(data);

错误: 未捕获的 TransactionInactiveError:无法在 'IDBObjectStore' 上执行 'put':事务已完成。

【问题讨论】:

    标签: javascript firefox indexeddb


    【解决方案1】:

    尝试使用相同的读写事务。看起来您在两个地方调用 db.transaction(...) 。然后,您尝试在不同事务的上下文中更新链接到不同事务的对象存储。结果是其中一个事务完成(其生命周期结束),可能是因为它超时了,因为它没有检测到任何已注册的请求。 objectStore 变量存在于提前完成的事务的生命周期内,因此您会收到事务完成错误。

    这很容易解决。您只需要在其生命周期结束之前在同一事务上注册一个新请求(put 请求)。为此,您可以 (a) 内联语句 request = getObjectStoreClienteDB("name",valor); 以便它附加到同一个事务实例,或者 (b) 将事务实例存储在单独的变量中并在两个调用中引用它。

    例如,以下代码是对您使用单个事务的修改:

    // this function was changed, it now takes an active transaction as its first argument.
    
    function getObjectStoreClienteDB(transaction, clave,valor){
      //Ahora recogeremos los datos de nuestro almacén "Productos"
    
      // this was changed. instead of creating a new transaction we just reference the
      // transaction instance passed to this function
      var objectStore = transaction.objectStore("customers");
    
      var index = objectStore.index(clave);
      var singleKeyRange = IDBKeyRange.only(valor);
    
      // To use one of the key ranges, pass it in as the first argument of openCursor()/openKeyCursor()
    
      return  index.openCursor(singleKeyRange);
    } 
    
    function updateClienteDB(clave,valor,newvalor){
      console.log("updateClienteDB ... clave: "+clave+" valor: "+valor+" newvalor: "+newvalor);
    
      // this line was added. we create the transaction here, once
      var transaction = db.transaction(["customers"], "readwrite");
    
      // this line was changed, we simply reference the transaction instance here instead of 
      // creating a second transaction
      var objectStore = transaction.objectStore("customers");
    
      // this line was  changed, we pass in the one active transaction instance to the function
      // now instead of having the function create its own transaction
      request = getObjectStoreClienteDB(transaction, "name",valor);
    
      request.onsuccess = function(event) {
        // Get the old value that we want to update
        var data = request.result;
    
        // update the value(s) in the object that you want to change
        if(clave=="name")
          data.name = newvalor;
        else if(clave=="email")
          data.email = newvalor;
        else if(clave=="matricula")
          data.matricula = newvalor;
        else if(clave=="telefono")
          data.telefono = newvalor;
    
        // Put this updated object back into the database.
    
        // this line now works. objectStore is attached to our 1 transaction that is still 'alive' 
        // because it gets registered 'in time' (before transaction finishes due to timeout due 
        // to no additional requests registered in allowed time window).
        var requestUpdate = objectStore.put(data);
    
    
        requestUpdate.onerror = function(event) {
          console.log("addCliente ..."+name+" "+email +" "+ event.target.errorCode);
        };
        requestUpdate.onsuccess = function(event) {
          console.log("All done!");
        };
      };
    }
    

    而且,为了清楚起见,这里是第二个例子。它使用调用者的事务重新创建对对象存储的引用,而不是交叉引用附加到不同事务的对象存储:

    function updateClienteDB(clave,valor,newvalor){
      console.log("updateClienteDB ... clave: "+clave+" valor: "+valor+" newvalor: "+newvalor);
      var objectStore = db.transaction(["customers"], "readwrite").objectStore("customers");
    
      request = getObjectStoreClienteDB("name",valor);
    
      request.onsuccess = function(event) {
        // Get the old value that we want to update
        var data = request.result;
    
        // update the value(s) in the object that you want to change
        if(clave=="name")
          data.name = newvalor;
        else if(clave=="email")
          data.email = newvalor;
        else if(clave=="matricula")
          data.matricula = newvalor;
        else if(clave=="telefono")
          data.telefono = newvalor;
    
        // Put this updated object back into the database.
    
        // the following line is changed so that it works. 
        //var requestUpdate = objectStore.put(data);
    
        var theOtherTransactionThatIsStillAlive = event.transaction;
        var objectStoreFromValidTransaction = theOtherTransactionThatIsStillAlive.objectStore('customers');
    
        var requestUpdate = objectStoreFromValidTransaction.put(data);
    
        requestUpdate.onerror = function(event) {
          console.log("addCliente ..."+name+" "+email +" "+ event.target.errorCode);
        };
        requestUpdate.onsuccess = function(event) {
          console.log("All done!");
        };
      };
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2022-10-08
      • 1970-01-01
      • 1970-01-01
      • 2012-06-28
      • 1970-01-01
      • 2021-06-24
      • 1970-01-01
      • 2017-11-29
      相关资源
      最近更新 更多