Skip to content

Commit 296b914

Browse files
committed
Refactor browser fixtures for tests
1 parent 7ef741a commit 296b914

File tree

4 files changed

+83
-56
lines changed

4 files changed

+83
-56
lines changed

tests/browser_args.py

Lines changed: 0 additions & 19 deletions
This file was deleted.

tests/conftest.py

Lines changed: 74 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,14 @@
11
import logging
22
import os
33
import signal
4+
from contextlib import AbstractAsyncContextManager
45
from enum import Enum
56
from threading import Event
67
from typing import AsyncGenerator
78

89
import pytest
910

1011
import zendriver as zd
11-
from tests.browser_args import get_browser_args
1212

1313
logger = logging.getLogger(__name__)
1414

@@ -28,26 +28,82 @@ def fixture_params(self):
2828
return [{"headless": True}, {"headless": False}]
2929

3030

31-
BROWSER_MODE = BrowserMode(os.getenv("ZENDRIVER_TEST_BROWSERS", "all"))
32-
33-
PAUSE_AFTER_TEST = os.getenv("ZENDRIVER_PAUSE_AFTER_TEST", "false") == "true"
3431
NEXT_TEST_EVENT = Event()
3532

3633

37-
@pytest.fixture(params=BROWSER_MODE.fixture_params)
38-
async def browser(request: pytest.FixtureRequest) -> AsyncGenerator[zd.Browser, None]:
34+
class TestConfig:
35+
BROWSER_MODE = BrowserMode(os.getenv("ZENDRIVER_TEST_BROWSERS", "all"))
36+
PAUSE_AFTER_TEST = os.getenv("ZENDRIVER_PAUSE_AFTER_TEST", "false") == "true"
37+
SANDBOX = os.getenv("ZENDRIVER_TEST_SANDBOX", "false") == "true"
38+
USE_WAYLAND = os.getenv("WAYLAND_DISPLAY") is not None
39+
40+
41+
class CreateBrowser(AbstractAsyncContextManager):
42+
def __init__(
43+
self,
44+
*,
45+
headless: bool = True,
46+
sandbox: bool = TestConfig.SANDBOX,
47+
browser_args: list[str] | None = None,
48+
):
49+
self.headless = headless
50+
self.sandbox = sandbox
51+
self.browser_args = browser_args
52+
self.browser: zd.Browser | None = None
53+
self.browser_pid: int | None = None
54+
55+
def _browser_args(self) -> list[str]:
56+
args = []
57+
if not self.headless and TestConfig.USE_WAYLAND:
58+
# use wayland backend instead of x11
59+
args.extend(
60+
["--disable-features=UseOzonePlatform", "--ozone-platform=wayland"]
61+
)
62+
if self.browser_args is not None:
63+
args.extend(self.browser_args)
64+
65+
return args
66+
67+
def config(self) -> zd.Config:
68+
return zd.Config(
69+
headless=self.headless,
70+
sandbox=self.sandbox,
71+
browser_args=self._browser_args(),
72+
)
73+
74+
async def __aenter__(self) -> zd.Browser:
75+
self.browser = await zd.start(self.config())
76+
browser_pid = self.browser._process_pid
77+
assert browser_pid is not None and browser_pid > 0
78+
await self.browser.wait(0)
79+
return self.browser
80+
81+
async def __aexit__(self, exc_type, exc_val, exc_tb):
82+
if self.browser is not None:
83+
await self.browser.stop()
84+
assert self.browser_pid is None
85+
86+
87+
@pytest.fixture
88+
def create_browser() -> type[CreateBrowser]:
89+
return CreateBrowser
90+
91+
92+
@pytest.fixture(params=TestConfig.BROWSER_MODE.fixture_params)
93+
def headless(request: pytest.FixtureRequest) -> bool:
94+
return request.param["headless"]
95+
96+
97+
@pytest.fixture
98+
async def browser(
99+
headless: bool, create_browser: type[CreateBrowser]
100+
) -> AsyncGenerator[zd.Browser, None]:
39101
NEXT_TEST_EVENT.clear()
40-
args = get_browser_args(headless=request.param["headless"])
41-
browser = await zd.start(
42-
# use wayland for rendering instead of default X11 backend
43-
browser_args=args,
44-
headless=request.param["headless"],
45-
)
46-
browser_pid = browser._process_pid
47-
assert browser_pid is not None and browser_pid > 0
48-
await browser.wait(0)
49-
yield browser
50-
if PAUSE_AFTER_TEST:
102+
103+
async with create_browser(headless=headless) as browser:
104+
yield browser
105+
106+
if TestConfig.PAUSE_AFTER_TEST:
51107
logger.info(
52108
"Pausing after test. Send next test hotkey (default Mod+Return) to continue to next test"
53109
)
@@ -58,7 +114,7 @@ async def browser(request: pytest.FixtureRequest) -> AsyncGenerator[zd.Browser,
58114

59115
# signal handler for starting next test
60116
def handle_next_test(signum, frame):
61-
if not PAUSE_AFTER_TEST:
117+
if not TestConfig.PAUSE_AFTER_TEST:
62118
logger.warning(
63119
"Next test signal received, but ZENDRIVER_PAUSE_AFTER_TEST is not set."
64120
)

tests/core/test_browser.py

Lines changed: 6 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -2,23 +2,22 @@
22
from pytest_mock import MockerFixture
33

44
import zendriver as zd
5-
from tests.browser_args import get_browser_args
5+
from tests.conftest import CreateBrowser
66

77

88
async def test_connection_error_raises_exception_and_logs_stderr(
9-
mocker: MockerFixture, caplog: pytest.LogCaptureFixture
9+
create_browser: type[CreateBrowser],
10+
mocker: MockerFixture,
11+
caplog: pytest.LogCaptureFixture,
1012
):
1113
mocker.patch(
1214
"zendriver.core.browser.Browser.test_connection",
1315
return_value=False,
1416
)
1517
with caplog.at_level("INFO"):
1618
with pytest.raises(Exception):
17-
await zd.start(
18-
headless=True,
19-
browser_args=get_browser_args(headless=True),
20-
browser_connection_max_tries=1,
21-
)
19+
async with create_browser() as _:
20+
pass
2221
assert "Browser stderr" in caplog.text
2322

2423

tests/core/test_multiple_browsers.py

Lines changed: 3 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -1,18 +1,9 @@
11
import zendriver as zd
2-
from tests.browser_args import get_browser_args
2+
from tests.conftest import CreateBrowser
33

4-
# browser fixture not used here because this is a special case
54

6-
7-
async def test_multiple_browsers_diff_userdata():
8-
config = zd.Config(
9-
headless=True,
10-
browser_args=get_browser_args(headless=True)
11-
+ [
12-
"--window-size=800,800",
13-
"--wait-for-debugger-webui",
14-
],
15-
)
5+
async def test_multiple_browsers_diff_userdata(create_browser: type[CreateBrowser]):
6+
config = create_browser().config()
167
config.browser_connection_timeout = 1
178
config.browser_connection_max_tries = 15
189

0 commit comments

Comments
 (0)