Add a fake clipboard for tests
There are a lot of problems and flakiness with using a real clipboard. Instead we now have a :debug-set-fake-clipboard command to set a text, and use logging when getting the contents. Fixes #1285.
This commit is contained in:
parent
7fe818f9c8
commit
79f83a033d
@ -1236,6 +1236,7 @@ These commands are mainly intended for debugging. They are hidden if qutebrowser
|
||||
|<<debug-crash,debug-crash>>|Crash for debugging purposes.
|
||||
|<<debug-dump-page,debug-dump-page>>|Dump the current page's content to a file.
|
||||
|<<debug-pyeval,debug-pyeval>>|Evaluate a python string and display the results as a web page.
|
||||
|<<debug-set-fake-clipboard,debug-set-fake-clipboard>>|Put data into the fake clipboard and enable logging, used for tests.
|
||||
|<<debug-trace,debug-trace>>|Trace executed code via hunter.
|
||||
|<<debug-webaction,debug-webaction>>|Execute a webaction.
|
||||
|==============
|
||||
@ -1292,6 +1293,15 @@ Evaluate a python string and display the results as a web page.
|
||||
* This command does not split arguments after the last argument and handles quotes literally.
|
||||
* With this command, +;;+ is interpreted literally instead of splitting off a second command.
|
||||
|
||||
[[debug-set-fake-clipboard]]
|
||||
=== debug-set-fake-clipboard
|
||||
Syntax: +:debug-set-fake-clipboard ['s']+
|
||||
|
||||
Put data into the fake clipboard and enable logging, used for tests.
|
||||
|
||||
==== positional arguments
|
||||
* +'s'+: The text to put into the fake clipboard, or unset to enable logging.
|
||||
|
||||
[[debug-trace]]
|
||||
=== debug-trace
|
||||
Syntax: +:debug-trace ['expr']+
|
||||
|
@ -260,7 +260,7 @@ def process_pos_args(args, via_ipc=False, cwd=None, target_arg=None):
|
||||
if cmd.startswith(':'):
|
||||
if win_id is None:
|
||||
win_id = mainwindow.get_window(via_ipc, force_tab=True)
|
||||
log.init.debug("Startup cmd {}".format(cmd))
|
||||
log.init.debug("Startup cmd {!r}".format(cmd))
|
||||
commandrunner = runners.CommandRunner(win_id)
|
||||
commandrunner.run_safely_init(cmd[1:])
|
||||
elif not cmd:
|
||||
|
@ -30,7 +30,7 @@ import xml.etree.ElementTree
|
||||
from PyQt5.QtWebKit import QWebSettings
|
||||
from PyQt5.QtWidgets import QApplication, QTabBar
|
||||
from PyQt5.QtCore import Qt, QUrl, QEvent
|
||||
from PyQt5.QtGui import QClipboard, QKeyEvent
|
||||
from PyQt5.QtGui import QKeyEvent
|
||||
from PyQt5.QtPrintSupport import QPrintDialog, QPrintPreviewDialog
|
||||
from PyQt5.QtWebKitWidgets import QWebPage
|
||||
import pygments
|
||||
@ -659,7 +659,6 @@ class CommandDispatcher:
|
||||
title: Yank the title instead of the URL.
|
||||
domain: Yank only the scheme, domain, and port number.
|
||||
"""
|
||||
clipboard = QApplication.clipboard()
|
||||
if title:
|
||||
s = self._tabbed_browser.page_title(self._current_index())
|
||||
what = 'title'
|
||||
@ -673,14 +672,14 @@ class CommandDispatcher:
|
||||
s = self._current_url().toString(
|
||||
QUrl.FullyEncoded | QUrl.RemovePassword)
|
||||
what = 'URL'
|
||||
if sel and clipboard.supportsSelection():
|
||||
mode = QClipboard.Selection
|
||||
|
||||
if sel and QApplication.clipboard().supportsSelection():
|
||||
target = "primary selection"
|
||||
else:
|
||||
mode = QClipboard.Clipboard
|
||||
sel = False
|
||||
target = "clipboard"
|
||||
log.misc.debug("Yanking to {}: '{}'".format(target, s))
|
||||
clipboard.setText(s, mode)
|
||||
|
||||
utils.set_clipboard(s, selection=sel)
|
||||
message.info(self._win_id, "Yanked {} to {}: {}".format(
|
||||
what, target, s))
|
||||
|
||||
@ -811,14 +810,12 @@ class CommandDispatcher:
|
||||
bg: Open in a background tab.
|
||||
window: Open in new window.
|
||||
"""
|
||||
clipboard = QApplication.clipboard()
|
||||
if sel and clipboard.supportsSelection():
|
||||
mode = QClipboard.Selection
|
||||
if sel and QApplication.clipboard().supportsSelection():
|
||||
target = "Primary selection"
|
||||
else:
|
||||
mode = QClipboard.Clipboard
|
||||
sel = False
|
||||
target = "Clipboard"
|
||||
text = clipboard.text(mode)
|
||||
text = utils.get_clipboard(selection=sel)
|
||||
if not text.strip():
|
||||
raise cmdexc.CommandError("{} is empty.".format(target))
|
||||
log.misc.debug("{} contained: '{}'".format(target,
|
||||
@ -1313,17 +1310,19 @@ class CommandDispatcher:
|
||||
if not elem.is_editable(strict=True):
|
||||
raise cmdexc.CommandError("Focused element is not editable!")
|
||||
|
||||
clipboard = QApplication.clipboard()
|
||||
if clipboard.supportsSelection():
|
||||
sel = clipboard.text(QClipboard.Selection)
|
||||
log.misc.debug("Pasting primary selection into element {}".format(
|
||||
elem.debug_text()))
|
||||
elem.evaluateJavaScript("""
|
||||
var sel = '{}';
|
||||
var event = document.createEvent('TextEvent');
|
||||
event.initTextEvent('textInput', true, true, null, sel);
|
||||
this.dispatchEvent(event);
|
||||
""".format(webelem.javascript_escape(sel)))
|
||||
try:
|
||||
sel = utils.get_clipboard(selection=True)
|
||||
except utils.SelectionUnsupportedError:
|
||||
return
|
||||
|
||||
log.misc.debug("Pasting primary selection into element {}".format(
|
||||
elem.debug_text()))
|
||||
elem.evaluateJavaScript("""
|
||||
var sel = '{}';
|
||||
var event = document.createEvent('TextEvent');
|
||||
event.initTextEvent('textInput', true, true, null, sel);
|
||||
this.dispatchEvent(event);
|
||||
""".format(webelem.javascript_escape(sel)))
|
||||
|
||||
def _clear_search(self, view, text):
|
||||
"""Clear search string/highlights for the given view.
|
||||
@ -1667,14 +1666,12 @@ class CommandDispatcher:
|
||||
message.info(self._win_id, "Nothing to yank")
|
||||
return
|
||||
|
||||
clipboard = QApplication.clipboard()
|
||||
if sel and clipboard.supportsSelection():
|
||||
mode = QClipboard.Selection
|
||||
if sel and QApplication.clipboard().supportsSelection():
|
||||
target = "primary selection"
|
||||
else:
|
||||
mode = QClipboard.Clipboard
|
||||
sel = False
|
||||
target = "clipboard"
|
||||
clipboard.setText(s, mode)
|
||||
utils.set_clipboard(s, sel)
|
||||
message.info(self._win_id, "{} {} yanked to {}".format(
|
||||
len(s), "char" if len(s) == 1 else "chars", target))
|
||||
if not keep:
|
||||
|
@ -27,8 +27,7 @@ import string
|
||||
|
||||
from PyQt5.QtCore import (pyqtSignal, pyqtSlot, QObject, QEvent, Qt, QUrl,
|
||||
QTimer)
|
||||
from PyQt5.QtGui import QMouseEvent, QClipboard
|
||||
from PyQt5.QtWidgets import QApplication
|
||||
from PyQt5.QtGui import QMouseEvent
|
||||
from PyQt5.QtWebKit import QWebElement
|
||||
from PyQt5.QtWebKitWidgets import QWebPage
|
||||
|
||||
@ -36,8 +35,7 @@ from qutebrowser.config import config
|
||||
from qutebrowser.keyinput import modeman, modeparsers
|
||||
from qutebrowser.browser import webelem
|
||||
from qutebrowser.commands import userscripts, cmdexc, cmdutils, runners
|
||||
from qutebrowser.utils import (usertypes, log, qtutils, message,
|
||||
objreg)
|
||||
from qutebrowser.utils import usertypes, log, qtutils, message, objreg, utils
|
||||
from qutebrowser.misc import guiprocess
|
||||
|
||||
|
||||
@ -481,9 +479,9 @@ class HintManager(QObject):
|
||||
context: The HintContext to use.
|
||||
"""
|
||||
sel = context.target == Target.yank_primary
|
||||
mode = QClipboard.Selection if sel else QClipboard.Clipboard
|
||||
urlstr = url.toString(QUrl.FullyEncoded | QUrl.RemovePassword)
|
||||
QApplication.clipboard().setText(urlstr, mode)
|
||||
utils.set_clipboard(urlstr, selection=sel)
|
||||
|
||||
msg = "Yanked URL to {}: {}".format(
|
||||
"primary selection" if sel else "clipboard",
|
||||
urlstr)
|
||||
|
@ -20,9 +20,9 @@
|
||||
"""Misc. widgets used at different places."""
|
||||
|
||||
from PyQt5.QtCore import pyqtSlot, pyqtSignal, Qt, QSize
|
||||
from PyQt5.QtWidgets import (QLineEdit, QApplication, QWidget, QHBoxLayout,
|
||||
QLabel, QStyleOption, QStyle)
|
||||
from PyQt5.QtGui import QValidator, QClipboard, QPainter
|
||||
from PyQt5.QtWidgets import (QLineEdit, QWidget, QHBoxLayout, QLabel,
|
||||
QStyleOption, QStyle)
|
||||
from PyQt5.QtGui import QValidator, QPainter
|
||||
|
||||
from qutebrowser.utils import utils
|
||||
from qutebrowser.misc import cmdhistory
|
||||
@ -101,10 +101,12 @@ class CommandLineEdit(QLineEdit):
|
||||
def keyPressEvent(self, e):
|
||||
"""Override keyPressEvent to paste primary selection on Shift + Ins."""
|
||||
if e.key() == Qt.Key_Insert and e.modifiers() == Qt.ShiftModifier:
|
||||
clipboard = QApplication.clipboard()
|
||||
if clipboard.supportsSelection():
|
||||
try:
|
||||
text = utils.get_clipboard(selection=True)
|
||||
except utils.SelectionUnsupportedError:
|
||||
pass
|
||||
else:
|
||||
e.accept()
|
||||
text = clipboard.text(QClipboard.Selection)
|
||||
self.insert(text)
|
||||
return
|
||||
super().keyPressEvent(e)
|
||||
|
@ -29,7 +29,7 @@ except ImportError:
|
||||
hunter = None
|
||||
|
||||
from qutebrowser.browser.network import qutescheme
|
||||
from qutebrowser.utils import log, objreg, usertypes, message, debug
|
||||
from qutebrowser.utils import log, objreg, usertypes, message, debug, utils
|
||||
from qutebrowser.commands import cmdutils, runners, cmdexc
|
||||
from qutebrowser.config import style
|
||||
from qutebrowser.misc import consolewidget
|
||||
@ -198,3 +198,16 @@ def debug_pyeval(s, quiet=False):
|
||||
tabbed_browser = objreg.get('tabbed-browser', scope='window',
|
||||
window='last-focused')
|
||||
tabbed_browser.openurl(QUrl('qute:pyeval'), newtab=True)
|
||||
|
||||
|
||||
@cmdutils.register(debug=True)
|
||||
def debug_set_fake_clipboard(s=None):
|
||||
"""Put data into the fake clipboard and enable logging, used for tests.
|
||||
|
||||
Args:
|
||||
s: The text to put into the fake clipboard, or unset to enable logging.
|
||||
"""
|
||||
if s is None:
|
||||
utils.log_clipboard = True
|
||||
else:
|
||||
utils.fake_clipboard = s
|
||||
|
@ -29,13 +29,23 @@ import contextlib
|
||||
import itertools
|
||||
|
||||
from PyQt5.QtCore import Qt
|
||||
from PyQt5.QtGui import QKeySequence, QColor
|
||||
from PyQt5.QtGui import QKeySequence, QColor, QClipboard
|
||||
from PyQt5.QtWidgets import QApplication
|
||||
import pkg_resources
|
||||
|
||||
import qutebrowser
|
||||
from qutebrowser.utils import qtutils, log
|
||||
|
||||
|
||||
fake_clipboard = None
|
||||
log_clipboard = False
|
||||
|
||||
|
||||
class SelectionUnsupportedError(Exception):
|
||||
|
||||
"""Raised if [gs]et_clipboard is used and selection=True is unsupported."""
|
||||
|
||||
|
||||
def elide(text, length):
|
||||
"""Elide text so it uses a maximum of length chars."""
|
||||
if length < 1:
|
||||
@ -743,3 +753,33 @@ def newest_slice(iterable, count):
|
||||
return iterable
|
||||
else:
|
||||
return itertools.islice(iterable, len(iterable) - count, len(iterable))
|
||||
|
||||
|
||||
def set_clipboard(data, selection=False):
|
||||
"""Set the clipboard to some given data."""
|
||||
clipboard = QApplication.clipboard()
|
||||
if selection and not clipboard.supportsSelection():
|
||||
raise SelectionUnsupportedError
|
||||
if log_clipboard:
|
||||
what = 'primary selection' if selection else 'clipboard'
|
||||
log.misc.debug("Setting fake {}: {!r}".format(what, data))
|
||||
else:
|
||||
mode = QClipboard.Selection if selection else QClipboard.Clipboard
|
||||
clipboard.setText(data, mode=mode)
|
||||
|
||||
|
||||
def get_clipboard(selection=False):
|
||||
"""Get data from the clipboard."""
|
||||
global fake_clipboard
|
||||
clipboard = QApplication.clipboard()
|
||||
if selection and not clipboard.supportsSelection():
|
||||
raise SelectionUnsupportedError
|
||||
|
||||
if fake_clipboard is not None:
|
||||
data = fake_clipboard
|
||||
fake_clipboard = None
|
||||
else:
|
||||
mode = QClipboard.Selection if selection else QClipboard.Clipboard
|
||||
data = clipboard.text(mode=mode)
|
||||
|
||||
return data
|
||||
|
@ -81,6 +81,8 @@ def whitelist_generator():
|
||||
yield 'qutebrowser.misc.utilcmds.pyeval_output'
|
||||
yield 'utils.use_color'
|
||||
yield 'qutebrowser.browser.mhtml.last_used_directory'
|
||||
yield 'qutebrowser.utils.utils.fake_clipboard'
|
||||
yield 'qutebrowser.utils.utils.log_clipboard'
|
||||
|
||||
# Other false-positives
|
||||
yield ('qutebrowser.completion.models.sortfilter.CompletionFilterModel().'
|
||||
|
@ -30,28 +30,10 @@ import textwrap
|
||||
import pytest
|
||||
import yaml
|
||||
import pytest_bdd as bdd
|
||||
from PyQt5.QtCore import QElapsedTimer
|
||||
from PyQt5.QtGui import QClipboard
|
||||
|
||||
from helpers import utils
|
||||
|
||||
|
||||
class WaitForClipboardTimeout(Exception):
|
||||
|
||||
"""Raised when _wait_for_clipboard didn't get the expected message."""
|
||||
|
||||
|
||||
def _clipboard_mode(qapp, what):
|
||||
"""Get the QClipboard::Mode to use based on a string."""
|
||||
if what == 'clipboard':
|
||||
return QClipboard.Clipboard
|
||||
elif what == 'primary selection':
|
||||
assert qapp.clipboard().supportsSelection()
|
||||
return QClipboard.Selection
|
||||
else:
|
||||
raise AssertionError
|
||||
|
||||
|
||||
## Given
|
||||
|
||||
|
||||
@ -207,21 +189,17 @@ def selection_supported(qapp):
|
||||
|
||||
@bdd.when(bdd.parsers.re(r'I put "(?P<content>.*)" into the '
|
||||
r'(?P<what>primary selection|clipboard)'))
|
||||
def fill_clipboard(qtbot, qapp, httpbin, what, content):
|
||||
mode = _clipboard_mode(qapp, what)
|
||||
def fill_clipboard(quteproc, httpbin, what, content):
|
||||
content = content.replace('(port)', str(httpbin.port))
|
||||
content = content.replace(r'\n', '\n')
|
||||
|
||||
clipboard = qapp.clipboard()
|
||||
clipboard.setText(content, mode)
|
||||
_wait_for_clipboard(qtbot, qapp.clipboard(), mode, content)
|
||||
quteproc.send_cmd(':debug-set-fake-clipboard "{}"'.format(content))
|
||||
|
||||
|
||||
@bdd.when(bdd.parsers.re(r'I put the following lines into the '
|
||||
r'(?P<what>primary selection|clipboard):\n'
|
||||
r'(?P<content>.+)$', flags=re.DOTALL))
|
||||
def fill_clipboard_multiline(qtbot, qapp, httpbin, what, content):
|
||||
fill_clipboard(qtbot, qapp, httpbin, what, textwrap.dedent(content))
|
||||
def fill_clipboard_multiline(quteproc, httpbin, what, content):
|
||||
fill_clipboard(quteproc, httpbin, what, textwrap.dedent(content))
|
||||
|
||||
|
||||
## Then
|
||||
@ -417,51 +395,18 @@ def check_open_tabs(quteproc, tabs):
|
||||
assert 'active' not in session_tab
|
||||
|
||||
|
||||
def _wait_for_clipboard(qtbot, clipboard, mode, expected):
|
||||
timeout = 1000
|
||||
timer = QElapsedTimer()
|
||||
timer.start()
|
||||
|
||||
while True:
|
||||
if clipboard.text(mode=mode) == expected:
|
||||
return
|
||||
|
||||
# We need to poll the clipboard, as for some reason it can change with
|
||||
# emitting changed (?).
|
||||
with qtbot.waitSignal(clipboard.changed, timeout=100, raising=False):
|
||||
pass
|
||||
|
||||
if timer.hasExpired(timeout):
|
||||
mode_names = {
|
||||
QClipboard.Clipboard: 'clipboard',
|
||||
QClipboard.Selection: 'primary selection',
|
||||
}
|
||||
raise WaitForClipboardTimeout(
|
||||
"Timed out after {timeout}ms waiting for {what}:\n"
|
||||
" expected: {expected!r}\n"
|
||||
" clipboard: {clipboard!r}\n"
|
||||
" primary: {primary!r}.".format(
|
||||
timeout=timeout, what=mode_names[mode],
|
||||
expected=expected,
|
||||
clipboard=clipboard.text(mode=QClipboard.Clipboard),
|
||||
primary=clipboard.text(mode=QClipboard.Selection))
|
||||
)
|
||||
|
||||
|
||||
@bdd.then(bdd.parsers.re(r'the (?P<what>primary selection|clipboard) should '
|
||||
r'contain "(?P<content>.*)"'))
|
||||
def clipboard_contains(qtbot, qapp, httpbin, what, content):
|
||||
mode = _clipboard_mode(qapp, what)
|
||||
def clipboard_contains(quteproc, httpbin, what, content):
|
||||
expected = content.replace('(port)', str(httpbin.port))
|
||||
expected = expected.replace('\\n', '\n')
|
||||
_wait_for_clipboard(qtbot, qapp.clipboard(), mode, expected)
|
||||
quteproc.wait_for(message='Setting fake {}: {!r}'.format(what, expected))
|
||||
|
||||
|
||||
@bdd.then(bdd.parsers.parse('the clipboard should contain:\n{content}'))
|
||||
def clipboard_contains_multiline(qtbot, qapp, content):
|
||||
def clipboard_contains_multiline(quteproc, content):
|
||||
expected = textwrap.dedent(content)
|
||||
_wait_for_clipboard(qtbot, qapp.clipboard(), QClipboard.Clipboard,
|
||||
expected)
|
||||
quteproc.wait_for(message='Setting fake clipboard: {!r}'.format(expected))
|
||||
|
||||
|
||||
@bdd.then("qutebrowser should quit")
|
||||
|
@ -20,7 +20,7 @@
|
||||
import pytest_bdd as bdd
|
||||
|
||||
# pylint: disable=unused-import
|
||||
from test_yankpaste import skip_with_broken_clipboard
|
||||
from test_yankpaste import init_fake_clipboard
|
||||
|
||||
|
||||
bdd.scenarios('caret.feature')
|
||||
|
@ -20,7 +20,7 @@
|
||||
import pytest_bdd as bdd
|
||||
|
||||
# pylint: disable=unused-import
|
||||
from test_yankpaste import skip_with_broken_clipboard
|
||||
from test_yankpaste import init_fake_clipboard
|
||||
|
||||
|
||||
bdd.scenarios('search.feature')
|
||||
|
@ -26,21 +26,9 @@ bdd.scenarios('yankpaste.feature')
|
||||
|
||||
|
||||
@pytest.fixture(autouse=True)
|
||||
def skip_with_broken_clipboard(qtbot, qapp):
|
||||
"""The clipboard seems to be broken on some platforms (OS X Yosemite?).
|
||||
|
||||
This skips the tests if this is the case.
|
||||
"""
|
||||
clipboard = qapp.clipboard()
|
||||
|
||||
with qtbot.waitSignal(clipboard.changed, raising=False):
|
||||
clipboard.setText("Does this work?")
|
||||
|
||||
if clipboard.text() != "Does this work?":
|
||||
pytest.skip("Clipboard seems to be broken on this platform.")
|
||||
|
||||
with qtbot.waitSignal(clipboard.changed):
|
||||
clipboard.clear()
|
||||
def init_fake_clipboard(quteproc):
|
||||
"""Make sure the fake clipboard will be used."""
|
||||
quteproc.send_cmd(':debug-set-fake-clipboard')
|
||||
|
||||
|
||||
@bdd.when(bdd.parsers.parse('I set the text field to "{value}"'))
|
||||
|
@ -182,8 +182,6 @@ Feature: Yanking and pasting.
|
||||
And I run :paste -t
|
||||
Then no crash should happen
|
||||
|
||||
# https://github.com/The-Compiler/qutebrowser/issues/1285
|
||||
@xfail
|
||||
Scenario: Pasting multiple urls with an almost empty one
|
||||
When I open about:blank
|
||||
And I put "http://localhost:(port)/data/hello.txt\n \nhttp://localhost:(port)/data/hello2.txt" into the clipboard
|
||||
@ -192,8 +190,6 @@ Feature: Yanking and pasting.
|
||||
|
||||
#### :paste-primary
|
||||
|
||||
# https://github.com/The-Compiler/qutebrowser/issues/1285
|
||||
@xfail
|
||||
Scenario: Pasting the primary selection into an empty text field
|
||||
When selection is supported
|
||||
And I open data/paste_primary.html
|
||||
|
@ -29,7 +29,7 @@ import functools
|
||||
import collections
|
||||
|
||||
from PyQt5.QtCore import Qt
|
||||
from PyQt5.QtGui import QColor
|
||||
from PyQt5.QtGui import QColor, QClipboard
|
||||
import pytest
|
||||
|
||||
import qutebrowser
|
||||
@ -930,3 +930,50 @@ class TestNewestSlice:
|
||||
"""Test slices which shouldn't raise an exception."""
|
||||
sliced = utils.newest_slice(items, count)
|
||||
assert list(sliced) == list(expected)
|
||||
|
||||
|
||||
class TestGetSetClipboard:
|
||||
|
||||
@pytest.fixture(autouse=True)
|
||||
def clipboard_mock(self, mocker):
|
||||
m = mocker.patch('qutebrowser.utils.utils.QApplication.clipboard',
|
||||
autospec=True)
|
||||
clipboard = m()
|
||||
clipboard.text.return_value = 'mocked clipboard text'
|
||||
return clipboard
|
||||
|
||||
def test_set(self, clipboard_mock, caplog):
|
||||
utils.set_clipboard('Hello World')
|
||||
clipboard_mock.setText.assert_called_with('Hello World',
|
||||
mode=QClipboard.Clipboard)
|
||||
assert not caplog.records
|
||||
|
||||
def test_set_unsupported_selection(self, clipboard_mock):
|
||||
clipboard_mock.supportsSelection.return_value = False
|
||||
with pytest.raises(utils.SelectionUnsupportedError):
|
||||
utils.set_clipboard('foo', selection=True)
|
||||
|
||||
@pytest.mark.parametrize('selection, what', [
|
||||
(True, 'primary selection'),
|
||||
(False, 'clipboard'),
|
||||
])
|
||||
def test_set_logging(self, clipboard_mock, caplog, selection, what):
|
||||
utils.log_clipboard = True
|
||||
utils.set_clipboard('fake clipboard text', selection=selection)
|
||||
assert not clipboard_mock.setText.called
|
||||
expected = "Setting fake {}: 'fake clipboard text'".format(what)
|
||||
assert caplog.records[0].message == expected
|
||||
|
||||
def test_get(self):
|
||||
assert utils.get_clipboard() == 'mocked clipboard text'
|
||||
|
||||
def test_get_unsupported_selection(self, clipboard_mock):
|
||||
clipboard_mock.supportsSelection.return_value = False
|
||||
with pytest.raises(utils.SelectionUnsupportedError):
|
||||
utils.get_clipboard(selection=True)
|
||||
|
||||
@pytest.mark.parametrize('selection', [True, False])
|
||||
def test_get_fake_clipboard(self, selection):
|
||||
utils.fake_clipboard = 'fake clipboard text'
|
||||
utils.get_clipboard(selection=selection)
|
||||
assert utils.fake_clipboard is None
|
||||
|
Loading…
Reference in New Issue
Block a user