diff --git a/changelog.d/1147.doc.rst b/changelog.d/1147.doc.rst new file mode 100644 index 00000000..645a2a03 --- /dev/null +++ b/changelog.d/1147.doc.rst @@ -0,0 +1 @@ +Fix sphinx linkcheck errors diff --git a/docs/_intersphinx/README.md b/docs/_intersphinx/README.md new file mode 100644 index 00000000..9577cd42 --- /dev/null +++ b/docs/_intersphinx/README.md @@ -0,0 +1,82 @@ +# Creating a Custom Intersphinx Mapping + +Copied from [exhale documentation.](https://github.com/svenevs/exhale/blob/master/docs/_intersphinx/README.md) + +## The Issue + +The BeautifulSoup intersphinx mapping does not work; see [bug here][bug]. + +[bug]: https://bugs.launchpad.net/beautifulsoup/+bug/1453370 + +So we'll just do it manually. + +## The Tool + +Use the tool `sphobjinv` to do this (`pip install sphobjinv`). + +- [Explanation of syntax][syntax]. + +[syntax]: https://sphinx-objectsinv-encoderdecoder.readthedocs.io/en/latest/syntax.html + +## How to Reproduce + +1. Downloaded original objects.inv from bs4 docs + + ```console + $ curl -O https://www.crummy.com/software/BeautifulSoup/bs4/doc/objects.inv + $ mv objects.inv bs4_objects.inv + ``` + +2. Converted that bad boy to human readable (the file `bs4_objects.txt`). + + ```console + $ sphobjinv convert plain bs4_objects.inv bs4_objects.txt + ``` + +3. Any time I have a class I want to add a reference for, just add that line to + `bs4_objects.txt`. Recall that there is a specific [syntax][syntax] associated + with these files. + +4. When you add a new line, simply run (assuming you are in this directory) + + ```console + $ sphobjinv convert zlib bs4_objects.txt bs4_objects.inv + ``` + +5. Re-run sphinx, usually you need to clean it for the doctree index to be rebuilt. + + ```console + $ make clean html + ``` + +## Note + +These changes apply because we have **2** things in `conf.py`: + +1. In the `extensions` list, we have `"sphinx.ext.intersphinx"`. +2. We have configured our intersphinx mapping to point to here (as opposed to the + one being hosted online): + + ```py + intersphinx_mapping = { + 'bs4': ('https://www.crummy.com/software/BeautifulSoup/bs4/doc/', "_intersphinx/bs4_objects.inv") + } + ``` + +## In the Documentation + +So now we can do something like + +```rst +- See :class:`bs4.BeautifulSoup` +- See :meth:`bs4.BeautifulSoup.get_text` +- See :class:`bs4.element.Tag` +``` + +because we added the following line to our `bs4_objects.txt`: + +``` +bs4.BeautifulSoup py:class 1 index.html#beautifulsoup - +bs4.BeautifulSoup.get_text py:method 1 index.html#get-text - +bs4.element.Tag py:class 1 index.html#tag - +``` diff --git a/docs/_intersphinx/importlib_metadata_objects.inv b/docs/_intersphinx/importlib_metadata_objects.inv new file mode 100644 index 00000000..66d334be Binary files /dev/null and b/docs/_intersphinx/importlib_metadata_objects.inv differ diff --git a/docs/_intersphinx/importlib_metadata_objects.txt b/docs/_intersphinx/importlib_metadata_objects.txt new file mode 100644 index 00000000..99ecc24d --- /dev/null +++ b/docs/_intersphinx/importlib_metadata_objects.txt @@ -0,0 +1,6 @@ +# Sphinx inventory version 2 +# Project: importlib_metadata +# Version: 8.0.1.dev0+gf390168.d20240623 +# From https://github.com/svenevs/exhale/tree/master/docs/_intersphinx +# The remainder of this file is compressed using zlib. +importlib.metadata.EntryPoint py:class 1 library/importlib.metadata.html#entry-points - diff --git a/docs/api/cache.rst b/docs/api/cache.rst index c446b64e..039cc49a 100644 --- a/docs/api/cache.rst +++ b/docs/api/cache.rst @@ -18,4 +18,5 @@ Cache Refer to dogpile.cache's `region configuration documentation -`_ to see how to configure the region +`_ +to see how to configure the region. diff --git a/docs/conf.py b/docs/conf.py index 4fd55708..42da56a9 100644 --- a/docs/conf.py +++ b/docs/conf.py @@ -39,6 +39,7 @@ 'sphinx.ext.intersphinx', 'sphinx.ext.viewcode', 'sphinxcontrib.programoutput', + 'sphinx_autodoc_typehints', ] # Add any paths that contain templates here, relative to this directory. @@ -307,10 +308,22 @@ 'dogpilecache': ('https://dogpilecache.sqlalchemy.org/en/latest', None), 'stevedore': ('https://docs.openstack.org/stevedore/latest', None), 'click': ('https://click.palletsprojects.com/en/latest/', None), + 'requests': ('https://docs.python-requests.org/en/latest/', None), + 'sympy': ('https://docs.sympy.org/latest/', None), + 'bs4': ('https://www.crummy.com/software/BeautifulSoup/bs4/doc/', None), + 'importlib.metadata': ('https://docs.python.org/3/', '_intersphinx/importlib_metadata_objects.inv'), } -# -- Options for autodoc ------------------------------------------------------- +# -- Options for autodoc ----------------------------------------------------- autodoc_member_order = 'bysource' autodoc_default_flags = ['members'] + + +# -- Options for sphinx-autodoc-typehints ------------------------------------ +# https://github.com/tox-dev/sphinx-autodoc-typehints + +always_use_bars_union = True + +set_type_checking_flag = False diff --git a/pyproject.toml b/pyproject.toml index cc0587e9..880d8d95 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -57,6 +57,7 @@ docs = [ "sphinx", "sphinx_rtd_theme", "sphinxcontrib-programoutput", + "sphinx_autodoc_typehints", "towncrier", ] test = [ diff --git a/subliminal/extensions.py b/subliminal/extensions.py index 949b5695..c7e9a725 100644 --- a/subliminal/extensions.py +++ b/subliminal/extensions.py @@ -13,7 +13,7 @@ class RegistrableExtensionManager(ExtensionManager): - """:class:`stevedore.extensions.ExtensionManager` with support for registration. + """:class:`stevedore.extension.ExtensionManager` with support for registration. It allows loading of internal extensions without setup and registering/unregistering additional extensions. @@ -23,9 +23,9 @@ class RegistrableExtensionManager(ExtensionManager): * Internal extensions * Registered extensions - :param str namespace: namespace argument for :class:`stevedore.extensions.ExtensionManager`. + :param str namespace: namespace argument for :class:`stevedore.extension.ExtensionManager`. :param list internal_extensions: internal extensions to use with entry point syntax. - :param kwargs: additional parameters for the :class:`stevedore.extensions.ExtensionManager` constructor. + :param kwargs: additional parameters for the :class:`stevedore.extension.ExtensionManager` constructor. """ diff --git a/subliminal/providers/__init__.py b/subliminal/providers/__init__.py index eb6c88bf..eab25359 100644 --- a/subliminal/providers/__init__.py +++ b/subliminal/providers/__init__.py @@ -1,12 +1,9 @@ """ Providers list and download subtitles for a :class:`~subliminal.video.Video` object. -A Provider is a ContextManager with :meth:`~subliminal.Provider.__enter__` and -:meth:`~subliminal.Provider.__exit__` -methods and two public methods, -:py:meth:`~subliminal.Provider.list_subtitles(video, languages)` and -:py:meth:`~subliminal.Provider.download_subtitle(subtitle)`. - +A Provider is a ContextManager with ``__enter__`` and ``__exit__`` methods and +two public methods: :meth:`~subliminal.providers.Provider.list_subtitles` and +:meth:`~subliminal.providers.Provider.download_subtitle`. """ from __future__ import annotations @@ -16,6 +13,8 @@ from typing import TYPE_CHECKING, Any, ClassVar, Generic, TypeVar from xmlrpc.client import SafeTransport +# Do not put babelfish in a TYPE_CHECKING block for intersphinx to work properly +from babelfish import Language # type: ignore[import-untyped] # noqa: TCH002 from bs4 import BeautifulSoup, FeatureNotFound from requests import adapters from urllib3 import poolmanager # type: ignore[import-untyped] @@ -29,9 +28,6 @@ from http.client import HTTPSConnection from types import TracebackType from typing import Self - from xmlrpc.client import _HostType - - from babelfish import Language # type: ignore[import-untyped] logger = logging.getLogger(__name__) @@ -54,7 +50,7 @@ def init_poolmanager(self, connections: int, maxsize: int, block: bool = False, class TimeoutSafeTransport(SafeTransport): - """Timeout support for :class:`~xmlrpc.client.SafeTransport`.""" + """Timeout support for :library/xmlrpc.client:class:`~xmlrpc.client.SafeTransport`.""" timeout: float | None @@ -62,13 +58,13 @@ def __init__(self, timeout: float | None, *args: Any, **kwargs: Any) -> None: super().__init__(*args, **kwargs) self.timeout = timeout - def make_connection(self, host: _HostType) -> HTTPSConnection: + def make_connection(self, host: Any) -> HTTPSConnection: """Make connection to host. :param host: the connection host. - :type host: :class:`~xmlrpc.client._HostType` + :type host: ``xmlrpc.client._HostType`` :return: the HTTPS connection. - :rtype: :class:`~http.client import HTTPSConnection` + :rtype: :library/http.client:class:`~http.client.HTTPSConnection` """ c = SafeTransport.make_connection(self, host) diff --git a/subliminal/utils.py b/subliminal/utils.py index bf343fc4..3afb26bd 100644 --- a/subliminal/utils.py +++ b/subliminal/utils.py @@ -148,7 +148,7 @@ def handle_exception(e: Exception, msg: str) -> None: Exception traceback is only logged for specific cases. - :param exception e: The exception to handle. + :param Exception e: The exception to handle. :param str msg: The message to log. """ if isinstance(e, (requests.Timeout, socket.timeout)): @@ -174,7 +174,7 @@ def is_iterable(obj: Any) -> TypeGuard[Iterable]: def ensure_list(value: T | Sequence[T] | None) -> list[T]: """Ensure to return a list of values. - From :func:`rebulk.loose.ensure_list`. + From ``rebulk.loose.ensure_list``. """ if value is None: return []