idb: fix renaming, make renaming tests pass
This commit is contained in:
parent
47bddb2a1b
commit
69b62c62a0
@ -55,7 +55,7 @@ import {
|
|||||||
TransactionInactiveError,
|
TransactionInactiveError,
|
||||||
VersionError,
|
VersionError,
|
||||||
} from "./util/errors";
|
} from "./util/errors";
|
||||||
import { fakeDOMStringList } from "./util/fakeDOMStringList";
|
import { FakeDOMStringList, fakeDOMStringList } from "./util/fakeDOMStringList";
|
||||||
import FakeEvent from "./util/FakeEvent";
|
import FakeEvent from "./util/FakeEvent";
|
||||||
import FakeEventTarget from "./util/FakeEventTarget";
|
import FakeEventTarget from "./util/FakeEventTarget";
|
||||||
import { makeStoreKeyValue } from "./util/makeStoreKeyValue";
|
import { makeStoreKeyValue } from "./util/makeStoreKeyValue";
|
||||||
@ -73,12 +73,6 @@ import { valueToKey } from "./util/valueToKey";
|
|||||||
/** @public */
|
/** @public */
|
||||||
export type CursorSource = BridgeIDBIndex | BridgeIDBObjectStore;
|
export type CursorSource = BridgeIDBIndex | BridgeIDBObjectStore;
|
||||||
|
|
||||||
/** @public */
|
|
||||||
export interface FakeDOMStringList extends Array<string> {
|
|
||||||
contains: (value: string) => boolean;
|
|
||||||
item: (i: number) => string | undefined;
|
|
||||||
}
|
|
||||||
|
|
||||||
/** @public */
|
/** @public */
|
||||||
export interface RequestObj {
|
export interface RequestObj {
|
||||||
operation: () => Promise<any>;
|
operation: () => Promise<any>;
|
||||||
@ -828,7 +822,9 @@ export class BridgeIDBFactory {
|
|||||||
);
|
);
|
||||||
|
|
||||||
// We need to expose the new version number to the upgrade transaction.
|
// We need to expose the new version number to the upgrade transaction.
|
||||||
db._schema = this.backend.getCurrentTransactionSchema(backendTransaction);
|
db._schema = this.backend.getCurrentTransactionSchema(
|
||||||
|
backendTransaction,
|
||||||
|
);
|
||||||
|
|
||||||
const transaction = db._internalTransaction(
|
const transaction = db._internalTransaction(
|
||||||
[],
|
[],
|
||||||
@ -1405,6 +1401,14 @@ export class BridgeIDBObjectStore implements IDBObjectStore {
|
|||||||
this._transaction._db._schema = this._backend.getCurrentTransactionSchema(
|
this._transaction._db._schema = this._backend.getCurrentTransactionSchema(
|
||||||
btx,
|
btx,
|
||||||
);
|
);
|
||||||
|
|
||||||
|
// We don't modify scope, as the scope of the transaction
|
||||||
|
// doesn't matter if we're in an upgrade transaction.
|
||||||
|
this._transaction._objectStoresCache.delete(oldName);
|
||||||
|
this._transaction._objectStoresCache.set(newName, this);
|
||||||
|
this._transaction._cachedObjectStoreNames = undefined;
|
||||||
|
|
||||||
|
this._name = newName;
|
||||||
}
|
}
|
||||||
|
|
||||||
public _store(value: any, key: IDBValidKey | undefined, overwrite: boolean) {
|
public _store(value: any, key: IDBValidKey | undefined, overwrite: boolean) {
|
||||||
@ -1910,9 +1914,19 @@ export class BridgeIDBTransaction
|
|||||||
|
|
||||||
_backendTransaction?: DatabaseTransaction;
|
_backendTransaction?: DatabaseTransaction;
|
||||||
|
|
||||||
_objectStoreNames: FakeDOMStringList;
|
_cachedObjectStoreNames: DOMStringList | undefined;
|
||||||
|
|
||||||
get objectStoreNames(): DOMStringList {
|
get objectStoreNames(): DOMStringList {
|
||||||
return this._objectStoreNames as DOMStringList;
|
if (!this._cachedObjectStoreNames) {
|
||||||
|
if (this._openRequest) {
|
||||||
|
this._cachedObjectStoreNames = this._db.objectStoreNames;
|
||||||
|
} else {
|
||||||
|
this._cachedObjectStoreNames = fakeDOMStringList(
|
||||||
|
Array.from(this._scope).sort(),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return this._cachedObjectStoreNames;
|
||||||
}
|
}
|
||||||
mode: IDBTransactionMode;
|
mode: IDBTransactionMode;
|
||||||
_db: BridgeIDBDatabase;
|
_db: BridgeIDBDatabase;
|
||||||
@ -1961,7 +1975,6 @@ export class BridgeIDBTransaction
|
|||||||
this._backendTransaction = backendTransaction;
|
this._backendTransaction = backendTransaction;
|
||||||
this.mode = mode;
|
this.mode = mode;
|
||||||
this._db = db;
|
this._db = db;
|
||||||
this._objectStoreNames = fakeDOMStringList(Array.from(this._scope).sort());
|
|
||||||
|
|
||||||
this._db._transactions.push(this);
|
this._db._transactions.push(this);
|
||||||
|
|
||||||
@ -2049,12 +2062,24 @@ export class BridgeIDBTransaction
|
|||||||
throw new InvalidStateError();
|
throw new InvalidStateError();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (!this._db._schema.objectStores[name]) {
|
||||||
|
throw new NotFoundError();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!this._db._upgradeTransaction) {
|
||||||
|
if (!this._scope.has(name)) {
|
||||||
|
throw new NotFoundError();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
const objectStore = this._objectStoresCache.get(name);
|
const objectStore = this._objectStoresCache.get(name);
|
||||||
if (objectStore !== undefined) {
|
if (objectStore !== undefined) {
|
||||||
return objectStore;
|
return objectStore;
|
||||||
}
|
}
|
||||||
|
|
||||||
return new BridgeIDBObjectStore(this, name);
|
const newObjectStore = new BridgeIDBObjectStore(this, name);
|
||||||
|
this._objectStoresCache.set(name, newObjectStore);
|
||||||
|
return newObjectStore;
|
||||||
}
|
}
|
||||||
|
|
||||||
// http://www.w3.org/TR/2015/REC-IndexedDB-20150108/#dfn-steps-for-asynchronously-executing-a-request
|
// http://www.w3.org/TR/2015/REC-IndexedDB-20150108/#dfn-steps-for-asynchronously-executing-a-request
|
||||||
|
@ -1,4 +1,6 @@
|
|||||||
import test from "ava";
|
import test from "ava";
|
||||||
|
import { BridgeIDBVersionChangeEvent } from "../bridge-idb";
|
||||||
|
import FakeEvent from "../util/FakeEvent";
|
||||||
import { createdb, format_value, idbFactory } from "./wptsupport";
|
import { createdb, format_value, idbFactory } from "./wptsupport";
|
||||||
|
|
||||||
// IDBFactory.open() - request has no source
|
// IDBFactory.open() - request has no source
|
||||||
@ -466,3 +468,62 @@ test("WPT idbfactory-open11.htm", async (t) => {
|
|||||||
});
|
});
|
||||||
t.pass();
|
t.pass();
|
||||||
});
|
});
|
||||||
|
|
||||||
|
// IDBFactory.open() - upgradeneeded gets VersionChangeEvent
|
||||||
|
test("WPT idbfactory-open12.htm", async (t) => {
|
||||||
|
const indexedDB = idbFactory;
|
||||||
|
|
||||||
|
var db: any;
|
||||||
|
var open_rq = createdb(t, undefined, 9);
|
||||||
|
|
||||||
|
await new Promise<void>((resolve, reject) => {
|
||||||
|
open_rq.onupgradeneeded = function (e: any) {
|
||||||
|
db = e.target.result;
|
||||||
|
|
||||||
|
t.true(
|
||||||
|
e instanceof BridgeIDBVersionChangeEvent,
|
||||||
|
"e instanceof IDBVersionChangeEvent",
|
||||||
|
);
|
||||||
|
t.deepEqual(e.oldVersion, 0, "oldVersion");
|
||||||
|
t.deepEqual(e.newVersion, 9, "newVersion");
|
||||||
|
t.deepEqual(e.type, "upgradeneeded", "event type");
|
||||||
|
|
||||||
|
t.deepEqual(db.version, 9, "db.version");
|
||||||
|
};
|
||||||
|
open_rq.onsuccess = function (e) {
|
||||||
|
t.true(e instanceof FakeEvent, "e instanceof Event");
|
||||||
|
t.false(
|
||||||
|
e instanceof BridgeIDBVersionChangeEvent,
|
||||||
|
"e not instanceof IDBVersionChangeEvent",
|
||||||
|
);
|
||||||
|
t.deepEqual(e.type, "success", "event type");
|
||||||
|
resolve();
|
||||||
|
};
|
||||||
|
});
|
||||||
|
|
||||||
|
await new Promise<void>((resolve, reject) => {
|
||||||
|
/**
|
||||||
|
* Second test
|
||||||
|
*/
|
||||||
|
db.onversionchange = function () {
|
||||||
|
db.close();
|
||||||
|
};
|
||||||
|
|
||||||
|
var open_rq2 = createdb(t, db.name, 10);
|
||||||
|
open_rq2.onupgradeneeded = function (e: any) {
|
||||||
|
var db2 = e.target.result;
|
||||||
|
t.true(
|
||||||
|
e instanceof BridgeIDBVersionChangeEvent,
|
||||||
|
"e instanceof IDBVersionChangeEvent",
|
||||||
|
);
|
||||||
|
t.deepEqual(e.oldVersion, 9, "oldVersion");
|
||||||
|
t.deepEqual(e.newVersion, 10, "newVersion");
|
||||||
|
t.deepEqual(e.type, "upgradeneeded", "event type");
|
||||||
|
|
||||||
|
t.deepEqual(db2.version, 10, "new db.version");
|
||||||
|
|
||||||
|
resolve();
|
||||||
|
};
|
||||||
|
});
|
||||||
|
t.pass();
|
||||||
|
});
|
||||||
|
@ -1,13 +1,10 @@
|
|||||||
import test, { ExecutionContext } from "ava";
|
import test, { ExecutionContext } from "ava";
|
||||||
import { BridgeIDBRequest } from "..";
|
|
||||||
import { EventTarget, IDBDatabase } from "../idbtypes";
|
|
||||||
import {
|
import {
|
||||||
checkStoreContents,
|
checkStoreContents,
|
||||||
checkStoreGenerator,
|
checkStoreGenerator,
|
||||||
checkStoreIndexes,
|
checkStoreIndexes,
|
||||||
createBooksStore,
|
createBooksStore,
|
||||||
createDatabase,
|
createDatabase,
|
||||||
createdb,
|
|
||||||
createNotBooksStore,
|
createNotBooksStore,
|
||||||
migrateDatabase,
|
migrateDatabase,
|
||||||
} from "./wptsupport";
|
} from "./wptsupport";
|
||||||
@ -15,183 +12,175 @@ import {
|
|||||||
// IndexedDB: object store renaming support
|
// IndexedDB: object store renaming support
|
||||||
// IndexedDB object store rename in new transaction
|
// IndexedDB object store rename in new transaction
|
||||||
test("WPT idbobjectstore-rename-store.html (subtest 1)", async (t) => {
|
test("WPT idbobjectstore-rename-store.html (subtest 1)", async (t) => {
|
||||||
await new Promise<void>((resolve, reject) => {
|
let bookStore: any = null;
|
||||||
let bookStore: any = null;
|
let bookStore2: any = null;
|
||||||
let bookStore2: any = null;
|
let renamedBookStore: any = null;
|
||||||
let renamedBookStore: any = null;
|
let renamedBookStore2: any = null;
|
||||||
let renamedBookStore2: any = null;
|
await createDatabase(t, (database, transaction) => {
|
||||||
|
bookStore = createBooksStore(t, database);
|
||||||
return createDatabase(t, (database, transaction) => {
|
})
|
||||||
bookStore = createBooksStore(t, database);
|
.then((database) => {
|
||||||
|
t.deepEqual(
|
||||||
|
database.objectStoreNames as any,
|
||||||
|
["books"],
|
||||||
|
'Test setup should have created a "books" object store',
|
||||||
|
);
|
||||||
|
const transaction = database.transaction("books", "readonly");
|
||||||
|
bookStore2 = transaction.objectStore("books");
|
||||||
|
return checkStoreContents(
|
||||||
|
t,
|
||||||
|
bookStore2,
|
||||||
|
"The store should have the expected contents before any renaming",
|
||||||
|
).then(() => database.close());
|
||||||
})
|
})
|
||||||
.then((database) => {
|
.then(() =>
|
||||||
t.deepEqual(
|
migrateDatabase(t, 2, (database, transaction) => {
|
||||||
database.objectStoreNames as any,
|
renamedBookStore = transaction.objectStore("books");
|
||||||
["books"],
|
renamedBookStore.name = "renamed_books";
|
||||||
'Test setup should have created a "books" object store',
|
|
||||||
);
|
|
||||||
const transaction = database.transaction("books", "readonly");
|
|
||||||
bookStore2 = transaction.objectStore("books");
|
|
||||||
return checkStoreContents(
|
|
||||||
t,
|
|
||||||
bookStore2,
|
|
||||||
"The store should have the expected contents before any renaming",
|
|
||||||
).then(() => database.close());
|
|
||||||
})
|
|
||||||
.then(() =>
|
|
||||||
migrateDatabase(t, 2, (database, transaction) => {
|
|
||||||
renamedBookStore = transaction.objectStore("books");
|
|
||||||
renamedBookStore.name = "renamed_books";
|
|
||||||
|
|
||||||
t.deepEqual(
|
|
||||||
renamedBookStore.name,
|
|
||||||
"renamed_books",
|
|
||||||
"IDBObjectStore name should change immediately after a rename",
|
|
||||||
);
|
|
||||||
t.deepEqual(
|
|
||||||
database.objectStoreNames as any,
|
|
||||||
["renamed_books"],
|
|
||||||
"IDBDatabase.objectStoreNames should immediately reflect the " +
|
|
||||||
"rename",
|
|
||||||
);
|
|
||||||
t.deepEqual(
|
|
||||||
transaction.objectStoreNames as any,
|
|
||||||
["renamed_books"],
|
|
||||||
"IDBTransaction.objectStoreNames should immediately reflect the " +
|
|
||||||
"rename",
|
|
||||||
);
|
|
||||||
t.deepEqual(
|
|
||||||
transaction.objectStore("renamed_books"),
|
|
||||||
renamedBookStore,
|
|
||||||
"IDBTransaction.objectStore should return the renamed object " +
|
|
||||||
"store when queried using the new name immediately after the " +
|
|
||||||
"rename",
|
|
||||||
);
|
|
||||||
t.throws(
|
|
||||||
() => transaction.objectStore("books"),
|
|
||||||
{ name: "NotFoundError" },
|
|
||||||
"IDBTransaction.objectStore should throw when queried using the " +
|
|
||||||
"renamed object store's old name immediately after the rename",
|
|
||||||
);
|
|
||||||
}),
|
|
||||||
)
|
|
||||||
.then((database) => {
|
|
||||||
t.deepEqual(
|
|
||||||
database.objectStoreNames as any,
|
|
||||||
["renamed_books"],
|
|
||||||
"IDBDatabase.objectStoreNames should still reflect the rename " +
|
|
||||||
"after the versionchange transaction commits",
|
|
||||||
);
|
|
||||||
const transaction = database.transaction("renamed_books", "readonly");
|
|
||||||
renamedBookStore2 = transaction.objectStore("renamed_books");
|
|
||||||
return checkStoreContents(
|
|
||||||
t,
|
|
||||||
renamedBookStore2,
|
|
||||||
"Renaming an object store should not change its records",
|
|
||||||
).then(() => database.close());
|
|
||||||
})
|
|
||||||
.then(() => {
|
|
||||||
t.deepEqual(
|
|
||||||
bookStore.name,
|
|
||||||
"books",
|
|
||||||
"IDBObjectStore obtained before the rename transaction should " +
|
|
||||||
"not reflect the rename",
|
|
||||||
);
|
|
||||||
t.deepEqual(
|
|
||||||
bookStore2.name,
|
|
||||||
"books",
|
|
||||||
"IDBObjectStore obtained before the rename transaction should " +
|
|
||||||
"not reflect the rename",
|
|
||||||
);
|
|
||||||
t.deepEqual(
|
t.deepEqual(
|
||||||
renamedBookStore.name,
|
renamedBookStore.name,
|
||||||
"renamed_books",
|
"renamed_books",
|
||||||
"IDBObjectStore used in the rename transaction should keep " +
|
"IDBObjectStore name should change immediately after a rename",
|
||||||
"reflecting the new name after the transaction is committed",
|
|
||||||
);
|
);
|
||||||
t.deepEqual(
|
t.deepEqual(
|
||||||
renamedBookStore2.name,
|
database.objectStoreNames as any,
|
||||||
"renamed_books",
|
["renamed_books"],
|
||||||
"IDBObjectStore obtained after the rename transaction should " +
|
"IDBDatabase.objectStoreNames should immediately reflect the " +
|
||||||
"reflect the new name",
|
"rename",
|
||||||
);
|
);
|
||||||
});
|
t.deepEqual(
|
||||||
});
|
transaction.objectStoreNames as any,
|
||||||
t.pass();
|
["renamed_books"],
|
||||||
|
"IDBTransaction.objectStoreNames should immediately reflect the " +
|
||||||
|
"rename",
|
||||||
|
);
|
||||||
|
t.deepEqual(
|
||||||
|
transaction.objectStore("renamed_books"),
|
||||||
|
renamedBookStore,
|
||||||
|
"IDBTransaction.objectStore should return the renamed object " +
|
||||||
|
"store when queried using the new name immediately after the " +
|
||||||
|
"rename",
|
||||||
|
);
|
||||||
|
t.throws(
|
||||||
|
() => transaction.objectStore("books"),
|
||||||
|
{ name: "NotFoundError" },
|
||||||
|
"IDBTransaction.objectStore should throw when queried using the " +
|
||||||
|
"renamed object store's old name immediately after the rename",
|
||||||
|
);
|
||||||
|
}),
|
||||||
|
)
|
||||||
|
.then((database) => {
|
||||||
|
t.deepEqual(
|
||||||
|
database.objectStoreNames as any,
|
||||||
|
["renamed_books"],
|
||||||
|
"IDBDatabase.objectStoreNames should still reflect the rename " +
|
||||||
|
"after the versionchange transaction commits",
|
||||||
|
);
|
||||||
|
const transaction = database.transaction("renamed_books", "readonly");
|
||||||
|
renamedBookStore2 = transaction.objectStore("renamed_books");
|
||||||
|
return checkStoreContents(
|
||||||
|
t,
|
||||||
|
renamedBookStore2,
|
||||||
|
"Renaming an object store should not change its records",
|
||||||
|
).then(() => database.close());
|
||||||
|
})
|
||||||
|
.then(() => {
|
||||||
|
t.deepEqual(
|
||||||
|
bookStore.name,
|
||||||
|
"books",
|
||||||
|
"IDBObjectStore obtained before the rename transaction should " +
|
||||||
|
"not reflect the rename",
|
||||||
|
);
|
||||||
|
t.deepEqual(
|
||||||
|
bookStore2.name,
|
||||||
|
"books",
|
||||||
|
"IDBObjectStore obtained before the rename transaction should " +
|
||||||
|
"not reflect the rename",
|
||||||
|
);
|
||||||
|
t.deepEqual(
|
||||||
|
renamedBookStore.name,
|
||||||
|
"renamed_books",
|
||||||
|
"IDBObjectStore used in the rename transaction should keep " +
|
||||||
|
"reflecting the new name after the transaction is committed",
|
||||||
|
);
|
||||||
|
t.deepEqual(
|
||||||
|
renamedBookStore2.name,
|
||||||
|
"renamed_books",
|
||||||
|
"IDBObjectStore obtained after the rename transaction should " +
|
||||||
|
"reflect the new name",
|
||||||
|
);
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
// IndexedDB: object store renaming support
|
// IndexedDB: object store renaming support
|
||||||
// IndexedDB object store rename in the transaction where it is created
|
// IndexedDB object store rename in the transaction where it is created
|
||||||
test("WPT idbobjectstore-rename-store.html (subtest 2)", async (t) => {
|
test("WPT idbobjectstore-rename-store.html (subtest 2)", async (t) => {
|
||||||
await new Promise<void>((resolve, reject) => {
|
let renamedBookStore: any = null,
|
||||||
let renamedBookStore: any = null,
|
renamedBookStore2: any = null;
|
||||||
renamedBookStore2: any = null;
|
await createDatabase(t, (database, transaction) => {
|
||||||
return createDatabase(t, (database, transaction) => {
|
renamedBookStore = createBooksStore(t, database);
|
||||||
renamedBookStore = createBooksStore(t, database);
|
renamedBookStore.name = "renamed_books";
|
||||||
renamedBookStore.name = "renamed_books";
|
|
||||||
|
|
||||||
t.deepEqual(
|
t.deepEqual(
|
||||||
renamedBookStore.name,
|
renamedBookStore.name,
|
||||||
"renamed_books",
|
"renamed_books",
|
||||||
"IDBObjectStore name should change immediately after a rename",
|
"IDBObjectStore name should change immediately after a rename",
|
||||||
);
|
);
|
||||||
|
t.deepEqual(
|
||||||
|
database.objectStoreNames as any,
|
||||||
|
["renamed_books"],
|
||||||
|
"IDBDatabase.objectStoreNames should immediately reflect the " + "rename",
|
||||||
|
);
|
||||||
|
t.deepEqual(
|
||||||
|
transaction.objectStoreNames as any,
|
||||||
|
["renamed_books"],
|
||||||
|
"IDBTransaction.objectStoreNames should immediately reflect the " +
|
||||||
|
"rename",
|
||||||
|
);
|
||||||
|
t.deepEqual(
|
||||||
|
transaction.objectStore("renamed_books"),
|
||||||
|
renamedBookStore,
|
||||||
|
"IDBTransaction.objectStore should return the renamed object " +
|
||||||
|
"store when queried using the new name immediately after the " +
|
||||||
|
"rename",
|
||||||
|
);
|
||||||
|
t.throws(
|
||||||
|
() => transaction.objectStore("books"),
|
||||||
|
{ name: "NotFoundError" },
|
||||||
|
"IDBTransaction.objectStore should throw when queried using the " +
|
||||||
|
"renamed object store's old name immediately after the rename",
|
||||||
|
);
|
||||||
|
})
|
||||||
|
.then((database) => {
|
||||||
t.deepEqual(
|
t.deepEqual(
|
||||||
database.objectStoreNames as any,
|
database.objectStoreNames as any,
|
||||||
["renamed_books"],
|
["renamed_books"],
|
||||||
"IDBDatabase.objectStoreNames should immediately reflect the " +
|
"IDBDatabase.objectStoreNames should still reflect the rename " +
|
||||||
"rename",
|
"after the versionchange transaction commits",
|
||||||
);
|
|
||||||
t.deepEqual(
|
|
||||||
transaction.objectStoreNames as any,
|
|
||||||
["renamed_books"],
|
|
||||||
"IDBTransaction.objectStoreNames should immediately reflect the " +
|
|
||||||
"rename",
|
|
||||||
);
|
|
||||||
t.deepEqual(
|
|
||||||
transaction.objectStore("renamed_books"),
|
|
||||||
renamedBookStore,
|
|
||||||
"IDBTransaction.objectStore should return the renamed object " +
|
|
||||||
"store when queried using the new name immediately after the " +
|
|
||||||
"rename",
|
|
||||||
);
|
|
||||||
t.throws(
|
|
||||||
() => transaction.objectStore("books"),
|
|
||||||
{ name: "NotFoundError" },
|
|
||||||
"IDBTransaction.objectStore should throw when queried using the " +
|
|
||||||
"renamed object store's old name immediately after the rename",
|
|
||||||
);
|
);
|
||||||
|
const transaction = database.transaction("renamed_books", "readonly");
|
||||||
|
renamedBookStore2 = transaction.objectStore("renamed_books");
|
||||||
|
return checkStoreContents(
|
||||||
|
t,
|
||||||
|
renamedBookStore2,
|
||||||
|
"Renaming an object store should not change its records",
|
||||||
|
).then(() => database.close());
|
||||||
})
|
})
|
||||||
.then((database) => {
|
.then(() => {
|
||||||
t.deepEqual(
|
t.deepEqual(
|
||||||
database.objectStoreNames as any,
|
renamedBookStore.name,
|
||||||
["renamed_books"],
|
"renamed_books",
|
||||||
"IDBDatabase.objectStoreNames should still reflect the rename " +
|
"IDBObjectStore used in the rename transaction should keep " +
|
||||||
"after the versionchange transaction commits",
|
"reflecting the new name after the transaction is committed",
|
||||||
);
|
);
|
||||||
const transaction = database.transaction("renamed_books", "readonly");
|
t.deepEqual(
|
||||||
renamedBookStore2 = transaction.objectStore("renamed_books");
|
renamedBookStore2.name,
|
||||||
return checkStoreContents(
|
"renamed_books",
|
||||||
t,
|
"IDBObjectStore obtained after the rename transaction should " +
|
||||||
renamedBookStore2,
|
"reflect the new name",
|
||||||
"Renaming an object store should not change its records",
|
);
|
||||||
).then(() => database.close());
|
});
|
||||||
})
|
|
||||||
.then(() => {
|
|
||||||
t.deepEqual(
|
|
||||||
renamedBookStore.name,
|
|
||||||
"renamed_books",
|
|
||||||
"IDBObjectStore used in the rename transaction should keep " +
|
|
||||||
"reflecting the new name after the transaction is committed",
|
|
||||||
);
|
|
||||||
t.deepEqual(
|
|
||||||
renamedBookStore2.name,
|
|
||||||
"renamed_books",
|
|
||||||
"IDBObjectStore obtained after the rename transaction should " +
|
|
||||||
"reflect the new name",
|
|
||||||
);
|
|
||||||
});
|
|
||||||
});
|
|
||||||
t.pass();
|
|
||||||
});
|
});
|
||||||
|
|
||||||
// Renames the 'books' store to 'renamed_books'.
|
// Renames the 'books' store to 'renamed_books'.
|
||||||
@ -333,13 +322,13 @@ test("WPT idbobjectstore-rename-store.html (IndexedDB object store swapping via
|
|||||||
"IDBDatabase.objectStoreNames should immediately reflect the swap",
|
"IDBDatabase.objectStoreNames should immediately reflect the swap",
|
||||||
);
|
);
|
||||||
|
|
||||||
t.deepEqual(
|
t.is(
|
||||||
transaction.objectStore("books"),
|
transaction.objectStore("books"),
|
||||||
notBookStore,
|
notBookStore,
|
||||||
'IDBTransaction.objectStore should return the original "books" ' +
|
'IDBTransaction.objectStore should return the original "books" ' +
|
||||||
'store when queried with "not_books" after the swap',
|
'store when queried with "not_books" after the swap',
|
||||||
);
|
);
|
||||||
t.deepEqual(
|
t.is(
|
||||||
transaction.objectStore("not_books"),
|
transaction.objectStore("not_books"),
|
||||||
bookStore,
|
bookStore,
|
||||||
"IDBTransaction.objectStore should return the original " +
|
"IDBTransaction.objectStore should return the original " +
|
||||||
@ -452,9 +441,12 @@ test("WPT idbobjectstore-rename-store.html (IndexedDB object store rename string
|
|||||||
t.pass();
|
t.pass();
|
||||||
});
|
});
|
||||||
|
|
||||||
function rename_test_macro(t: ExecutionContext, escapedName: string) {
|
function rename_test_macro(
|
||||||
|
t: ExecutionContext,
|
||||||
|
escapedName: string,
|
||||||
|
): Promise<void> {
|
||||||
const name = JSON.parse('"' + escapedName + '"');
|
const name = JSON.parse('"' + escapedName + '"');
|
||||||
createDatabase(t, (database, transaction) => {
|
return createDatabase(t, (database, transaction) => {
|
||||||
createBooksStore(t, database);
|
createBooksStore(t, database);
|
||||||
})
|
})
|
||||||
.then((database) => {
|
.then((database) => {
|
||||||
|
@ -14,10 +14,12 @@
|
|||||||
* permissions and limitations under the License.
|
* permissions and limitations under the License.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
import { DOMStringList } from "../idbtypes";
|
||||||
|
|
||||||
/** @public */
|
/** @public */
|
||||||
export interface FakeDOMStringList extends Array<string> {
|
export interface FakeDOMStringList extends Array<string> {
|
||||||
contains: (value: string) => boolean;
|
contains: (value: string) => boolean;
|
||||||
item: (i: number) => string | undefined;
|
item: (i: number) => string | null;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Would be nicer to sublcass Array, but I'd have to sacrifice Node 4 support to do that.
|
// Would be nicer to sublcass Array, but I'd have to sacrifice Node 4 support to do that.
|
||||||
@ -26,13 +28,16 @@ export const fakeDOMStringList = (arr: string[]): FakeDOMStringList => {
|
|||||||
const arr2 = arr.slice();
|
const arr2 = arr.slice();
|
||||||
|
|
||||||
Object.defineProperty(arr2, "contains", {
|
Object.defineProperty(arr2, "contains", {
|
||||||
// tslint:disable-next-line object-literal-shorthand
|
|
||||||
value: (value: string) => arr2.indexOf(value) >= 0,
|
value: (value: string) => arr2.indexOf(value) >= 0,
|
||||||
});
|
});
|
||||||
|
|
||||||
Object.defineProperty(arr2, "item", {
|
Object.defineProperty(arr2, "item", {
|
||||||
// tslint:disable-next-line object-literal-shorthand
|
value: (i: number) => {
|
||||||
value: (i: number) => arr2[i],
|
if (i < 0 || i >= arr2.length) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
return arr2[i];
|
||||||
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
return arr2 as FakeDOMStringList;
|
return arr2 as FakeDOMStringList;
|
||||||
|
Loading…
Reference in New Issue
Block a user