Xqt has submitted this change. ( https://gerrit.wikimedia.org/r/c/pywikibot/core/+/1318689?usp=email )
Change subject: tests: Show duration together with the test result
......................................................................
tests: Show duration together with the test result
Change-Id: I3cfbe85ad40bc0b54fad7e875c663c2b90db4d6d
---
M tests/aspects.py
1 file changed, 20 insertions(+), 16 deletions(-)
Approvals:
Xqt: Verified; Looks good to me, approved
diff --git a/tests/aspects.py b/tests/aspects.py
index e892af8..589bd97 100644
--- a/tests/aspects.py
+++ b/tests/aspects.py
@@ -212,25 +212,29 @@
class TestTimerMixin(unittest.TestCase):
- """Time each test and report excessive durations."""
+ """Time each test and report excessive durations.
- # Number of seconds each test may consume
- # before a note is added after the test.
- test_duration_warning_interval = 10
+ .. version-changed:: 11.7
+ Test durations are now measured in :meth:`run` using
+ :func:`time.perf_counter`.
+ """
- def setUp(self) -> None:
- """Set up test."""
- self.test_start = time.time()
- super().setUp()
+ #: Number of seconds each test may consume
+ #: before a note is added after the test.
+ test_duration_warning_interval = 10.0
- def tearDown(self) -> None:
- """Tear down test."""
- super().tearDown()
- self.test_completed = time.time()
- duration = self.test_completed - self.test_start
- if duration > self.test_duration_warning_interval:
- unittest_print(f' {duration:.3f}s', end=' ')
- sys.stdout.flush()
+ def run(
+ self,
+ result: unittest.TestResult | None = None
+ ) -> unittest.TestResult:
+ """Run the test and report its duration."""
+ start = time.perf_counter()
+ try:
+ return super().run(result)
+ finally:
+ duration = time.perf_counter() - start
+ if duration > self.test_duration_warning_interval:
+ unittest_print(f'{self._testMethodName}: {duration:.1f} s')
# Add Python314AssertionsMixin on Python < 3.14
--
To view, visit https://gerrit.wikimedia.org/r/c/pywikibot/core/+/1318689?usp=email
To unsubscribe, or for help writing mail filters, visit https://gerrit.wikimedia.org/r/settings?usp=email
Gerrit-MessageType: merged
Gerrit-Project: pywikibot/core
Gerrit-Branch: master
Gerrit-Change-Id: I3cfbe85ad40bc0b54fad7e875c663c2b90db4d6d
Gerrit-Change-Number: 1318689
Gerrit-PatchSet: 2
Gerrit-Owner: Xqt <info(a)gno.de>
Gerrit-Reviewer: Xqt <info(a)gno.de>
Gerrit-Reviewer: jenkins-bot
jenkins-bot has submitted this change. ( https://gerrit.wikimedia.org/r/c/pywikibot/core/+/1313084?usp=email )
Change subject: i18n.altlang: Improve fallback language lookup
......................................................................
i18n.altlang: Improve fallback language lookup
- use a dict for _LANG_TO_GROUP_NAME to avoid adding empty strings for
missing keys
- make the lang parameter positional-only
- do not include lang in the returned fallback list
- return fallback languages as tuple
- update documentation
- update tests
Change-Id: Ia8b219bc2a995738014152425ea4ffd29fb61348
---
M pywikibot/i18n.py
M tests/i18n_tests.py
2 files changed, 27 insertions(+), 16 deletions(-)
Approvals:
Xqt: Looks good to me, approved
jenkins-bot: Verified
diff --git a/pywikibot/i18n.py b/pywikibot/i18n.py
index 5e1eb1a..89a3c93 100644
--- a/pywikibot/i18n.py
+++ b/pywikibot/i18n.py
@@ -25,7 +25,7 @@
import os
import pkgutil
import re
-from collections import abc, defaultdict
+from collections import abc
from collections.abc import Generator, Iterable, Iterator, Mapping, Sequence
from contextlib import suppress
from functools import cache
@@ -48,7 +48,7 @@
# Flag to indicate whether translation messages are available
_messages_available = None
-_LANG_TO_GROUP_NAME = defaultdict(str, {
+_LANG_TO_GROUP_NAME: dict[str, str] = {
'aa': 'aa',
'ab': 'ab',
'ace': 'ace',
@@ -264,10 +264,11 @@
'zh-hans': 'zh-classical',
'zh-min-nan': 'zh-min-nan',
'zh-tw': 'zh-classical',
- 'zh-yue': 'cdo'})
+ 'zh-yue': 'cdo'
+}
_GROUP_NAME_TO_FALLBACKS: dict[str, list[str]] = {
- '': [],
+ '_default': [],
'aa': ['am'],
'ab': ['ru'],
'ace': ['id', 'ms', 'jv'],
@@ -392,25 +393,36 @@
return _messages_available
-def altlang(lang: str) -> list[str]:
+def altlang(lang: str, /) -> tuple[str, ...]:
"""Define fallback languages for particular languages.
- If no translation is available to a specified language, translate() will
- try each of the specified fallback languages, in order, until it finds
- one with a translation, with 'en' and '_default' as a last resort.
+ If no translation is available to a specified language,
+ :func:`translate` will try each of the specified fallback languages,
+ in order, until it finds one with a translation, with ``'_default'``
+ (for :func:`translate`) and finally ``'en'`` as a last resort.
- For example, if for language 'xx', you want the preference of languages
- to be: xx > fr > ru > en, you let this method return ['fr', 'ru'].
+ For example, if for language 'xx', you want the preference of
+ languages to be: ``xx > fr > ru > en``, you let this method return
+ ``('fr', 'ru')``.
- This code is used by other translating methods below.
+ This function is used by :func:`translate` and :func:`twtranslate`.
.. version-changed:: 11.6
- renamed from :func:`_altlang`.
+ Renamed from ``_altlang``.
+ .. version-changed:: 11.7
+ The *lang* parameter is now positional-only. The function now
+ returns a tuple of fallback anguages instead of a list and no
+ longer includes *lang* itself.
:param lang: The language code
- :return: Language codes
+ :return: Fallback language codes
"""
- return _GROUP_NAME_TO_FALLBACKS[_LANG_TO_GROUP_NAME[lang]]
+ return tuple(
+ code for code in _GROUP_NAME_TO_FALLBACKS[
+ _LANG_TO_GROUP_NAME.get(lang, '_default')
+ ]
+ if code != lang
+ )
@cache
diff --git a/tests/i18n_tests.py b/tests/i18n_tests.py
index cbb9a8e..9d9871f 100755
--- a/tests/i18n_tests.py
+++ b/tests/i18n_tests.py
@@ -40,10 +40,9 @@
def test_groupnames(self):
"""Test that groupnames are in groups."""
groupnames = set(i18n._LANG_TO_GROUP_NAME.values())
- groupnames.discard('') # might be created by defaultdict
self.assertLess(groupnames, i18n._LANG_TO_GROUP_NAME.keys())
groups = list(i18n._GROUP_NAME_TO_FALLBACKS)
- groups.remove('') # remove empty fallback
+ groups.remove('_default') # remove default fallback
self.assertEqual(sorted(groupnames), groups)
--
To view, visit https://gerrit.wikimedia.org/r/c/pywikibot/core/+/1313084?usp=email
To unsubscribe, or for help writing mail filters, visit https://gerrit.wikimedia.org/r/settings?usp=email
Gerrit-MessageType: merged
Gerrit-Project: pywikibot/core
Gerrit-Branch: master
Gerrit-Change-Id: Ia8b219bc2a995738014152425ea4ffd29fb61348
Gerrit-Change-Number: 1313084
Gerrit-PatchSet: 5
Gerrit-Owner: Xqt <info(a)gno.de>
Gerrit-Reviewer: Xqt <info(a)gno.de>
Gerrit-Reviewer: jenkins-bot
jenkins-bot has submitted this change. ( https://gerrit.wikimedia.org/r/c/pywikibot/core/+/1318204?usp=email )
Change subject: citoid: raise CitoidError on error response
......................................................................
citoid: raise CitoidError on error response
Raise new implemented CitoidError when the Citoid service returns an
error response. This prevents confusing error messages caused by
unexpected response.
Bug: T433230
Change-Id: Ib9c2fd98343946f9dbc23597426e01ccfef95371
---
M pywikibot/data/citoid.py
M pywikibot/exceptions.py
2 files changed, 27 insertions(+), 9 deletions(-)
Approvals:
jenkins-bot: Verified
Strainu: Looks good to me, approved
diff --git a/pywikibot/data/citoid.py b/pywikibot/data/citoid.py
index 6f0ceb7..99afefc 100644
--- a/pywikibot/data/citoid.py
+++ b/pywikibot/data/citoid.py
@@ -13,9 +13,8 @@
from dataclasses import dataclass
from typing import Any
-import pywikibot
from pywikibot.comms import http
-from pywikibot.exceptions import ApiNotAvailableError, Error
+from pywikibot.exceptions import ApiNotAvailableError, CitoidError
from pywikibot.site import BaseSite
@@ -41,9 +40,19 @@
) -> dict[str, Any]:
"""Get a citation from the citoid service.
- :param response_format: Return format, e.g. 'bibtex', 'wikibase', etc.
+ .. version-changed:: 11.7
+ Raise :exc:`CitoidError` if the Citoid service returns an
+ error with the response dict.
+
+ :param response_format: Return format, e.g. 'bibtex', 'wikibase',
+ etc.
:param ref_url: The URL to get the citation for.
:return: A dictionary with the citation data.
+ :raises ApiNotAvailableError: Citoid endpoint not configured for
+ the given site.
+ :raises CitoidError: Raised with the error returned by the
+ Citoid service.
+ :raises ValueError: Invalid format for *response_format*.
"""
if response_format not in VALID_FORMAT:
raise ValueError(f'Invalid format {response_format}, '
@@ -56,9 +65,9 @@
ref_url = urllib.parse.quote(ref_url, safe='')
api_url = urllib.parse.urljoin(base_url,
f'{response_format}/{ref_url}')
- try:
- json = http.request(self.site, api_url).json()
- return json
- except Error as e:
- pywikibot.log(f'Caught pywikibot error {e}')
- raise
+ data = http.request(self.site, api_url).json()
+
+ if 'error' in data:
+ raise CitoidError(data['error'])
+
+ return data
diff --git a/pywikibot/exceptions.py b/pywikibot/exceptions.py
index 9cd75cb..30af4ad 100644
--- a/pywikibot/exceptions.py
+++ b/pywikibot/exceptions.py
@@ -15,6 +15,7 @@
| └── UploadError
├── AutoblockUserError
├── CaptchaError
+ ├── CitoidError
├── ClientError
| └── Client414Error
├── InvalidTitleError
@@ -289,6 +290,14 @@
return self.info
+class CitoidError(Error):
+
+ """The Citoid service returned an error.
+
+ .. version-added:: 11.7
+ """
+
+
class PageRelatedError(Error):
"""Abstract Exception, used when the exception concerns a particular Page.
--
To view, visit https://gerrit.wikimedia.org/r/c/pywikibot/core/+/1318204?usp=email
To unsubscribe, or for help writing mail filters, visit https://gerrit.wikimedia.org/r/settings?usp=email
Gerrit-MessageType: merged
Gerrit-Project: pywikibot/core
Gerrit-Branch: master
Gerrit-Change-Id: Ib9c2fd98343946f9dbc23597426e01ccfef95371
Gerrit-Change-Number: 1318204
Gerrit-PatchSet: 2
Gerrit-Owner: Xqt <info(a)gno.de>
Gerrit-Reviewer: Strainu <wiki(a)strainu.ro>
Gerrit-Reviewer: jenkins-bot