From de4540d4dbd5b6efea9b002f3a691b59814018c3 Mon Sep 17 00:00:00 2001 From: Maksim Sadym Date: Wed, 8 Oct 2025 11:09:13 +0200 Subject: [PATCH] [wdspec] `emulation.setNetworkConditions:offline` --- .../webdriver/bidi/modules/emulation.py | 13 ++ .../set_network_conditions/__init__.py | 1 + .../set_network_conditions/conftest.py | 78 ++++++++ .../set_network_conditions/contexts.py | 171 ++++++++++++++++++ .../set_network_conditions/global.py | 47 +++++ .../set_network_conditions/invalid.py | 129 +++++++++++++ .../network_conditions_offline.py | 123 +++++++++++++ .../set_network_conditions/user_contexts.py | 120 ++++++++++++ webdriver/tests/support/fixtures_bidi.py | 25 ++- 9 files changed, 706 insertions(+), 1 deletion(-) create mode 100644 webdriver/tests/bidi/emulation/set_network_conditions/__init__.py create mode 100644 webdriver/tests/bidi/emulation/set_network_conditions/conftest.py create mode 100644 webdriver/tests/bidi/emulation/set_network_conditions/contexts.py create mode 100644 webdriver/tests/bidi/emulation/set_network_conditions/global.py create mode 100644 webdriver/tests/bidi/emulation/set_network_conditions/invalid.py create mode 100644 webdriver/tests/bidi/emulation/set_network_conditions/network_conditions_offline.py create mode 100644 webdriver/tests/bidi/emulation/set_network_conditions/user_contexts.py diff --git a/tools/webdriver/webdriver/bidi/modules/emulation.py b/tools/webdriver/webdriver/bidi/modules/emulation.py index 01d06e648ac88d..abe7f4d4fba3bd 100644 --- a/tools/webdriver/webdriver/bidi/modules/emulation.py +++ b/tools/webdriver/webdriver/bidi/modules/emulation.py @@ -104,3 +104,16 @@ def set_user_agent_override( "contexts": contexts, "userContexts": user_contexts, } + + @command + def set_network_conditions( + self, + network_conditions: Nullable[Dict[str, Any]], + contexts: Maybe[List[str]] = UNDEFINED, + user_contexts: Maybe[List[str]] = UNDEFINED, + ) -> Mapping[str, Any]: + return { + "networkConditions": network_conditions, + "contexts": contexts, + "userContexts": user_contexts, + } diff --git a/webdriver/tests/bidi/emulation/set_network_conditions/__init__.py b/webdriver/tests/bidi/emulation/set_network_conditions/__init__.py new file mode 100644 index 00000000000000..55fd2c282d0717 --- /dev/null +++ b/webdriver/tests/bidi/emulation/set_network_conditions/__init__.py @@ -0,0 +1 @@ +OFFLINE_NETWORK_CONDITIONS = {"type": "offline"} diff --git a/webdriver/tests/bidi/emulation/set_network_conditions/conftest.py b/webdriver/tests/bidi/emulation/set_network_conditions/conftest.py new file mode 100644 index 00000000000000..6c8b93352037d2 --- /dev/null +++ b/webdriver/tests/bidi/emulation/set_network_conditions/conftest.py @@ -0,0 +1,78 @@ +import uuid + +import pytest_asyncio + +from webdriver.bidi.error import UnknownErrorException +from webdriver.bidi.modules.script import ContextTarget, \ + ScriptEvaluateResultException + + +@pytest_asyncio.fixture +async def get_navigator_online(bidi_session): + async def get_navigator_online(context): + result = await bidi_session.script.evaluate( + expression="navigator.onLine", + target=ContextTarget(context["context"]), + await_promise=True, + ) + + return result["value"] + + return get_navigator_online + + +@pytest_asyncio.fixture +async def get_can_fetch(bidi_session, url): + async def get_can_fetch(context): + try: + await bidi_session.script.call_function( + function_declaration=f"(url)=>fetch(url)", + arguments=[{ + "type": "string", + "value": url(f"/common/blank.html?{uuid.uuid4()}") + }], + target=ContextTarget(context["context"]), + await_promise=True, + ) + return True + except ScriptEvaluateResultException: + return False + + return get_can_fetch + + +@pytest_asyncio.fixture +async def get_can_navigate(bidi_session, url): + async def get_can_navigate(context): + try: + await bidi_session.browsing_context.navigate( + context=context["context"], + url=url(f"/common/blank.html?{uuid.uuid4()}"), + wait="complete") + return True + except UnknownErrorException: + return False + + return get_can_navigate + + +@pytest_asyncio.fixture(params=['default', 'new'], + ids=["Default user context", "Custom user context"]) +async def target_user_context(request, create_user_context): + return request.param + + +@pytest_asyncio.fixture +async def affected_user_context(target_user_context, create_user_context): + """ Returns either a new or default user context. """ + if target_user_context == 'default': + return 'default' + return await create_user_context() + + +@pytest_asyncio.fixture +async def not_affected_user_context(target_user_context, create_user_context): + """ Returns opposite to `affected_user_context user context. """ + if target_user_context == 'new': + return 'default' + return await create_user_context() diff --git a/webdriver/tests/bidi/emulation/set_network_conditions/contexts.py b/webdriver/tests/bidi/emulation/set_network_conditions/contexts.py new file mode 100644 index 00000000000000..d07aa9338293d8 --- /dev/null +++ b/webdriver/tests/bidi/emulation/set_network_conditions/contexts.py @@ -0,0 +1,171 @@ +import pytest + +from . import OFFLINE_NETWORK_CONDITIONS + +pytestmark = pytest.mark.asyncio + + +async def test_isolation(bidi_session, top_context, + get_navigator_online): + another_context = await bidi_session.browsing_context.create( + type_hint="tab") + + assert await get_navigator_online(top_context) + assert await get_navigator_online(another_context) + + await bidi_session.emulation.set_network_conditions( + network_conditions=OFFLINE_NETWORK_CONDITIONS, + contexts=[top_context["context"]]) + + assert not await get_navigator_online(top_context) + assert await get_navigator_online(another_context) + yet_another_context = await bidi_session.browsing_context.create( + type_hint="tab") + assert await get_navigator_online(yet_another_context) + + await bidi_session.emulation.set_network_conditions( + network_conditions=None, + contexts=[top_context["context"]]) + + assert await get_navigator_online(top_context) + assert await get_navigator_online(another_context) + assert await get_navigator_online(yet_another_context) + + +@pytest.mark.parametrize("domain", ["", "alt"], + ids=["same_origin", "cross_origin"]) +async def test_frame(bidi_session, url, get_navigator_online, + top_context, create_iframe, domain): + iframe_id = await create_iframe(top_context, url('/', domain=domain)); + + assert await get_navigator_online(iframe_id) + + await bidi_session.emulation.set_network_conditions( + network_conditions=OFFLINE_NETWORK_CONDITIONS, + contexts=[top_context["context"]]) + + assert not await get_navigator_online(iframe_id) + + await bidi_session.emulation.set_network_conditions( + network_conditions=None, + contexts=[top_context["context"]]) + + assert await get_navigator_online(iframe_id) + + +async def test_overrides_user_contexts(bidi_session, get_navigator_online, + affected_user_context): + affected_context = await bidi_session.browsing_context.create( + type_hint="tab", user_context=affected_user_context) + + assert await get_navigator_online(affected_context) + + await bidi_session.emulation.set_network_conditions( + network_conditions=OFFLINE_NETWORK_CONDITIONS, + contexts=[affected_context["context"]]) + + assert not await get_navigator_online(affected_context) + + await bidi_session.emulation.set_network_conditions( + network_conditions=None, + user_contexts=[affected_user_context]) + + assert not await get_navigator_online(affected_context) + + await bidi_session.emulation.set_network_conditions( + network_conditions=OFFLINE_NETWORK_CONDITIONS, + user_contexts=[affected_user_context]) + + assert not await get_navigator_online(affected_context) + + await bidi_session.emulation.set_network_conditions( + network_conditions=None, + contexts=[affected_context["context"]]) + + assert not await get_navigator_online(affected_context) + + await bidi_session.emulation.set_network_conditions( + network_conditions=None, + user_contexts=[affected_user_context]) + + assert await get_navigator_online(affected_context) + + +async def test_restores_to_user_contexts_when_removed(bidi_session, + get_navigator_online, + affected_user_context): + affected_context = await bidi_session.browsing_context.create( + type_hint="tab", user_context=affected_user_context) + + assert await get_navigator_online(affected_context) + + await bidi_session.emulation.set_network_conditions( + network_conditions=OFFLINE_NETWORK_CONDITIONS, + contexts=[affected_context["context"]]) + + await bidi_session.emulation.set_network_conditions( + network_conditions=OFFLINE_NETWORK_CONDITIONS, + user_contexts=[affected_user_context]) + + await bidi_session.emulation.set_network_conditions( + network_conditions=None, + contexts=[affected_context["context"]]) + + assert not await get_navigator_online(affected_context) + + +async def test_overrides_global(bidi_session, get_navigator_online, + affected_user_context): + affected_context = await bidi_session.browsing_context.create( + type_hint="tab", user_context=affected_user_context) + + assert await get_navigator_online(affected_context) + + await bidi_session.emulation.set_network_conditions( + network_conditions=OFFLINE_NETWORK_CONDITIONS, + contexts=[affected_context["context"]]) + + assert not await get_navigator_online(affected_context) + + await bidi_session.emulation.set_network_conditions( + network_conditions=None) + + assert not await get_navigator_online(affected_context) + + await bidi_session.emulation.set_network_conditions( + network_conditions=OFFLINE_NETWORK_CONDITIONS) + + assert not await get_navigator_online(affected_context) + + await bidi_session.emulation.set_network_conditions( + network_conditions=None, + contexts=[affected_context["context"]]) + + assert not await get_navigator_online(affected_context) + + await bidi_session.emulation.set_network_conditions( + network_conditions=None) + + assert await get_navigator_online(affected_context) + + +async def test_restores_to_global_when_removed(bidi_session, + get_navigator_online, + affected_user_context): + affected_context = await bidi_session.browsing_context.create( + type_hint="tab", user_context=affected_user_context) + + assert await get_navigator_online(affected_context) + + await bidi_session.emulation.set_network_conditions( + network_conditions=OFFLINE_NETWORK_CONDITIONS, + contexts=[affected_context["context"]]) + + await bidi_session.emulation.set_network_conditions( + network_conditions=OFFLINE_NETWORK_CONDITIONS) + + await bidi_session.emulation.set_network_conditions( + network_conditions=None, + contexts=[affected_context["context"]]) + + assert not await get_navigator_online(affected_context) diff --git a/webdriver/tests/bidi/emulation/set_network_conditions/global.py b/webdriver/tests/bidi/emulation/set_network_conditions/global.py new file mode 100644 index 00000000000000..f48d27d2664e71 --- /dev/null +++ b/webdriver/tests/bidi/emulation/set_network_conditions/global.py @@ -0,0 +1,47 @@ +import pytest + +from . import OFFLINE_NETWORK_CONDITIONS + +pytestmark = pytest.mark.asyncio + + +async def test_top_level(bidi_session, create_user_context, + get_navigator_online, affected_user_context): + affected_context = await bidi_session.browsing_context.create( + type_hint="tab", user_context=affected_user_context) + + assert await get_navigator_online(affected_context) + + await bidi_session.emulation.set_network_conditions( + network_conditions=OFFLINE_NETWORK_CONDITIONS) + + assert not await get_navigator_online(affected_context) + + another_affected_context = await bidi_session.browsing_context.create( + type_hint="tab", user_context=affected_user_context) + assert not await get_navigator_online(another_affected_context) + + await bidi_session.emulation.set_network_conditions(network_conditions=None) + + assert await get_navigator_online(affected_context) + assert await get_navigator_online(another_affected_context) + + +@pytest.mark.parametrize("domain", ["", "alt"], + ids=["same_origin", "cross_origin"]) +async def test_iframe(bidi_session, url, get_navigator_online, + top_context, create_iframe, domain, affected_user_context): + affected_context = await bidi_session.browsing_context.create( + type_hint="tab", user_context=affected_user_context) + iframe_id = await create_iframe(affected_context, url('/', domain=domain)) + + assert await get_navigator_online(iframe_id) + + await bidi_session.emulation.set_network_conditions( + network_conditions=OFFLINE_NETWORK_CONDITIONS) + + assert not await get_navigator_online(iframe_id) + + await bidi_session.emulation.set_network_conditions(network_conditions=None) + + assert await get_navigator_online(iframe_id) diff --git a/webdriver/tests/bidi/emulation/set_network_conditions/invalid.py b/webdriver/tests/bidi/emulation/set_network_conditions/invalid.py new file mode 100644 index 00000000000000..3d320d0cff7aee --- /dev/null +++ b/webdriver/tests/bidi/emulation/set_network_conditions/invalid.py @@ -0,0 +1,129 @@ +import pytest + +import webdriver.bidi.error as error +from tests.bidi import get_invalid_cases +from webdriver.bidi.undefined import UNDEFINED + +pytestmark = pytest.mark.asyncio + + +@pytest.mark.parametrize("value", get_invalid_cases("list")) +async def test_params_contexts_invalid_type(bidi_session, value): + with pytest.raises(error.InvalidArgumentException): + await bidi_session.emulation.set_network_conditions( + network_conditions=None, + contexts=value + ) + + +async def test_params_contexts_empty_list(bidi_session): + with pytest.raises(error.InvalidArgumentException): + await bidi_session.emulation.set_network_conditions( + network_conditions=None, + contexts=[]) + + +@pytest.mark.parametrize("value", get_invalid_cases("string")) +async def test_params_contexts_entry_invalid_type(bidi_session, value): + with pytest.raises(error.InvalidArgumentException): + await bidi_session.emulation.set_network_conditions( + network_conditions=None, + contexts=[value]) + + +async def test_params_contexts_entry_invalid_value(bidi_session): + with pytest.raises(error.NoSuchFrameException): + await bidi_session.emulation.set_network_conditions( + network_conditions=None, + contexts=["_invalid_"], + ) + + +async def test_params_contexts_iframe(bidi_session, new_tab, get_test_page): + url = get_test_page(as_frame=True) + await bidi_session.browsing_context.navigate( + context=new_tab["context"], url=url, wait="complete" + ) + + contexts = await bidi_session.browsing_context.get_tree( + root=new_tab["context"]) + assert len(contexts) == 1 + frames = contexts[0]["children"] + assert len(frames) == 1 + + with pytest.raises(error.InvalidArgumentException): + await bidi_session.emulation.set_network_conditions( + network_conditions=None, + contexts=[frames[0]["context"]], + ) + + +@pytest.mark.parametrize("value", get_invalid_cases("list")) +async def test_params_user_contexts_invalid_type(bidi_session, value): + with pytest.raises(error.InvalidArgumentException): + await bidi_session.emulation.set_network_conditions( + network_conditions=None, + user_contexts=value, + ) + + +async def test_params_user_contexts_empty_list(bidi_session): + with pytest.raises(error.InvalidArgumentException): + await bidi_session.emulation.set_network_conditions( + network_conditions=None, + user_contexts=[], + ) + + +@pytest.mark.parametrize("value", get_invalid_cases("string")) +async def test_params_user_contexts_entry_invalid_type(bidi_session, value): + with pytest.raises(error.InvalidArgumentException): + await bidi_session.emulation.set_network_conditions( + network_conditions=None, + user_contexts=[value], + ) + + +@pytest.mark.parametrize("value", ["", "somestring"]) +async def test_params_user_contexts_entry_invalid_value(bidi_session, value): + with pytest.raises(error.NoSuchUserContextException): + await bidi_session.emulation.set_network_conditions( + network_conditions=None, + user_contexts=[value], + ) + + +async def test_params_contexts_and_user_contexts(bidi_session, top_context): + with pytest.raises(error.InvalidArgumentException): + await bidi_session.emulation.set_network_conditions( + network_conditions=None, + contexts=[top_context["context"]], + user_contexts=["default"], + ) + + +async def test_params_network_conditions_missing(bidi_session, top_context): + with pytest.raises(error.InvalidArgumentException): + await bidi_session.emulation.set_network_conditions( + network_conditions=UNDEFINED, + contexts=[top_context["context"]], + ) + + +@pytest.mark.parametrize("value", get_invalid_cases("dict", nullable=True)) +async def test_params_network_conditions_invalid_type(bidi_session, top_context, + value): + with pytest.raises(error.InvalidArgumentException): + await bidi_session.emulation.set_network_conditions( + network_conditions=value, + contexts=[top_context["context"]], + ) + + +async def test_params_network_conditions_invalid_value(bidi_session, + top_context): + with pytest.raises(error.InvalidArgumentException): + await bidi_session.emulation.set_network_conditions( + network_conditions={"type": "SOME_INVALID_TYPE"}, + contexts=[top_context["context"]], + ) diff --git a/webdriver/tests/bidi/emulation/set_network_conditions/network_conditions_offline.py b/webdriver/tests/bidi/emulation/set_network_conditions/network_conditions_offline.py new file mode 100644 index 00000000000000..5558d6ddff7d83 --- /dev/null +++ b/webdriver/tests/bidi/emulation/set_network_conditions/network_conditions_offline.py @@ -0,0 +1,123 @@ +import pytest + +from tests.bidi import recursive_compare +from webdriver.bidi.modules.script import ContextTarget +from . import OFFLINE_NETWORK_CONDITIONS + +pytestmark = pytest.mark.asyncio + + +async def test_navigator_online(bidi_session, top_context, + get_navigator_online): + assert await get_navigator_online(top_context) + await bidi_session.emulation.set_network_conditions( + network_conditions=OFFLINE_NETWORK_CONDITIONS, + contexts=[top_context["context"]]) + assert not await get_navigator_online(top_context) + await bidi_session.emulation.set_network_conditions( + network_conditions=None, + contexts=[top_context["context"]]) + assert await get_navigator_online(top_context) + + +async def test_fetch(bidi_session, top_context, url, get_can_fetch): + # Navigate away from about:blank to allow fetch requests. + await bidi_session.browsing_context.navigate( + context=top_context["context"], + url=url(f"/common/blank.html"), + wait="complete") + + assert await get_can_fetch(top_context) + await bidi_session.emulation.set_network_conditions( + network_conditions=OFFLINE_NETWORK_CONDITIONS, + contexts=[top_context["context"]]) + assert not await get_can_fetch(top_context) + await bidi_session.emulation.set_network_conditions( + network_conditions=None, + contexts=[top_context["context"]]) + assert await get_can_fetch(top_context) + + +async def test_navigate(bidi_session, top_context, url, + get_can_navigate): + assert await get_can_navigate(top_context) + await bidi_session.emulation.set_network_conditions( + network_conditions=OFFLINE_NETWORK_CONDITIONS, + contexts=[top_context["context"]]) + assert not await get_can_navigate(top_context) + await bidi_session.emulation.set_network_conditions( + network_conditions=None, + contexts=[top_context["context"]]) + assert await get_can_navigate(top_context) + + +async def test_window_offline_online_events(bidi_session, top_context, url, + subscribe_events, wait_for_event, wait_for_future_safe): + await subscribe_events(["script.message"]) + await bidi_session.script.call_function( + function_declaration="""(channel)=>{ + window.addEventListener("offline", (e) => {{ + channel("offline, isTrusted: "+ e.isTrusted); + }}); + window.addEventListener("online", (e) => {{ + channel("online, isTrusted: "+ e.isTrusted); + }}); + }""", + arguments=[{ + "type": "channel", + "value": { + "channel": "channel_name" + } + }], + target=ContextTarget(top_context["context"]), + await_promise=True, + ) + + on_script_message = wait_for_event("script.message") + await bidi_session.emulation.set_network_conditions( + network_conditions=OFFLINE_NETWORK_CONDITIONS, + contexts=[top_context["context"]]) + + # Wait for the window `offline` event. + event_data = await wait_for_future_safe(on_script_message) + recursive_compare( + { + 'channel': 'channel_name', + 'data': { + 'type': 'string', + 'value': 'offline, isTrusted: true' + }, + }, event_data, + ) + + on_script_message = wait_for_event("script.message") + await bidi_session.emulation.set_network_conditions( + network_conditions=None, + contexts=[top_context["context"]]) + + # Wait for the window `online` event. + event_data = await wait_for_future_safe(on_script_message) + recursive_compare( + { + 'channel': 'channel_name', + 'data': { + 'type': 'string', + 'value': 'online, isTrusted: true' + }, + }, event_data, + ) + + +@pytest.mark.skip("TODO: implement the test") +async def test_websocket_disconnected(): + pass + + +@pytest.mark.skip("TODO: implement the test") +async def test_service_worker_fetch(): + pass + + +@pytest.mark.skip("TODO: implement the test") +async def test_service_worker_websocket_disconnected(): + pass diff --git a/webdriver/tests/bidi/emulation/set_network_conditions/user_contexts.py b/webdriver/tests/bidi/emulation/set_network_conditions/user_contexts.py new file mode 100644 index 00000000000000..c3b32f90008390 --- /dev/null +++ b/webdriver/tests/bidi/emulation/set_network_conditions/user_contexts.py @@ -0,0 +1,120 @@ +import pytest + +from . import OFFLINE_NETWORK_CONDITIONS + +pytestmark = pytest.mark.asyncio + + +async def test_isolation(bidi_session, create_user_context, + get_navigator_online, affected_user_context, not_affected_user_context): + affected_context = await bidi_session.browsing_context.create( + type_hint="tab", user_context=affected_user_context) + not_affected_context = await bidi_session.browsing_context.create( + type_hint="tab", user_context=not_affected_user_context) + + assert await get_navigator_online(affected_context) + assert await get_navigator_online(not_affected_context) + + await bidi_session.emulation.set_network_conditions( + network_conditions=OFFLINE_NETWORK_CONDITIONS, + user_contexts=[affected_user_context]) + + assert not await get_navigator_online(affected_context) + assert await get_navigator_online(not_affected_context) + + another_affected_context = await bidi_session.browsing_context.create( + type_hint="tab", user_context=affected_user_context) + another_not_affected_context = await bidi_session.browsing_context.create( + type_hint="tab", user_context=not_affected_user_context) + assert not await get_navigator_online(another_affected_context) + assert await get_navigator_online(another_not_affected_context) + + await bidi_session.emulation.set_network_conditions( + network_conditions=None, + user_contexts=[affected_user_context]) + + assert await get_navigator_online(affected_context) + assert await get_navigator_online(not_affected_context) + assert await get_navigator_online(another_affected_context) + assert await get_navigator_online(another_not_affected_context) + + +@pytest.mark.parametrize("domain", ["", "alt"], + ids=["same_origin", "cross_origin"]) +async def test_frame(bidi_session, url, get_navigator_online, + top_context, create_iframe, domain, affected_user_context): + affected_context = await bidi_session.browsing_context.create( + type_hint="tab", user_context=affected_user_context) + + iframe_id = await create_iframe(affected_context, url('/', domain=domain)) + + assert await get_navigator_online(iframe_id) + + await bidi_session.emulation.set_network_conditions( + network_conditions=OFFLINE_NETWORK_CONDITIONS, + user_contexts=[affected_user_context]) + + assert not await get_navigator_online(iframe_id) + + await bidi_session.emulation.set_network_conditions( + network_conditions=None, + user_contexts=[affected_user_context]) + + assert await get_navigator_online(iframe_id) + + +async def test_overrides_global(bidi_session, get_navigator_online, + affected_user_context): + affected_context = await bidi_session.browsing_context.create( + type_hint="tab", user_context=affected_user_context) + + assert await get_navigator_online(affected_context) + + await bidi_session.emulation.set_network_conditions( + network_conditions=OFFLINE_NETWORK_CONDITIONS, + user_contexts=[affected_user_context]) + + assert not await get_navigator_online(affected_context) + + await bidi_session.emulation.set_network_conditions( + network_conditions=None) + + assert not await get_navigator_online(affected_context) + + await bidi_session.emulation.set_network_conditions( + network_conditions=OFFLINE_NETWORK_CONDITIONS) + + assert not await get_navigator_online(affected_context) + + await bidi_session.emulation.set_network_conditions( + network_conditions=None, + user_contexts=[affected_user_context]) + + assert not await get_navigator_online(affected_context) + + await bidi_session.emulation.set_network_conditions( + network_conditions=None) + + assert await get_navigator_online(affected_context) + + +async def test_restores_to_global_when_removed(bidi_session, + get_navigator_online, + affected_user_context): + affected_context = await bidi_session.browsing_context.create( + type_hint="tab", user_context=affected_user_context) + + assert await get_navigator_online(affected_context) + + await bidi_session.emulation.set_network_conditions( + network_conditions=OFFLINE_NETWORK_CONDITIONS, + user_contexts=[affected_user_context]) + + await bidi_session.emulation.set_network_conditions( + network_conditions=OFFLINE_NETWORK_CONDITIONS) + + await bidi_session.emulation.set_network_conditions( + network_conditions=None, + user_contexts=[affected_user_context]) + + assert not await get_navigator_online(affected_context) diff --git a/webdriver/tests/support/fixtures_bidi.py b/webdriver/tests/support/fixtures_bidi.py index 532d7051e1f221..0e2c21345e3c3e 100644 --- a/webdriver/tests/support/fixtures_bidi.py +++ b/webdriver/tests/support/fixtures_bidi.py @@ -241,7 +241,30 @@ async def current_time(): @pytest.fixture -def add_and_remove_iframe(bidi_session): +def create_iframe(bidi_session): + """ + Create an iframe and wait for it to load. Return the iframe's context id. + """ + + async def create_iframe(context, url): + resp = await bidi_session.script.call_function( + function_declaration="""(url) => { + const iframe = document.createElement("iframe"); + iframe.src = url; + document.documentElement.lastElementChild.append(iframe); + return new Promise(resolve => iframe.onload = () => resolve(iframe.contentWindow)); + }""", + arguments=[{"type": "string", "value": url}], + target=ContextTarget(context["context"]), + await_promise=True) + assert resp["type"] == "window" + return resp["value"] + + return create_iframe + + +@pytest.fixture +def add_and_remove_iframe(bidi_session, create_iframe): """Create a frame, wait for load, and remove it. Return the frame's context id, which allows to test for invalid