summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--.bumpversion.cfg2
-rw-r--r--doc/changelog.asciidoc65
-rw-r--r--misc/org.qutebrowser.qutebrowser.appdata.xml1
-rw-r--r--misc/requirements/requirements-pyqt-pyinstaller.txt7
-rw-r--r--misc/requirements/requirements-pyqt-pyinstaller.txt-raw2
-rw-r--r--qutebrowser/__init__.py2
-rw-r--r--qutebrowser/browser/commands.py5
-rw-r--r--qutebrowser/browser/hints.py4
-rw-r--r--qutebrowser/browser/shared.py13
-rw-r--r--qutebrowser/browser/webengine/darkmode.py3
-rw-r--r--qutebrowser/browser/webengine/webengineinspector.py17
-rw-r--r--qutebrowser/browser/webengine/webenginesettings.py3
-rw-r--r--qutebrowser/components/caretcommands.py8
-rw-r--r--qutebrowser/config/configdata.yml12
-rw-r--r--qutebrowser/html/warning-sessions.html2
-rw-r--r--qutebrowser/keyinput/macros.py4
-rw-r--r--qutebrowser/keyinput/modeman.py14
-rw-r--r--qutebrowser/utils/version.py10
-rw-r--r--scripts/dev/recompile_requirements.py20
-rw-r--r--scripts/dev/ua_fetch.py3
-rw-r--r--scripts/dev/update_version.py2
-rwxr-xr-xscripts/hist_importer.py3
-rwxr-xr-xscripts/mkvenv.py15
-rw-r--r--tests/end2end/data/darkmode/mathml.html23
-rw-r--r--tests/end2end/data/darkmode/mathml.svg159
-rw-r--r--tests/end2end/fixtures/quteprocess.py18
-rw-r--r--tests/end2end/test_invocations.py47
-rw-r--r--tests/unit/commands/test_userscripts.py22
-rw-r--r--tests/unit/completion/test_models.py7
-rw-r--r--tests/unit/mainwindow/test_prompt.py14
-rw-r--r--tests/unit/utils/test_version.py21
-rw-r--r--tox.ini2
32 files changed, 441 insertions, 89 deletions
diff --git a/.bumpversion.cfg b/.bumpversion.cfg
index 098658797..0b507dc65 100644
--- a/.bumpversion.cfg
+++ b/.bumpversion.cfg
@@ -1,5 +1,5 @@
[bumpversion]
-current_version = 2.0.2
+current_version = 2.1.0
commit = True
message = Release v{new_version}
tag = True
diff --git a/doc/changelog.asciidoc b/doc/changelog.asciidoc
index 8bbaef0b1..2d399ad6d 100644
--- a/doc/changelog.asciidoc
+++ b/doc/changelog.asciidoc
@@ -15,10 +15,42 @@ breaking changes (such as renamed commands) can happen in minor releases.
// `Fixed` for any bug fixes.
// `Security` to invite users to upgrade in case of vulnerabilities.
+[[v2.1.1]]
+v2.1.1 (unreleased)
+-------------------
+
+Changed
+~~~~~~~
+
+- Clicking the 'x' in the devtools window to hide it now also leaves insert
+ mode.
+
+Fixed
+~~~~~
+
+- The workaround for black on (almost) black formula images in dark mode now
+ also works with Qt 5.12 and 5.13.
+
[[v2.1.0]]
-v2.1.0 (unreleased)
+v2.1.0 (2021-03-12)
-------------------
+Removed
+~~~~~~~
+
+- The following command aliases were deprecated in v2.0.0 and are now removed:
+ * `run-macro` -> `macro-run`
+ * `record-macro` -> `macro-record`
+ * `buffer` -> `tab-select`
+ * `open-editor` -> `edit-text`
+ * `toggle-selection` -> `selection-toggle`
+ * `drop-selection` -> `selection-drop`
+ * `reverse-selection` -> `selection-reverse`
+ * `follow-selected` -> `selection-follow`
+ * `follow-hint` -> `hint-follow`
+ * `enter-mode` -> `mode-enter`
+ * `leave-mode` -> `mode-leave`
+
Added
~~~~~
@@ -32,7 +64,7 @@ Added
Changed
~~~~~~~
-- Initial support for Qt 5.15.3 and PyQt 5.15.3
+- Initial support for QtWebEngine 5.15.3 and PyQt 5.15.3/.4
- The `colors.webpage.prefers_color_scheme_dark` setting got renamed to
`colors.webpage.preferred_color_scheme` and now takes the values `auto`, `light`
and `dark` (instead of being `True` for dark and `False` for auto).
@@ -70,9 +102,15 @@ Changed
Fixed
~~~~~
+- With QtWebEngine 5.15.3 and some locales, Chromium can't start its
+ subprocesses. As a result, qutebrowser only shows a blank page and logs
+ "Network service crashed, restarting service.". This release adds a
+ `qt.workarounds.locale` setting working around the issue. It is disabled by
+ default since distributions shipping 5.15.3 will probably have a proper patch
+ for it backported very soon.
- The `colors.webpage.preferred_color_scheme` and `colors.webpage.darkmode.*`
- settings now work correctly with the upcoming QtWebEngine 5.15.3 (and Gentoo,
- which at the time of writing packages 5.15.3 disguised as 5.15.2).
+ settings now work correctly with QtWebEngine 5.15.3 (and Gentoo, which at the
+ time of writing packages 5.15.3 disguised as 5.15.2).
- When dark mode settings were set, existing `blink-features` arguments in
`qt.args` (or `--qt-flag`) were overridden. They are now combined properly.
- On QtWebEngine 5.15.2, auto detection for the `prefers-color-scheme` media
@@ -97,12 +135,19 @@ Fixed
accidentally treated that as "@run-at document-idle". However, other
GreaseMonkey implementations default to "@run-at document-end" instead, which
is what qutebrowser now does, too.
-- With QtWebEngine 5.15.3 and some locales, Chromium can't start its
- subprocesses. As a result, qutebrowser only shows a blank page and logs
- "Network service crashed, restarting service.". This release adds a
- `qt.workarounds.locale` setting working around the issue. It is disabled by
- default since distributions shipping 5.15.3 will probably have a proper patch
- for it backported very soon.
+- The `hist_importer.py` script didn't work correctly after qutebrowser v2.0.0
+ and resulted in a history database qutebrowser couldn't read properly. It now
+ works properly again.
+- With certain QtWebEngine versions (5.15.0 based on Chromium 80 and 5.15.3
+ based on Chromium 87), Chromium's dark mode doesn't invert certain SVG images,
+ even with `colors.wegpage.darkmode.policy.images` set to `smart`.
+ Most notably, this causes formulae on Wikipedia to display black on (almost)
+ black. If `content.site_specific_quirks` is enabled, qutebrowser now injects
+ some CSS as a workaround, which inverts all math formula images on Wikipedia
+ (and potentially other sites, if they use the same CSS class).
+- When a hint label text started with an apostrophe, it would show an escaped
+ text until the hints first character has been pressed. It now shows up
+ correctly.
[[v2.0.2]]
v2.0.2 (2021-02-04)
diff --git a/misc/org.qutebrowser.qutebrowser.appdata.xml b/misc/org.qutebrowser.qutebrowser.appdata.xml
index 343633cf6..a449e1ea8 100644
--- a/misc/org.qutebrowser.qutebrowser.appdata.xml
+++ b/misc/org.qutebrowser.qutebrowser.appdata.xml
@@ -44,6 +44,7 @@
</content_rating>
<releases>
<!-- Add new releases here -->
+<release version="2.1.0" date="2021-03-12"/>
<release version="2.0.2" date="2021-02-04"/>
<release version="2.0.1" date="2021-01-28"/>
<release version="2.0.0" date="2021-01-28"/>
diff --git a/misc/requirements/requirements-pyqt-pyinstaller.txt b/misc/requirements/requirements-pyqt-pyinstaller.txt
new file mode 100644
index 000000000..31ecefad5
--- /dev/null
+++ b/misc/requirements/requirements-pyqt-pyinstaller.txt
@@ -0,0 +1,7 @@
+# This file is automatically generated by scripts/dev/recompile_requirements.py
+
+PyQt5==5.15.3
+PyQt5-Qt==5.15.2
+PyQt5-sip==12.8.1
+PyQtWebEngine==5.15.3
+PyQtWebEngine-Qt==5.15.2
diff --git a/misc/requirements/requirements-pyqt-pyinstaller.txt-raw b/misc/requirements/requirements-pyqt-pyinstaller.txt-raw
new file mode 100644
index 000000000..89b5644da
--- /dev/null
+++ b/misc/requirements/requirements-pyqt-pyinstaller.txt-raw
@@ -0,0 +1,2 @@
+PyQt5==5.15.3
+PyQtWebEngine==5.15.3
diff --git a/qutebrowser/__init__.py b/qutebrowser/__init__.py
index 9abb8a30e..b2542cacc 100644
--- a/qutebrowser/__init__.py
+++ b/qutebrowser/__init__.py
@@ -26,7 +26,7 @@ __copyright__ = "Copyright 2014-2021 Florian Bruhin (The Compiler)"
__license__ = "GPL"
__maintainer__ = __author__
__email__ = "mail@qutebrowser.org"
-__version__ = "2.0.2"
+__version__ = "2.1.0"
__version_info__ = tuple(int(part) for part in __version__.split('.'))
__description__ = "A keyboard-driven, vim-like browser based on PyQt5."
diff --git a/qutebrowser/browser/commands.py b/qutebrowser/browser/commands.py
index f2dd282df..f1710adb9 100644
--- a/qutebrowser/browser/commands.py
+++ b/qutebrowser/browser/commands.py
@@ -917,7 +917,7 @@ class CommandDispatcher:
return (tabbed_browser, tabbed_browser.widget.widget(idx-1))
@cmdutils.register(instance='command-dispatcher', scope='window',
- maxsplit=0, deprecated_name='buffer')
+ maxsplit=0)
@cmdutils.argument('index', completion=miscmodels.tabs)
@cmdutils.argument('count', value=cmdutils.Value.count)
def tab_select(self, index=None, count=None):
@@ -1488,8 +1488,7 @@ class CommandDispatcher:
objreg.last_focused_window(), alert=False))
ed.edit(text, caret_position)
- @cmdutils.register(instance='command-dispatcher', scope='window',
- deprecated_name='open-editor')
+ @cmdutils.register(instance='command-dispatcher', scope='window')
def edit_text(self):
"""Open an external editor with the currently selected form field.
diff --git a/qutebrowser/browser/hints.py b/qutebrowser/browser/hints.py
index 0e71f2373..333c532d3 100644
--- a/qutebrowser/browser/hints.py
+++ b/qutebrowser/browser/hints.py
@@ -92,6 +92,8 @@ class HintLabel(QLabel):
self._context = context
self.elem = elem
+ self.setTextFormat(Qt.RichText)
+
# Make sure we can style the background via a style sheet, and we don't
# get any extra text indent from Qt.
# The real stylesheet lives in mainwindow.py for performance reasons..
@@ -1000,7 +1002,7 @@ class HintManager(QObject):
self._context.first_run = False
@cmdutils.register(instance='hintmanager', scope='window',
- modes=[usertypes.KeyMode.hint], deprecated_name='follow-hint')
+ modes=[usertypes.KeyMode.hint])
def hint_follow(self, select: bool = False, keystring: str = None) -> None:
"""Follow a hint.
diff --git a/qutebrowser/browser/shared.py b/qutebrowser/browser/shared.py
index 94332ffcb..b3a0da51d 100644
--- a/qutebrowser/browser/shared.py
+++ b/qutebrowser/browser/shared.py
@@ -30,9 +30,9 @@ from PyQt5.QtCore import QUrl
from qutebrowser.config import config
from qutebrowser.utils import (usertypes, message, log, objreg, jinja, utils,
- qtutils)
+ qtutils, version)
from qutebrowser.mainwindow import mainwindow
-from qutebrowser.misc import guiprocess
+from qutebrowser.misc import guiprocess, objects
class CallSuper(Exception):
@@ -298,6 +298,15 @@ def get_user_stylesheet(searching=False):
if setting == 'never' or setting == 'when-searching' and not searching:
css += '\nhtml > ::-webkit-scrollbar { width: 0px; height: 0px; }'
+ if (objects.backend == usertypes.Backend.QtWebEngine and
+ version.qtwebengine_versions().chromium_major in [69, 73, 80, 87] and
+ config.val.colors.webpage.darkmode.enabled and
+ config.val.colors.webpage.darkmode.policy.images == 'smart' and
+ config.val.content.site_specific_quirks):
+ # WORKAROUND for MathML-output on Wikipedia being black on black.
+ # See https://bugs.chromium.org/p/chromium/issues/detail?id=1126606
+ css += '\nimg.mwe-math-fallback-image-inline { filter: invert(100%); }'
+
return css
diff --git a/qutebrowser/browser/webengine/darkmode.py b/qutebrowser/browser/webengine/darkmode.py
index 30a9ac6eb..1c6530b49 100644
--- a/qutebrowser/browser/webengine/darkmode.py
+++ b/qutebrowser/browser/webengine/darkmode.py
@@ -342,8 +342,7 @@ def _variant(versions: version.WebEngineVersions) -> Variant:
log.init.warning(f"Ignoring invalid QUTE_DARKMODE_VARIANT={env_var}")
if (versions.webengine == utils.VersionNumber(5, 15, 2) and
- versions.chromium is not None and
- versions.chromium.startswith('87.')):
+ versions.chromium_major == 87):
# WORKAROUND for Gentoo packaging something newer as 5.15.2...
return Variant.qt_515_3
elif versions.webengine >= utils.VersionNumber(5, 15, 3):
diff --git a/qutebrowser/browser/webengine/webengineinspector.py b/qutebrowser/browser/webengine/webengineinspector.py
index ee7782e10..ae31c0bee 100644
--- a/qutebrowser/browser/webengine/webengineinspector.py
+++ b/qutebrowser/browser/webengine/webengineinspector.py
@@ -28,7 +28,8 @@ from PyQt5.QtWidgets import QWidget
from qutebrowser.browser import inspector
from qutebrowser.browser.webengine import webenginesettings
from qutebrowser.misc import miscwidgets
-from qutebrowser.utils import version
+from qutebrowser.utils import version, usertypes
+from qutebrowser.keyinput import modeman
class WebEngineInspectorView(QWebEngineView):
@@ -60,9 +61,23 @@ class WebEngineInspector(inspector.AbstractWebInspector):
parent: QWidget = None) -> None:
super().__init__(splitter, win_id, parent)
self._check_devtools_resources()
+
view = WebEngineInspectorView()
self._settings = webenginesettings.WebEngineSettings(view.settings())
self._set_widget(view)
+ page = view.page()
+ page.windowCloseRequested.connect( # type: ignore[attr-defined]
+ self._on_window_close_requested)
+
+ def _on_window_close_requested(self) -> None:
+ """Called when the 'x' was clicked in the devtools."""
+ modeman.leave(
+ self._win_id,
+ usertypes.KeyMode.insert,
+ 'devtools close requested',
+ maybe=True,
+ )
+ self.hide()
def _check_devtools_resources(self) -> None:
"""Make sure that the devtools resources are available on Fedora.
diff --git a/qutebrowser/browser/webengine/webenginesettings.py b/qutebrowser/browser/webengine/webenginesettings.py
index a2e81da5f..830c818fc 100644
--- a/qutebrowser/browser/webengine/webenginesettings.py
+++ b/qutebrowser/browser/webengine/webenginesettings.py
@@ -489,13 +489,16 @@ def init():
from qutebrowser.misc import quitter
quitter.instance.shutting_down.connect(_download_manager.shutdown)
+ log.init.debug("Initializing global settings...")
global _global_settings
_global_settings = WebEngineSettings(_SettingsWrapper())
+ log.init.debug("Initializing profiles...")
_init_default_profile()
init_private_profile()
config.instance.changed.connect(_update_settings)
+ log.init.debug("Initializing site specific quirks...")
_init_site_specific_quirks()
_init_devtools_settings()
diff --git a/qutebrowser/components/caretcommands.py b/qutebrowser/components/caretcommands.py
index 7b1eb47ea..8ab175012 100644
--- a/qutebrowser/components/caretcommands.py
+++ b/qutebrowser/components/caretcommands.py
@@ -183,7 +183,7 @@ def move_to_end_of_document(tab: apitypes.Tab) -> None:
tab.caret.move_to_end_of_document()
-@cmdutils.register(modes=[cmdutils.KeyMode.caret], deprecated_name='toggle-selection')
+@cmdutils.register(modes=[cmdutils.KeyMode.caret])
@cmdutils.argument('tab', value=cmdutils.Value.cur_tab)
def selection_toggle(tab: apitypes.Tab, line: bool = False) -> None:
"""Toggle caret selection mode.
@@ -194,14 +194,14 @@ def selection_toggle(tab: apitypes.Tab, line: bool = False) -> None:
tab.caret.toggle_selection(line)
-@cmdutils.register(modes=[cmdutils.KeyMode.caret], deprecated_name='drop-selection')
+@cmdutils.register(modes=[cmdutils.KeyMode.caret])
@cmdutils.argument('tab', value=cmdutils.Value.cur_tab)
def selection_drop(tab: apitypes.Tab) -> None:
"""Drop selection and keep selection mode enabled."""
tab.caret.drop_selection()
-@cmdutils.register(deprecated_name='follow-selected')
+@cmdutils.register()
@cmdutils.argument('tab_obj', value=cmdutils.Value.cur_tab)
def selection_follow(tab_obj: apitypes.Tab, *, tab: bool = False) -> None:
"""Follow the selected text.
@@ -215,7 +215,7 @@ def selection_follow(tab_obj: apitypes.Tab, *, tab: bool = False) -> None:
raise cmdutils.CommandError(str(e))
-@cmdutils.register(modes=[cmdutils.KeyMode.caret], deprecated_name='reverse-selection')
+@cmdutils.register(modes=[cmdutils.KeyMode.caret])
@cmdutils.argument('tab', value=cmdutils.Value.cur_tab)
def selection_reverse(tab: apitypes.Tab) -> None:
"""Swap the stationary and moving end of the current selection."""
diff --git a/qutebrowser/config/configdata.yml b/qutebrowser/config/configdata.yml
index 6b5687fc2..22a4b2151 100644
--- a/qutebrowser/config/configdata.yml
+++ b/qutebrowser/config/configdata.yml
@@ -621,14 +621,14 @@ content.headers.user_agent:
# Vim-protip: Place your cursor below this comment and run
# :r!python scripts/dev/ua_fetch.py
- - "Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like
- Gecko) Chrome/87.0.4280.66 Safari/537.36"
- - Chrome 87 Linux
+ Gecko) Chrome/88.0.4324.96 Safari/537.36"
+ - Chrome 88 Linux
- - "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML,
- like Gecko) Chrome/87.0.4280.66 Safari/537.36"
- - Chrome 87 Win10
+ like Gecko) Chrome/88.0.4324.104 Safari/537.36"
+ - Chrome 88 Win10
- - "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36
- (KHTML, like Gecko) Chrome/87.0.4280.67 Safari/537.36"
- - Chrome 87 macOS
+ (KHTML, like Gecko) Chrome/88.0.4324.96 Safari/537.36"
+ - Chrome 88 macOS
supports_pattern: true
desc: |
User agent to send.
diff --git a/qutebrowser/html/warning-sessions.html b/qutebrowser/html/warning-sessions.html
index d297a2656..422b409a9 100644
--- a/qutebrowser/html/warning-sessions.html
+++ b/qutebrowser/html/warning-sessions.html
@@ -9,7 +9,7 @@ qute://warning/sessions</span> to show it again at a later time.</span>
<p>Since Qt doesn't provide an API to load the history of a tab, qutebrowser relies on a reverse-engineered binary serialization format to load tab history from session files. With Qt 5.15, unfortunately that format changed (due to the underlying Chromium upgrade), in a way which makes it impossible for qutebrowser to load tab history from existing session data.</p>
-<p>At the time of writing (January 2021), a new session format which stores part of the needed binary data in saved sessions is <a href="https://github.com/qutebrowser/qutebrowser/issues/5359">in development</a>. However, it unfortunately wasn't ready in time for qutebrowser v2.0.0, as it's a rather big refactoring. It's currently expected to be released as part of qutebrowser v2.1.0.</p>
+<p>At the time of writing (January 2021), a new session format which stores part of the needed binary data in saved sessions is <a href="https://github.com/qutebrowser/qutebrowser/issues/5359">in development</a>. However, it unfortunately wasn't ready in time for qutebrowser v2.0.0, as it's a rather big refactoring. It's currently expected to be released in a future v2.x.0 release.</p>
<p>As a stop-gap measure:</p>
diff --git a/qutebrowser/keyinput/macros.py b/qutebrowser/keyinput/macros.py
index fc67a7387..fdef7c669 100644
--- a/qutebrowser/keyinput/macros.py
+++ b/qutebrowser/keyinput/macros.py
@@ -52,7 +52,7 @@ class MacroRecorder:
self._macro_count: Dict[int, int] = {}
self._last_register: Optional[str] = None
- @cmdutils.register(instance='macro-recorder', deprecated_name='record-macro')
+ @cmdutils.register(instance='macro-recorder')
@cmdutils.argument('win_id', value=cmdutils.Value.win_id)
def macro_record(self, win_id: int, register: str = None) -> None:
"""Start or stop recording a macro.
@@ -77,7 +77,7 @@ class MacroRecorder:
self._macros[register] = []
self._recording_macro = register
- @cmdutils.register(instance='macro-recorder', deprecated_name='run-macro')
+ @cmdutils.register(instance='macro-recorder')
@cmdutils.argument('win_id', value=cmdutils.Value.win_id)
@cmdutils.argument('count', value=cmdutils.Value.count)
def macro_run(self, win_id: int, count: int = 1, register: str = None) -> None:
diff --git a/qutebrowser/keyinput/modeman.py b/qutebrowser/keyinput/modeman.py
index c00120596..3c47fafe3 100644
--- a/qutebrowser/keyinput/modeman.py
+++ b/qutebrowser/keyinput/modeman.py
@@ -386,11 +386,7 @@ class ModeManager(QObject):
self.mode = mode
self.entered.emit(mode, self._win_id)
- @cmdutils.register(
- instance='mode-manager',
- scope='window',
- deprecated_name='enter-mode',
- )
+ @cmdutils.register(instance='mode-manager', scope='window')
def mode_enter(self, mode: str) -> None:
"""Enter a key mode.
@@ -443,12 +439,8 @@ class ModeManager(QObject):
self.enter(self._prev_mode,
reason='restore mode before {}'.format(mode.name))
- @cmdutils.register(
- instance='mode-manager',
- not_modes=[usertypes.KeyMode.normal],
- scope='window',
- deprecated_name='leave-mode',
- )
+ @cmdutils.register(instance='mode-manager',
+ not_modes=[usertypes.KeyMode.normal], scope='window')
def mode_leave(self) -> None:
"""Leave the mode we're currently in."""
if self.mode == usertypes.KeyMode.normal:
diff --git a/qutebrowser/utils/version.py b/qutebrowser/utils/version.py
index 46916c516..a1b8e6c72 100644
--- a/qutebrowser/utils/version.py
+++ b/qutebrowser/utils/version.py
@@ -525,6 +525,7 @@ class WebEngineVersions:
webengine: utils.VersionNumber
chromium: Optional[str]
source: str
+ chromium_major: Optional[int] = dataclasses.field(init=False)
_CHROMIUM_VERSIONS: ClassVar[Dict[utils.VersionNumber, str]] = {
# Qt 5.12: Chromium 69
@@ -562,11 +563,20 @@ class WebEngineVersions:
# 5.15.1: Security fixes up to 85.0.4183.83 (2020-08-25)
# 5.15.2: Updated to 83.0.4103.122 (~2020-06-24)
# Security fixes up to 86.0.4240.183 (2020-11-02)
+ # 5.15.3: Updated to 87.0.4280.144 (~2020-12-02)
+ # Security fixes up to 88.0.4324.150 (2021-02-04)
utils.VersionNumber(5, 15): '80.0.3987.163',
utils.VersionNumber(5, 15, 2): '83.0.4103.122',
utils.VersionNumber(5, 15, 3): '87.0.4280.144',
}
+ def __post_init__(self) -> None:
+ """Set the major Chromium version."""
+ if self.chromium is None:
+ self.chromium_major = None
+ else:
+ self.chromium_major = int(self.chromium.split('.')[0])
+
def __str__(self) -> str:
s = f'QtWebEngine {self.webengine}'
if self.chromium is not None:
diff --git a/scripts/dev/recompile_requirements.py b/scripts/dev/recompile_requirements.py
index 1849a5218..ce50cd504 100644
--- a/scripts/dev/recompile_requirements.py
+++ b/scripts/dev/recompile_requirements.py
@@ -137,8 +137,10 @@ CHANGELOG_URLS = {
'cryptography': 'https://cryptography.io/en/latest/changelog.html',
'toml': 'https://github.com/uiri/toml/releases',
'PyQt5': 'https://www.riverbankcomputing.com/news',
+ 'PyQt5-Qt': 'https://www.riverbankcomputing.com/news',
'PyQt5-Qt5': 'https://www.riverbankcomputing.com/news',
'PyQtWebEngine': 'https://www.riverbankcomputing.com/news',
+ 'PyQtWebEngine-Qt': 'https://www.riverbankcomputing.com/news',
'PyQtWebEngine-Qt5': 'https://www.riverbankcomputing.com/news',
'PyQt-builder': 'https://www.riverbankcomputing.com/news',
'PyQt5-sip': 'https://www.riverbankcomputing.com/news',
@@ -279,7 +281,7 @@ def run_pip(venv_dir, *args, quiet=False, **kwargs):
arg_str = ' '.join(str(arg) for arg in args)
utils.print_col('venv$ pip {}'.format(arg_str), 'blue')
- venv_python = os.path.join(venv_dir, 'bin', 'python')
+ venv_python = get_venv_python(venv_dir)
return subprocess.run([venv_python, '-m', 'pip'] + args, check=True, **kwargs)
@@ -399,7 +401,13 @@ def _get_changes(diff):
for line in diff:
if not line.startswith('-') and not line.startswith('+'):
continue
- if line.startswith('+++ ') or line.startswith('--- '):
+ elif line.startswith('+++ ') or line.startswith('--- '):
+ continue
+ elif not line.strip():
+ # Could be newline changes on Windows
+ continue
+ elif line[1:].startswith('# This file is automatically'):
+ # Could be newline changes on Windows
continue
name, version = parse_versioned_line(line[1:])
@@ -458,6 +466,12 @@ def get_host_python(name):
return sys.executable
+def get_venv_python(venv_dir):
+ """Get the path to Python inside a virtualenv."""
+ subdir = 'Scripts' if os.name == 'nt' else 'bin'
+ return os.path.join(venv_dir, subdir, 'python')
+
+
def get_outfile(name):
"""Get the path to the output requirements.txt file."""
if name == 'qutebrowser':
@@ -510,7 +524,7 @@ def test_tox():
with tempfile.TemporaryDirectory() as tmpdir:
venv_dir = os.path.join(tmpdir, 'venv')
tox_workdir = os.path.join(tmpdir, 'tox-workdir')
- venv_python = os.path.join(venv_dir, 'bin', 'python')
+ venv_python = get_venv_python(venv_dir)
init_venv(host_python, venv_dir, req_path)
list_proc = subprocess.run([venv_python, '-m', 'tox', '--listenvs'],
check=True,
diff --git a/scripts/dev/ua_fetch.py b/scripts/dev/ua_fetch.py
index a4ef889a0..7c0692cb4 100644
--- a/scripts/dev/ua_fetch.py
+++ b/scripts/dev/ua_fetch.py
@@ -50,6 +50,9 @@ for ua_string in reversed(response.json()):
continue
if any(part.startswith("OPR/") or part.startswith("Edg/") for part in parts):
continue
+ if 'Chrome/99.0.7113.93' in parts:
+ # Fake or false-positive entry
+ continue
user_agent = qutebrowser.config.websettings.UserAgent.parse(ua_string)
diff --git a/scripts/dev/update_version.py b/scripts/dev/update_version.py
index 1f476113c..975787415 100644
--- a/scripts/dev/update_version.py
+++ b/scripts/dev/update_version.py
@@ -82,7 +82,7 @@ if __name__ == "__main__":
.format(v=version))
print("* Windows: git fetch; git checkout v{v}; "
"py -3.9 -m tox -e build-release -- --asciidoc "
- "$env:userprofile\\bin\\asciidoc-9.0.5\\asciidoc.py --upload"
+ "$env:userprofile\\bin\\asciidoc-9.1.0\\asciidoc.py --upload"
.format(v=version))
print("* macOS: git fetch && git checkout v{v} && "
"tox -e build-release -- --upload"
diff --git a/scripts/hist_importer.py b/scripts/hist_importer.py
index 6f2b9fa87..df12bcf2e 100755
--- a/scripts/hist_importer.py
+++ b/scripts/hist_importer.py
@@ -135,7 +135,8 @@ def insert_qb(history, dest):
'INSERT INTO History (url,title,atime,redirect) VALUES (?,?,?,?)',
history
)
- cursor.execute('DROP TABLE CompletionHistory')
+ cursor.execute('UPDATE CompletionMetaInfo SET value = 1 '
+ 'WHERE key = "force_rebuild"')
conn.commit()
conn.close()
diff --git a/scripts/mkvenv.py b/scripts/mkvenv.py
index d510ba75b..a3b3bf32d 100755
--- a/scripts/mkvenv.py
+++ b/scripts/mkvenv.py
@@ -99,6 +99,18 @@ def parse_args(argv: List[str] = None) -> argparse.Namespace:
return parser.parse_args(argv)
+def _version_key(v):
+ """Sort PyQt requirement file prefixes.
+
+ If we have a filename like requirements-pyqt-pyinstaller.txt, that should
+ always be sorted after all others (hence we return a "999" key).
+ """
+ try:
+ return tuple(int(v) for c in v.split('.'))
+ except ValueError:
+ return 999
+
+
def pyqt_versions() -> List[str]:
"""Get a list of all available PyQt versions.
@@ -110,8 +122,7 @@ def pyqt_versions() -> List[str]:
for req in requirements_dir.glob('requirements-pyqt-*.txt'):
version_set.add(req.stem.split('-')[-1])
- versions = sorted(version_set,
- key=lambda v: [int(c) for c in v.split('.')])
+ versions = sorted(version_set, key=_version_key)
return versions + ['auto']
diff --git a/tests/end2end/data/darkmode/mathml.html b/tests/end2end/data/darkmode/mathml.html
new file mode 100644
index 000000000..fa2371638
--- /dev/null
+++ b/tests/end2end/data/darkmode/mathml.html
@@ -0,0 +1,23 @@
+<!DOCTYPE html>
+<html>
+ <head>
+ <meta charset="utf-8">
+ <title>MathML-like SVG</title>
+ </head>
+ <body style="margin: 0; background-color: #ffff99">
+ <!--
+ Image based on: https://en.wikipedia.org/wiki/Pythagorean_theorem
+ with a black square added for testing.
+
+ onload based on:
+ https://stackoverflow.com/questions/53423742/waiting-for-an-image-to-finish-rendering
+ -->
+ <img
+ class="mwe-math-fallback-image-inline"
+ src="mathml.svg"
+ alt="Pythagorean theorem"
+ onload="requestAnimationFrame(() => requestAnimationFrame(() => console.log('Image loaded')));"
+ >
+ <!-- -->
+ </body>
+</html>
diff --git a/tests/end2end/data/darkmode/mathml.svg b/tests/end2end/data/darkmode/mathml.svg
new file mode 100644
index 000000000..30b03ffac
--- /dev/null
+++ b/tests/end2end/data/darkmode/mathml.svg
@@ -0,0 +1,159 @@
+<?xml version="1.0" encoding="UTF-8" standalone="no"?>
+<svg
+ xmlns:dc="http://purl.org/dc/elements/1.1/"
+ xmlns:cc="http://creativecommons.org/ns#"
+ xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
+ xmlns:svg="http://www.w3.org/2000/svg"
+ xmlns="http://www.w3.org/2000/svg"
+ xmlns:xlink="http://www.w3.org/1999/xlink"
+ xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
+ xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
+ width="12.983ex"
+ height="2.843ex"
+ style="vertical-align: -0.505ex;"
+ viewBox="0 -1006.6 5589.7 1223.9"
+ role="img"
+ focusable="false"
+ aria-labelledby="MathJax-SVG-1-Title"
+ version="1.1"
+ id="svg36"
+ sodipodi:docname="mathml.svg"
+ inkscape:version="1.0.2 (e86c870879, 2021-01-15)">
+ <metadata
+ id="metadata40">
+ <rdf:RDF>
+ <cc:Work
+ rdf:about="">
+ <dc:format>image/svg+xml</dc:format>
+ <dc:type
+ rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
+ <dc:title>{\displaystyle a^{2}+b^{2}=c^{2}.}</dc:title>
+ </cc:Work>
+ </rdf:RDF>
+ </metadata>
+ <sodipodi:namedview
+ pagecolor="#ffffff"
+ bordercolor="#666666"
+ borderopacity="1"
+ objecttolerance="10"
+ gridtolerance="10"
+ guidetolerance="10"
+ inkscape:pageopacity="0"
+ inkscape:pageshadow="2"
+ inkscape:window-width="944"
+ inkscape:window-height="1036"
+ id="namedview38"
+ showgrid="false"
+ inkscape:zoom="0.27282322"
+ inkscape:cx="1686.0735"
+ inkscape:cy="602.78657"
+ inkscape:window-x="964"
+ inkscape:window-y="22"
+ inkscape:window-maximized="0"
+ inkscape:current-layer="svg36" />
+ <title
+ id="MathJax-SVG-1-Title">{\displaystyle a^{2}+b^{2}=c^{2}.}</title>
+ <defs
+ aria-hidden="true"
+ id="defs10">
+ <path
+ stroke-width="1"
+ id="E1-MJMATHI-61"
+ d="M33 157Q33 258 109 349T280 441Q331 441 370 392Q386 422 416 422Q429 422 439 414T449 394Q449 381 412 234T374 68Q374 43 381 35T402 26Q411 27 422 35Q443 55 463 131Q469 151 473 152Q475 153 483 153H487Q506 153 506 144Q506 138 501 117T481 63T449 13Q436 0 417 -8Q409 -10 393 -10Q359 -10 336 5T306 36L300 51Q299 52 296 50Q294 48 292 46Q233 -10 172 -10Q117 -10 75 30T33 157ZM351 328Q351 334 346 350T323 385T277 405Q242 405 210 374T160 293Q131 214 119 129Q119 126 119 118T118 106Q118 61 136 44T179 26Q217 26 254 59T298 110Q300 114 325 217T351 328Z" />
+ <path
+ stroke-width="1"
+ id="E1-MJMAIN-32"
+ d="M109 429Q82 429 66 447T50 491Q50 562 103 614T235 666Q326 666 387 610T449 465Q449 422 429 383T381 315T301 241Q265 210 201 149L142 93L218 92Q375 92 385 97Q392 99 409 186V189H449V186Q448 183 436 95T421 3V0H50V19V31Q50 38 56 46T86 81Q115 113 136 137Q145 147 170 174T204 211T233 244T261 278T284 308T305 340T320 369T333 401T340 431T343 464Q343 527 309 573T212 619Q179 619 154 602T119 569T109 550Q109 549 114 549Q132 549 151 535T170 489Q170 464 154 447T109 429Z" />
+ <path
+ stroke-width="1"
+ id="E1-MJMAIN-2B"
+ d="M56 237T56 250T70 270H369V420L370 570Q380 583 389 583Q402 583 409 568V270H707Q722 262 722 250T707 230H409V-68Q401 -82 391 -82H389H387Q375 -82 369 -68V230H70Q56 237 56 250Z" />
+ <path
+ stroke-width="1"
+ id="E1-MJMATHI-62"
+ d="M73 647Q73 657 77 670T89 683Q90 683 161 688T234 694Q246 694 246 685T212 542Q204 508 195 472T180 418L176 399Q176 396 182 402Q231 442 283 442Q345 442 383 396T422 280Q422 169 343 79T173 -11Q123 -11 82 27T40 150V159Q40 180 48 217T97 414Q147 611 147 623T109 637Q104 637 101 637H96Q86 637 83 637T76 640T73 647ZM336 325V331Q336 405 275 405Q258 405 240 397T207 376T181 352T163 330L157 322L136 236Q114 150 114 114Q114 66 138 42Q154 26 178 26Q211 26 245 58Q270 81 285 114T318 219Q336 291 336 325Z" />
+ <path
+ stroke-width="1"
+ id="E1-MJMAIN-3D"
+ d="M56 347Q56 360 70 367H707Q722 359 722 347Q722 336 708 328L390 327H72Q56 332 56 347ZM56 153Q56 168 72 173H708Q722 163 722 153Q722 140 707 133H70Q56 140 56 153Z" />
+ <path
+ stroke-width="1"
+ id="E1-MJMATHI-63"
+ d="M34 159Q34 268 120 355T306 442Q362 442 394 418T427 355Q427 326 408 306T360 285Q341 285 330 295T319 325T330 359T352 380T366 386H367Q367 388 361 392T340 400T306 404Q276 404 249 390Q228 381 206 359Q162 315 142 235T121 119Q121 73 147 50Q169 26 205 26H209Q321 26 394 111Q403 121 406 121Q410 121 419 112T429 98T420 83T391 55T346 25T282 0T202 -11Q127 -11 81 37T34 159Z" />
+ <path
+ stroke-width="1"
+ id="E1-MJMAIN-2E"
+ d="M78 60Q78 84 95 102T138 120Q162 120 180 104T199 61Q199 36 182 18T139 0T96 17T78 60Z" />
+ </defs>
+ <g
+ stroke="currentColor"
+ fill="currentColor"
+ stroke-width="0"
+ transform="matrix(1 0 0 -1 0 0)"
+ aria-hidden="true"
+ id="g34">
+ <use
+ xlink:href="#E1-MJMATHI-61"
+ x="0"
+ y="0"
+ id="use12" />
+ <use
+ transform="scale(0.707)"
+ xlink:href="#E1-MJMAIN-32"
+ x="748"
+ y="583"
+ id="use14" />
+ <use
+ xlink:href="#E1-MJMAIN-2B"
+ x="1205"
+ y="0"
+ id="use16" />
+ <g
+ transform="translate(2206,0)"
+ id="g22">
+ <use
+ xlink:href="#E1-MJMATHI-62"
+ x="0"
+ y="0"
+ id="use18" />
+ <use
+ transform="scale(0.707)"
+ xlink:href="#E1-MJMAIN-32"
+ x="607"
+ y="583"
+ id="use20" />
+ </g>
+ <use
+ xlink:href="#E1-MJMAIN-3D"
+ x="3367"
+ y="0"
+ id="use24" />
+ <g
+ transform="translate(4423,0)"
+ id="g30">
+ <use
+ xlink:href="#E1-MJMATHI-63"
+ x="0"
+ y="0"
+ id="use26" />
+ <use
+ transform="scale(0.707)"
+ xlink:href="#E1-MJMAIN-32"
+ x="613"
+ y="583"
+ id="use28" />
+ </g>
+ <use
+ xlink:href="#E1-MJMAIN-2E"
+ x="5311"
+ y="0"
+ id="use32" />
+ </g>
+ <rect
+ style="fill:#000000"
+ id="rect865"
+ width="338.88928"
+ height="316.48901"
+ x="2.5373409"
+ y="-1004.8583" />
+</svg>
diff --git a/tests/end2end/fixtures/quteprocess.py b/tests/end2end/fixtures/quteprocess.py
index 9ef338768..90d7f9647 100644
--- a/tests/end2end/fixtures/quteprocess.py
+++ b/tests/end2end/fixtures/quteprocess.py
@@ -29,6 +29,7 @@ import logging
import tempfile
import contextlib
import itertools
+import collections
import json
import yaml
@@ -453,6 +454,7 @@ class QuteProc(testprocess.Process):
self.basedir = None
self._instance_id = next(instance_counter)
self._run_counter = itertools.count()
+ self._screenshot_counters = collections.defaultdict(itertools.count)
def _process_line(self, log_line):
"""Check if the line matches any initial lines we're interested in."""
@@ -902,9 +904,14 @@ class QuteProc(testprocess.Process):
"""
for _ in range(5):
tmp_path = self.request.getfixturevalue('tmp_path')
- path = tmp_path / 'screenshot.png'
- self.send_cmd(f':screenshot --force {path}')
- self.wait_for(message=f'Screenshot saved to {path}')
+ counter = self._screenshot_counters[self.request.node.nodeid]
+
+ path = tmp_path / f'screenshot-{next(counter)}.png'
+ self.send_cmd(f':screenshot {path}')
+
+ screenshot_msg = f'Screenshot saved to {path}'
+ self.wait_for(message=screenshot_msg)
+ print(screenshot_msg)
img = QImage(str(path))
assert not img.isNull()
@@ -919,8 +926,9 @@ class QuteProc(testprocess.Process):
# Rendering might not be completed yet...
time.sleep(0.5)
- raise ValueError(
- f"Pixel probing for {probe_color} failed (got {probed_color} on last try)")
+ # Using assert again for pytest introspection
+ assert probed_color == probe_color, "Color probing failed, values on last try:"
+ raise utils.Unreachable()
def press_keys(self, keys):
"""Press the given keys using :fake-key."""
diff --git a/tests/end2end/test_invocations.py b/tests/end2end/test_invocations.py
index 38e40f9b7..82473e50d 100644
--- a/tests/end2end/test_invocations.py
+++ b/tests/end2end/test_invocations.py
@@ -501,19 +501,21 @@ def test_preferred_colorscheme_with_dark_mode(
quteproc_new.open_path('data/darkmode/prefers-color-scheme.html')
content = quteproc_new.get_content()
- if webengine_versions.webengine == utils.VersionNumber(5, 15, 3):
+ qtwe_version = webengine_versions.webengine
+ xfail = None
+ if utils.VersionNumber(5, 15, 3) <= qtwe_version <= utils.VersionNumber(6):
# https://bugs.chromium.org/p/chromium/issues/detail?id=1177973
# No workaround known.
expected_text = 'Light preference detected.'
# light website color, inverted by darkmode
expected_color = testutils.Color(127, 127, 127)
- xfail = True
- elif webengine_versions.webengine == utils.VersionNumber(5, 15, 2):
+ xfail = "Chromium bug 1177973"
+ elif qtwe_version == utils.VersionNumber(5, 15, 2):
# Our workaround breaks when dark mode is enabled...
# Also, for some reason, dark mode doesn't work on that page either!
expected_text = 'No preference detected.'
expected_color = testutils.Color(0, 170, 0) # green
- xfail = True
+ xfail = "QTBUG-89753"
else:
# Qt 5.14 and 5.15.0/.1 work correctly.
# Hopefully, so does Qt 6.x in the future?
@@ -529,7 +531,7 @@ def test_preferred_colorscheme_with_dark_mode(
assert color == expected_color
if xfail:
# We still do some checks, but we want to mark the test outcome as xfail.
- pytest.xfail("QTBUG-89753")
+ pytest.xfail(xfail)
@pytest.mark.qtwebkit_skip
@@ -664,12 +666,37 @@ def test_dark_mode(webengine_versions, quteproc_new, request,
# Position chosen by fair dice roll.
# https://xkcd.com/221/
- pos = QPoint(4, 4)
- img = quteproc_new.get_screenshot(probe_pos=pos, probe_color=expected)
+ quteproc_new.get_screenshot(
+ probe_pos=QPoint(4, 4),
+ probe_color=expected,
+ )
- color = testutils.Color(img.pixelColor(pos))
- # For pytest debug output
- assert color == expected
+
+def test_dark_mode_mathml(quteproc_new, request, qtbot):
+ if not request.config.webengine:
+ pytest.skip("Skipped with QtWebKit")
+
+ args = _base_args(request.config) + [
+ '--temp-basedir',
+ '-s', 'colors.webpage.darkmode.enabled', 'true',
+ '-s', 'colors.webpage.darkmode.algorithm', 'brightness-rgb',
+ ]
+ quteproc_new.start(args)
+
+ quteproc_new.open_path('data/darkmode/mathml.html')
+ quteproc_new.wait_for_js('Image loaded')
+
+ # First make sure loading finished by looking outside of the image
+ quteproc_new.get_screenshot(
+ probe_pos=QPoint(105, 0),
+ probe_color=testutils.Color(0, 0, 204),
+ )
+
+ # Then get the actual formula color, probing again in case it's not displayed yet...
+ quteproc_new.get_screenshot(
+ probe_pos=QPoint(4, 4),
+ probe_color=testutils.Color(255, 255, 255),
+ )
def test_unavailable_backend(request, quteproc_new):
diff --git a/tests/unit/commands/test_userscripts.py b/tests/unit/commands/test_userscripts.py
index 48bc31c32..436e9e2a7 100644
--- a/tests/unit/commands/test_userscripts.py
+++ b/tests/unit/commands/test_userscripts.py
@@ -18,6 +18,7 @@
# along with qutebrowser. If not, see <https://www.gnu.org/licenses/>.
import os
+import pathlib
import json
import time
import logging
@@ -34,8 +35,8 @@ from qutebrowser.utils import utils
class TestQtFIFOReader:
@pytest.fixture
- def reader(self, tmpdir, qapp):
- fifo_path = str(tmpdir / 'fifo')
+ def reader(self, tmp_path, qapp):
+ fifo_path = str(tmp_path / 'fifo')
os.mkfifo(fifo_path) # pylint: disable=no-member,useless-suppression
reader = userscripts._QtFIFOReader(fifo_path)
yield reader
@@ -142,8 +143,8 @@ def test_source(qtbot, py_proc, runner):
assert parsed['text'] == 'This is text'
assert parsed['html'] == 'This is HTML'
- assert not os.path.exists(parsed['text_file'])
- assert not os.path.exists(parsed['html_file'])
+ assert not pathlib.Path(parsed['text_file']).exists()
+ assert not pathlib.Path(parsed['html_file']).exists()
def test_command_with_error(qtbot, py_proc, runner, caplog):
@@ -165,13 +166,13 @@ def test_command_with_error(qtbot, py_proc, runner, caplog):
runner.store_html('')
data = json.loads(blocker.args[0])
- assert not os.path.exists(data)
+ assert not pathlib.Path(data).exists()
-def test_killed_command(qtbot, tmpdir, py_proc, runner, caplog):
- data_file = tmpdir / 'data'
+def test_killed_command(qtbot, tmp_path, py_proc, runner, caplog):
+ data_file = tmp_path / 'data'
watcher = QFileSystemWatcher()
- watcher.addPath(str(tmpdir))
+ watcher.addPath(str(tmp_path))
cmd, args = py_proc(r"""
import os
@@ -203,13 +204,14 @@ def test_killed_command(qtbot, tmpdir, py_proc, runner, caplog):
# Make sure the PID was written to the file, not just the file created
time.sleep(0.5)
- data = json.load(data_file)
+ with data_file.open() as f:
+ data = json.load(f)
with caplog.at_level(logging.ERROR):
with qtbot.wait_signal(runner.finished):
os.kill(int(data['pid']), signal.SIGTERM)
- assert not os.path.exists(data['text_file'])
+ assert not pathlib.Path(data['text_file']).exists()
def test_temporary_files_failed_cleanup(caplog, qtbot, py_proc, runner):
diff --git a/tests/unit/completion/test_models.py b/tests/unit/completion/test_models.py
index 22e9c6490..12e623517 100644
--- a/tests/unit/completion/test_models.py
+++ b/tests/unit/completion/test_models.py
@@ -21,6 +21,7 @@
import collections
import os
+import pathlib
import random
import string
import time
@@ -426,11 +427,11 @@ def test_filesystem_completion(qtmodeltester, config_stub, info,
homedir = str(local_files_path)
monkeypatch.setenv('HOME', homedir) # POSIX
monkeypatch.setenv('USERPROFILE', homedir) # Windows
- assert os.path.expanduser('~') == homedir
+ assert str(pathlib.Path.home()) == homedir
base = '~'
- expected_1 = os.path.join('~', 'file1.txt')
- expected_2 = os.path.join('~', 'file2.txt')
+ expected_1 = str(pathlib.Path('~') / 'file1.txt')
+ expected_2 = str(pathlib.Path('~') / 'file2.txt')
config_stub.val.completion.open_categories = ['filesystem']
model = urlmodel.url(info=info)
diff --git a/tests/unit/mainwindow/test_prompt.py b/tests/unit/mainwindow/test_prompt.py
index f8d4cdee6..668cd0710 100644
--- a/tests/unit/mainwindow/test_prompt.py
+++ b/tests/unit/mainwindow/test_prompt.py
@@ -53,26 +53,26 @@ class TestFileCompletion:
(2, 'next', 'a'),
(2, 'prev', 'b'),
])
- def test_simple_completion(self, tmpdir, get_prompt, steps, where,
+ def test_simple_completion(self, tmp_path, get_prompt, steps, where,
subfolder):
"""Simply trying to tab through items."""
- testdir = tmpdir / 'test'
+ testdir = tmp_path / 'test'
for directory in 'abc':
- (testdir / directory).ensure(dir=True)
+ (testdir / directory).mkdir(parents=True)
prompt = get_prompt(str(testdir) + os.sep)
for _ in range(steps):
prompt.item_focus(where)
- assert prompt._lineedit.text() == str(testdir / subfolder)
+ assert prompt._lineedit.text() == str((testdir / subfolder).resolve())
- def test_backspacing_path(self, qtbot, tmpdir, get_prompt):
+ def test_backspacing_path(self, qtbot, tmp_path, get_prompt):
"""When we start deleting a path we want to see the subdir."""
- testdir = tmpdir / 'test'
+ testdir = tmp_path / 'test'
for directory in ['bar', 'foo']:
- (testdir / directory).ensure(dir=True)
+ (testdir / directory).mkdir(parents=True)
prompt = get_prompt(str(testdir / 'foo') + os.sep)
diff --git a/tests/unit/utils/test_version.py b/tests/unit/utils/test_version.py
index 879f84a1f..c91017e84 100644
--- a/tests/unit/utils/test_version.py
+++ b/tests/unit/utils/test_version.py
@@ -926,6 +926,25 @@ class TestWebEngineVersions:
def test_str(self, version, expected):
assert str(version) == expected
+ @pytest.mark.parametrize('version, expected', [
+ (
+ version.WebEngineVersions(
+ webengine=utils.VersionNumber(5, 15, 2),
+ chromium=None,
+ source='test'),
+ None,
+ ),
+ (
+ version.WebEngineVersions(
+ webengine=utils.VersionNumber(5, 15, 2),
+ chromium='87.0.4280.144',
+ source='test'),
+ 87,
+ ),
+ ])
+ def test_chromium_major(self, version, expected):
+ assert version.chromium_major == expected
+
def test_from_ua(self):
ua = websettings.UserAgent(
os_info='X11; Linux x86_64',
@@ -1038,7 +1057,7 @@ class TestChromiumVersion:
assert version.qtwebengine_versions().chromium == ver
def test_prefers_saved_user_agent(self, monkeypatch):
- version.webenginesettings._init_user_agent_str(_QTWE_USER_AGENT)
+ version.webenginesettings._init_user_agent_str(_QTWE_USER_AGENT.format('87'))
class FakeProfile:
def defaultProfile(self):
diff --git a/tox.ini b/tox.ini
index 5ccf486a7..70329f9e6 100644
--- a/tox.ini
+++ b/tox.ini
@@ -150,7 +150,7 @@ passenv = APPDATA HOME PYINSTALLER_DEBUG
deps =
-r{toxinidir}/requirements.txt
-r{toxinidir}/misc/requirements/requirements-pyinstaller.txt
- -r{toxinidir}/misc/requirements/requirements-pyqt.txt
+ -r{toxinidir}/misc/requirements/requirements-pyqt-pyinstaller.txt
commands =
{envbindir}/pyinstaller --noconfirm misc/qutebrowser.spec