2

I am trying to wrap my head around IndexedDB.

I created an object store that uses a key-generator with no key-path.

var objectStore = db.createObjectStore("domains", {autoIncrement: true });
objectStore.createIndex("domain", "domain", { unique: true, multiEntry: true });

In order to access my records, I created an index that references my object store. The index's key path is the domain property of my records.

Here is an example of what one record in my object store might look like:

{ domain: ["stackexchange",
           "stackoverflow",
           "superuser",
           "askubuntu",
           "serverfault"], 

  bold          : ["<strong>",1], 
  italic        : ["<em>",1],
  strikethrough : ["<del>",1],
  superscript   : ["<sup>",1],
  subscript     : ["<sub>",1],
  heading1      : ["<h1>",1],
  heading2      : ["<h2>",1],
  heading3      : ["<h3>",1],
  blockquote    : ["<blockquote>",1],
  code          : ["<code>",1],
  newline       : ["<br>",2],
  horizontal    : ["<hr>",2]
},

Each entry appearing in the domain property is guaranteed to be unique among the set consisting of the union of every domain key's value out of every record of my object store. I.E. You won't find any of these domains anywhere else in my object store.

I need to let user's edit the objects in the object store. Provided with a single domain, I can retrieve the associated object like this:

var DBOpenRequest= window.indexedDB.open(db_name, db_version);
DBOpenRequest.onsuccess= function(event){   
    var db= DBOpenRequest.result;
    var domains=db.transaction('domains', 'readwrite').objectStore('domains');

    var query = domains.index("domain").get("stackoverflow");   
};

Now, here is the part where I am confused. Once the user has changed the properties that they want to edit/added new properties as they please, I need to save their changes by replacing the object retrieved above with the new object that the user created. (or modify the original object and save the changes).

I think I need to use IDBObjectStore.put() to do this.

The put() method takes two parameters, one required and one optional:

value
    The value to be stored.
key
    The key to use to identify the record. If unspecified, it results to null.

The second parameter is presumably optional for the instances in which you are using inline keys. I am using out-of-line keys that were generated with a key generator.

How can I get the (auto-generated, out-of-line) key of the object that I retrieved through my index, so I can communicate to the object store that I want to modify that pre-existing object and not create a new one?

Is there another way I should be going about this?

4

2 回答 2

1

以下是IndexedDB 索引规范中的文本。

每个索引也有一个唯一的标志。当此标志设置为 true 时,索引强制索引中没有两条记录具有相同的键。如果尝试插入或修改索引的引用对象存储中的记录,以便在记录新值上评估索引的键路径产生索引中已存在的结果,则尝试修改对象存储失败

因此,如果在该属性上创建了唯一索引,则不能使用“put()” 。因此,您可以创建一个主键,即在创建对象存储时使用keyPath 。

var objectStore = db.createObjectStore("domains", {keyPath: "domain"});

检查以下 2 个 URL,这将帮助您更深入地了解如果其上存在唯一索引,则无法执行更新。

于 2015-06-01T15:07:22.303 回答
0

给未来的读者。作为使用密钥路径的替代方法:

而不是使用IDBObjectStore.put()您可以迭代对象存储中的对象IDBObjectStore.openCursor()

一旦你击中你正在寻找的对象,你可以使用:

于 2015-06-02T14:47:11.273 回答