jenkins-bot submitted this change.

View Change

Approvals: Xqt: Looks good to me, approved jenkins-bot: Verified
[sphinx] Provide additional external links in sphinx

- provide 'api' for MediaWiki API namespace
- provide 'bug' and 'issue' for python bug trackers
- provide 'pyhow', 'pylib' ans 'python' for Python documentation
- replace urls by these shortcuts

Change-Id: I1c0806b923e8ac69be6dacf5389f11f656e25414
---
M docs/conf.py
M docs/faq.rst
M docs/installation.rst
M docs/scripts/administrative.rst
M docs/scripts/general.rst
M pywikibot/data/api.py
M pywikibot/diff.py
M pywikibot/logging.py
M pywikibot/login.py
M pywikibot/page/_filepage.py
M pywikibot/page/_pages.py
M pywikibot/page/_user.py
M pywikibot/pagegenerators.py
M pywikibot/site/_apisite.py
M pywikibot/site/_generators.py
M pywikibot/site/_siteinfo.py
M pywikibot/site/_upload.py
M pywikibot/specialbots/_upload.py
M pywikibot/textlib.py
M scripts/archivebot.py
M scripts/clean_sandbox.py
M scripts/dataextend.py
M scripts/protect.py
23 files changed, 195 insertions(+), 160 deletions(-)

diff --git a/docs/conf.py b/docs/conf.py
index 6997f15..1b2a310 100644
--- a/docs/conf.py
+++ b/docs/conf.py
@@ -357,7 +357,23 @@
autodoc_typehints = 'description'

extlinks = {
- 'phab': ('https://phabricator.wikimedia.org/%s', '%s')
+ # MediaWiki API
+ 'api': ('https://www.mediawiki.org/wiki/API:%s', 'API:%s'),
+ # Python bug tracker
+ 'bug': ('https://bugs.python.org/issue%s', 'Python issue %s'),
+ # Python bug tracker
+ 'issue': ('https://github.com/python/cpython/issues/%s',
+ 'Python issue %s'),
+ # Phabricator tasks
+ 'phab': ('https://phabricator.wikimedia.org/%s', '%s'),
+ # Python howto link
+ 'pyhow': ('https://docs.python.org/3/howto/%s.html',
+ 'Python Howto %s'),
+ # Python library link
+ 'pylib': ('https://docs.python.org/3/library/%s.html',
+ 'Python Library %s'),
+ # Generic Python link; should be used with explicit title
+ 'python': ('https://docs.python.org/3/%s', None),
}


@@ -418,7 +434,7 @@
"""Convert Phabricator tasks id to a link using sphinx.ext.extlinks."""
result = []
for line in lines:
- line = re.sub(r'(T\d{5,6})', r':phab:`\1`', line)
+ line = re.sub(r'(?<!:phab:`)(T\d{5,6})', r':phab:`\1`', line)
result.append(line)
lines[:] = result[:]

diff --git a/docs/faq.rst b/docs/faq.rst
index a0f9555..f7aca82 100644
--- a/docs/faq.rst
+++ b/docs/faq.rst
@@ -18,7 +18,7 @@
to the ``PreloadingGenerator`` function mentioned above.
4. Use :py:mod:`MySQLPageGenerator
<pywikibot.pagegenerators.MySQLPageGenerator >` if direct DB access is
- available and appropriate. See also: `MySQL`_
+ available and appropriate. See also: :manpage:`MySQL`

**The bot cannot delete pages**
Your account needs delete rights on your wiki. If you have setup another
@@ -30,13 +30,9 @@
Using ``-help`` option is a good way to find all generators which can be
used with that script. You can also find all generator options and filter
options at :py:mod:`pywikibot.pagegenerators` module.
- See also `Page Generators`_ MediaWiki page for additional information.
+ See also :manpage:`Page Generators` for additional information.

**pywikibot.i18n.TranslationError: No English translation has been defined**
It can happen due to lack of i18n submodule or files. Update i18n submodule
- or download these files first. See also: `i18n submodule`_
+ or download these files first. See also: :manpage:`i18n` manual.

-
-.. _i18n submodule: https://www.mediawiki.org/wiki/Manual:Pywikibot/i18n
-.. _MySQL: https://www.mediawiki.org/wiki/Manual:Pywikibot/MySQL
-.. _Page Generators: https://www.mediawiki.org/wiki/Manual:Pywikibot/Page_Generators
diff --git a/docs/installation.rst b/docs/installation.rst
index 1c7f6c3..cc555a4 100644
--- a/docs/installation.rst
+++ b/docs/installation.rst
@@ -27,7 +27,7 @@
Some of the framework input interaction is translated. The user interface
language to be used can be set as follows:

-#. set the `userinterface_lang` in your :ref:`user-config.py<user-interface-settings>` to your preferred language
+#. set the `userinterface_lang` in your :ref:`user-config.py<User Interface Settings>` to your preferred language
#. set environment variable `PYWIKIBOT_USERINTERFACE_LANG` to your preferred language
#. default is obtained from `locale.getdefaultlocale`
#. fallback is `'en'` for english if all other options fails
diff --git a/docs/scripts/administrative.rst b/docs/scripts/administrative.rst
index 7916b44..3c829fa 100644
--- a/docs/scripts/administrative.rst
+++ b/docs/scripts/administrative.rst
@@ -1,38 +1,38 @@
Administrative scripts
======================

-blockpageschecker script
-------------------------
+blockpageschecker script description
+------------------------------------

.. automodule:: scripts.blockpageschecker
:no-members:

-delete script
--------------
+delete script description
+-------------------------

.. automodule:: scripts.delete
:no-members:

-patrol script
--------------
+patrol script description
+-------------------------

.. automodule:: scripts.patrol
:no-members:

-protect script
---------------
+protect script description
+--------------------------

.. automodule:: scripts.protect
:no-members:

-revertbot script
-----------------
+revertbot script description
+----------------------------

.. automodule:: scripts.revertbot
:no-members:

-speedy\_delete script
----------------------
+speedy\_delete script description
+---------------------------------

.. automodule:: scripts.speedy_delete
:no-members:
diff --git a/docs/scripts/general.rst b/docs/scripts/general.rst
index bceead8..6f4856a 100644
--- a/docs/scripts/general.rst
+++ b/docs/scripts/general.rst
@@ -1,20 +1,20 @@
General pages changes scripts
=============================

-archivebot script
------------------
+archivebot script description
+-----------------------------

.. automodule:: scripts.archivebot
:no-members:

-movepages script
-----------------
+movepages script description
+----------------------------

.. automodule:: scripts.movepages
:no-members:

-pagefromfile script
--------------------
+pagefromfile script description
+-------------------------------

.. automodule:: scripts.pagefromfile
:no-members:
diff --git a/pywikibot/data/api.py b/pywikibot/data/api.py
index f5f0d0c..59d6dcc 100644
--- a/pywikibot/data/api.py
+++ b/pywikibot/data/api.py
@@ -53,7 +53,7 @@
Clear cookies for site's second level domain.

get_login_token() will generate new cookies needed.
- This is a workaround for requests bug, see T224712
+ This is a workaround for requests bug, see :phab:`T224712`
and https://github.com/psf/requests/issues/5411
for more details.
"""
@@ -3038,13 +3038,11 @@


def encode_url(query) -> str:
- """
- Encode parameters to pass with a url.
+ """Encode parameters to pass with a url.

Reorder parameters so that token parameters go last and call wraps
- :py:obj:`urlencode`. Return an HTTP URL query fragment which complies with
- https://www.mediawiki.org/wiki/API:Edit#Parameters
- (See the 'token' bullet.)
+ :py:obj:`urlencode`. Return an HTTP URL query fragment which
+ complies with :api:`Edit#Parameters` (See the 'token' bullet.)

:param query: keys and values to be uncoded for passing with a url
:type query: mapping object or a sequence of two-element tuples
diff --git a/pywikibot/diff.py b/pywikibot/diff.py
index 91d99b4..d67a8b9 100644
--- a/pywikibot/diff.py
+++ b/pywikibot/diff.py
@@ -86,10 +86,13 @@
return '{0} -{1} +{2} {0}'.format(affix, a_rng, b_rng)

def create_diff(self) -> Iterable[str]:
- """Generator of diff text for this hunk, without formatting."""
- # make sure each line ends with '\n' to prevent
- # behaviour like https://bugs.python.org/issue2142
+ """Generator of diff text for this hunk, without formatting.
+
+ Check each line ends with line feed to prevent behaviour like
+ :bug:`2142`
+ """
def check_line(line: str) -> str:
+ r"""Make sure each line ends with '\n'."""
return line if line.endswith('\n') else line + '\n'

for tag, i1, i2, j1, j2 in self.group:
diff --git a/pywikibot/logging.py b/pywikibot/logging.py
index 39b6ac1..1eaa02a 100644
--- a/pywikibot/logging.py
+++ b/pywikibot/logging.py
@@ -38,6 +38,11 @@
STDOUT = 16 #:
VERBOSE = 18 #:
INPUT = 25 #:
+"""Three additional logging levels which are implemented beside
+`CRITICAL`, `DEBUG`, `ERROR`, `INFO` and `WARNING`.
+
+.. seealso:: :python:`Python Logging Levels<logging.html#logging-levels>`
+"""

_init_routines = [] # type: List[Callable[[], Any]]
_inited_routines = set()
@@ -66,6 +71,8 @@
"""Format output and send to the logging module.

Helper function used by all the user-output convenience functions.
+ It can be used to implement your own high-level output function with
+ a different lgging level.
"""
if _logger:
logger = logging.getLogger('pywiki.' + _logger)
@@ -142,7 +149,7 @@
be encoded in the given encoding.
:param newline: If True, a line feed will be added after printing the text.
:param kwargs: The keyword arguments can be found in the python doc:
- https://docs.python.org/3/howto/logging-cookbook.html
+ :pyhow:`logging-cookbook`
"""
logoutput(text, decoder, newline, STDOUT, **kwargs)

@@ -156,7 +163,7 @@
should be encoded in the given encoding.
:param newline: If True, a line feed will be added after printing the text.
:param kwargs: The keyword arguments can be found in the python doc:
- https://docs.python.org/3/howto/logging-cookbook.html
+ :pyhow:`logging-cookbook`
"""
logoutput(text, decoder, newline, WARNING, **kwargs)

@@ -170,7 +177,7 @@
be encoded in the given encoding.
:param newline: If True, a line feed will be added after printing the text.
:param kwargs: The keyword arguments can be found in the python doc:
- https://docs.python.org/3/howto/logging-cookbook.html
+ :pyhow:`logging-cookbook`
"""
logoutput(text, decoder, newline, ERROR, **kwargs)

@@ -184,7 +191,7 @@
be encoded in the given encoding.
:param newline: If True, a line feed will be added after printing the text.
:param kwargs: The keyword arguments can be found in the python doc:
- https://docs.python.org/3/howto/logging-cookbook.html
+ :pyhow:`logging-cookbook`
"""
logoutput(text, decoder, newline, VERBOSE, **kwargs)

@@ -198,7 +205,7 @@
be encoded in the given encoding.
:param newline: If True, a line feed will be added after printing the text.
:param kwargs: The keyword arguments can be found in the python doc:
- https://docs.python.org/3/howto/logging-cookbook.html
+ :pyhow:`logging-cookbook`
"""
logoutput(text, decoder, newline, CRITICAL, **kwargs)

@@ -217,7 +224,7 @@
be encoded in the given encoding.
:param newline: If True, a line feed will be added after printing the text.
:param kwargs: The keyword arguments can be found in the python doc:
- https://docs.python.org/3/howto/logging-cookbook.html
+ :pyhow:`logging-cookbook`
"""
logoutput(text, decoder, newline, DEBUG, layer, **kwargs)

@@ -253,7 +260,7 @@
be encoded in the given encoding.
:param newline: If True, a line feed will be added after printing the text.
:param kwargs: The keyword arguments can be found in the python doc:
- https://docs.python.org/3/howto/logging-cookbook.html
+ :pyhow:`logging-cookbook`
:param tb: Set to True in order to output traceback also.
"""
if isinstance(msg, BaseException):
diff --git a/pywikibot/login.py b/pywikibot/login.py
index a58fa1d..d14195e 100644
--- a/pywikibot/login.py
+++ b/pywikibot/login.py
@@ -115,7 +115,7 @@
"""
Check that the username exists on the site.

- :see: https://www.mediawiki.org/wiki/API:Users
+ .. seealso:: :api:`Users`

:raises pywikibot.exceptions.NoUsernameError: Username doesn't exist in
user list.
@@ -265,7 +265,7 @@
"""
Attempt to log into the server.

- :see: https://www.mediawiki.org/wiki/API:Login
+ .. seealso:: :api:`Login`

:param retry: infinitely retry if the API returns an unknown error
:param autocreate: if true, allow auto-creation of the account
@@ -384,7 +384,7 @@
"""
Attempt to log into the server.

- :see: https://www.mediawiki.org/wiki/API:Login
+ .. seealso:: :api:`Login`

:param retry: infinitely retry if exception occurs during
authentication.
@@ -424,7 +424,7 @@
"""
Return OAuth consumer key token and secret token.

- :see: https://www.mediawiki.org/wiki/API:Tokens
+ .. seealso:: :api:`Tokens`
"""
return self._consumer_token

@@ -433,7 +433,7 @@
"""
Return OAuth access key token and secret token.

- :see: https://www.mediawiki.org/wiki/API:Tokens
+ .. seealso:: :api:`Tokens`
"""
return self._access_token

diff --git a/pywikibot/page/_filepage.py b/pywikibot/page/_filepage.py
index 6f074ce..9ff917d 100644
--- a/pywikibot/page/_filepage.py
+++ b/pywikibot/page/_filepage.py
@@ -118,7 +118,7 @@
- url, thumburl, thumbwidth and thumbheight

Parameters correspond to iiprops in:
- [1] https://www.mediawiki.org/wiki/API:Imageinfo
+ [1] :api:`Imageinfo`

Parameters validation and error handling left to the API call.

@@ -222,10 +222,10 @@
or None it'll raise an UploadError exception if the static
boolean is False.
:type ignore_warnings: bool or callable or iterable of str
- :keyword chunk_size: The chunk size in bytesfor chunked uploading (see
- https://www.mediawiki.org/wiki/API:Upload#Chunked_uploading). It
- will only upload in chunks, if the chunk size is positive but lower
- than the file size.
+ :keyword chunk_size: The chunk size in bytesfor chunked
+ uploading (see :api:`Upload#Chunked_uploading`). It will
+ only upload in chunks, if the chunk size is positive but
+ lower than the file size.
:type chunk_size: int
:keyword report_success: If the upload was successful it'll print a
success message and if ignore_warnings is set to False it'll
diff --git a/pywikibot/page/_pages.py b/pywikibot/page/_pages.py
index 893b236..aee95a2 100644
--- a/pywikibot/page/_pages.py
+++ b/pywikibot/page/_pages.py
@@ -1417,7 +1417,7 @@
.. deprecated:: 7.0
the positional arguments

- .. seealso:: https://www.mediawiki.org/wiki/API:Links
+ .. seealso:: :api:`Links`

:keyword namespaces: Only iterate pages in these namespaces
(default: all)
diff --git a/pywikibot/page/_user.py b/pywikibot/page/_user.py
index dc96be0..b095775 100644
--- a/pywikibot/page/_user.py
+++ b/pywikibot/page/_user.py
@@ -417,9 +417,9 @@
"""
Determine if the user has thanks notifications enabled.

- NOTE: This doesn't accurately determine if thanks is enabled for user.
- Privacy of thanks preferences is under discussion, please see
- https://phabricator.wikimedia.org/T57401#2216861, and
- https://phabricator.wikimedia.org/T120753#1863894
+ .. note::
+ This doesn't accurately determine if thanks is enabled for user.
+ Privacy of thanks preferences is under discussion, please see
+ :phab:`T57401#2216861` and :phab:`T120753#1863894`.
"""
return self.isRegistered() and 'bot' not in self.groups()
diff --git a/pywikibot/pagegenerators.py b/pywikibot/pagegenerators.py
index 59d8ecb..50160b1 100644
--- a/pywikibot/pagegenerators.py
+++ b/pywikibot/pagegenerators.py
@@ -246,9 +246,8 @@

-mysqlquery Takes a MySQL query string like
"SELECT page_namespace, page_title FROM page
- WHERE page_namespace = 0" and treats
- the resulting pages. See
- https://www.mediawiki.org/wiki/Manual:Pywikibot/MySQL
+ WHERE page_namespace = 0"
+ and treats the resulting pages. See :manpage:`MySQL`
for more details.

-sparql Takes a SPARQL SELECT query string including ?item
@@ -317,7 +316,7 @@
-linter:show just shows available categories.

-querypage:name Work on pages provided by a QueryPage-based special page,
- see https://www.mediawiki.org/wiki/API:Querypage.
+ see :api:`Querypage`.
(tip: use -limit:n to fetch only n pages).

-querypage shows special pages available.
@@ -2750,7 +2749,7 @@
FROM page
WHERE page_namespace = 0;

- See https://www.mediawiki.org/wiki/Manual:Pywikibot/MySQL
+ .. seealso:: :manpage:`MySQL`

:param query: MySQL query to execute
:param site: Site object
diff --git a/pywikibot/site/_apisite.py b/pywikibot/site/_apisite.py
index a8b5120..ce2c893 100644
--- a/pywikibot/site/_apisite.py
+++ b/pywikibot/site/_apisite.py
@@ -327,6 +327,8 @@
"""
Log the user in if not already logged in.

+ .. seealso:: :api:`Login`
+
:param autocreate: if true, allow auto-creation of the account
using unified login
:param user: bot user name. Overrides the username set by
@@ -334,7 +336,6 @@

:raises pywikibot.exceptions.NoUsernameError: Username is not
recognised by the site.
- :see: https://www.mediawiki.org/wiki/API:Login
"""
# TODO: this should include an assert that loginstatus
# is not already IN_PROGRESS, however the
@@ -429,7 +430,8 @@
Logout of the site and load details for the logged out user.

Also logs out of the global account if linked to the user.
- https://www.mediawiki.org/wiki/API:Logout
+
+ .. seealso:: :api:`Logout`

:raises APIError: Logout is not available when OAuth enabled.
"""
@@ -471,7 +473,7 @@
To force retrieving userinfo ignoring cache, just delete this
property.

- .. seealso:: https://www.mediawiki.org/wiki/API:Userinfo
+ .. seealso:: :api:`Userinfo`

:return: A dict with the following keys and values:

@@ -589,10 +591,11 @@

To check whether a user can perform an action,
the method has_right should be used.
- https://www.mediawiki.org/wiki/API:Userinfo
+
+ .. seealso:: :api:`Userinfo`

.. versionadded:: 7.0
- The *force* parameter
+ The `force` parameter

:param force: Whether the cache should be discarded.
"""
@@ -713,7 +716,8 @@
"""Return true if and only if the user has a specific right.

Possible values of 'right' may vary depending on wiki settings.
- https://www.mediawiki.org/wiki/API:Userinfo
+
+ .. seealso:: :api:`Userinfo`

:param right: a specific right to be validated
"""
@@ -724,7 +728,8 @@

Possible values of 'group' may vary depending on wiki settings,
but will usually include bot.
- https://www.mediawiki.org/wiki/API:Userinfo
+
+ .. seealso:: :api:`Userinfo`
"""
return group.lower() in self.userinfo['groups']

@@ -741,7 +746,7 @@

The returned dict uses each key to store the associated message.

- :see: https://www.mediawiki.org/wiki/API:Allmessages
+ .. seealso:: :api:`Allmessages`

:param keys: MediaWiki messages to fetch
:param lang: a language code, default is self.lang
@@ -1214,7 +1219,7 @@
) -> None:
"""Load page info from api and store in page attributes.

- :see: https://www.mediawiki.org/wiki/API:Info
+ .. seealso:: :api:`Info`
"""
title = page.title(with_section=False)
inprop = 'protection'
@@ -1247,7 +1252,7 @@
"""Load image info from api and save in page attributes.

Parameters correspond to iiprops in:
- [1] https://www.mediawiki.org/wiki/API:Imageinfo
+ [1] :api:`Imageinfo`

Parameters validation and error handling left to the API call.

@@ -1453,7 +1458,7 @@
- userrights
- watch

- :see: https://www.mediawiki.org/wiki/API:Tokens
+ .. seealso:: :api:`Tokens`

:param types: the types of token (e.g., "edit", "move", "delete");
see API documentation for full list of types
@@ -1505,7 +1510,7 @@
raises KeyError instead of AssertionError

.. seealso::
- - https://www.mediawiki.org/wiki/API:Parse
+ - :api:`Parse`
- :meth:`pywikibot.page.BasePage.get_parsed_page`.
"""
req = self.simple_request(action='parse', page=page)
@@ -1519,7 +1524,7 @@
def getcategoryinfo(self, category: 'pywikibot.page.Category') -> None:
"""Retrieve data on contents of category.

- :see: https://www.mediawiki.org/wiki/API:Categoryinfo
+ .. seealso:: :api:`Categoryinfo`
"""
cititle = category.title(with_section=False)
ciquery = self._generator(api.PropertyGenerator,
@@ -1564,7 +1569,7 @@
) -> None:
"""Delete or undelete specified page revisions, file versions or logs.

- :see: https://www.mediawiki.org/wiki/API:Revisiondelete
+ .. seealso:: :api:`Revisiondelete`

If more than one target id is provided, the same action is taken for
all of them.
@@ -1677,7 +1682,7 @@
) -> bool:
"""Submit an edit to be saved to the wiki.

- :see: https://www.mediawiki.org/wiki/API:Edit
+ .. seealso:: :api:`Edit`

:param page: The Page to be saved.
By default its .text property will be used
@@ -1905,7 +1910,7 @@
) -> None:
"""Merge revisions from one page into another.

- :see: https://www.mediawiki.org/wiki/API:Mergehistory
+ .. seealso:: :api:`Mergehistory`

Revisions dating up to the given timestamp in the source will be
moved into the destination page history. History merge fails if
@@ -2022,7 +2027,7 @@
) -> 'pywikibot.page.Page':
"""Move a Page to a new title.

- .. seealso:: https://www.mediawiki.org/wiki/API:Move
+ .. seealso:: :api:`Move`

.. versionchanged:: 7.2
The `movesubpages` parameter was added
@@ -2131,7 +2136,7 @@
) -> None:
"""Roll back page to version before last user's edits.

- :see: https://www.mediawiki.org/wiki/API:Rollback
+ .. seealso:: :api:`Rollback`

The keyword arguments are those supported by the rollback API.

@@ -2211,19 +2216,20 @@

Requires appropriate privileges.

- :see: https://www.mediawiki.org/wiki/API:Delete
+ .. seealso: :api:`Delete`
+
Page to be deleted can be given either as Page object or as pageid.
To delete a specific version of an image the oldimage identifier
must be provided.

.. versionadded:: 6.1
- renamed from *deletepage*
+ renamed from `deletepage`

.. versionchanged:: 6.1
- keyword only parameter *oldimage* was added.
+ keyword only parameter `oldimage` was added.

.. versionchanged:: 7.1
- keyword only parameter *deletetalk* was added.
+ keyword only parameter `deletetalk` was added.

:param page: Page to be deleted or its pageid.
:param reason: Deletion reason.
@@ -2295,14 +2301,14 @@
) -> None:
"""Undelete page from the wiki. Requires appropriate privilege level.

- :see: https://www.mediawiki.org/wiki/API:Undelete
+ .. seealso:: :api:`Undelete`

.. versionadded:: 6.1
- renamed from *undelete_page*
+ renamed from `undelete_page`

.. versionchanged:: 6.1
- *fileids* parameter was added,
- keyword argument required for *revisions*.
+ `fileids` parameter was added,
+ keyword argument required for `revisions`.

:param page: Page to be deleted.
:param reason: Undeletion reason.
@@ -2355,8 +2361,9 @@
"""
Return the protection types available on this site.

+ .. seealso:: :py:obj:`Siteinfo._get_default()`
+
:return: protection types available
- :see: :py:obj:`Siteinfo._get_default()`
"""
return set(self.siteinfo.get('restrictions')['types'])

@@ -2364,8 +2371,9 @@
"""
Return the protection levels available on this site.

+ .. seealso:: :py:obj:`Siteinfo._get_default()`
+
:return: protection types available
- :see: :py:obj:`Siteinfo._get_default()`
"""
# implemented in b73b5883d486db0e9278ef16733551f28d9e096d
return set(self.siteinfo.get('restrictions')['levels'])
@@ -2381,7 +2389,7 @@
) -> None:
"""(Un)protect a wiki page. Requires administrator status.

- :see: https://www.mediawiki.org/wiki/API:Protect
+ .. seealso:: :api:`Protect`

:param protections: A dict mapping type of protection to protection
level of that type. Valid restriction types are 'edit', 'create',
@@ -2449,7 +2457,7 @@
"""
Block a user for certain amount of time and for a certain reason.

- :see: https://www.mediawiki.org/wiki/API:Block
+ .. seealso:: :api:`Block

:param user: The username/IP to be blocked without a namespace.
:param expiry: The length or date/time when the block expires. If
@@ -2497,7 +2505,7 @@
"""
Remove the block for the user.

- :see: https://www.mediawiki.org/wiki/API:Block
+ .. seealso:: :api:`Block`

:param user: The username/IP without a namespace.
:param reason: Reason for the unblock.
@@ -2521,7 +2529,7 @@
) -> bool:
"""Add or remove pages from watchlist.

- :see: https://www.mediawiki.org/wiki/API:Watch
+ .. seealso:: :api:`Watch`

:param pages: A single page or a sequence of pages.
:param unwatch: If True, remove pages from watchlist;
@@ -2630,7 +2638,7 @@
) -> Dict[str, Any]:
"""Get the stash info for a given file key.

- :see: https://www.mediawiki.org/wiki/API:Stashimageinfo
+ .. seealso:: :api:`Stashimageinfo`
"""
props = props or None
req = self.simple_request(action='query', prop='stashimageinfo',
@@ -2645,7 +2653,7 @@
) -> bool:
"""Upload a file to the wiki.

- :see: https://www.mediawiki.org/wiki/API:Upload
+ .. seealso:: :api:`Upload`

Either source_filename or source_url, but not both, must be provided.

@@ -2668,7 +2676,7 @@
"""
Get property names for pages_with_property().

- :see: https://www.mediawiki.org/wiki/API:Pagepropnames
+ .. seealso:: :api:`Pagepropnames`

:param force: force to retrieve userinfo ignoring cache
"""
@@ -2681,7 +2689,7 @@
"""
Corresponding method to the 'action=compare' API action.

- :see: https://www.mediawiki.org/wiki/API:Compare
+ .. seealso: :api:`Compare`

See: https://en.wikipedia.org/w/api.php?action=help&modules=compare
Use pywikibot.diff's html_comparator() method to parse result.
diff --git a/pywikibot/site/_generators.py b/pywikibot/site/_generators.py
index 7bc537c..ce94db9 100644
--- a/pywikibot/site/_generators.py
+++ b/pywikibot/site/_generators.py
@@ -195,7 +195,7 @@
content: bool = False):
"""Iterate all pages that link to the given page.

- :see: https://www.mediawiki.org/wiki/API:Backlinks
+ .. seealso:: :api:`Backlinks`

:param page: The Page to get links to.
:param follow_redirects: Also return links to redirects pointing to
@@ -257,7 +257,7 @@
total=None, content: bool = False):
"""Iterate all pages that embedded the given page as a template.

- :see: https://www.mediawiki.org/wiki/API:Embeddedin
+ .. seealso:: :api:`Embeddedin`

:param page: The Page to get inclusions for.
:param filter_redirects: If True, only return redirects that embed
@@ -296,7 +296,9 @@
) -> 'Iterable[pywikibot.Page]':
"""Iterale all redirects to the given page.

- :see: https://www.mediawiki.org/wiki/API:Redirects
+ .. seealso:: :api:`Redirects`
+
+ .. versionadded:: 7.0

:param page: The Page to get redirects for.
:param filter_fragments: If True, only return redirects with fragments.
@@ -305,8 +307,6 @@
:param namespaces: Only return redirects from the namespaces
:param total: maximum number of redirects to retrieve in total
:param content: load the current content of each redirect
-
- .. versionadded:: 7.0
"""
rdargs = {
'titles': page.title(with_section=False).encode(self.encoding()),
@@ -371,7 +371,7 @@
) -> Generator['pywikibot.Page', None, None]:
"""Iterate internal wikilinks contained (or transcluded) on page.

- .. seealso:: https://www.mediawiki.org/wiki/API:Links
+ .. seealso:: :api:`Links`

:param namespaces: Only iterate pages in these namespaces
(default: all)
@@ -401,7 +401,7 @@
def pagecategories(self, page, *, total=None, content: bool = False):
"""Iterate categories to which page belongs.

- :see: https://www.mediawiki.org/wiki/API:Categories
+ .. seealso:: :api:`Categories`

:param content: if True, load the current content of each iterated page
(default False); note that this means the contents of the
@@ -420,7 +420,7 @@
def pageimages(self, page, *, total=None, content: bool = False):
"""Iterate images used (not just linked) on the page.

- :see: https://www.mediawiki.org/wiki/API:Images
+ .. seealso:: :api:`Images`

:param content: if True, load the current content of each iterated page
(default False); note that this means the content of the image
@@ -436,7 +436,7 @@
content: bool = False):
"""Iterate templates transcluded (not just linked) on the page.

- :see: https://www.mediawiki.org/wiki/API:Templates
+ .. seealso:: :api:`Templates`

:param namespaces: Only iterate pages in these namespaces
:type namespaces: iterable of str or Namespace key,
@@ -467,7 +467,7 @@
endprefix: Optional[str] = None):
"""Iterate members of specified category.

- :see: https://www.mediawiki.org/wiki/API:Categorymembers
+ .. seealso:: :api:`Categorymembers`

:param category: The Category to iterate.
:param namespaces: If present, only return category members from
@@ -634,7 +634,7 @@
endid if both are specified; likewise, starttime must be greater
than endtime. If rvdir is True, these relationships are reversed.

- :see: https://www.mediawiki.org/wiki/API:Revisions
+ .. seealso:: :api:`Revisions`

:param page: retrieve revisions of this Page and hold the data.
:type page: pywikibot.Page
@@ -754,9 +754,9 @@
"""Iterate all interlanguage links on page, yielding Link objects.

.. versionchanged:: 6.2:
- *include_empty_titles* parameter was added.
+ `include_empty_titles` parameter was added.

- :see: https://www.mediawiki.org/wiki/API:Langlinks
+ .. seealso:: :api:`Langlinks`

:param include_obsolete: if true, yield even Link objects whose
site is obsolete
@@ -786,7 +786,7 @@
def page_extlinks(self, page, *, total=None):
"""Iterate all external links on page, yielding URL strings.

- :see: https://www.mediawiki.org/wiki/API:Extlinks
+ .. seealso:: :api:`Extlinks`
"""
eltitle = page.title(with_section=False)
elquery = self._generator(api.PropertyGenerator, type_arg='extlinks',
@@ -817,7 +817,7 @@
):
"""Iterate pages in a single namespace.

- :see: https://www.mediawiki.org/wiki/API:Allpages
+ .. seealso:: :api:`Allpages`

:param start: Start at this title (page need not exist).
:param prefix: Only yield pages starting with this string.
@@ -898,7 +898,7 @@
been deleted may not have been removed from the links table, so this
method can return false positives.

- :see: https://www.mediawiki.org/wiki/API:Alllinks
+ .. seealso:: :api:`Alllinks`

:param start: Start at this title (page need not exist).
:param prefix: Only yield pages starting with this string.
@@ -936,7 +936,7 @@
were found on pages that have been deleted may not have been removed
from the database table, so this method can return false positives.

- :see: https://www.mediawiki.org/wiki/API:Allcategories
+ .. seealso:: :api:`Allcategories`

:param start: Start at this category title (category need not exist).
:param prefix: Only yield categories starting with this string.
@@ -987,7 +987,7 @@
will be a list of str; all the other values are str and should
always be present.

- :see: https://www.mediawiki.org/wiki/API:Allusers
+ .. seealso:: :api:`Allusers`

:param start: start at this username (name need not exist)
:param prefix: only iterate usernames starting with this substring
@@ -1019,7 +1019,7 @@

Yields FilePages, but these pages need not exist on the wiki.

- :see: https://www.mediawiki.org/wiki/API:Allimages
+ .. seealso:: :api:`Allimages`

:param start: start at this title (name need not exist)
:param prefix: only iterate titles starting with this substring
@@ -1062,7 +1062,7 @@

Yields dict of file archive informations.

- :see: https://www.mediawiki.org/wiki/API:filearchive
+ .. seealso:: :api:`filearchive`

:param start: start at this title (name need not exist)
:param end: end at this title (name need not exist)
@@ -1095,11 +1095,13 @@
The iterator yields dicts containing keys corresponding to the
block properties.

- :see: https://www.mediawiki.org/wiki/API:Blocks
+ .. seealso:: :api:`Blocks`

- :note: logevents only logs user blocks, while this method
- iterates all blocks including IP ranges.
- :note: ``iprange`` parameter cannot be used together with ``users``.
+ .. note::
+ logevents only logs user blocks, while this method iterates
+ all blocks including IP ranges.
+ .. warning::
+ ``iprange`` parameter cannot be used together with ``users``.

:param starttime: start iterating at this Timestamp
:type starttime: pywikibot.Timestamp
@@ -1148,7 +1150,7 @@
total: Optional[int] = None, content: bool = False):
"""Iterate Pages that contain links to the given URL.

- :see: https://www.mediawiki.org/wiki/API:Exturlusage
+ .. seealso:: :api:`Exturlusage`

:param url: The URL to search for (with or without the protocol
prefix); this may include a '*' as a wildcard, only at the start
@@ -1188,7 +1190,7 @@
content: bool = False):
"""Iterate Pages that contain links to the given FilePage.

- .. seealso:: https://www.mediawiki.org/wiki/API:Imageusage
+ .. seealso:: :api:`Imageusage`
.. versionchanged:: 7.2
all parameters except `image` are keyword only.

@@ -1222,10 +1224,11 @@
total: Optional[int] = None):
"""Iterate all log entries.

- :see: https://www.mediawiki.org/wiki/API:Logevents
+ .. seealso:: :api:`Logevents`

- :note: logevents with logtype='block' only logs user blocks whereas
- site.blocks iterates all blocks including IP ranges.
+ .. note::
+ logevents with `logtype='block'` only logs user blocks
+ whereas `site.blocks` iterates all blocks including IP ranges.

:param logtype: only iterate entries of this type
(see mediawiki api documentation for available types)
@@ -1292,7 +1295,7 @@
tag: Optional[str] = None):
"""Iterate recent changes.

- :see: https://www.mediawiki.org/wiki/API:RecentChanges
+ .. seealso:: :api:`RecentChanges`

:param start: Timestamp to start listing from
:type start: pywikibot.Timestamp
@@ -1378,7 +1381,7 @@
raises APIError instead of Error if searchstring is not set
or what parameter is wrong.

- .. seealso:: https://www.mediawiki.org/wiki/API:Search
+ .. seealso:: :api:`Search`

:param searchstring: the text to search for
:param where: Where to search; value must be "text", "title",
@@ -1412,7 +1415,7 @@

Iterated values are in the same format as recentchanges.

- :see: https://www.mediawiki.org/wiki/API:Usercontribs
+ .. seealso:: :api:`Usercontribs`

:param user: Iterate contributions by this user (name or IP)
:param userprefix: Iterate contributions by all users whose names
@@ -1468,7 +1471,7 @@

Iterated values will be in same format as recentchanges.

- :see: https://www.mediawiki.org/wiki/API:Watchlist
+ .. seealso:: :api:`Watchlist`

:param start: Iterate revisions starting at this Timestamp
:param end: Iterate revisions ending at this Timestamp
@@ -1537,7 +1540,7 @@
when 'content' parameter is set. For older wikis a 'token' key is
also given with the content request.

- :see: https://www.mediawiki.org/wiki/API:Deletedrevisions
+ .. seealso:: :api:`Deletedrevisions`

:param titles: The page titles to check for deleted revisions
:type titles: str (multiple titles delimited with '|')
@@ -1644,7 +1647,7 @@
"""
Iterate all deleted revisions.

- :see: https://www.mediawiki.org/wiki/API:Alldeletedrevisions
+ .. seealso:: :api:`Alldeletedrevisions`

:param namespaces: Only iterate pages in these namespaces
:type namespaces: iterable of str or Namespace key,
@@ -1691,7 +1694,7 @@
def users(self, usernames):
"""Iterate info about a list of users by name or IP.

- :see: https://www.mediawiki.org/wiki/API:Users
+ .. seealso:: :api:`Users`

:param usernames: a list of user names
:type usernames: list, or other iterable, of str
@@ -1707,7 +1710,7 @@
redirects: Optional[bool] = False, content: bool = False):
"""Iterate a number of random pages.

- :see: https://www.mediawiki.org/wiki/API:Random
+ .. seealso: :api:`Random`

Pages are listed in a fixed sequence, only the starting point is
random.
@@ -1761,7 +1764,7 @@
def patrol(self, rcid=None, revid=None, revision=None):
"""Return a generator of patrolled pages.

- :see: https://www.mediawiki.org/wiki/API:Patrol
+ .. seealso:: :api:`Patrol`

Pages to be patrolled are identified by rcid, revid or revision.
At least one of the parameters is mandatory.
@@ -1858,11 +1861,10 @@
specified in the first argument.

The objects yielded are dependent on parameter returndict.
- When true, it yields a tuple composed of a Page object and a dict of
- attributes.
- When false, it yields a tuple composed of the Page object,
- timestamp (str), length (int), an empty string, username or IP
- address (str), comment (str).
+ When true, it yields a tuple composed of a Page object and a
+ dict of attributes. When false, it yields a tuple composed of
+ the Page object, timestamp (str), length (int), an empty string,
+ username or IP address (str), comment (str).

:param namespaces: only iterate pages in these namespaces
:type namespaces: iterable of str or Namespace key,
@@ -1895,7 +1897,7 @@
def querypage(self, special_page, total=True):
"""Yield Page objects retrieved from Special:{special_page}.

- :see: https://www.mediawiki.org/wiki/API:Querypage
+ .. seealso:: :api:`Querypage`

Generic function for all special pages supported by the site MW API.

@@ -2087,7 +2089,7 @@
:py:obj:`APISite.allpages`, while it uses for 'create' the
'query+protectedtitles' module.

- :see: https://www.mediawiki.org/wiki/API:Protectedtitles
+ .. seealso:: :api:`Protectedtitles`

:param namespace: The searched namespace.
:type namespace: int or Namespace or str
@@ -2113,7 +2115,7 @@
total: Optional[int] = None):
"""Yield Page objects from Special:PagesWithProp.

- :see: https://www.mediawiki.org/wiki/API:Pageswithprop
+ .. seealso:: :api:`Pageswithprop`

:param propname: must be a valid property.
:param total: number of pages to return
@@ -2130,7 +2132,7 @@
"""
Return watchlist.

- :see: https://www.mediawiki.org/wiki/API:Watchlistraw
+ .. seealso:: :api:`Watchlistraw`

:param force: Reload watchlist
:param total: if not None, limit the generator to yielding this many
diff --git a/pywikibot/site/_siteinfo.py b/pywikibot/site/_siteinfo.py
index bc0aa76..92d2563 100644
--- a/pywikibot/site/_siteinfo.py
+++ b/pywikibot/site/_siteinfo.py
@@ -127,6 +127,8 @@
returned when a property doesn't exists, it queries each property
independetly if a property is invalid.

+ .. seealso:: :api:Siteinfo
+
:param prop: The property names of the siteinfo.
:type prop: str or iterable
:param expiry: The expiry date of the cached request.
@@ -134,7 +136,6 @@
:return: A dictionary with the properties of the site. Each entry in
the dictionary is a tuple of the value and a boolean to save if it
is the default value.
- :see: https://www.mediawiki.org/wiki/API:Meta#siteinfo_.2F_si
"""
def warn_handler(mod, message) -> bool:
"""Return True if the warning is handled."""
diff --git a/pywikibot/site/_upload.py b/pywikibot/site/_upload.py
index 8dba558..c3391c7 100644
--- a/pywikibot/site/_upload.py
+++ b/pywikibot/site/_upload.py
@@ -39,10 +39,10 @@
:param text: Initial page text; if this is not set, then
filepage.text will be used, or comment.
:param watch: If true, add filepage to the bot user's watchlist
- :param chunk_size: The chunk size in bytes for chunked uploading (see
- https://www.mediawiki.org/wiki/API:Upload#Chunked_uploading).
- It will only upload in chunks, if the chunk size is positive
- but lower than the file size.
+ :param chunk_size: The chunk size in bytes for chunked uploading
+ (see :api:`Upload#Chunked_uploading`). It will only upload in
+ chunks, if the chunk size is positive but lower than the file
+ size.
:param asynchronous: Make potentially large file operations
asynchronous on the server side when possible.
:param ignore_warnings: It may be a static boolean, a callable
diff --git a/pywikibot/specialbots/_upload.py b/pywikibot/specialbots/_upload.py
index 043a345..66a81bb 100644
--- a/pywikibot/specialbots/_upload.py
+++ b/pywikibot/specialbots/_upload.py
@@ -373,7 +373,7 @@
"""
Upload the image at file_url to the target wiki.

- :see: https://www.mediawiki.org/wiki/API:Upload
+ .. seealso:: :api:`Upload`

Return the filename that was used to upload the image.
If the upload fails, ask the user whether to try again or not.
diff --git a/pywikibot/textlib.py b/pywikibot/textlib.py
index 4b6270b..7425d44 100644
--- a/pywikibot/textlib.py
+++ b/pywikibot/textlib.py
@@ -533,12 +533,13 @@
return parser.textdata


-# thanks to https://docs.python.org/3/library/html.parser.html
class _GetDataHTML(HTMLParser):

"""HTML parser which removes html tags except they are listed in keeptags.

This class is also a context manager which closes itself at exit time.
+
+ .. seealso:: :pylib:`html.parser`
"""

textdata = ''
diff --git a/scripts/archivebot.py b/scripts/archivebot.py
index 2b02bf7..13d362d 100755
--- a/scripts/archivebot.py
+++ b/scripts/archivebot.py
@@ -72,9 +72,9 @@
between Friday or Sunday (including) the following week is then the first week
of the year. So up to three days are still counted as the year before.

-See also:
- - https://webspace.science.uu.nl/~gent0113/calendar/isocalendar.htm
- - https://docs.python.org/3/library/datetime.html#datetime.date.isocalendar
+.. seealso:: Python :python:`datetime.date.isocalendar
+ <library/datetime.html#datetime.date.isocalendar>`,
+ https://webspace.science.uu.nl/~gent0113/calendar/isocalendar.htm

Options (may be omitted):

diff --git a/scripts/clean_sandbox.py b/scripts/clean_sandbox.py
index fa8c659..a6b199a 100755
--- a/scripts/clean_sandbox.py
+++ b/scripts/clean_sandbox.py
@@ -25,8 +25,10 @@

This script is a :py:obj:`ConfigParserBot <pywikibot.bot.ConfigParserBot>`.
All local parameters can be given inside a scripts.ini file. Options
-passed to the script are priorized over options read from ini file. See:
-https://docs.python.org/3/library/configparser.html#supported-ini-file-structure
+passed to the script are priorized over options read from ini file.
+
+.. seealso:: :python:`Supported .ini File Structure
+ <library/configparser.html#supported-ini-file-structure>`

For example:

diff --git a/scripts/dataextend.py b/scripts/dataextend.py
index e294fc5..f8ee391 100644
--- a/scripts/dataextend.py
+++ b/scripts/dataextend.py
@@ -50,6 +50,8 @@
on in the browser afterward, to correct any mistakes it has made, or
cases where a more precise and less precise value have both been
included.
+
+.. versionadded:: 7.2
"""
#
# (C) Pywikibot team, 2020-2022
diff --git a/scripts/protect.py b/scripts/protect.py
index 985442d..a2f13d4 100755
--- a/scripts/protect.py
+++ b/scripts/protect.py
@@ -37,7 +37,7 @@
-expiry: Supply a custom protection expiry, which defaults to
indefinite. Any string understandable by MediaWiki, including
relative and absolute, is acceptable. See:
- https://www.mediawiki.org/wiki/API:Protect#Parameters
+ :api:`Protect#Parameters`

Usage:


To view, visit change 785373. To unsubscribe, or for help writing mail filters, visit settings.

Gerrit-Project: pywikibot/core
Gerrit-Branch: master
Gerrit-Change-Id: I1c0806b923e8ac69be6dacf5389f11f656e25414
Gerrit-Change-Number: 785373
Gerrit-PatchSet: 3
Gerrit-Owner: Xqt <info@gno.de>
Gerrit-Reviewer: Xqt <info@gno.de>
Gerrit-Reviewer: jenkins-bot
Gerrit-MessageType: merged