diff options
Diffstat (limited to 'test/unit')
-rw-r--r-- | test/unit/conftest.py | 3 | ||||
-rw-r--r-- | test/unit/test_indexeddb.py | 169 |
2 files changed, 123 insertions, 49 deletions
diff --git a/test/unit/conftest.py b/test/unit/conftest.py index beffaf5..e7be339 100644 --- a/test/unit/conftest.py +++ b/test/unit/conftest.py @@ -122,7 +122,8 @@ def _execute_in_page_context(driver, script, args): try: result = driver.execute_script(script_injector_script, script_url, args) - if type(result) == list and result[0] == 'haketilo_selenium_error': + if type(result) is list and len(result) == 2 and \ + result[0] == 'haketilo_selenium_error': raise Exception(result[1]) return result except Exception as e: diff --git a/test/unit/test_indexeddb.py b/test/unit/test_indexeddb.py index df3df81..447ee6e 100644 --- a/test/unit/test_indexeddb.py +++ b/test/unit/test_indexeddb.py @@ -296,8 +296,7 @@ def test_haketilodb_item_modifications(driver, execute_in_page): def test_haketilodb_settings(driver, execute_in_page): """ indexeddb.js facilitates operating on Haketilo's internal database. - Verify database assigning/retrieving values of simple "settings" works - properly. + Verify assigning/retrieving values of simple "settings" item works properly. """ execute_in_page(indexeddb_js()) mock_broadcast(execute_in_page) @@ -315,17 +314,66 @@ def test_haketilodb_settings(driver, execute_in_page): execute_in_page('returnval(set_setting("option15", "enable"));') assert execute_in_page('returnval(get_setting("option15"));') == 'enable' +@pytest.mark.get_page('https://gotmyowndoma.in') +def test_haketilodb_allowing(driver, execute_in_page): + """ + indexeddb.js facilitates operating on Haketilo's internal database. + Verify changing the "blocking" configuration for a URL works properly. + """ + execute_in_page(indexeddb_js()) + mock_broadcast(execute_in_page) + + # Start with no database. + clear_indexeddb(execute_in_page) + + assert get_db_contents(execute_in_page)['blocking'] == [] + + def run_with_sample_url(expr): + return execute_in_page(f'returnval({expr});', 'https://example.com/**') + + assert None == run_with_sample_url('get_allowing(arguments[0])') + + run_with_sample_url('set_disallowed(arguments[0])') + assert False == run_with_sample_url('get_allowing(arguments[0])') + + run_with_sample_url('set_allowed(arguments[0])') + assert True == run_with_sample_url('get_allowing(arguments[0])') + + run_with_sample_url('set_default_allowing(arguments[0])') + assert None == run_with_sample_url('get_allowing(arguments[0])') + +@pytest.mark.get_page('https://gotmyowndoma.in') +def test_haketilodb_repos(driver, execute_in_page): + """ + indexeddb.js facilitates operating on Haketilo's internal database. + Verify operations on repositories list work properly. + """ + execute_in_page(indexeddb_js()) + mock_broadcast(execute_in_page) + + # Start with no database. + clear_indexeddb(execute_in_page) + + assert get_db_contents(execute_in_page)['repos'] == [] + + sample_urls = ['https://hdrlla.example.com/', 'https://hdrlla.example.org'] + + assert [] == execute_in_page('returnval(get_repos());') + + execute_in_page('returnval(set_repo(arguments[0]));', sample_urls[0]) + assert [sample_urls[0]] == execute_in_page('returnval(get_repos());') + + execute_in_page('returnval(set_repo(arguments[0]));', sample_urls[1]) + assert set(sample_urls) == set(execute_in_page('returnval(get_repos());')) + + execute_in_page('returnval(del_repo(arguments[0]));', sample_urls[0]) + assert [sample_urls[1]] == execute_in_page('returnval(get_repos());') + test_page_html = ''' <!DOCTYPE html> <script src="/testpage.js"></script> -<script>console.log("inline!")</script> -<script nonce="123456789">console.log("inline nonce!")</script> -<h2>resources</h2> -<ul id="resources"></ul> -<h2>mappings</h2> -<ul id="mappings"></ul> -<h2>settings</h2> -<ul id="settings"></ul> +<body> +</body> ''' @pytest.mark.ext_data({ @@ -342,13 +390,27 @@ def test_haketilodb_track(driver, execute_in_page, wait_elem_text): through extension's background script and allow for object store contents to be tracked in any execution context. """ - # Let's open the same extension's test page in a second window. Window 0 - # will be used to make changed to IndexedDB and window 1 to "track" those + # Let's open the same extension's test page in a second window. Window 1 + # will be used to make changes to IndexedDB and window 0 to "track" those # changes. driver.execute_script('window.open(window.location.href, "_blank");') windows = [*driver.window_handles] assert len(windows) == 2 + # Create elements that will have tracked data inserted under them. + driver.switch_to.window(windows[0]) + execute_in_page(''' + for (const store_name of trackable) { + const h2 = document.createElement("h2"); + h2.innerText = store_name; + document.body.append(h2); + + const ul = document.createElement("ul"); + ul.id = store_name; + document.body.append(ul); + } + ''') + # Mock initial_data. sample_resource = make_sample_resource() sample_mapping = make_sample_mapping() @@ -365,22 +427,19 @@ def test_haketilodb_track(driver, execute_in_page, wait_elem_text): }, 'files': sample_files_by_hash } - for window in reversed(windows): - driver.switch_to.window(window) - try : - driver.execute_script('console.log("uuuuuuu");') - execute_in_page('initial_data = arguments[0];', initial_data) - except: - from time import sleep - sleep(100000) - execute_in_page('returnval(set_setting("option15", "123"));') + driver.switch_to.window(windows[1]) + execute_in_page('initial_data = arguments[0];', initial_data) + execute_in_page('returnval(set_setting("option15", "123"));') + execute_in_page('returnval(set_repo("https://hydril.la"));') + execute_in_page('returnval(set_disallowed("file:///*"));') # See if track.*() functions properly return the already-existing items. + driver.switch_to.window(windows[0]) execute_in_page( ''' function update_item(store_name, change) { - console.log('update', ...arguments); + console.log('# update', ...arguments); const elem_id = `${store_name}_${change.key}`; let elem = document.getElementById(elem_id); elem = elem || document.createElement("li"); @@ -395,10 +454,11 @@ def test_haketilodb_track(driver, execute_in_page, wait_elem_text): async function start_reporting() { - for (const store_name of ["resources", "mappings", "settings"]) { + const props = new Map(stores.map(([sn, opt]) => [sn, opt.keyPath])); + for (const store_name of trackable) { [tracking, items] = await track[store_name](ch => update_item(store_name, ch)); - const prop = store_name === "settings" ? "name" : "identifier"; + const prop = props.get(store_name); for (const item of items) update_item(store_name, {key: item[prop], new_val: item}); } @@ -407,18 +467,20 @@ def test_haketilodb_track(driver, execute_in_page, wait_elem_text): returnval(start_reporting()); ''') - item_counts = driver.execute_script( - ''' + item_counts = execute_in_page( + '''{ const childcount = id => document.getElementById(id).childElementCount; - return ["resources", "mappings", "settings"].map(childcount); - ''') - assert item_counts == [1, 1, 1] - resource_json = driver.find_element_by_id('resources_helloapple').text - mapping_json = driver.find_element_by_id('mappings_helloapple').text - setting_json = driver.find_element_by_id('settings_option15').text - assert json.loads(resource_json) == sample_resource - assert json.loads(mapping_json) == sample_mapping - assert json.loads(setting_json) == {'name': 'option15', 'value': '123'} + returnval(trackable.map(childcount)); + }''') + assert item_counts == [1 for _ in item_counts] + for elem_id, json_value in [ + ('resources_helloapple', sample_resource), + ('mappings_helloapple', sample_mapping), + ('settings_option15', {'name': 'option15', 'value': '123'}), + ('repos_https://hydril.la', {'url': 'https://hydril.la'}), + ('blocking_file:///*', {'pattern': 'file:///*', 'allow': False}) + ]: + assert json.loads(driver.find_element_by_id(elem_id).text) == json_value # See if item additions get tracked properly. driver.switch_to.window(windows[1]) @@ -441,22 +503,26 @@ def test_haketilodb_track(driver, execute_in_page, wait_elem_text): } execute_in_page('returnval(save_items(arguments[0]));', sample_data) execute_in_page('returnval(set_setting("option22", "abc"));') + execute_in_page('returnval(set_repo("https://hydril2.la"));') + execute_in_page('returnval(set_allowed("ftp://a.bc/"));') driver.switch_to.window(windows[0]) driver.implicitly_wait(10) - resource_json = driver.find_element_by_id('resources_helloapple-copy').text - mapping_json = driver.find_element_by_id('mappings_helloapple-copy').text - setting_json = driver.find_element_by_id('settings_option22').text + for elem_id, json_value in [ + ('resources_helloapple-copy', sample_resource2), + ('mappings_helloapple-copy', sample_mapping2), + ('settings_option22', {'name': 'option22', 'value': 'abc'}), + ('repos_https://hydril2.la', {'url': 'https://hydril2.la'}), + ('blocking_ftp://a.bc/', {'pattern': 'ftp://a.bc/', 'allow': True}) + ]: + assert json.loads(driver.find_element_by_id(elem_id).text) == json_value driver.implicitly_wait(0) - assert json.loads(resource_json) == sample_resource2 - assert json.loads(mapping_json) == sample_mapping2 - assert json.loads(setting_json) == {'name': 'option22', 'value': 'abc'} - # See if item deletions get tracked properly. + # See if item deletions/modifications get tracked properly. driver.switch_to.window(windows[1]) execute_in_page( '''{ - async function remove_items() + async function change_remove_items() { const store_names = ["resources", "mappings"]; const ctx = await start_items_transaction(store_names, {}); @@ -464,20 +530,27 @@ def test_haketilodb_track(driver, execute_in_page, wait_elem_text): await remove_mapping("helloapple-copy", ctx); await finalize_transaction(ctx); await set_setting("option22", null); + await del_repo("https://hydril.la"); + await set_default_allowing("file:///*"); + await set_disallowed("ftp://a.bc/"); } - returnval(remove_items()); + returnval(change_remove_items()); }''') - removed_ids = ['mappings_helloapple-copy', 'resources_helloapple'] - def condition_items_absent(driver): + removed_ids = ['mappings_helloapple-copy', 'resources_helloapple', + 'repos_https://hydril.la', 'blocking_file:///*'] + def condition_items_absent_and_changed(driver): for id in removed_ids: try: driver.find_element_by_id(id) return False except WebDriverException: pass + option_text = driver.find_element_by_id('settings_option22').text - return json.loads(option_text)['value'] == None + blocking_text = driver.find_element_by_id('blocking_ftp://a.bc/').text + return (json.loads(option_text)['value'] == None and + json.loads(blocking_text)['allow'] == False) driver.switch_to.window(windows[0]) - WebDriverWait(driver, 10).until(condition_items_absent) + WebDriverWait(driver, 10).until(condition_items_absent_and_changed) |