【问题标题】:IndexedDB throws an error when adding a new value into database向数据库中添加新值时,IndexedDB 引发错误
【发布时间】:2017-05-03 09:27:55
【问题描述】:

我在IndexedDb 中成功创建了一个数据库,但是当我尝试向数据库中添加一个值时,我看到了以下错误:

DOMException:无法在“IDBObjectStore”上执行“添加”:正在评估 对象存储的键路径没有产生值。

代码sn-p:

let db = new AngularIndexedDB('myDb', 1);

db.createStore(1, (evt) => {
  const objectStore = evt.currentTarget.result.createObjectStore('people', { keyPath: 'id', unique: true });
    objectStore.createIndex("name", "name", { unique: false });
    objectStore.createIndex("email", "email", { unique: true });
  }).then(() => {
    db.add('people', { name: 'name', email: 'email' }).then(() => {
  }, (error) => {
    console.log(error);
  });

}, (error) => {
   console.log(error);
});

我检查了表的名称。那是完全一样的。以及它的值各自的键。

我该如何解决这个问题?您能否分享对此错误的见解?

您的帮助将不胜感激。提前致谢。

【问题讨论】:

    标签: angularjs indexeddb


    【解决方案1】:

    当您使用键路径创建对象存储时:

     const store = db.createObjectStore('people', { keyPath: 'id' });
    

    然后:

    1. 您还必须指定存储应使用密钥生成器,即{keyPath: 'id', autoIncrement: true},这将为您生成数字键(1、2、3,...)并注入到值中;或:
    2. 您存储的值必须已经包含与键路径匹配的属性,例如store.put({name: 'foo', id: 1234})

    (另外,unique 不是对象存储的属性,只是索引。键在对象存储中始终是唯一的。)

    【讨论】:

      【解决方案2】:

      在我的情况下,当我尝试强制 IndexDB 通过保存其中键被分配为“未定义”的记录的深层副本来在数据库中创建记录的副本时遇到此错误。 显然,诀窍是从对象中删除属性:

       const record: T = JSON.parse(JSON.stringify(r));
       r.key = undefined; // does not work!
       delete(r.key); // works! with autoincrement it forces IndexDB to create a new key
       await datastore.add(record);
      

      【讨论】:

        【解决方案3】:

        对于那些在 TypeScript 属性方面遇到类似问题的人。

        假设我们有这个模型

        export default class Model {
           private _id: number;
           public get id(){
              return this._id;
           }
           public set id(value: number){
              this._id = value;
           }
        }
        

        让我们像这样初始化objectStore

           db.createObjectStore('Models', {
                                keyPath: 'id'
                            });
        

        然后我们要保存我们的模型

           let model = new Model();
           let ts = db.transaction('Models', "readwrite");
           let store = ts.objectStore('Models');
           store.add(model);
        

        很遗憾我们会收到一个

        DOMException: Failed to execute 'add' on 'IDBObjectStore': Evaluating the object store's key path did not yield a value.
        

        那是因为现在 IndexedDB 在解释我们的转译模型时遇到了问题(我不知道为什么,它可能与 tsconfig.json 相关?)

        一旦我们将模型更改为

           export default class Model {
              public id: number;
           }
        

        然后尝试保存,就实现了一个成功完成的交易。

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 2011-04-01
          • 1970-01-01
          • 1970-01-01
          • 2020-11-14
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多