100% test coverage for misc.guiprocess.
This commit is contained in:
parent
8fe3a1e9ce
commit
aca082ce83
@ -49,6 +49,7 @@ PERFECT_FILES = [
|
|||||||
'qutebrowser/misc/split.py',
|
'qutebrowser/misc/split.py',
|
||||||
'qutebrowser/misc/msgbox.py',
|
'qutebrowser/misc/msgbox.py',
|
||||||
'qutebrowser/misc/checkpyver.py',
|
'qutebrowser/misc/checkpyver.py',
|
||||||
|
'qutebrowser/misc/guiprocess.py',
|
||||||
|
|
||||||
'qutebrowser/mainwindow/statusbar/keystring.py',
|
'qutebrowser/mainwindow/statusbar/keystring.py',
|
||||||
'qutebrowser/mainwindow/statusbar/percentage.py',
|
'qutebrowser/mainwindow/statusbar/percentage.py',
|
||||||
|
@ -21,11 +21,12 @@
|
|||||||
|
|
||||||
import os
|
import os
|
||||||
import sys
|
import sys
|
||||||
|
import json
|
||||||
import textwrap
|
import textwrap
|
||||||
import logging
|
import logging
|
||||||
|
|
||||||
import pytest
|
import pytest
|
||||||
from PyQt5.QtCore import QProcess
|
from PyQt5.QtCore import QProcess, QIODevice
|
||||||
|
|
||||||
from helpers import messagemock # pylint: disable=import-error
|
from helpers import messagemock # pylint: disable=import-error
|
||||||
from qutebrowser.misc import guiprocess
|
from qutebrowser.misc import guiprocess
|
||||||
@ -51,7 +52,7 @@ def proc(qtbot):
|
|||||||
if os.name == 'nt':
|
if os.name == 'nt':
|
||||||
# WORKAROUND for https://github.com/pytest-dev/pytest-qt/issues/67
|
# WORKAROUND for https://github.com/pytest-dev/pytest-qt/issues/67
|
||||||
pytest.skip("Test is flaky on Windows...")
|
pytest.skip("Test is flaky on Windows...")
|
||||||
p = guiprocess.GUIProcess(0, 'test')
|
p = guiprocess.GUIProcess(0, 'testprocess')
|
||||||
yield p
|
yield p
|
||||||
if p._proc.state() == QProcess.Running:
|
if p._proc.state() == QProcess.Running:
|
||||||
with qtbot.waitSignal(p.finished, timeout=10000) as blocker:
|
with qtbot.waitSignal(p.finished, timeout=10000) as blocker:
|
||||||
@ -63,7 +64,7 @@ def proc(qtbot):
|
|||||||
@pytest.fixture()
|
@pytest.fixture()
|
||||||
def fake_proc(monkeypatch, stubs):
|
def fake_proc(monkeypatch, stubs):
|
||||||
"""A fixture providing a GUIProcess with a mocked QProcess."""
|
"""A fixture providing a GUIProcess with a mocked QProcess."""
|
||||||
p = guiprocess.GUIProcess(0, 'test')
|
p = guiprocess.GUIProcess(0, 'testprocess')
|
||||||
monkeypatch.setattr(p, '_proc', stubs.fake_qprocess())
|
monkeypatch.setattr(p, '_proc', stubs.fake_qprocess())
|
||||||
return p
|
return p
|
||||||
|
|
||||||
@ -94,21 +95,67 @@ def test_start_verbose(proc, qtbot, guiprocess_message_mock):
|
|||||||
assert msgs[0].level == messagemock.Level.info
|
assert msgs[0].level == messagemock.Level.info
|
||||||
assert msgs[1].level == messagemock.Level.info
|
assert msgs[1].level == messagemock.Level.info
|
||||||
assert msgs[0].text.startswith("Executing:")
|
assert msgs[0].text.startswith("Executing:")
|
||||||
assert msgs[1].text == "Test exited successfully."
|
assert msgs[1].text == "Testprocess exited successfully."
|
||||||
assert bytes(proc._proc.readAll()).rstrip() == b'test'
|
assert bytes(proc._proc.readAll()).rstrip() == b'test'
|
||||||
|
|
||||||
|
|
||||||
@pytest.mark.parametrize('argv', [
|
# WORKAROUND for https://github.com/pytest-dev/pytest-qt/issues/67
|
||||||
pytest.mark.not_frozen(_py_proc('import sys; sys.exit(0)')),
|
@pytest.mark.skipif(os.name == 'nt', reason="Test is flaky on Windows...")
|
||||||
('does_not', 'exist'),
|
@pytest.mark.not_frozen
|
||||||
])
|
def test_start_env(monkeypatch, qtbot):
|
||||||
def test_start_detached(fake_proc, argv):
|
monkeypatch.setenv('QUTEBROWSER_TEST_1', '1')
|
||||||
|
env = {'QUTEBROWSER_TEST_2': '2'}
|
||||||
|
proc = guiprocess.GUIProcess(0, 'testprocess', additional_env=env)
|
||||||
|
|
||||||
|
argv = _py_proc("""
|
||||||
|
import os
|
||||||
|
import json
|
||||||
|
env = dict(os.environ)
|
||||||
|
print(json.dumps(env))
|
||||||
|
sys.exit(0)
|
||||||
|
""")
|
||||||
|
|
||||||
|
with qtbot.waitSignals([proc.started, proc.finished], raising=True,
|
||||||
|
timeout=10000):
|
||||||
|
proc.start(*argv)
|
||||||
|
|
||||||
|
data = bytes(proc._proc.readAll()).decode('utf-8')
|
||||||
|
ret_env = json.loads(data)
|
||||||
|
assert 'QUTEBROWSER_TEST_1' in ret_env
|
||||||
|
assert 'QUTEBROWSER_TEST_2' in ret_env
|
||||||
|
|
||||||
|
|
||||||
|
@pytest.mark.not_frozen
|
||||||
|
@pytest.mark.qt_log_ignore('QIODevice::read.*: WriteOnly device')
|
||||||
|
def test_start_mode(proc, qtbot):
|
||||||
|
"""Test simply starting a process with mode parameter."""
|
||||||
|
with qtbot.waitSignals([proc.started, proc.finished], raising=True,
|
||||||
|
timeout=10000):
|
||||||
|
argv = _py_proc("import sys; print('test'); sys.exit(0)")
|
||||||
|
proc.start(*argv, mode=QIODevice.NotOpen)
|
||||||
|
|
||||||
|
assert not proc._proc.readAll()
|
||||||
|
|
||||||
|
|
||||||
|
def test_start_detached(fake_proc):
|
||||||
"""Test starting a detached process."""
|
"""Test starting a detached process."""
|
||||||
|
argv = ['foo', 'bar']
|
||||||
fake_proc._proc.startDetached.return_value = (True, 0)
|
fake_proc._proc.startDetached.return_value = (True, 0)
|
||||||
fake_proc.start_detached(*argv)
|
fake_proc.start_detached(*argv)
|
||||||
fake_proc._proc.startDetached.assert_called_with(*list(argv) + [None])
|
fake_proc._proc.startDetached.assert_called_with(*list(argv) + [None])
|
||||||
|
|
||||||
|
|
||||||
|
def test_start_detached_error(fake_proc, guiprocess_message_mock):
|
||||||
|
"""Test starting a detached process with ok=False."""
|
||||||
|
argv = ['foo', 'bar']
|
||||||
|
fake_proc._proc.startDetached.return_value = (False, 0)
|
||||||
|
fake_proc._proc.error.return_value = "Error message"
|
||||||
|
fake_proc.start_detached(*argv)
|
||||||
|
msg = guiprocess_message_mock.getmsg()
|
||||||
|
assert msg.level == messagemock.Level.error
|
||||||
|
assert msg.text == "Error while spawning testprocess: Error message."
|
||||||
|
|
||||||
|
|
||||||
@pytest.mark.not_frozen
|
@pytest.mark.not_frozen
|
||||||
def test_double_start(qtbot, proc):
|
def test_double_start(qtbot, proc):
|
||||||
"""Test starting a GUIProcess twice."""
|
"""Test starting a GUIProcess twice."""
|
||||||
@ -148,7 +195,8 @@ def test_error(qtbot, proc, caplog, guiprocess_message_mock):
|
|||||||
|
|
||||||
msg = guiprocess_message_mock.getmsg()
|
msg = guiprocess_message_mock.getmsg()
|
||||||
assert msg.level == messagemock.Level.error
|
assert msg.level == messagemock.Level.error
|
||||||
expected_msg = "Error while spawning test: The process failed to start."
|
expected_msg = ("Error while spawning testprocess: The process failed to "
|
||||||
|
"start.")
|
||||||
assert msg.text == expected_msg
|
assert msg.text == expected_msg
|
||||||
|
|
||||||
|
|
||||||
@ -159,4 +207,4 @@ def test_exit_unsuccessful(qtbot, proc, guiprocess_message_mock):
|
|||||||
|
|
||||||
msg = guiprocess_message_mock.getmsg()
|
msg = guiprocess_message_mock.getmsg()
|
||||||
assert msg.level == messagemock.Level.error
|
assert msg.level == messagemock.Level.error
|
||||||
assert msg.text == "Test exited with status 1."
|
assert msg.text == "Testprocess exited with status 1."
|
||||||
|
Loading…
Reference in New Issue
Block a user