Title: [120967] trunk
Revision
120967
Author
[email protected]
Date
2012-06-21 15:28:40 -0700 (Thu, 21 Jun 2012)

Log Message

IndexedDB: Implement spec behavior for multiEntry indexes with invalid/duplicate subkeys
https://bugs.webkit.org/show_bug.cgi?id=86123

Patch by Alec Flett <[email protected]> on 2012-06-21
Reviewed by Darin Fisher.

Source/WebCore:

Distinguish between an actual invalid IDBKey, and an array of
possibly-invalid subkeys by making IDBKey::isValid() check subkeys
if the type is an array.

Introduce a new way to transform an IDBKey into a
multiEntry-specific IDBKey, (IDBKey::createMultiEntryArray)
throwing out duplicates and invalid keys. Use it when storing
index entries for multiEntry indexes.

No new tests: existing tests have been altered to include new behavior.

* Modules/indexeddb/IDBCursor.cpp:
(WebCore::IDBCursor::continueFunction):
* Modules/indexeddb/IDBFactory.cpp:
(WebCore::IDBFactory::cmp):
* Modules/indexeddb/IDBIndex.cpp:
(WebCore::IDBIndex::get):
(WebCore::IDBIndex::getKey):
* Modules/indexeddb/IDBKey.cpp:
(WebCore::IDBKey::isValid):
(WebCore):
* Modules/indexeddb/IDBKey.h:
(WebCore::IDBKey::createMultiEntryArray):
(IDBKey):
* Modules/indexeddb/IDBKeyRange.cpp:
(WebCore::IDBKeyRange::only):
(WebCore::IDBKeyRange::lowerBound):
(WebCore::IDBKeyRange::upperBound):
(WebCore::IDBKeyRange::bound):
* Modules/indexeddb/IDBLevelDBBackingStore.cpp:
(WebCore::IDBLevelDBBackingStore::putObjectStoreRecord):
(WebCore::IDBLevelDBBackingStore::putIndexDataForRecord):
* Modules/indexeddb/IDBLevelDBCoding.cpp:
(WebCore::IDBLevelDBCoding::encodeIDBKey):
* Modules/indexeddb/IDBObjectStore.cpp:
(WebCore::IDBObjectStore::get):
(WebCore::IDBObjectStore::add):
(WebCore::IDBObjectStore::put):
* Modules/indexeddb/IDBObjectStoreBackendImpl.cpp:
(WebCore::IDBObjectStoreBackendImpl::putInternal):
(WebCore):
* bindings/v8/IDBBindingUtilities.cpp:
(WebCore::createIDBKeyFromValue):

Source/WebKit/chromium:

Add matching isValid() to WebIDBKey to match the one in IDBKey.

* public/WebIDBKey.h:
* src/WebIDBKey.cpp:
(WebKit::WebIDBKey::isValid):
(WebKit):
* src/WebIDBKeyRange.cpp:
(WebKit::WebIDBKeyRange::assign):

LayoutTests:

* storage/indexeddb/index-multientry-expected.txt:
* storage/indexeddb/resources/index-multientry.js:
(addData):
(verifyIndexes.request.onsuccess):
(verifyIndexes):
(verifyUniqueConstraint.request.onsuccess.request.onsuccess.request.onerror):
(verifyUniqueConstraint.request.onsuccess.request.onsuccess):
(verifyUniqueConstraint.request.onsuccess):
(verifyUniqueConstraint):

Modified Paths

Diff

Modified: trunk/LayoutTests/ChangeLog (120966 => 120967)


--- trunk/LayoutTests/ChangeLog	2012-06-21 22:02:32 UTC (rev 120966)
+++ trunk/LayoutTests/ChangeLog	2012-06-21 22:28:40 UTC (rev 120967)
@@ -1,3 +1,20 @@
+2012-06-21  Alec Flett  <[email protected]>
+
+        IndexedDB: Implement spec behavior for multiEntry indexes with invalid/duplicate subkeys
+        https://bugs.webkit.org/show_bug.cgi?id=86123
+
+        Reviewed by Darin Fisher.
+
+        * storage/indexeddb/index-multientry-expected.txt:
+        * storage/indexeddb/resources/index-multientry.js:
+        (addData):
+        (verifyIndexes.request.onsuccess):
+        (verifyIndexes):
+        (verifyUniqueConstraint.request.onsuccess.request.onsuccess.request.onerror):
+        (verifyUniqueConstraint.request.onsuccess.request.onsuccess):
+        (verifyUniqueConstraint.request.onsuccess):
+        (verifyUniqueConstraint):
+
 2012-06-21  Tim Horton  <[email protected]>
 
         SVGImageCache isn't invalidated for <img> on dynamic page scale changes

Modified: trunk/LayoutTests/storage/indexeddb/index-multientry-expected.txt (120966 => 120967)


--- trunk/LayoutTests/storage/indexeddb/index-multientry-expected.txt	2012-06-21 22:02:32 UTC (rev 120966)
+++ trunk/LayoutTests/storage/indexeddb/index-multientry-expected.txt	2012-06-21 22:28:40 UTC (rev 120967)
@@ -25,6 +25,8 @@
 Now overwrite them with what we're expecting
 transaction.objectStore('store').put({x: [1, 2, 3], y: 'a'}, 'foo')
 transaction.objectStore('store').put({x: [4, 5, 6], y: 'b'}, 'bar')
+transaction.objectStore('store').put({x: [7, 7, 8, 7], y: 'c'}, 'baz')
+transaction.objectStore('store').put({x: [null, 9, 9], y: 'd'}, 'bloop')
 
 Verifying index: index
 transaction = db.transaction(['store'], 'readonly')
@@ -34,32 +36,56 @@
 PASS cursor.key is 1
 PASS cursor.primaryKey is "foo"
 PASS cursor.value.y is "a"
+cursor.continue()
 cursor = event.target.result
 PASS ex is non-null.
 PASS cursor.key is 2
 PASS cursor.primaryKey is "foo"
 PASS cursor.value.y is "a"
+cursor.continue()
 cursor = event.target.result
 PASS ex is non-null.
 PASS cursor.key is 3
 PASS cursor.primaryKey is "foo"
 PASS cursor.value.y is "a"
+cursor.continue()
 cursor = event.target.result
 PASS ex is non-null.
 PASS cursor.key is 4
 PASS cursor.primaryKey is "bar"
 PASS cursor.value.y is "b"
+cursor.continue()
 cursor = event.target.result
 PASS ex is non-null.
 PASS cursor.key is 5
 PASS cursor.primaryKey is "bar"
 PASS cursor.value.y is "b"
+cursor.continue()
 cursor = event.target.result
 PASS ex is non-null.
 PASS cursor.key is 6
 PASS cursor.primaryKey is "bar"
 PASS cursor.value.y is "b"
+cursor.continue()
 cursor = event.target.result
+PASS ex is non-null.
+PASS cursor.key is 7
+PASS cursor.primaryKey is "baz"
+PASS cursor.value.y is "c"
+cursor.continue()
+cursor = event.target.result
+PASS ex is non-null.
+PASS cursor.key is 8
+PASS cursor.primaryKey is "baz"
+PASS cursor.value.y is "c"
+cursor.continue()
+cursor = event.target.result
+PASS ex is non-null.
+PASS cursor.key is 9
+PASS cursor.primaryKey is "bloop"
+PASS cursor.value.y is "d"
+cursor.continue()
+cursor = event.target.result
 PASS expected.length is 0
 
 Verifying unique constraint on multiEntry index
@@ -71,7 +97,7 @@
 success!
 This should fail the uniqueness constraint on the index, and fail:
 transaction.objectStore('store-unique').put({x: [5, 2], y: 'c'}, 'should fail')
-Request failed, as expected
+Request failed, as expected (DataError)
 Transaction aborted as expected
 
 Create an index on a populated store
@@ -89,32 +115,56 @@
 PASS cursor.key is 1
 PASS cursor.primaryKey is "foo"
 PASS cursor.value.y is "a"
+cursor.continue()
 cursor = event.target.result
 PASS ex is non-null.
 PASS cursor.key is 2
 PASS cursor.primaryKey is "foo"
 PASS cursor.value.y is "a"
+cursor.continue()
 cursor = event.target.result
 PASS ex is non-null.
 PASS cursor.key is 3
 PASS cursor.primaryKey is "foo"
 PASS cursor.value.y is "a"
+cursor.continue()
 cursor = event.target.result
 PASS ex is non-null.
 PASS cursor.key is 4
 PASS cursor.primaryKey is "bar"
 PASS cursor.value.y is "b"
+cursor.continue()
 cursor = event.target.result
 PASS ex is non-null.
 PASS cursor.key is 5
 PASS cursor.primaryKey is "bar"
 PASS cursor.value.y is "b"
+cursor.continue()
 cursor = event.target.result
 PASS ex is non-null.
 PASS cursor.key is 6
 PASS cursor.primaryKey is "bar"
 PASS cursor.value.y is "b"
+cursor.continue()
 cursor = event.target.result
+PASS ex is non-null.
+PASS cursor.key is 7
+PASS cursor.primaryKey is "baz"
+PASS cursor.value.y is "c"
+cursor.continue()
+cursor = event.target.result
+PASS ex is non-null.
+PASS cursor.key is 8
+PASS cursor.primaryKey is "baz"
+PASS cursor.value.y is "c"
+cursor.continue()
+cursor = event.target.result
+PASS ex is non-null.
+PASS cursor.key is 9
+PASS cursor.primaryKey is "bloop"
+PASS cursor.value.y is "d"
+cursor.continue()
+cursor = event.target.result
 PASS expected.length is 0
 PASS successfullyParsed is true
 

Modified: trunk/LayoutTests/storage/indexeddb/resources/index-multientry.js (120966 => 120967)


--- trunk/LayoutTests/storage/indexeddb/resources/index-multientry.js	2012-06-21 22:02:32 UTC (rev 120966)
+++ trunk/LayoutTests/storage/indexeddb/resources/index-multientry.js	2012-06-21 22:28:40 UTC (rev 120967)
@@ -54,6 +54,10 @@
     request._onerror_ = unexpectedErrorCallback;
     request = evalAndLog("transaction.objectStore('store').put({x: [4, 5, 6], y: 'b'}, 'bar')");
     request._onerror_ = unexpectedErrorCallback;
+    request = evalAndLog("transaction.objectStore('store').put({x: [7, 7, 8, 7], y: 'c'}, 'baz')");
+    request._onerror_ = unexpectedErrorCallback;
+    request = evalAndLog("transaction.objectStore('store').put({x: [null, 9, 9], y: 'd'}, 'bloop')");
+    request._onerror_ = unexpectedErrorCallback;
 }
 
 function verifyIndexes(indexName, callback)
@@ -71,6 +75,9 @@
         { key: 4, primaryKey: 'bar', y: 'b' },
         { key: 5, primaryKey: 'bar', y: 'b' },
         { key: 6, primaryKey: 'bar', y: 'b' },
+        { key: 7, primaryKey: 'baz', y: 'c' },
+        { key: 8, primaryKey: 'baz', y: 'c' },
+        { key: 9, primaryKey: 'bloop', y: 'd' },
     ];
 
     var request = evalAndLog("transaction.objectStore('store').index('" + indexName + "').openCursor()");
@@ -83,7 +90,7 @@
             shouldBe("cursor.key", String(ex.key));
             shouldBeEqualToString("cursor.primaryKey", ex.primaryKey);
             shouldBeEqualToString("cursor.value.y", ex.y);
-            cursor.continue();
+            evalAndLog("cursor.continue()");
         } else {
             shouldBe("expected.length", "0");
         }
@@ -113,7 +120,7 @@
             debug("This should fail the uniqueness constraint on the index, and fail:");
             request = evalAndLog("transaction.objectStore('store-unique').put({x: [5, 2], y: 'c'}, 'should fail')");
             request._onsuccess_ = unexpectedSuccessCallback;
-            request._onerror_ = function() { debug("Request failed, as expected"); };
+            request._onerror_ = function() { debug("Request failed, as expected (" + request.error.name + ")"); };
         };
     };
 }

Modified: trunk/Source/WebCore/ChangeLog (120966 => 120967)


--- trunk/Source/WebCore/ChangeLog	2012-06-21 22:02:32 UTC (rev 120966)
+++ trunk/Source/WebCore/ChangeLog	2012-06-21 22:28:40 UTC (rev 120967)
@@ -1,3 +1,54 @@
+2012-06-21  Alec Flett  <[email protected]>
+
+        IndexedDB: Implement spec behavior for multiEntry indexes with invalid/duplicate subkeys
+        https://bugs.webkit.org/show_bug.cgi?id=86123
+
+        Reviewed by Darin Fisher.
+
+        Distinguish between an actual invalid IDBKey, and an array of
+        possibly-invalid subkeys by making IDBKey::isValid() check subkeys
+        if the type is an array.
+
+        Introduce a new way to transform an IDBKey into a
+        multiEntry-specific IDBKey, (IDBKey::createMultiEntryArray)
+        throwing out duplicates and invalid keys. Use it when storing
+        index entries for multiEntry indexes.
+
+        No new tests: existing tests have been altered to include new behavior.
+
+        * Modules/indexeddb/IDBCursor.cpp:
+        (WebCore::IDBCursor::continueFunction):
+        * Modules/indexeddb/IDBFactory.cpp:
+        (WebCore::IDBFactory::cmp):
+        * Modules/indexeddb/IDBIndex.cpp:
+        (WebCore::IDBIndex::get):
+        (WebCore::IDBIndex::getKey):
+        * Modules/indexeddb/IDBKey.cpp:
+        (WebCore::IDBKey::isValid):
+        (WebCore):
+        * Modules/indexeddb/IDBKey.h:
+        (WebCore::IDBKey::createMultiEntryArray):
+        (IDBKey):
+        * Modules/indexeddb/IDBKeyRange.cpp:
+        (WebCore::IDBKeyRange::only):
+        (WebCore::IDBKeyRange::lowerBound):
+        (WebCore::IDBKeyRange::upperBound):
+        (WebCore::IDBKeyRange::bound):
+        * Modules/indexeddb/IDBLevelDBBackingStore.cpp:
+        (WebCore::IDBLevelDBBackingStore::putObjectStoreRecord):
+        (WebCore::IDBLevelDBBackingStore::putIndexDataForRecord):
+        * Modules/indexeddb/IDBLevelDBCoding.cpp:
+        (WebCore::IDBLevelDBCoding::encodeIDBKey):
+        * Modules/indexeddb/IDBObjectStore.cpp:
+        (WebCore::IDBObjectStore::get):
+        (WebCore::IDBObjectStore::add):
+        (WebCore::IDBObjectStore::put):
+        * Modules/indexeddb/IDBObjectStoreBackendImpl.cpp:
+        (WebCore::IDBObjectStoreBackendImpl::putInternal):
+        (WebCore):
+        * bindings/v8/IDBBindingUtilities.cpp:
+        (WebCore::createIDBKeyFromValue):
+
 2012-06-21  Ian Vollick  <[email protected]>
 
         [chromium] Overlays when using the web inspector are blurry with device scale factor > 1

Modified: trunk/Source/WebCore/Modules/indexeddb/IDBCursor.cpp (120966 => 120967)


--- trunk/Source/WebCore/Modules/indexeddb/IDBCursor.cpp	2012-06-21 22:02:32 UTC (rev 120966)
+++ trunk/Source/WebCore/Modules/indexeddb/IDBCursor.cpp	2012-06-21 22:28:40 UTC (rev 120967)
@@ -183,7 +183,7 @@
 void IDBCursor::continueFunction(PassRefPtr<IDBKey> key, ExceptionCode& ec)
 {
     IDB_TRACE("IDBCursor::continue");
-    if (key && (key->type() == IDBKey::InvalidType)) {
+    if (key && !key->isValid()) {
         ec = IDBDatabaseException::DATA_ERR;
         return;
     }

Modified: trunk/Source/WebCore/Modules/indexeddb/IDBFactory.cpp (120966 => 120967)


--- trunk/Source/WebCore/Modules/indexeddb/IDBFactory.cpp	2012-06-21 22:02:32 UTC (rev 120966)
+++ trunk/Source/WebCore/Modules/indexeddb/IDBFactory.cpp	2012-06-21 22:28:40 UTC (rev 120967)
@@ -133,7 +133,7 @@
     ASSERT(first);
     ASSERT(second);
 
-    if (first->type() == IDBKey::InvalidType || second->type() == IDBKey::InvalidType) {
+    if (!first->isValid() || !second->isValid()) {
         ec = IDBDatabaseException::DATA_ERR;
         return 0;
     }    

Modified: trunk/Source/WebCore/Modules/indexeddb/IDBKey.cpp (120966 => 120967)


--- trunk/Source/WebCore/Modules/indexeddb/IDBKey.cpp	2012-06-21 22:02:32 UTC (rev 120966)
+++ trunk/Source/WebCore/Modules/indexeddb/IDBKey.cpp	2012-06-21 22:28:40 UTC (rev 120967)
@@ -40,6 +40,21 @@
 {
 }
 
+bool IDBKey::isValid() const
+{
+    if (m_type == InvalidType)
+        return false;
+
+    if (m_type == ArrayType) {
+        for (size_t i = 0; i < m_array.size(); i++) {
+            if (!m_array[i]->isValid())
+                return false;
+        }
+    }
+
+    return true;
+}
+
 int IDBKey::compare(const IDBKey* other) const
 {
     ASSERT(other);

Modified: trunk/Source/WebCore/Modules/indexeddb/IDBKey.h (120966 => 120967)


--- trunk/Source/WebCore/Modules/indexeddb/IDBKey.h	2012-06-21 22:02:32 UTC (rev 120966)
+++ trunk/Source/WebCore/Modules/indexeddb/IDBKey.h	2012-06-21 22:28:40 UTC (rev 120967)
@@ -73,6 +73,32 @@
         return idbKey.release();
     }
 
+    static PassRefPtr<IDBKey> createMultiEntryArray(const KeyArray& array)
+    {
+        RefPtr<IDBKey> idbKey = adoptRef(new IDBKey());
+        idbKey->m_type = ArrayType;
+        KeyArray& result = idbKey->m_array;
+
+        for (size_t i = 0; i < array.size(); i++) {
+            if (!array[i]->isValid())
+                continue;
+
+            bool skip = false;
+            for (size_t j = 0; j < result.size(); j++) {
+                if (array[i]->isEqual(result[j].get())) {
+                    skip = true;
+                    break;
+                }
+            }
+            if (!skip) {
+                result.append(array[i]);
+                idbKey->m_sizeEstimate += array[i]->m_sizeEstimate;
+            }
+        }
+        ASSERT(idbKey->isValid());
+        return idbKey.release();
+    }
+
     static PassRefPtr<IDBKey> createArray(const KeyArray& array)
     {
         RefPtr<IDBKey> idbKey = adoptRef(new IDBKey());
@@ -98,7 +124,7 @@
     };
 
     Type type() const { return m_type; }
-    bool isValid() const { return m_type != InvalidType; }
+    bool isValid() const;
 
     const KeyArray& array() const
     {

Modified: trunk/Source/WebCore/Modules/indexeddb/IDBLevelDBBackingStore.cpp (120966 => 120967)


--- trunk/Source/WebCore/Modules/indexeddb/IDBLevelDBBackingStore.cpp	2012-06-21 22:02:32 UTC (rev 120966)
+++ trunk/Source/WebCore/Modules/indexeddb/IDBLevelDBBackingStore.cpp	2012-06-21 22:28:40 UTC (rev 120967)
@@ -587,6 +587,7 @@
 
 bool IDBLevelDBBackingStore::putObjectStoreRecord(int64_t databaseId, int64_t objectStoreId, const IDBKey& key, const String& value, ObjectStoreRecordIdentifier* recordIdentifier)
 {
+    ASSERT(key.isValid());
     ASSERT(m_currentTransaction);
     int64_t version = getNewVersionNumber(m_currentTransaction.get(), databaseId, objectStoreId);
     const Vector<char> objectStoredataKey = ObjectStoreDataKey::encode(databaseId, objectStoreId, key);
@@ -869,6 +870,7 @@
 
 bool IDBLevelDBBackingStore::putIndexDataForRecord(int64_t databaseId, int64_t objectStoreId, int64_t indexId, const IDBKey& key, const ObjectStoreRecordIdentifier* recordIdentifier)
 {
+    ASSERT(key.isValid());
     ASSERT(indexId >= kMinimumIndexId);
     const LevelDBRecordIdentifier* levelDBRecordIdentifier = static_cast<const LevelDBRecordIdentifier*>(recordIdentifier);
 

Modified: trunk/Source/WebCore/Modules/indexeddb/IDBLevelDBCoding.cpp (120966 => 120967)


--- trunk/Source/WebCore/Modules/indexeddb/IDBLevelDBCoding.cpp	2012-06-21 22:02:32 UTC (rev 120966)
+++ trunk/Source/WebCore/Modules/indexeddb/IDBLevelDBCoding.cpp	2012-06-21 22:28:40 UTC (rev 120967)
@@ -387,6 +387,7 @@
 void encodeIDBKey(const IDBKey& key, Vector<char>& into)
 {
     size_t previousSize = into.size();
+    ASSERT(key.isValid());
     switch (key.type()) {
     case IDBKey::InvalidType:
     case IDBKey::MinType:

Modified: trunk/Source/WebCore/Modules/indexeddb/IDBObjectStore.cpp (120966 => 120967)


--- trunk/Source/WebCore/Modules/indexeddb/IDBObjectStore.cpp	2012-06-21 22:02:32 UTC (rev 120966)
+++ trunk/Source/WebCore/Modules/indexeddb/IDBObjectStore.cpp	2012-06-21 22:28:40 UTC (rev 120967)
@@ -126,7 +126,7 @@
         return 0;
     }
 
-    if (key && (key->type() == IDBKey::InvalidType)) {
+    if (key && !key->isValid()) {
         ec = IDBDatabaseException::DATA_ERR;
         return 0;
     }
@@ -159,7 +159,7 @@
         return 0;
     }
 
-    if (key && (key->type() == IDBKey::InvalidType)) {
+    if (key && !key->isValid()) {
         ec = IDBDatabaseException::DATA_ERR;
         return 0;
     }

Modified: trunk/Source/WebCore/Modules/indexeddb/IDBObjectStoreBackendImpl.cpp (120966 => 120967)


--- trunk/Source/WebCore/Modules/indexeddb/IDBObjectStoreBackendImpl.cpp	2012-06-21 22:02:32 UTC (rev 120966)
+++ trunk/Source/WebCore/Modules/indexeddb/IDBObjectStoreBackendImpl.cpp	2012-06-21 22:28:40 UTC (rev 120967)
@@ -264,6 +264,9 @@
         const RefPtr<IDBIndexBackendImpl>& index = it->second;
 
         RefPtr<IDBKey> indexKey = fetchKeyFromKeyPath(value.get(), index->keyPath());
+        if (indexKey && index->multiEntry() && indexKey->type() == IDBKey::ArrayType)
+            indexKey = IDBKey::createMultiEntryArray(indexKey->array());
+
         if (!indexKey || !indexKey->isValid()) {
             // Null/invalid keys not added to index; null entry keeps iterator/vector indexes consistent.
             indexKey.clear();
@@ -279,7 +282,7 @@
         }
 
         if (index->multiEntry() && indexKey->type() == IDBKey::ArrayType) {
-           for (size_t j = 0; j < indexKey->array().size(); ++j) {
+            for (size_t j = 0; j < indexKey->array().size(); ++j) {
                 if (!index->addingKeyAllowed(indexKey->array()[j].get(), key.get())) {
                     objectStore->resetAutoIncrementKeyCache();
                     callbacks->onError(IDBDatabaseError::create(IDBDatabaseException::DATA_ERR, "One of the derived (from a keyPath) keys for an index does not satisfy its uniqueness requirements."));
@@ -426,8 +429,10 @@
         } else {
             ASSERT(m_index->multiEntry());
             ASSERT(indexKey->type() == IDBKey::ArrayType);
+
+            indexKey = IDBKey::createMultiEntryArray(indexKey->array());
             for (size_t i = 0; i < indexKey->array().size(); ++i) {
-                if (!m_index->addingKeyAllowed(indexKey.get()))
+                if (!m_index->addingKeyAllowed(indexKey->array()[i].get()))
                     return false;
                 if (!m_backingStore.putIndexDataForRecord(m_databaseId, m_objectStoreId, m_index->id(), *indexKey->array()[i], recordIdentifier))
                     return false;

Modified: trunk/Source/WebCore/bindings/v8/IDBBindingUtilities.cpp (120966 => 120967)


--- trunk/Source/WebCore/bindings/v8/IDBBindingUtilities.cpp	2012-06-21 22:02:32 UTC (rev 120966)
+++ trunk/Source/WebCore/bindings/v8/IDBBindingUtilities.cpp	2012-06-21 22:28:40 UTC (rev 120967)
@@ -65,8 +65,9 @@
             v8::Local<v8::Value> item = array->Get(v8::Int32::New(i));
             RefPtr<IDBKey> subkey = createIDBKeyFromValue(item, stack);
             if (!subkey)
-                return 0;
-            subkeys.append(subkey);
+                subkeys.append(IDBKey::createInvalid());
+            else
+                subkeys.append(subkey);
         }
 
         stack.removeLast();

Modified: trunk/Source/WebKit/chromium/ChangeLog (120966 => 120967)


--- trunk/Source/WebKit/chromium/ChangeLog	2012-06-21 22:02:32 UTC (rev 120966)
+++ trunk/Source/WebKit/chromium/ChangeLog	2012-06-21 22:28:40 UTC (rev 120967)
@@ -1,3 +1,19 @@
+2012-06-21  Alec Flett  <[email protected]>
+
+        IndexedDB: Implement spec behavior for multiEntry indexes with invalid/duplicate subkeys
+        https://bugs.webkit.org/show_bug.cgi?id=86123
+
+        Reviewed by Darin Fisher.
+
+        Add matching isValid() to WebIDBKey to match the one in IDBKey.
+
+        * public/WebIDBKey.h:
+        * src/WebIDBKey.cpp:
+        (WebKit::WebIDBKey::isValid):
+        (WebKit):
+        * src/WebIDBKeyRange.cpp:
+        (WebKit::WebIDBKeyRange::assign):
+
 2012-06-21  Ian Vollick  <[email protected]>
 
         [chromium] Overlays when using the web inspector are blurry with device scale factor > 1

Modified: trunk/Source/WebKit/chromium/public/WebIDBKey.h (120966 => 120967)


--- trunk/Source/WebKit/chromium/public/WebIDBKey.h	2012-06-21 22:02:32 UTC (rev 120966)
+++ trunk/Source/WebKit/chromium/public/WebIDBKey.h	2012-06-21 22:28:40 UTC (rev 120967)
@@ -79,6 +79,7 @@
     };
 
     WEBKIT_EXPORT Type type() const;
+    WEBKIT_EXPORT bool isValid() const;
     WEBKIT_EXPORT WebVector<WebIDBKey> array() const; // Only valid for ArrayType.
     WEBKIT_EXPORT WebString string() const; // Only valid for StringType.
     WEBKIT_EXPORT double date() const; // Only valid for DateType.

Modified: trunk/Source/WebKit/chromium/src/WebIDBKey.cpp (120966 => 120967)


--- trunk/Source/WebKit/chromium/src/WebIDBKey.cpp	2012-06-21 22:02:32 UTC (rev 120966)
+++ trunk/Source/WebKit/chromium/src/WebIDBKey.cpp	2012-06-21 22:28:40 UTC (rev 120967)
@@ -120,6 +120,8 @@
             keys.append(IDBKey::createNumber(array[i].number()));
             break;
         case WebIDBKey::InvalidType:
+            keys.append(IDBKey::createInvalid());
+            break;
         case WebIDBKey::NullType:
             ASSERT_NOT_REACHED();
             break;
@@ -149,6 +151,8 @@
             keys[i] = WebIDBKey::createNumber(key->number());
             break;
         case IDBKey::InvalidType:
+            keys[i] = WebIDBKey::createInvalid();
+            break;
         case IDBKey::MinType:
             ASSERT_NOT_REACHED();
             break;
@@ -199,6 +203,13 @@
     return Type(m_private->type());
 }
 
+bool WebIDBKey::isValid() const
+{
+    if (!m_private.get())
+        return false;
+    return m_private->isValid();
+}
+
 WebVector<WebIDBKey> WebIDBKey::array() const
 {
     WebVector<WebIDBKey> keys;

Modified: trunk/Source/WebKit/chromium/src/WebIDBKeyRange.cpp (120966 => 120967)


--- trunk/Source/WebKit/chromium/src/WebIDBKeyRange.cpp	2012-06-21 22:02:32 UTC (rev 120966)
+++ trunk/Source/WebKit/chromium/src/WebIDBKeyRange.cpp	2012-06-21 22:28:40 UTC (rev 120967)
@@ -43,7 +43,7 @@
 
 void WebIDBKeyRange::assign(const WebIDBKey& lower, const WebIDBKey& upper, bool lowerOpen, bool upperOpen)
 {
-    if (lower.type() == WebIDBKey::InvalidType && upper.type() == WebIDBKey::InvalidType)
+    if (!lower.isValid() && !upper.isValid())
         m_private = 0;
     else
         m_private = IDBKeyRange::create(lower, upper, lowerOpen ? IDBKeyRange::LowerBoundOpen : IDBKeyRange::LowerBoundClosed, upperOpen ? IDBKeyRange::UpperBoundOpen : IDBKeyRange::UpperBoundClosed);
_______________________________________________
webkit-changes mailing list
[email protected]
http://lists.webkit.org/mailman/listinfo.cgi/webkit-changes

Reply via email to