<!DOCTYPE html>
<script src="../../resources/js-test.js"></script>
<script src="resources/shared.js"></script>
<script>
description("Verify edge cases that lazy index population in an IndexedDB implementation might reveal.");
indexedDBTest(prepareDatabase, verifyPreExistingIndex);
function prepareDatabase()
{
connection = event.target.result;
deleteAllObjectStores(connection);
evalAndLog("store = connection.createObjectStore('store')");
evalAndLog("store.createIndex('index1', 'name', {unique: true})");
}
function verifyPreExistingIndex()
{
debug("Verify that uniqueness constraints are enforced with a pre-existing index:");
evalAndLog("trans = connection.transaction('store', 'readwrite', {durability: 'relaxed'})");
evalAndLog("store = trans.objectStore('store')");
evalAndLog("request1 = store.put({name: 'bob'}, 1)");
evalAndLog("request2 = store.put({name: 'bob'}, 2)");
evalAndLog("state = 0");
request1.onerror = unexpectedErrorCallback;
request1.onsuccess = function () {
debug("request1 received success event");
shouldBe("++state", "1");
};
request2.onsuccess = unexpectedSuccessCallback;
request2.onerror = function () {
debug("request2 received error event");
shouldBe("++state", "2");
};
trans.oncomplete = unexpectedCompleteCallback;
trans.onabort = function () {
debug("transaction aborted");
shouldBe("++state", "3");
shouldBe("trans.error.name", "'ConstraintError'");
verifyCreateThenPut();
};
}
function verifyCreateThenPut()
{
debug("");
debug("Verify that uniqueness constraints are enforced when index is created before puts:");
evalAndLog("connection.close()");
request = evalAndLog("indexedDB.open(dbname, 2)");
request.onerror = verifyPutThenCreate;
request.onblocked = unexpectedBlockedCallback;
request.onsuccess = unexpectedSuccessCallback;
request.onupgradeneeded = function() {
connection = request.result;
trans = request.transaction;
evalAndLog("deleteAllObjectStores(connection)");
evalAndLog("store = connection.createObjectStore('store')");
evalAndLog("store.createIndex('index2', 'name', {unique: true})");
evalAndLog("request1 = store.put({name: 'carol'}, 1)");
evalAndLog("request2 = store.put({name: 'carol'}, 2)");
evalAndLog("state = 0");
request1.onerror = unexpectedErrorCallback;
request1.onsuccess = function () {
debug("request1 (index2) received success event");
shouldBe("++state", "1");
};
request2.onsuccess = unexpectedSuccessCallback;
request2.onerror = function () {
debug("request2 (index2) received error event");
shouldBe("++state", "2");
};
trans.oncomplete = unexpectedCompleteCallback;
trans.onabort = function () {
debug("transaction aborted");
shouldBe("++state", "3");
shouldBe("trans.error.name", "'ConstraintError'");
};
};
}
function verifyPutThenCreate()
{
debug("");
debug("Verify that uniqueness constraints are enforced when index is created after puts:");
request = evalAndLog("indexedDB.open(dbname, 3)");
request.onerror = verifyPutThenCreateThenPut;
request.onblocked = unexpectedBlockedCallback;
request.onsuccess = unexpectedSuccessCallback;
request.onupgradeneeded = function() {
connection = request.result;
trans = request.transaction;
evalAndLog("deleteAllObjectStores(connection)");
evalAndLog("store = connection.createObjectStore('store')");
evalAndLog("request1 = store.put({name: 'ted'}, 1)");
evalAndLog("request2 = store.put({name: 'ted'}, 2)");
evalAndLog("store.createIndex('index3', 'name', {unique: true})");
evalAndLog("state = 0");
request1.onerror = unexpectedErrorCallback;
request1.onsuccess = function () {
debug("request1 received success event");
shouldBe("++state", "1");
};
request2.onerror = unexpectedErrorCallback;
request2.onsuccess = function () {
debug("request2 received success event");
shouldBe("++state", "2");
};
trans.oncomplete = unexpectedCompleteCallback;
trans.onabort = function () {
debug("transaction aborted");
shouldBe("++state", "3");
shouldBe("trans.error.name", "'ConstraintError'");
};
};
}
function verifyPutThenCreateThenPut()
{
debug("");
debug("Verify that uniqueness constraints are enforced when index is created between puts:");
request = evalAndLog("indexedDB.open(dbname, 4)");
request.onerror = finishJSTest;
request.onblocked = unexpectedBlockedCallback;
request.onsuccess = unexpectedSuccessCallback;
request.onupgradeneeded = function() {
connection = request.result;
trans = request.transaction;
evalAndLog("deleteAllObjectStores(connection)");
evalAndLog("store = connection.createObjectStore('store')");
evalAndLog("request1 = store.put({name: 'alice'}, 1)");
evalAndLog("store.createIndex('index4', 'name', {unique: true})");
evalAndLog("request2 = store.put({name: 'alice'}, 2)");
evalAndLog("state = 0");
request1.onerror = unexpectedErrorCallback;
request1.onsuccess = function () {
debug("request1 received success event");
shouldBe("++state", "1");
};
request2.onsuccess = unexpectedSuccessCallback;
request2.onerror = function () {
debug("request2 received error event");
shouldBe("++state", "2");
};
trans.oncomplete = unexpectedCompleteCallback;
trans.onabort = function () {
debug("transaction aborted");
shouldBe("++state", "3");
shouldBe("trans.error.name", "'ConstraintError'");
};
};
}
</script>