80 lines
2.6 KiB
Python
80 lines
2.6 KiB
Python
import json
|
|
import subprocess
|
|
from pathlib import Path
|
|
|
|
|
|
MODULE = Path(__file__).parents[1] / "frontend" / "private-data-inventory.js"
|
|
|
|
|
|
def run_inventory(databases: dict[str, list[int]], registered: list[str]) -> dict:
|
|
script = r"""
|
|
const createInspector = require(__MODULE__);
|
|
const databases = __DATABASES__;
|
|
const indexedDB = {
|
|
async databases() { return Object.keys(databases).map(name => ({name})); },
|
|
open(name) {
|
|
const request = {};
|
|
queueMicrotask(() => {
|
|
const stores = databases[name];
|
|
const db = {
|
|
objectStoreNames: stores.map((_records, index) => `store-${index}`),
|
|
transaction(names) {
|
|
return {
|
|
objectStore(storeName) {
|
|
return {
|
|
count() {
|
|
const countRequest = {};
|
|
const index = Number(storeName.split('-')[1]);
|
|
queueMicrotask(() => {
|
|
countRequest.result = stores[index];
|
|
countRequest.onsuccess?.();
|
|
});
|
|
return countRequest;
|
|
},
|
|
};
|
|
},
|
|
};
|
|
},
|
|
close() {},
|
|
};
|
|
request.result = db;
|
|
request.onsuccess?.();
|
|
});
|
|
return request;
|
|
},
|
|
};
|
|
createInspector(indexedDB)(__REGISTERED__)
|
|
.then(result => process.stdout.write(JSON.stringify(result)))
|
|
.catch(error => { console.error(error); process.exit(1); });
|
|
"""
|
|
script = (
|
|
script.replace("__MODULE__", json.dumps(str(MODULE)))
|
|
.replace("__DATABASES__", json.dumps(databases))
|
|
.replace("__REGISTERED__", json.dumps(registered))
|
|
)
|
|
completed = subprocess.run(["node", "-e", script], capture_output=True, text=True)
|
|
assert completed.returncode == 0, completed.stderr
|
|
return json.loads(completed.stdout)
|
|
|
|
|
|
def test_inventory_counts_records_without_creating_absent_registered_databases():
|
|
result = run_inventory(
|
|
{"private-a": [2, 1], "other-app": [99]},
|
|
["private-a", "private-empty", "private-missing"],
|
|
)
|
|
|
|
assert result == {"recordCount": 3, "unavailable": False}
|
|
|
|
|
|
def test_inventory_is_conservatively_unavailable_when_enumeration_is_unsupported():
|
|
script = f"""
|
|
const createInspector = require({json.dumps(str(MODULE))});
|
|
createInspector({{}})(['private-a'])
|
|
.then(result => process.stdout.write(JSON.stringify(result)))
|
|
.catch(error => {{ console.error(error.message); process.exit(1); }});
|
|
"""
|
|
completed = subprocess.run(["node", "-e", script], capture_output=True, text=True)
|
|
|
|
assert completed.returncode == 0, completed.stderr
|
|
assert json.loads(completed.stdout) == {"recordCount": 0, "unavailable": True}
|