[SCM] WebKit Debian packaging branch, debian/experimental, updated. upstream/1.3.3-9427-gc2be6fc

jorlow at chromium.org jorlow at chromium.org
Wed Dec 22 16:35:08 UTC 2010


The following commit has been merged in the debian/experimental branch:
commit b89d0c363ecec917f3d9b3d0b0bc33ad88b49556
Author: jorlow at chromium.org <jorlow at chromium.org@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Date:   Fri Nov 26 16:30:33 2010 +0000

    2010-11-25  Jeremy Orlow  <jorlow at chromium.org>
    
            Reviewed by Steve Block.
    
            Clean up IDBDatabase.transaction and add checks to IDBTransaction.objectStore
            https://bugs.webkit.org/show_bug.cgi?id=50081
    
            * storage/indexeddb/create-and-remove-object-store-expected.txt: Renamed from LayoutTests/storage/indexeddb/createAndRemoveObjectStore-expected.txt.
            * storage/indexeddb/create-and-remove-object-store.html: Renamed from LayoutTests/storage/indexeddb/createAndRemoveObjectStore.html.
            * storage/indexeddb/create-object-store-options-expected.txt:
            * storage/indexeddb/create-object-store-options.html:
            * storage/indexeddb/resources/shared.js:
            (evalAndExpectException):
            * storage/indexeddb/transaction-and-objectstore-calls-expected.txt: Added.
            * storage/indexeddb/transaction-and-objectstore-calls.html: Added.
            * storage/indexeddb/tutorial.html:
    2010-11-25  Jeremy Orlow  <jorlow at chromium.org>
    
            Reviewed by Steve Block.
    
            Clean up IDBDatabase.transaction and add checks to IDBTransaction.objectStore
            https://bugs.webkit.org/show_bug.cgi?id=50081
    
            IDBDatabase.transaction should use the new optional OptionsObject way
            of taking optional paramters. Modify that object to get numbers and
            domStringLists from it. Verify that any requested resources exist and
            return an exception if not.
    
            When IDBTransaction.objectStore is called, verify that it's one of the
            requested resources. Also verify that it still exists. Plumb the
            exception code to make this work.
    
            Tests: storage/indexeddb/create-and-remove-object-store.html
                   storage/indexeddb/transaction-and-objectstore-calls.html
    
            * bindings/v8/OptionsObject.cpp:
            (WebCore::OptionsObject::getKeyInteger):
            (WebCore::OptionsObject::getKeyString):
            (WebCore::OptionsObject::getKeyDOMStringList):
            * bindings/v8/OptionsObject.h:
            * storage/IDBDatabase.cpp:
            (WebCore::IDBDatabase::createObjectStore):
            (WebCore::IDBDatabase::transaction):
            * storage/IDBDatabase.h:
            (WebCore::IDBDatabase::transaction):
            * storage/IDBDatabase.idl:
            * storage/IDBDatabaseBackendImpl.cpp:
            (WebCore::IDBDatabaseBackendImpl::transaction):
            * storage/IDBTransaction.cpp:
            (WebCore::IDBTransaction::objectStore):
            * storage/IDBTransactionBackendImpl.cpp:
            (WebCore::IDBTransactionBackendImpl::IDBTransactionBackendImpl):
            (WebCore::IDBTransactionBackendImpl::objectStore):
            * storage/IDBTransactionBackendImpl.h:
            * storage/IDBTransactionBackendInterface.h:
    2010-11-25  Jeremy Orlow  <jorlow at chromium.org>
    
            Reviewed by Steve Block.
    
            Clean up IDBDatabase.transaction and add checks to IDBTransaction.objectStore
            https://bugs.webkit.org/show_bug.cgi?id=50081
    
            Plumb IDBTransaction.objectStore's exception code.
    
            * public/WebIDBTransaction.h:
            (WebKit::WebIDBTransaction::objectStore):
            * src/IDBDatabaseProxy.cpp:
            (WebCore::IDBDatabaseProxy::transaction):
            * src/IDBTransactionBackendProxy.cpp:
            (WebCore::IDBTransactionBackendProxy::objectStore):
            * src/IDBTransactionBackendProxy.h:
            * src/WebIDBDatabaseImpl.cpp:
            (WebKit::WebIDBDatabaseImpl::createObjectStore):
            (WebKit::WebIDBDatabaseImpl::transaction):
            * src/WebIDBTransactionImpl.cpp:
            (WebKit::WebIDBTransactionImpl::objectStore):
            * src/WebIDBTransactionImpl.h:
    
    git-svn-id: http://svn.webkit.org/repository/webkit/trunk@72765 268f45cc-cd09-0410-ab3c-d52691b4dbfc

diff --git a/LayoutTests/ChangeLog b/LayoutTests/ChangeLog
index 4cbbca8..4b471a7 100644
--- a/LayoutTests/ChangeLog
+++ b/LayoutTests/ChangeLog
@@ -1,3 +1,20 @@
+2010-11-25  Jeremy Orlow  <jorlow at chromium.org>
+
+        Reviewed by Steve Block.
+
+        Clean up IDBDatabase.transaction and add checks to IDBTransaction.objectStore
+        https://bugs.webkit.org/show_bug.cgi?id=50081
+
+        * storage/indexeddb/create-and-remove-object-store-expected.txt: Renamed from LayoutTests/storage/indexeddb/createAndRemoveObjectStore-expected.txt.
+        * storage/indexeddb/create-and-remove-object-store.html: Renamed from LayoutTests/storage/indexeddb/createAndRemoveObjectStore.html.
+        * storage/indexeddb/create-object-store-options-expected.txt:
+        * storage/indexeddb/create-object-store-options.html:
+        * storage/indexeddb/resources/shared.js:
+        (evalAndExpectException):
+        * storage/indexeddb/transaction-and-objectstore-calls-expected.txt: Added.
+        * storage/indexeddb/transaction-and-objectstore-calls.html: Added.
+        * storage/indexeddb/tutorial.html:
+
 2010-11-26  Ilya Tikhonovsky  <loislo at chromium.org>
 
         Unreviewed fix for chromium test expectations.
diff --git a/LayoutTests/storage/indexeddb/create-and-remove-object-store-expected.txt b/LayoutTests/storage/indexeddb/create-and-remove-object-store-expected.txt
new file mode 100644
index 0000000..fd14c83
--- /dev/null
+++ b/LayoutTests/storage/indexeddb/create-and-remove-object-store-expected.txt
@@ -0,0 +1,60 @@
+Test IndexedDB's create and removeObjectStore
+
+On success, you will see a series of "PASS" messages, followed by "TEST COMPLETE".
+
+
+PASS 'webkitIndexedDB' in window is true
+PASS webkitIndexedDB == null is false
+webkitIndexedDB.open('name')
+PASS 'onsuccess' in result is true
+PASS 'onerror' in result is true
+PASS 'readyState' in result is true
+An event should fire shortly...
+
+openSuccess():
+Success event fired:
+PASS 'result' in event is true
+PASS 'code' in event is false
+PASS 'message' in event is false
+PASS 'source' in event is true
+PASS event.source != null is true
+PASS 'onsuccess' in event.target is true
+PASS 'onerror' in event.target is true
+PASS 'readyState' in event.target is true
+PASS event.target.readyState is event.target.DONE
+
+db = event.result
+Trying create
+PASS code is webkitIDBDatabaseException.NOT_ALLOWED_ERR
+Trying remove
+PASS code is webkitIDBDatabaseException.NOT_ALLOWED_ERR
+result = db.setVersion('version 1')
+Trying create
+PASS code is webkitIDBDatabaseException.NOT_ALLOWED_ERR
+Trying remove
+PASS code is webkitIDBDatabaseException.NOT_ALLOWED_ERR
+Success event fired:
+PASS 'result' in event is true
+PASS 'code' in event is false
+PASS 'message' in event is false
+PASS 'source' in event is true
+PASS event.source != null is true
+PASS 'onsuccess' in event.target is true
+PASS 'onerror' in event.target is true
+PASS 'readyState' in event.target is true
+PASS event.target.readyState is event.target.DONE
+
+Deleted all object stores.
+db.createObjectStore('tmp')
+Adding 'tmp' again
+PASS code is webkitIDBDatabaseException.CONSTRAINT_ERR
+trans = db.transaction({mode: webkitIDBTransaction.READ_WRITE})
+trans.objectStore('tmp').get(0)
+Trying create
+PASS code is webkitIDBDatabaseException.NOT_ALLOWED_ERR
+Trying remove
+PASS code is webkitIDBDatabaseException.NOT_ALLOWED_ERR
+PASS successfullyParsed is true
+
+TEST COMPLETE
+
diff --git a/LayoutTests/storage/indexeddb/create-and-remove-object-store.html b/LayoutTests/storage/indexeddb/create-and-remove-object-store.html
new file mode 100644
index 0000000..c5284af
--- /dev/null
+++ b/LayoutTests/storage/indexeddb/create-and-remove-object-store.html
@@ -0,0 +1,96 @@
+<html>
+<head>
+<link rel="stylesheet" href="../../fast/js/resources/js-test-style.css">
+<script src="../../fast/js/resources/js-test-pre.js"></script>
+<script src="../../fast/js/resources/js-test-post-function.js"></script>
+<script src="resources/shared.js"></script>
+</head>
+<body>
+<p id="description"></p>
+<div id="console"></div>
+<script>
+
+description("Test IndexedDB's create and removeObjectStore");
+if (window.layoutTestController)
+    layoutTestController.waitUntilDone();
+
+function test()
+{
+    shouldBeTrue("'webkitIndexedDB' in window");
+    shouldBeFalse("webkitIndexedDB == null");
+
+    result = evalAndLog("webkitIndexedDB.open('name')");
+    verifyResult(result);
+    result.onsuccess = openSuccess;
+    result.onerror = unexpectedErrorCallback;
+}
+
+function openSuccess()
+{
+    debug("openSuccess():");
+    verifySuccessEvent(event);
+    window.db = evalAndLog("db = event.result");
+    testCreateAndRemove();
+    result = evalAndLog("result = db.setVersion('version 1')");
+    result.onsuccess = cleanDatabase;
+    result.onerror = unexpectedErrorCallback;
+    testCreateAndRemove();
+}
+
+function testCreateAndRemove()
+{
+    debug("Trying create");
+    try {
+        db.createObjectStore("some os");
+        testFailed("No exception thrown!");
+    } catch (e) {
+        code = e.code;
+        shouldBe("code", "webkitIDBDatabaseException.NOT_ALLOWED_ERR");
+    }
+    debug("Trying remove");
+    try {
+        db.createObjectStore("some os");
+        testFailed("No exception thrown!");
+    } catch (e) {
+        code = e.code;
+        shouldBe("code", "webkitIDBDatabaseException.NOT_ALLOWED_ERR");
+    }
+}
+
+function cleanDatabase()
+{
+    verifySuccessEvent(event);
+    deleteAllObjectStores(db, cleaned);
+}
+
+function cleaned()
+{
+    os = evalAndLog("db.createObjectStore('tmp')");
+    debug("Adding 'tmp' again");
+    try {
+        db.createObjectStore('tmp');
+        testFailed("No exception thrown!");
+    } catch (e) {
+        code = e.code;
+        shouldBe("code", "webkitIDBDatabaseException.CONSTRAINT_ERR");
+    }
+    trans = evalAndLog("trans = db.transaction({mode: webkitIDBTransaction.READ_WRITE})");
+    req = evalAndLog("trans.objectStore('tmp').get(0)");
+    req.onsuccess = unexpectedSuccessCallback;
+    req.onerror = tryOnceMore;
+}
+
+function tryOnceMore()
+{
+    testCreateAndRemove();
+
+    done();
+}
+
+var successfullyParsed = true;
+
+test();
+
+</script>
+</body>
+</html>
diff --git a/LayoutTests/storage/indexeddb/create-object-store-options-expected.txt b/LayoutTests/storage/indexeddb/create-object-store-options-expected.txt
index f116280..83016d6 100644
--- a/LayoutTests/storage/indexeddb/create-object-store-options-expected.txt
+++ b/LayoutTests/storage/indexeddb/create-object-store-options-expected.txt
@@ -19,7 +19,8 @@ db.createObjectStore('b')
 db.createObjectStore('c', {autoIncrement: true});
 PASS Exception thrown
 PASS code is webkitIDBDatabaseException.UNKNOWN_ERR
-trans = db.transaction([], webkitIDBTransaction.READ_WRITE)
+trans = db.transaction({mode: webkitIDBTransaction.READ_WRITE})
+PASS trans.mode is webkitIDBTransaction.READ_WRITE
 trans.objectStore('a').put({'a': 0})
 trans.objectStore('b').put({'a': 0}, 0)
 trans.objectStore('a').get(0)
diff --git a/LayoutTests/storage/indexeddb/create-object-store-options.html b/LayoutTests/storage/indexeddb/create-object-store-options.html
index 3db2dd4..4abb8f6 100644
--- a/LayoutTests/storage/indexeddb/create-object-store-options.html
+++ b/LayoutTests/storage/indexeddb/create-object-store-options.html
@@ -55,7 +55,8 @@ function cleaned()
         shouldBe("code", "webkitIDBDatabaseException.UNKNOWN_ERR");
     }
 
-    trans = evalAndLog("trans = db.transaction([], webkitIDBTransaction.READ_WRITE)");
+    trans = evalAndLog("trans = db.transaction({mode: webkitIDBTransaction.READ_WRITE})");
+    shouldBe("trans.mode", "webkitIDBTransaction.READ_WRITE");
 
     req = evalAndLog("trans.objectStore('a').put({'a': 0})");
     req.onsuccess = putB;
diff --git a/LayoutTests/storage/indexeddb/createAndRemoveObjectStore-expected.txt b/LayoutTests/storage/indexeddb/createAndRemoveObjectStore-expected.txt
deleted file mode 100644
index dc95546..0000000
--- a/LayoutTests/storage/indexeddb/createAndRemoveObjectStore-expected.txt
+++ /dev/null
@@ -1,60 +0,0 @@
-Test IndexedDB's create and removeObjectStore
-
-On success, you will see a series of "PASS" messages, followed by "TEST COMPLETE".
-
-
-PASS 'webkitIndexedDB' in window is true
-PASS webkitIndexedDB == null is false
-webkitIndexedDB.open('name')
-PASS 'onsuccess' in result is true
-PASS 'onerror' in result is true
-PASS 'readyState' in result is true
-An event should fire shortly...
-
-openSuccess():
-Success event fired:
-PASS 'result' in event is true
-PASS 'code' in event is false
-PASS 'message' in event is false
-PASS 'source' in event is true
-PASS event.source != null is true
-PASS 'onsuccess' in event.target is true
-PASS 'onerror' in event.target is true
-PASS 'readyState' in event.target is true
-PASS event.target.readyState is event.target.DONE
-
-db = event.result
-Trying create
-PASS code is webkitIDBDatabaseException.NOT_ALLOWED_ERR
-Trying remove
-PASS code is webkitIDBDatabaseException.NOT_ALLOWED_ERR
-result = db.setVersion('version 1')
-Trying create
-PASS code is webkitIDBDatabaseException.NOT_ALLOWED_ERR
-Trying remove
-PASS code is webkitIDBDatabaseException.NOT_ALLOWED_ERR
-Success event fired:
-PASS 'result' in event is true
-PASS 'code' in event is false
-PASS 'message' in event is false
-PASS 'source' in event is true
-PASS event.source != null is true
-PASS 'onsuccess' in event.target is true
-PASS 'onerror' in event.target is true
-PASS 'readyState' in event.target is true
-PASS event.target.readyState is event.target.DONE
-
-Deleted all object stores.
-db.createObjectStore('tmp')
-Adding 'tmp' again
-PASS code is webkitIDBDatabaseException.CONSTRAINT_ERR
-trans = db.transaction([], webkitIDBTransaction.READ_WRITE)
-trans.objectStore('tmp').get(0)
-Trying create
-PASS code is webkitIDBDatabaseException.NOT_ALLOWED_ERR
-Trying remove
-PASS code is webkitIDBDatabaseException.NOT_ALLOWED_ERR
-PASS successfullyParsed is true
-
-TEST COMPLETE
-
diff --git a/LayoutTests/storage/indexeddb/createAndRemoveObjectStore.html b/LayoutTests/storage/indexeddb/createAndRemoveObjectStore.html
deleted file mode 100644
index dd24696..0000000
--- a/LayoutTests/storage/indexeddb/createAndRemoveObjectStore.html
+++ /dev/null
@@ -1,96 +0,0 @@
-<html>
-<head>
-<link rel="stylesheet" href="../../fast/js/resources/js-test-style.css">
-<script src="../../fast/js/resources/js-test-pre.js"></script>
-<script src="../../fast/js/resources/js-test-post-function.js"></script>
-<script src="resources/shared.js"></script>
-</head>
-<body>
-<p id="description"></p>
-<div id="console"></div>
-<script>
-
-description("Test IndexedDB's create and removeObjectStore");
-if (window.layoutTestController)
-    layoutTestController.waitUntilDone();
-
-function test()
-{
-    shouldBeTrue("'webkitIndexedDB' in window");
-    shouldBeFalse("webkitIndexedDB == null");
-
-    result = evalAndLog("webkitIndexedDB.open('name')");
-    verifyResult(result);
-    result.onsuccess = openSuccess;
-    result.onerror = unexpectedErrorCallback;
-}
-
-function openSuccess()
-{
-    debug("openSuccess():");
-    verifySuccessEvent(event);
-    window.db = evalAndLog("db = event.result");
-    testCreateAndRemove();
-    result = evalAndLog("result = db.setVersion('version 1')");
-    result.onsuccess = cleanDatabase;
-    result.onerror = unexpectedErrorCallback;
-    testCreateAndRemove();
-}
-
-function testCreateAndRemove()
-{
-    debug("Trying create");
-    try {
-        db.createObjectStore("some os");
-        testFailed("No exception thrown!");
-    } catch (e) {
-        code = e.code;
-        shouldBe("code", "webkitIDBDatabaseException.NOT_ALLOWED_ERR");
-    }
-    debug("Trying remove");
-    try {
-        db.createObjectStore("some os");
-        testFailed("No exception thrown!");
-    } catch (e) {
-        code = e.code;
-        shouldBe("code", "webkitIDBDatabaseException.NOT_ALLOWED_ERR");
-    }
-}
-
-function cleanDatabase()
-{
-    verifySuccessEvent(event);
-    deleteAllObjectStores(db, cleaned);
-}
-
-function cleaned()
-{
-    os = evalAndLog("db.createObjectStore('tmp')");
-    debug("Adding 'tmp' again");
-    try {
-        db.createObjectStore('tmp');
-        testFailed("No exception thrown!");
-    } catch (e) {
-        code = e.code;
-        shouldBe("code", "webkitIDBDatabaseException.CONSTRAINT_ERR");
-    }
-    trans = evalAndLog("trans = db.transaction([], webkitIDBTransaction.READ_WRITE)");
-    req = evalAndLog("trans.objectStore('tmp').get(0)");
-    req.onsuccess = unexpectedSuccessCallback;
-    req.onerror = tryOnceMore;
-}
-
-function tryOnceMore()
-{
-    testCreateAndRemove();
-
-    done();
-}
-
-var successfullyParsed = true;
-
-test();
-
-</script>
-</body>
-</html>
diff --git a/LayoutTests/storage/indexeddb/resources/shared.js b/LayoutTests/storage/indexeddb/resources/shared.js
index 71abf44..c810253 100644
--- a/LayoutTests/storage/indexeddb/resources/shared.js
+++ b/LayoutTests/storage/indexeddb/resources/shared.js
@@ -87,6 +87,18 @@ function unexpectedCompleteCallback()
     done();
 }
 
+function evalAndExpectException(cmd, expected)
+{
+    debug("Expecting exception from " + cmd);
+    try {
+        eval(cmd);
+        testFailed("No exception thrown! Should have been " + expected);
+    } catch (e) {
+        code = e.code;
+        shouldBe("code", expected);
+    }
+}
+
 // FIXME: remove the onfinished parameter.
 function deleteAllObjectStores(db, onfinished)
 {
diff --git a/LayoutTests/storage/indexeddb/transaction-and-objectstore-calls-expected.txt b/LayoutTests/storage/indexeddb/transaction-and-objectstore-calls-expected.txt
new file mode 100644
index 0000000..df373d6
--- /dev/null
+++ b/LayoutTests/storage/indexeddb/transaction-and-objectstore-calls-expected.txt
@@ -0,0 +1,81 @@
+Test IndexedDB's transaction and objectStore calls
+
+On success, you will see a series of "PASS" messages, followed by "TEST COMPLETE".
+
+
+PASS 'webkitIndexedDB' in window is true
+PASS webkitIndexedDB == null is false
+webkitIndexedDB.open('name', 'description')
+PASS 'onsuccess' in result is true
+PASS 'onerror' in result is true
+PASS 'readyState' in result is true
+An event should fire shortly...
+
+db = event.result
+result = db.setVersion('version 1')
+trans = event.result
+Deleted all object stores.
+db.createObjectStore('a')
+db.createObjectStore('b')
+trans.oncomplete = created
+
+trans = db.transaction({objectStoreNames: 'a'})
+trans.objectStore('a')
+Expecting exception from trans.objectStore('b')
+PASS code is webkitIDBDatabaseException.NOT_FOUND_ERR
+Expecting exception from trans.objectStore('x')
+PASS code is webkitIDBDatabaseException.NOT_FOUND_ERR
+
+trans = db.transaction({objectStoreNames: ['a']})
+trans.objectStore('a')
+Expecting exception from trans.objectStore('b')
+PASS code is webkitIDBDatabaseException.NOT_FOUND_ERR
+Expecting exception from trans.objectStore('x')
+PASS code is webkitIDBDatabaseException.NOT_FOUND_ERR
+
+trans = db.transaction({objectStoreNames: ['b']})
+trans.objectStore('b')
+Expecting exception from trans.objectStore('a')
+PASS code is webkitIDBDatabaseException.NOT_FOUND_ERR
+Expecting exception from trans.objectStore('x')
+PASS code is webkitIDBDatabaseException.NOT_FOUND_ERR
+
+trans = db.transaction({objectStoreNames: ['a', 'b']})
+trans.objectStore('a')
+trans.objectStore('b')
+Expecting exception from trans.objectStore('x')
+PASS code is webkitIDBDatabaseException.NOT_FOUND_ERR
+
+trans = db.transaction({objectStoreNames: ['b', 'a']})
+trans.objectStore('a')
+trans.objectStore('b')
+Expecting exception from trans.objectStore('x')
+PASS code is webkitIDBDatabaseException.NOT_FOUND_ERR
+
+trans = db.transaction({objectStoreNames: []})
+trans.objectStore('a')
+trans.objectStore('b')
+Expecting exception from trans.objectStore('x')
+PASS code is webkitIDBDatabaseException.NOT_FOUND_ERR
+
+trans = db.transaction()
+trans.objectStore('a')
+trans.objectStore('b')
+Expecting exception from trans.objectStore('x')
+PASS code is webkitIDBDatabaseException.NOT_FOUND_ERR
+
+Expecting exception from db.transaction({objectStoreNames: 'x'})
+PASS code is webkitIDBDatabaseException.NOT_FOUND_ERR
+Expecting exception from db.transaction({objectStoreNames: ['x']})
+PASS code is webkitIDBDatabaseException.NOT_FOUND_ERR
+Expecting exception from db.transaction({objectStoreNames: ['a', 'x']})
+PASS code is webkitIDBDatabaseException.NOT_FOUND_ERR
+Expecting exception from db.transaction({objectStoreNames: ['x', 'x']})
+PASS code is webkitIDBDatabaseException.NOT_FOUND_ERR
+Expecting exception from db.transaction({objectStoreNames: ['a', 'x', 'b']})
+PASS code is webkitIDBDatabaseException.NOT_FOUND_ERR
+
+PASS successfullyParsed is true
+
+TEST COMPLETE
+
diff --git a/LayoutTests/storage/indexeddb/transaction-and-objectstore-calls.html b/LayoutTests/storage/indexeddb/transaction-and-objectstore-calls.html
new file mode 100644
index 0000000..580ca5d
--- /dev/null
+++ b/LayoutTests/storage/indexeddb/transaction-and-objectstore-calls.html
@@ -0,0 +1,110 @@
+<html>
+<head>
+<link rel="stylesheet" href="../../fast/js/resources/js-test-style.css">
+<script src="../../fast/js/resources/js-test-pre.js"></script>
+<script src="../../fast/js/resources/js-test-post-function.js"></script>
+<script src="resources/shared.js"></script>
+</head>
+<body>
+<p id="description"></p>
+<div id="console"></div>
+<script>
+
+description("Test IndexedDB's transaction and objectStore calls");
+if (window.layoutTestController)
+    layoutTestController.waitUntilDone();
+
+function test()
+{
+    shouldBeTrue("'webkitIndexedDB' in window");
+    shouldBeFalse("webkitIndexedDB == null");
+
+    result = evalAndLog("webkitIndexedDB.open('name', 'description')");
+    verifyResult(result);
+    result.onsuccess = openSuccess;
+    result.onerror = unexpectedErrorCallback;
+}
+
+function openSuccess()
+{
+    window.db = evalAndLog("db = event.result");
+    result = evalAndLog("result = db.setVersion('version 1')");
+    result.onsuccess = cleanDatabase;
+    result.onerror = unexpectedErrorCallback;
+}
+
+function cleanDatabase()
+{
+    trans = evalAndLog("trans = event.result");
+    deleteAllObjectStores(db, cleaned);
+}
+
+function cleaned()
+{
+    evalAndLog("db.createObjectStore('a')");
+    evalAndLog("db.createObjectStore('b')");
+    evalAndLog("trans.oncomplete = created");
+    debug("");
+}
+
+function created()
+{
+    trans = evalAndLog("trans = db.transaction({objectStoreNames: 'a'})");
+    evalAndLog("trans.objectStore('a')");
+    evalAndExpectException("trans.objectStore('b')", "webkitIDBDatabaseException.NOT_FOUND_ERR");
+    evalAndExpectException("trans.objectStore('x')", "webkitIDBDatabaseException.NOT_FOUND_ERR");
+    debug("");
+
+    trans = evalAndLog("trans = db.transaction({objectStoreNames: ['a']})");
+    evalAndLog("trans.objectStore('a')");
+    evalAndExpectException("trans.objectStore('b')", "webkitIDBDatabaseException.NOT_FOUND_ERR");
+    evalAndExpectException("trans.objectStore('x')", "webkitIDBDatabaseException.NOT_FOUND_ERR");
+    debug("");
+
+    trans = evalAndLog("trans = db.transaction({objectStoreNames: ['b']})");
+    evalAndLog("trans.objectStore('b')");
+    evalAndExpectException("trans.objectStore('a')", "webkitIDBDatabaseException.NOT_FOUND_ERR");
+    evalAndExpectException("trans.objectStore('x')", "webkitIDBDatabaseException.NOT_FOUND_ERR");
+    debug("");
+
+    trans = evalAndLog("trans = db.transaction({objectStoreNames: ['a', 'b']})");
+    evalAndLog("trans.objectStore('a')");
+    evalAndLog("trans.objectStore('b')");
+    evalAndExpectException("trans.objectStore('x')", "webkitIDBDatabaseException.NOT_FOUND_ERR");
+    debug("");
+
+    trans = evalAndLog("trans = db.transaction({objectStoreNames: ['b', 'a']})");
+    evalAndLog("trans.objectStore('a')");
+    evalAndLog("trans.objectStore('b')");
+    evalAndExpectException("trans.objectStore('x')", "webkitIDBDatabaseException.NOT_FOUND_ERR");
+    debug("");
+
+    trans = evalAndLog("trans = db.transaction({objectStoreNames: []})");
+    evalAndLog("trans.objectStore('a')");
+    evalAndLog("trans.objectStore('b')");
+    evalAndExpectException("trans.objectStore('x')", "webkitIDBDatabaseException.NOT_FOUND_ERR");
+    debug("");
+
+    trans = evalAndLog("trans = db.transaction()");
+    evalAndLog("trans.objectStore('a')");
+    evalAndLog("trans.objectStore('b')");
+    evalAndExpectException("trans.objectStore('x')", "webkitIDBDatabaseException.NOT_FOUND_ERR");
+    debug("");
+
+    evalAndExpectException("db.transaction({objectStoreNames: 'x'})", "webkitIDBDatabaseException.NOT_FOUND_ERR");
+    evalAndExpectException("db.transaction({objectStoreNames: ['x']})", "webkitIDBDatabaseException.NOT_FOUND_ERR");
+    evalAndExpectException("db.transaction({objectStoreNames: ['a', 'x']})", "webkitIDBDatabaseException.NOT_FOUND_ERR");
+    evalAndExpectException("db.transaction({objectStoreNames: ['x', 'x']})", "webkitIDBDatabaseException.NOT_FOUND_ERR");
+    evalAndExpectException("db.transaction({objectStoreNames: ['a', 'x', 'b']})", "webkitIDBDatabaseException.NOT_FOUND_ERR");
+    debug("");
+
+    done();
+}
+
+var successfullyParsed = true;
+
+test();
+
+</script>
+</body>
+</html>
diff --git a/LayoutTests/storage/indexeddb/tutorial.html b/LayoutTests/storage/indexeddb/tutorial.html
index 24fe47a..134f9de 100644
--- a/LayoutTests/storage/indexeddb/tutorial.html
+++ b/LayoutTests/storage/indexeddb/tutorial.html
@@ -207,23 +207,23 @@ function unexpectedAbort()
 function onSetVersionComplete()
 {
     // Lets create a new transaction and then not schedule any work on it to watch it abort itself.
-    // Transactions (besides those created with setVersion) are created synchronously. All three
-    // parameters are optional for transaction.
+    // Transactions (besides those created with setVersion) are created synchronously. Like
+    // createObjectStore, transaction optionally takes in an object with various optional parameters.
     //
-    // The first specifies which object stores to lock. The spec specifies "dynamic transactions"
-    // which don't require this and which have finer grained locks, but no one yet supports this and
-    // it may even be dropped from the first version of the spec, so I don't suggest you rely on it.
-    // Chromium/WebKit also does not yet support anything finer grained than database level locking,
-    // so in this tutorial we'll just pass in the empty array which means "lock the world".
+    // First of all is the parameter "objectStoreNames". If you pass in a string, we lock just that
+    // objectStore.  If you pass in an array, we lock those. Otherwise (for example, if you omit it
+    // or pass in null/undefined) we lock the whole database. By specifying locks over fewer
+    // objectStores you make it possible for browsers to run transactions concurrently. That said,
+    // Chromium/WebKit does not support this yet.
     //
-    // The second parameter specifies the locking mode. The default is READ_ONLY (i.e. a shared lock).
+    // Next is "mode" which specifies the locking mode. The default is READ_ONLY (i.e. a shared lock).
     // That's fine for this case, but later we'll ask for IDBTransaction.READ_WRITE. At the moment,
-    // Chromium/WebKit pretends every transaction is READ_WRITE, which is kind of bad. (Note that
-    // SNAPSHOT_READ will soon be removed from the spec.)
+    // Chromium/WebKit pretends every transaction is READ_WRITE, which is kind of bad.
     //
-    // The last parameter is the timeout length. At the moment, Chromium/WebKit defaults to 0 which
-    // means never, but it's possible we'll change this in the future, so set it if you really care.
-    window.currentTransaction = db.transaction([], IDBTransaction.READ_WRITE, 0);
+    // Last is "timeout" which is measured in seconds. At the moment, Chromium/WebKit defaults to 0 which
+    // means never, but it's possible we'll change this in the future and other implementations may
+    // use something different, so set it if you really care.
+    window.currentTransaction = db.transaction({mode: IDBTransaction.READ_WRITE, timeout: 0});
     currentTransaction.oncomplete = unexpectedComplete;
     currentTransaction.onabort = onTransactionAborted;
 
@@ -270,8 +270,10 @@ function unexpectedComplete()
 
 function onTransactionAborted()
 {
-    // Now let's make a real transaction and a person to our objectStore.
-    window.currentTransaction = db.transaction(["people"], IDBTransaction.READ_WRITE, 0);
+    // Now let's make a real transaction and a person to our objectStore. Just to show it's possible,
+    // we'll omit the objectStoreNames parameter which means we'll lock everything even though we only
+    // ever access "people".
+    window.currentTransaction = db.transaction({mode: IDBTransaction.READ_WRITE});
     currentTransaction.onabort = unexpectedAbort;
 
     var people = currentTransaction.objectStore("people");
@@ -307,8 +309,9 @@ function onPutSuccess()
 function onPutTransactionComplete()
 {
     // OK, now let's query the people objectStore in a couple different ways. First up, let's try get.
-    // It simply takes in a key and returns a request whose result will be the value.
-    window.currentTransaction = db.transaction(["people"], IDBTransaction.READ_WRITE, 0);
+    // It simply takes in a key and returns a request whose result will be the value. Note that here
+    // we're passing in an array for objectStoreNames rather than a simple string.
+    window.currentTransaction = db.transaction({objectStoreNames: ["people"], mode: IDBTransaction.READ_WRITE, timeout: 0});
     currentTransaction.onabort = unexpectedAbort;
 
     var people = currentTransaction.objectStore("people");
diff --git a/WebCore/ChangeLog b/WebCore/ChangeLog
index 54c7ab3..49c73d2 100644
--- a/WebCore/ChangeLog
+++ b/WebCore/ChangeLog
@@ -1,3 +1,43 @@
+2010-11-25  Jeremy Orlow  <jorlow at chromium.org>
+
+        Reviewed by Steve Block.
+
+        Clean up IDBDatabase.transaction and add checks to IDBTransaction.objectStore
+        https://bugs.webkit.org/show_bug.cgi?id=50081
+
+        IDBDatabase.transaction should use the new optional OptionsObject way
+        of taking optional paramters. Modify that object to get numbers and
+        domStringLists from it. Verify that any requested resources exist and
+        return an exception if not.
+
+        When IDBTransaction.objectStore is called, verify that it's one of the
+        requested resources. Also verify that it still exists. Plumb the
+        exception code to make this work.
+
+        Tests: storage/indexeddb/create-and-remove-object-store.html
+               storage/indexeddb/transaction-and-objectstore-calls.html
+
+        * bindings/v8/OptionsObject.cpp:
+        (WebCore::OptionsObject::getKeyInteger):
+        (WebCore::OptionsObject::getKeyString):
+        (WebCore::OptionsObject::getKeyDOMStringList):
+        * bindings/v8/OptionsObject.h:
+        * storage/IDBDatabase.cpp:
+        (WebCore::IDBDatabase::createObjectStore):
+        (WebCore::IDBDatabase::transaction):
+        * storage/IDBDatabase.h:
+        (WebCore::IDBDatabase::transaction):
+        * storage/IDBDatabase.idl:
+        * storage/IDBDatabaseBackendImpl.cpp:
+        (WebCore::IDBDatabaseBackendImpl::transaction):
+        * storage/IDBTransaction.cpp:
+        (WebCore::IDBTransaction::objectStore):
+        * storage/IDBTransactionBackendImpl.cpp:
+        (WebCore::IDBTransactionBackendImpl::IDBTransactionBackendImpl):
+        (WebCore::IDBTransactionBackendImpl::objectStore):
+        * storage/IDBTransactionBackendImpl.h:
+        * storage/IDBTransactionBackendInterface.h:
+
 2010-11-26  Mario Sanchez Prada  <msanchez at igalia.com>
 
         Reviewed by Xan Lopez.
diff --git a/WebCore/bindings/v8/OptionsObject.cpp b/WebCore/bindings/v8/OptionsObject.cpp
index dde511a..ab247eb 100644
--- a/WebCore/bindings/v8/OptionsObject.cpp
+++ b/WebCore/bindings/v8/OptionsObject.cpp
@@ -25,7 +25,10 @@
 
 #include "config.h"
 #include "OptionsObject.h"
+
+#include "DOMStringList.h"
 #include "V8Binding.h"
+#include <limits>
 
 namespace WebCore {
 
@@ -61,29 +64,58 @@ bool OptionsObject::getKeyBool(const String& key, bool& value) const
     if (!getKey(key, v8Value))
         return false;
 
-    if (!v8Value->IsBoolean())
-        return false;
     v8::Local<v8::Boolean> v8Bool = v8Value->ToBoolean();
-    ASSERT(!v8Bool.IsEmpty());
-
+    if (v8Bool.IsEmpty())
+        return false;
     value = v8Bool->Value();
     return true;
 }
 
-bool OptionsObject::getKeyString(const String& key, String& value) const
+bool OptionsObject::getKeyInt32(const String& key, int32_t& value) const
 {
     v8::Local<v8::Value> v8Value;
     if (!getKey(key, v8Value))
         return false;
 
-    if (!v8Value->IsString())
+    v8::Local<v8::Int32> v8Int32 = v8Value->ToInt32();
+    if (v8Int32.IsEmpty())
+        return false;
+    value = v8Int32->Value();
+    return true;
+}
+
+bool OptionsObject::getKeyString(const String& key, String& value) const
+{
+    v8::Local<v8::Value> v8Value;
+    if (!getKey(key, v8Value))
         return false;
 
+    // FIXME: It is possible for this to throw in which case we'd be getting back
+    //        an empty string and returning true when we should be returning false.
+    //        See fast/dom/Geolocation/script-tests/argument-types.js for a similar
+    //        example.
     value = v8ValueToWebCoreString(v8Value);
-    ASSERT(!value.isEmpty());
     return true;
 }
 
+PassRefPtr<DOMStringList> OptionsObject::getKeyDOMStringList(const String& key) const
+{
+    v8::Local<v8::Value> v8Value;
+    if (!getKey(key, v8Value))
+        return 0;
+
+    if (!v8Value->IsArray())
+        return 0;
+
+    RefPtr<DOMStringList> ret = DOMStringList::create();
+    v8::Local<v8::Array> v8Array = v8::Local<v8::Array>::Cast(v8Value);
+    for (size_t i = 0; i < v8Array->Length(); ++i) {
+        v8::Local<v8::Value> indexedValue = v8Array->Get(v8::Integer::New(i));
+        ret->append(v8ValueToWebCoreString(indexedValue));
+    }
+    return ret.release();
+}
+
 bool OptionsObject::getKey(const String& key, v8::Local<v8::Value>& value) const
 {
     if (isUndefinedOrNull())
@@ -95,8 +127,9 @@ bool OptionsObject::getKey(const String& key, v8::Local<v8::Value>& value) const
     if (!options->Has(v8Key))
         return false;
     value = options->Get(v8Key);
-    ASSERT(!value.IsEmpty());
-    return true;
+    if (value.IsEmpty()) 
+        return false;
+    return !value->IsUndefined(); // FIXME: Is the undefined check necessary?
 }
 
 } // namespace WebCore
diff --git a/WebCore/bindings/v8/OptionsObject.h b/WebCore/bindings/v8/OptionsObject.h
index fce597b..6b51f05 100644
--- a/WebCore/bindings/v8/OptionsObject.h
+++ b/WebCore/bindings/v8/OptionsObject.h
@@ -31,6 +31,8 @@
 
 namespace WebCore {
 
+class DOMStringList;
+
 class OptionsObject {
 public:
     OptionsObject();
@@ -41,7 +43,9 @@ public:
 
     bool isUndefinedOrNull() const;
     bool getKeyBool(const String& key, bool& value) const;
+    bool getKeyInt32(const String& key, int32_t& value) const;
     bool getKeyString(const String& key, String& value) const;
+    PassRefPtr<DOMStringList> getKeyDOMStringList(const String& key) const;
 
 private:
     bool getKey(const String& key, v8::Local<v8::Value>&) const;
diff --git a/WebCore/storage/IDBDatabase.cpp b/WebCore/storage/IDBDatabase.cpp
index 9a8727f..227be84 100644
--- a/WebCore/storage/IDBDatabase.cpp
+++ b/WebCore/storage/IDBDatabase.cpp
@@ -35,11 +35,15 @@
 #include "IDBRequest.h"
 #include "IDBTransaction.h"
 #include "ScriptExecutionContext.h"
+#include <limits>
 
 #if ENABLE(INDEXED_DATABASE)
 
 namespace WebCore {
 
+// FIXME: We need to spec this differently.
+const unsigned long defaultTimeout = 0; // Infinite.
+
 IDBDatabase::IDBDatabase(PassRefPtr<IDBDatabaseBackendInterface> backend)
     : m_backend(backend)
 {
@@ -100,13 +104,42 @@ PassRefPtr<IDBRequest> IDBDatabase::setVersion(ScriptExecutionContext* context,
     return request;
 }
 
-PassRefPtr<IDBTransaction> IDBDatabase::transaction(ScriptExecutionContext* context, DOMStringList* storeNames, unsigned short mode, unsigned long timeout, ExceptionCode& ec)
+PassRefPtr<IDBTransaction> IDBDatabase::transaction(ScriptExecutionContext* context, const OptionsObject& options, ExceptionCode& ec)
 {
+    RefPtr<DOMStringList> storeNames = options.getKeyDOMStringList("objectStoreNames");
+    if (!storeNames) {
+        storeNames = DOMStringList::create();
+        String storeName;
+        if (options.getKeyString("objectStoreNames", storeName))
+            storeNames->append(storeName);
+    }
+
+    // Gets cast to an unsigned short.
+    int32_t mode = IDBTransaction::READ_ONLY;
+    options.getKeyInt32("mode", mode);
+    if (mode != IDBTransaction::READ_WRITE && mode != IDBTransaction::READ_ONLY) {
+        // FIXME: May need to change when specced: http://www.w3.org/Bugs/Public/show_bug.cgi?id=11406
+        ec = IDBDatabaseException::CONSTRAINT_ERR;
+        return 0;
+    }
+
+    // Gets cast to an unsigned long.
+    // FIXME: The spec needs to be updated on this. It should probably take a double.
+    int32_t timeout = defaultTimeout; 
+    options.getKeyInt32("timeout", timeout);
+    int64_t unsignedLongMax = std::numeric_limits<unsigned long>::max();
+    if (timeout < 0 || timeout > unsignedLongMax)
+        timeout = defaultTimeout; // Ignore illegal values.
+
     // We need to create a new transaction synchronously. Locks are acquired asynchronously. Operations
     // can be queued against the transaction at any point. They will start executing as soon as the
     // appropriate locks have been acquired.
     // Also note that each backend object corresponds to exactly one IDBTransaction object.
-    RefPtr<IDBTransactionBackendInterface> transactionBackend = m_backend->transaction(storeNames, mode, timeout, ec);
+    RefPtr<IDBTransactionBackendInterface> transactionBackend = m_backend->transaction(storeNames.get(), mode, timeout, ec);
+    if (!transactionBackend) {
+        ASSERT(ec);
+        return 0;
+    }
     RefPtr<IDBTransaction> transaction = IDBTransaction::create(context, transactionBackend, this);
     transactionBackend->setCallbacks(transaction.get());
     return transaction.release();
diff --git a/WebCore/storage/IDBDatabase.h b/WebCore/storage/IDBDatabase.h
index 77fa5d0..a3a1e3a 100644
--- a/WebCore/storage/IDBDatabase.h
+++ b/WebCore/storage/IDBDatabase.h
@@ -61,14 +61,12 @@ public:
 
     // FIXME: Try to modify the code generator so this is unneeded.
     PassRefPtr<IDBObjectStore> createObjectStore(const String& name, ExceptionCode& ec) { return createObjectStore(name, OptionsObject(), ec); }
-    PassRefPtr<IDBTransaction> transaction(ScriptExecutionContext* context, ExceptionCode& ec) { return transaction(context, 0, ec); }
-    PassRefPtr<IDBTransaction> transaction(ScriptExecutionContext* context, DOMStringList* storeNames, ExceptionCode& ec) { return transaction(context, storeNames, IDBTransaction::READ_ONLY, ec); }
-    PassRefPtr<IDBTransaction> transaction(ScriptExecutionContext* context, DOMStringList* storeNames, unsigned short mode, ExceptionCode& ec) { return transaction(context, storeNames, mode, 0, ec); } // FIXME: what should the default timeout be?
+    PassRefPtr<IDBTransaction> transaction(ScriptExecutionContext* context, ExceptionCode& ec) { return transaction(context, OptionsObject(), ec); }
 
     PassRefPtr<IDBObjectStore> createObjectStore(const String& name, const OptionsObject&, ExceptionCode&);
     void removeObjectStore(const String& name, ExceptionCode&);
     PassRefPtr<IDBRequest> setVersion(ScriptExecutionContext*, const String& version, ExceptionCode&);
-    PassRefPtr<IDBTransaction> transaction(ScriptExecutionContext*, DOMStringList*, unsigned short mode, unsigned long timeout, ExceptionCode&);
+    PassRefPtr<IDBTransaction> transaction(ScriptExecutionContext*, const OptionsObject&, ExceptionCode&);
     void close();
 
 private:
diff --git a/WebCore/storage/IDBDatabase.idl b/WebCore/storage/IDBDatabase.idl
index 70d00a0..a778ecb 100644
--- a/WebCore/storage/IDBDatabase.idl
+++ b/WebCore/storage/IDBDatabase.idl
@@ -38,7 +38,7 @@ module storage {
             raises (IDBDatabaseException);
         [CallWith=ScriptExecutionContext] IDBRequest setVersion(in DOMString version)
             raises (IDBDatabaseException);
-        [CallWith=ScriptExecutionContext] IDBTransaction transaction (in [Optional] DOMStringList storeNames, in [Optional] unsigned short mode, in [Optional] unsigned long timeout)
+        [CallWith=ScriptExecutionContext] IDBTransaction transaction (in [Optional] OptionsObject optionsObject)
             raises (IDBDatabaseException);
         // FIXME: Implement.
         //void close();
diff --git a/WebCore/storage/IDBDatabaseBackendImpl.cpp b/WebCore/storage/IDBDatabaseBackendImpl.cpp
index 52b5b30..617e7ff 100644
--- a/WebCore/storage/IDBDatabaseBackendImpl.cpp
+++ b/WebCore/storage/IDBDatabaseBackendImpl.cpp
@@ -234,8 +234,15 @@ void IDBDatabaseBackendImpl::setVersionInternal(ScriptExecutionContext*, PassRef
     callbacks->onSuccess(transaction);
 }
 
-PassRefPtr<IDBTransactionBackendInterface> IDBDatabaseBackendImpl::transaction(DOMStringList* objectStoreNames, unsigned short mode, unsigned long timeout, ExceptionCode&)
+PassRefPtr<IDBTransactionBackendInterface> IDBDatabaseBackendImpl::transaction(DOMStringList* objectStoreNames, unsigned short mode, unsigned long timeout, ExceptionCode& ec)
 {
+    for (size_t i = 0; i < objectStoreNames->length(); ++i) {
+        if (!m_objectStores.contains(objectStoreNames->item(i))) {
+            ec = IDBDatabaseException::NOT_FOUND_ERR;
+            return 0;
+        }
+    }
+
     // FIXME: Return not allowed err if close has been called.
     return IDBTransactionBackendImpl::create(objectStoreNames, mode, timeout, this);
 }
diff --git a/WebCore/storage/IDBTransaction.cpp b/WebCore/storage/IDBTransaction.cpp
index 334c001..e3625d4 100644
--- a/WebCore/storage/IDBTransaction.cpp
+++ b/WebCore/storage/IDBTransaction.cpp
@@ -75,9 +75,9 @@ PassRefPtr<IDBObjectStore> IDBTransaction::objectStore(const String& name, Excep
         ec = IDBDatabaseException::NOT_ALLOWED_ERR;
         return 0;
     }
-    RefPtr<IDBObjectStoreBackendInterface> objectStoreBackend = m_backend->objectStore(name);
+    RefPtr<IDBObjectStoreBackendInterface> objectStoreBackend = m_backend->objectStore(name, ec);
     if (!objectStoreBackend) {
-        ec = IDBDatabaseException::NOT_ALLOWED_ERR;
+        ASSERT(ec);
         return 0;
     }
     RefPtr<IDBObjectStore> objectStore = IDBObjectStore::create(objectStoreBackend, m_backend.get());
diff --git a/WebCore/storage/IDBTransactionBackendImpl.cpp b/WebCore/storage/IDBTransactionBackendImpl.cpp
index e8d864d..336724a 100644
--- a/WebCore/storage/IDBTransactionBackendImpl.cpp
+++ b/WebCore/storage/IDBTransactionBackendImpl.cpp
@@ -29,6 +29,7 @@
 #if ENABLE(INDEXED_DATABASE)
 
 #include "IDBDatabaseBackendImpl.h"
+#include "IDBDatabaseException.h"
 #include "IDBTransactionCoordinator.h"
 #include "SQLiteDatabase.h"
 
@@ -50,6 +51,7 @@ IDBTransactionBackendImpl::IDBTransactionBackendImpl(DOMStringList* objectStores
     , m_taskEventTimer(this, &IDBTransactionBackendImpl::taskEventTimerFired)
     , m_pendingEvents(0)
 {
+    ASSERT(m_objectStoreNames);
     m_database->transactionCoordinator()->didCreateTransaction(this);
 }
 
@@ -59,11 +61,29 @@ IDBTransactionBackendImpl::~IDBTransactionBackendImpl()
     ASSERT(m_state == Finished);
 }
 
-PassRefPtr<IDBObjectStoreBackendInterface> IDBTransactionBackendImpl::objectStore(const String& name)
+PassRefPtr<IDBObjectStoreBackendInterface> IDBTransactionBackendImpl::objectStore(const String& name, ExceptionCode& ec)
 {
-    if (m_state == Finished)
+    if (m_state == Finished) {
+        ec = IDBDatabaseException::NOT_ALLOWED_ERR;
+        return 0;
+    }
+
+    // Does a linear search, but it really shouldn't be that slow in practice.
+    if (!m_objectStoreNames->isEmpty() && !m_objectStoreNames->contains(name)) {
+        ec = IDBDatabaseException::NOT_FOUND_ERR;
         return 0;
-    return m_database->objectStore(name);
+    }
+
+    RefPtr<IDBObjectStoreBackendInterface> objectStore = m_database->objectStore(name);
+    // FIXME: This is only necessary right now beacuse a setVersion transaction could modify things
+    //        between its creation (where another check occurs) and the .objectStore call.
+    //        There's a bug to make this impossible in the spec. When we make it impossible here, we
+    //        can remove this check.
+    if (!objectStore) {
+        ec = IDBDatabaseException::NOT_FOUND_ERR;
+        return 0;
+    }
+    return objectStore.release();
 }
 
 bool IDBTransactionBackendImpl::scheduleTask(PassOwnPtr<ScriptExecutionContext::Task> task, PassOwnPtr<ScriptExecutionContext::Task> abortTask)
diff --git a/WebCore/storage/IDBTransactionBackendImpl.h b/WebCore/storage/IDBTransactionBackendImpl.h
index 88542f4..f4dfaa8 100644
--- a/WebCore/storage/IDBTransactionBackendImpl.h
+++ b/WebCore/storage/IDBTransactionBackendImpl.h
@@ -45,7 +45,7 @@ public:
     static PassRefPtr<IDBTransactionBackendImpl> create(DOMStringList* objectStores, unsigned short mode, unsigned long timeout, IDBDatabaseBackendImpl*);
     virtual ~IDBTransactionBackendImpl();
 
-    virtual PassRefPtr<IDBObjectStoreBackendInterface> objectStore(const String& name);
+    virtual PassRefPtr<IDBObjectStoreBackendInterface> objectStore(const String& name, ExceptionCode&);
     virtual unsigned short mode() const { return m_mode; }
     virtual bool scheduleTask(PassOwnPtr<ScriptExecutionContext::Task> task, PassOwnPtr<ScriptExecutionContext::Task> abortTask);
     virtual void didCompleteTaskEvents();
diff --git a/WebCore/storage/IDBTransactionBackendInterface.h b/WebCore/storage/IDBTransactionBackendInterface.h
index 80135f0..9b1fce6 100644
--- a/WebCore/storage/IDBTransactionBackendInterface.h
+++ b/WebCore/storage/IDBTransactionBackendInterface.h
@@ -48,7 +48,7 @@ class IDBTransactionBackendInterface : public ThreadSafeShared<IDBTransactionBac
 public:
     virtual ~IDBTransactionBackendInterface() { }
 
-    virtual PassRefPtr<IDBObjectStoreBackendInterface> objectStore(const String& name) = 0;
+    virtual PassRefPtr<IDBObjectStoreBackendInterface> objectStore(const String& name, ExceptionCode&) = 0;
     virtual unsigned short mode() const = 0;
     virtual bool scheduleTask(PassOwnPtr<ScriptExecutionContext::Task> task, PassOwnPtr<ScriptExecutionContext::Task> abortTask = 0) = 0;
     virtual void didCompleteTaskEvents() = 0;
diff --git a/WebKit/chromium/ChangeLog b/WebKit/chromium/ChangeLog
index 97c5a1b..53c65a2 100644
--- a/WebKit/chromium/ChangeLog
+++ b/WebKit/chromium/ChangeLog
@@ -1,3 +1,26 @@
+2010-11-25  Jeremy Orlow  <jorlow at chromium.org>
+
+        Reviewed by Steve Block.
+
+        Clean up IDBDatabase.transaction and add checks to IDBTransaction.objectStore
+        https://bugs.webkit.org/show_bug.cgi?id=50081
+
+        Plumb IDBTransaction.objectStore's exception code.
+
+        * public/WebIDBTransaction.h:
+        (WebKit::WebIDBTransaction::objectStore):
+        * src/IDBDatabaseProxy.cpp:
+        (WebCore::IDBDatabaseProxy::transaction):
+        * src/IDBTransactionBackendProxy.cpp:
+        (WebCore::IDBTransactionBackendProxy::objectStore):
+        * src/IDBTransactionBackendProxy.h:
+        * src/WebIDBDatabaseImpl.cpp:
+        (WebKit::WebIDBDatabaseImpl::createObjectStore):
+        (WebKit::WebIDBDatabaseImpl::transaction):
+        * src/WebIDBTransactionImpl.cpp:
+        (WebKit::WebIDBTransactionImpl::objectStore):
+        * src/WebIDBTransactionImpl.h:
+
 2010-11-26  Hans Wennborg  <hans at chromium.org>
 
         Reviewed by Jeremy Orlow.
diff --git a/WebKit/chromium/public/WebIDBTransaction.h b/WebKit/chromium/public/WebIDBTransaction.h
index 584b67a..74919a8 100644
--- a/WebKit/chromium/public/WebIDBTransaction.h
+++ b/WebKit/chromium/public/WebIDBTransaction.h
@@ -48,13 +48,8 @@ public:
     }
     virtual WebIDBObjectStore* objectStore(const WebString& name, WebExceptionCode&)
     {
-        return objectStore(name);
-    }
-    // FIXME: Remove this after WebKit roll.
-    virtual WebIDBObjectStore* objectStore(const WebString& name)
-    {
-        WebExceptionCode ec;
-        return objectStore(name, ec);
+        WEBKIT_ASSERT_NOT_REACHED();
+        return 0;
     }
     virtual void abort() { WEBKIT_ASSERT_NOT_REACHED(); }
     virtual void didCompleteTaskEvents() { WEBKIT_ASSERT_NOT_REACHED(); }
diff --git a/WebKit/chromium/src/IDBDatabaseProxy.cpp b/WebKit/chromium/src/IDBDatabaseProxy.cpp
index f8fe1fa..d0fc7b9 100644
--- a/WebKit/chromium/src/IDBDatabaseProxy.cpp
+++ b/WebKit/chromium/src/IDBDatabaseProxy.cpp
@@ -104,6 +104,10 @@ PassRefPtr<IDBTransactionBackendInterface> IDBDatabaseProxy::transaction(DOMStri
 {
     WebKit::WebDOMStringList names(storeNames);
     WebKit::WebIDBTransaction* transaction = m_webIDBDatabase->transaction(names, mode, timeout, ec);
+    if (!transaction) {
+        ASSERT(ec);
+        return 0;
+    }
     return IDBTransactionBackendProxy::create(transaction);
 }
 
diff --git a/WebKit/chromium/src/IDBTransactionBackendProxy.cpp b/WebKit/chromium/src/IDBTransactionBackendProxy.cpp
index b95e22f..95c90d5 100644
--- a/WebKit/chromium/src/IDBTransactionBackendProxy.cpp
+++ b/WebKit/chromium/src/IDBTransactionBackendProxy.cpp
@@ -52,9 +52,9 @@ IDBTransactionBackendProxy::~IDBTransactionBackendProxy()
 {
 }
 
-PassRefPtr<IDBObjectStoreBackendInterface> IDBTransactionBackendProxy::objectStore(const String& name)
+PassRefPtr<IDBObjectStoreBackendInterface> IDBTransactionBackendProxy::objectStore(const String& name, ExceptionCode& ec)
 {
-    WebKit::WebIDBObjectStore* objectStore = m_webIDBTransaction->objectStore(name);
+    WebKit::WebIDBObjectStore* objectStore = m_webIDBTransaction->objectStore(name, ec);
     if (!objectStore)
         return 0;
     return IDBObjectStoreProxy::create(objectStore);
diff --git a/WebKit/chromium/src/IDBTransactionBackendProxy.h b/WebKit/chromium/src/IDBTransactionBackendProxy.h
index 0bf84da..96d7293 100644
--- a/WebKit/chromium/src/IDBTransactionBackendProxy.h
+++ b/WebKit/chromium/src/IDBTransactionBackendProxy.h
@@ -42,7 +42,7 @@ public:
     static PassRefPtr<IDBTransactionBackendInterface> create(PassOwnPtr<WebKit::WebIDBTransaction>);
     virtual ~IDBTransactionBackendProxy();
 
-    virtual PassRefPtr<IDBObjectStoreBackendInterface> objectStore(const String& name);
+    virtual PassRefPtr<IDBObjectStoreBackendInterface> objectStore(const String& name, ExceptionCode&);
     virtual unsigned short mode() const;
     virtual void abort();
     virtual bool scheduleTask(PassOwnPtr<ScriptExecutionContext::Task>, PassOwnPtr<ScriptExecutionContext::Task>);
diff --git a/WebKit/chromium/src/WebIDBDatabaseImpl.cpp b/WebKit/chromium/src/WebIDBDatabaseImpl.cpp
index 9724752..5afc646 100644
--- a/WebKit/chromium/src/WebIDBDatabaseImpl.cpp
+++ b/WebKit/chromium/src/WebIDBDatabaseImpl.cpp
@@ -67,8 +67,10 @@ WebDOMStringList WebIDBDatabaseImpl::objectStoreNames() const
 WebIDBObjectStore* WebIDBDatabaseImpl::createObjectStore(const WebString& name, const WebString& keyPath, bool autoIncrement, const WebIDBTransaction& transaction, WebExceptionCode& ec)
 {
     RefPtr<IDBObjectStoreBackendInterface> objectStore = m_databaseBackend->createObjectStore(name, keyPath, autoIncrement, transaction.getIDBTransactionBackendInterface(), ec);
-    if (!objectStore)
+    if (!objectStore) {
+        ASSERT(ec);
         return 0;
+    }
     return new WebIDBObjectStoreImpl(objectStore);
 }
 
@@ -86,8 +88,10 @@ WebIDBTransaction* WebIDBDatabaseImpl::transaction(const WebDOMStringList& names
 {
     RefPtr<DOMStringList> nameList = PassRefPtr<DOMStringList>(names);
     RefPtr<IDBTransactionBackendInterface> transaction = m_databaseBackend->transaction(nameList.get(), mode, timeout, ec);
-    if (!transaction)
+    if (!transaction) {
+        ASSERT(ec);
         return 0;
+    }
     return new WebIDBTransactionImpl(transaction);
 }
 
diff --git a/WebKit/chromium/src/WebIDBTransactionImpl.cpp b/WebKit/chromium/src/WebIDBTransactionImpl.cpp
index 4307cb5..1ed6f4b 100644
--- a/WebKit/chromium/src/WebIDBTransactionImpl.cpp
+++ b/WebKit/chromium/src/WebIDBTransactionImpl.cpp
@@ -51,9 +51,9 @@ int WebIDBTransactionImpl::mode() const
     return m_backend->mode();
 }
 
-WebIDBObjectStore* WebIDBTransactionImpl::objectStore(const WebString& name)
+WebIDBObjectStore* WebIDBTransactionImpl::objectStore(const WebString& name, ExceptionCode& ec)
 {
-    RefPtr<IDBObjectStoreBackendInterface> objectStore = m_backend->objectStore(name);
+    RefPtr<IDBObjectStoreBackendInterface> objectStore = m_backend->objectStore(name, ec);
     if (!objectStore)
         return 0;
     return new WebIDBObjectStoreImpl(objectStore);
diff --git a/WebKit/chromium/src/WebIDBTransactionImpl.h b/WebKit/chromium/src/WebIDBTransactionImpl.h
index b26b3ac..d26fc37 100644
--- a/WebKit/chromium/src/WebIDBTransactionImpl.h
+++ b/WebKit/chromium/src/WebIDBTransactionImpl.h
@@ -42,7 +42,7 @@ public:
     virtual ~WebIDBTransactionImpl();  
 
     virtual int mode() const;
-    virtual WebIDBObjectStore* objectStore(const WebString& name);
+    virtual WebIDBObjectStore* objectStore(const WebString& name, WebExceptionCode&);
     virtual void abort();
     virtual void didCompleteTaskEvents();
     virtual void setCallbacks(WebIDBTransactionCallbacks*);

-- 
WebKit Debian packaging



More information about the Pkg-webkit-commits mailing list