I've recently started using pytest to run my automated test suite. Test runs that were completing successfully when run sequentially, are now failing randomly when I use xdist to run the suite in parallel. I have pytest configured as follows;
[pytest]
addopts = -nauto --rerun 3 -ra --timeout=180 --junit-xml=pyresult.xml
python_files=test*.py
At random a test will fail to launch the Chromedriver and a timeout will be eventually thrown. For all other instances of failed tests for flaky reasons, pytest will gladly rerun the test for me. However in this instance, when the timeout is thrown, pytest outputs the timeout and then just hangs. My test run never ends and hence Jenkins doesn't get the results its waiting for. The only way to get pytest to finish is to manually send a control break.
My driver is started as follows (NOTE I don't think my code is the problem here);
@classmethod
def open_browser(cls, browser_name, configuration, down_dir=""):
"""
Returns the driver for the required browser
"""
if browser_name == 'Chrome':
chrome_options = webdriver.ChromeOptions()
prefs = {"download.default_directory" : down_dir}
chrome_options.add_experimental_option("prefs", prefs)
driver = webdriver.Chrome(
executable_path=configuration, chrome_options=chrome_options)
The timeout message is as follows;
~~~~~~~~~~~~~~~~~~~~~~~~~~ Stack of <unknown> (8460) ~~~~~~~~~~~~~~~~~~~~~~~~~~~
File "c:\python27\lib\site-packages\execnet\gateway_base.py", line 277, in _perform_spawn
reply.run()
File "c:\python27\lib\site-packages\execnet\gateway_base.py", line 213, in run
self._result = func(*args, **kwargs)
File "c:\python27\lib\site-packages\execnet\gateway_base.py", line 954, in _thread_receiver
msg = Message.from_io(io)
File "c:\python27\lib\site-packages\execnet\gateway_base.py", line 418, in from_io
header = io.read(9) # type 1, channel 4, payload 4
File "c:\python27\lib\site-packages\execnet\gateway_base.py", line 386, in read
data = self._read(numbytes-len(buf))
~~~~~~~~~~~~~~~~~~~~~~~~~ Stack of MainThread (12788) ~~~~~~~~~~~~~~~~~~~~~~~~~~
File "<string>", line 1, in <module>
File "<string>", line 7, in <module>
File "c:\python27\lib\site-packages\execnet\gateway_base.py", line 1534, in serve
SlaveGateway(io=io, id=id, _startcount=2).serve()
File "c:\python27\lib\site-packages\execnet\gateway_base.py", line 1047, in serve
self._execpool.integrate_as_primary_thread()
File "c:\python27\lib\site-packages\execnet\gateway_base.py", line 259, in integrate_as_primary_thread
self._perform_spawn(reply)
File "c:\python27\lib\site-packages\execnet\gateway_base.py", line 277, in _perform_spawn
reply.run()
File "c:\python27\lib\site-packages\execnet\gateway_base.py", line 213, in run
self._result = func(*args, **kwargs)
File "c:\python27\lib\site-packages\execnet\gateway_base.py", line 1072, in executetask
do_exec(co, loc) # noqa
File "<string>", line 1, in do_exec
File "<remote exec>", line 154, in <module>
File "c:\python27\lib\site-packages\_pytest\vendored_packages\pluggy.py", line 724, in __call__
return self._hookexec(self, self._nonwrappers + self._wrappers, kwargs)
File "c:\python27\lib\site-packages\_pytest\vendored_packages\pluggy.py", line 338, in _hookexec
return self._inner_hookexec(hook, methods, kwargs)
File "c:\python27\lib\site-packages\_pytest\vendored_packages\pluggy.py", line 333, in <lambda>
_MultiCall(methods, kwargs, hook.spec_opts).execute()
File "c:\python27\lib\site-packages\_pytest\vendored_packages\pluggy.py", line 596, in execute
res = hook_impl.function(*args)
File "c:\python27\lib\site-packages\_pytest\main.py", line 119, in pytest_cmdline_main
return wrap_session(config, _main)
File "c:\python27\lib\site-packages\_pytest\main.py", line 94, in wrap_session
session.exitstatus = doit(config, session) or 0
File "c:\python27\lib\site-packages\_pytest\main.py", line 125, in _main
config.hook.pytest_runtestloop(session=session)
File "c:\python27\lib\site-packages\_pytest\vendored_packages\pluggy.py", line 724, in __call__
return self._hookexec(self, self._nonwrappers + self._wrappers, kwargs)
File "c:\python27\lib\site-packages\_pytest\vendored_packages\pluggy.py", line 338, in _hookexec
return self._inner_hookexec(hook, methods, kwargs)
File "c:\python27\lib\site-packages\_pytest\vendored_packages\pluggy.py", line 333, in <lambda>
_MultiCall(methods, kwargs, hook.spec_opts).execute()
File "c:\python27\lib\site-packages\_pytest\vendored_packages\pluggy.py", line 596, in execute
res = hook_impl.function(*args)
File "<remote exec>", line 58, in pytest_runtestloop
File "<remote exec>", line 74, in run_tests
File "c:\python27\lib\site-packages\_pytest\vendored_packages\pluggy.py", line 724, in __call__
return self._hookexec(self, self._nonwrappers + self._wrappers, kwargs)
File "c:\python27\lib\site-packages\_pytest\vendored_packages\pluggy.py", line 338, in _hookexec
return self._inner_hookexec(hook, methods, kwargs)
File "c:\python27\lib\site-packages\_pytest\vendored_packages\pluggy.py", line 333, in <lambda>
_MultiCall(methods, kwargs, hook.spec_opts).execute()
File "c:\python27\lib\site-packages\_pytest\vendored_packages\pluggy.py", line 595, in execute
return _wrapped_call(hook_impl.function(*args), self.execute)
File "c:\python27\lib\site-packages\_pytest\vendored_packages\pluggy.py", line 247, in _wrapped_call
call_outcome = _CallOutcome(func)
File "c:\python27\lib\site-packages\_pytest\vendored_packages\pluggy.py", line 264, in __init__
self.result = func()
File "c:\python27\lib\site-packages\_pytest\vendored_packages\pluggy.py", line 595, in execute
return _wrapped_call(hook_impl.function(*args), self.execute)
File "c:\python27\lib\site-packages\_pytest\vendored_packages\pluggy.py", line 247, in _wrapped_call
call_outcome = _CallOutcome(func)
File "c:\python27\lib\site-packages\_pytest\vendored_packages\pluggy.py", line 264, in __init__
self.result = func()
File "c:\python27\lib\site-packages\_pytest\vendored_packages\pluggy.py", line 596, in execute
res = hook_impl.function(*args)
File "c:\python27\lib\site-packages\pytest_rerunfailures.py", line 73, in pytest_runtest_protocol
reports = runtestprotocol(item, nextitem=nextitem, log=False)
File "c:\python27\lib\site-packages\_pytest\runner.py", line 76, in runtestprotocol
reports.append(call_and_report(item, "call", log))
File "c:\python27\lib\site-packages\_pytest\runner.py", line 120, in call_and_report
call = call_runtest_hook(item, when, **kwds)
File "c:\python27\lib\site-packages\_pytest\runner.py", line 138, in call_runtest_hook
return CallInfo(lambda: ihook(item=item, **kwds), when=when)
File "c:\python27\lib\site-packages\_pytest\runner.py", line 150, in __init__
self.result = func()
File "c:\python27\lib\site-packages\_pytest\runner.py", line 138, in <lambda>
return CallInfo(lambda: ihook(item=item, **kwds), when=when)
File "c:\python27\lib\site-packages\_pytest\vendored_packages\pluggy.py", line 724, in __call__
return self._hookexec(self, self._nonwrappers + self._wrappers, kwargs)
File "c:\python27\lib\site-packages\_pytest\vendored_packages\pluggy.py", line 338, in _hookexec
return self._inner_hookexec(hook, methods, kwargs)
File "c:\python27\lib\site-packages\_pytest\vendored_packages\pluggy.py", line 333, in <lambda>
_MultiCall(methods, kwargs, hook.spec_opts).execute()
File "c:\python27\lib\site-packages\_pytest\vendored_packages\pluggy.py", line 595, in execute
return _wrapped_call(hook_impl.function(*args), self.execute)
File "c:\python27\lib\site-packages\_pytest\vendored_packages\pluggy.py", line 247, in _wrapped_call
call_outcome = _CallOutcome(func)
File "c:\python27\lib\site-packages\_pytest\vendored_packages\pluggy.py", line 264, in __init__
self.result = func()
File "c:\python27\lib\site-packages\_pytest\vendored_packages\pluggy.py", line 596, in execute
res = hook_impl.function(*args)
File "c:\python27\lib\site-packages\_pytest\runner.py", line 91, in pytest_runtest_call
item.runtest()
File "c:\python27\lib\site-packages\_pytest\unittest.py", line 151, in runtest
self._testcase(result=self)
File "c:\python27\lib\unittest\case.py", line 393, in __call__
return self.run(*args, **kwds)
File "c:\python27\lib\unittest\case.py", line 320, in run
self.setUp()
File "C:\Users\rhoward\Documents\GitHub\ui-selenium-tests\ui_selenium_tests\test010_provider_application_accordia
n.py", line 94, in setUp
self.used_browser, self.browser_config)
File "C:\Users\rhoward\Documents\GitHub\ui-selenium-tests\ui_selenium_tests\general_functions.py", line 198, in o
pen_browser
executable_path=configuration, chrome_options=chrome_options)
File "c:\python27\lib\site-packages\selenium\webdriver\chrome\webdriver.py", line 67, in __init__
desired_capabilities=desired_capabilities)
File "c:\python27\lib\site-packages\selenium\webdriver\remote\webdriver.py", line 91, in __init__
self.start_session(desired_capabilities, browser_profile)
File "c:\python27\lib\site-packages\selenium\webdriver\remote\webdriver.py", line 173, in start_session
'desiredCapabilities': desired_capabilities,
File "c:\python27\lib\site-packages\selenium\webdriver\remote\webdriver.py", line 231, in execute
response = self.command_executor.execute(driver_command, params)
File "c:\python27\lib\site-packages\selenium\webdriver\remote\remote_connection.py", line 395, in execute
return self._request(command_info[0], url, body=data)
File "c:\python27\lib\site-packages\selenium\webdriver\remote\remote_connection.py", line 426, in _request
resp = self._conn.getresponse()
File "c:\python27\lib\httplib.py", line 1136, in getresponse
response.begin()
File "c:\python27\lib\httplib.py", line 453, in begin
version, status, reason = self._read_status()
File "c:\python27\lib\httplib.py", line 409, in _read_status
line = self.fp.readline(_MAXLINE + 1)
File "c:\python27\lib\socket.py", line 480, in readline
data = self._sock.recv(self._rbufsize)
+++++++++++++++++++++++++++++++++++ Timeout ++++++++++++++++++++++++++++++++++++
Ideally I want pytest to note the timeout, but just rerun the test again and finish the test run as normal.