Skip to content

Commit

Permalink
[wdspec] Add call_function test for deserialization of remote references
Browse files Browse the repository at this point in the history
Depends on D156717

Add tests for deserialization of both this and arguments parameters, with various data structures (object, array, map, set) plus an additional test case nesting all
together.

Differential Revision: https://phabricator.services.mozilla.com/D156531

bugzilla-url: https://bugzilla.mozilla.org/show_bug.cgi?id=1788861
gecko-commit: 149ee65a5a3820cea4591d3d80fd6950419aeafc
gecko-reviewers: webdriver-reviewers, Sasha, whimboo
  • Loading branch information
juliandescottes authored and pull[bot] committed Jul 13, 2023
1 parent a8714cf commit 1197041
Show file tree
Hide file tree
Showing 4 changed files with 132 additions and 2 deletions.
48 changes: 48 additions & 0 deletions webdriver/tests/bidi/script/call_function/arguments.py
Expand Up @@ -174,3 +174,51 @@ async def test_local_values(bidi_session, top_context, argument, expected_type):
)

recursive_compare(argument, result)


@pytest.mark.asyncio
@pytest.mark.parametrize(
"value_fn, function_declaration",
[
(
lambda value: value,
"function(arg) { return arg === window.SOME_OBJECT; }",
),
(
lambda value: ({"type": "object", "value": [["nested", value]]}),
"function(arg) { return arg.nested === window.SOME_OBJECT; }",
),
(
lambda value: ({"type": "array", "value": [value]}),
"function(arg) { return arg[0] === window.SOME_OBJECT; }",
),
(
lambda value: ({"type": "map", "value": [["foobar", value]]}),
"function(arg) { return arg.get('foobar') === window.SOME_OBJECT; }",
),
(
lambda value: ({"type": "set", "value": [value]}),
"function(arg) { return arg.has(window.SOME_OBJECT); }",
),
],
)
async def test_remote_value_deserialization(
bidi_session, top_context, call_function, evaluate, value_fn, function_declaration
):
remote_value = await evaluate(
"window.SOME_OBJECT = {SOME_PROPERTY:'SOME_VALUE'}; window.SOME_OBJECT",
result_ownership="root",
)

# Check that a remote value can be successfully deserialized as an "argument"
# parameter and compared against the original object in the page.
result = await call_function(
function_declaration=function_declaration,
arguments=[value_fn(remote_value)],
)
assert result == {"type": "boolean", "value": True}

# Reload the page to cleanup the state
await bidi_session.browsing_context.navigate(
context=top_context["context"], url=top_context["url"], wait="complete"
)
48 changes: 48 additions & 0 deletions webdriver/tests/bidi/script/call_function/this.py
Expand Up @@ -35,3 +35,51 @@ async def test_default_this(bidi_session, top_context):
recursive_compare({
"type": 'window',
}, result)


@pytest.mark.asyncio
@pytest.mark.parametrize(
"value_fn, function_declaration",
[
(
lambda value: value,
"function() { return this === window.SOME_OBJECT; }",
),
(
lambda value: ({"type": "object", "value": [["nested", value]]}),
"function() { return this.nested === window.SOME_OBJECT; }",
),
(
lambda value: ({"type": "array", "value": [value]}),
"function() { return this[0] === window.SOME_OBJECT; }",
),
(
lambda value: ({"type": "map", "value": [["foobar", value]]}),
"function() { return this.get('foobar') === window.SOME_OBJECT; }",
),
(
lambda value: ({"type": "set", "value": [value]}),
"function() { return this.has(window.SOME_OBJECT); }",
),
],
)
async def test_remote_value_deserialization(
bidi_session, top_context, call_function, evaluate, value_fn, function_declaration
):
remote_value = await evaluate(
"window.SOME_OBJECT = {SOME_PROPERTY:'SOME_VALUE'}; window.SOME_OBJECT",
result_ownership="root",
)

# Check that a remote value can be successfully deserialized as the "this"
# parameter and compared against the original object in the page.
result = await call_function(
function_declaration=function_declaration,
this=value_fn(remote_value),
)
assert result == {"type": "boolean", "value": True}

# Reload the page to cleanup the state
await bidi_session.browsing_context.navigate(
context=top_context["context"], url=top_context["url"], wait="complete"
)
32 changes: 30 additions & 2 deletions webdriver/tests/bidi/script/conftest.py
@@ -1,16 +1,18 @@
import pytest
from typing import Any, List, Mapping

from webdriver.bidi.modules.script import ContextTarget
from webdriver.bidi.modules.script import ContextTarget, OwnershipModel


@pytest.fixture
def call_function(bidi_session, top_context):
async def call_function(
function_declaration: str,
arguments: List[Mapping[str, Any]],
arguments: List[Mapping[str, Any]] = [],
this: Any = None,
context: str = top_context["context"],
sandbox: str = None,
result_ownership: OwnershipModel = OwnershipModel.NONE.value,
) -> Mapping[str, Any]:
if sandbox is None:
target = ContextTarget(top_context["context"])
Expand All @@ -20,7 +22,9 @@ async def call_function(
result = await bidi_session.script.call_function(
function_declaration=function_declaration,
arguments=arguments,
this=this,
await_promise=False,
result_ownership=result_ownership,
target=target,
)
return result
Expand All @@ -32,3 +36,27 @@ async def call_function(
async def default_realm(bidi_session, top_context):
realms = await bidi_session.script.get_realms(context=top_context["context"])
return realms[0]["realm"]


@pytest.fixture
def evaluate(bidi_session, top_context):
async def evaluate(
expression: str,
context: str = top_context["context"],
sandbox: str = None,
result_ownership: OwnershipModel = OwnershipModel.NONE.value,
) -> Mapping[str, Any]:
if sandbox is None:
target = ContextTarget(top_context["context"])
else:
target = ContextTarget(top_context["context"], sandbox)

result = await bidi_session.script.evaluate(
expression=expression,
await_promise=False,
result_ownership=result_ownership,
target=target,
)
return result

return evaluate
6 changes: 6 additions & 0 deletions webdriver/tests/bidi/script/disown/handles.py
Expand Up @@ -114,6 +114,12 @@ async def test_multiple_handles_for_same_object(
result = await call_function("arg => arg.a", [remote_value2])
assert result == {"type": "number", "value": 1}

# Check that both handles point to the same value
result = await call_function(
"(arg1, arg2) => arg1 === arg2", [remote_value1, remote_value2]
)
assert result == {"type": "boolean", "value": True}

# Disown the handle 1
await bidi_session.script.disown(
handles=[remote_value1["handle"]], target=ContextTarget(top_context["context"])
Expand Down

0 comments on commit 1197041

Please sign in to comment.