Skip to content

Commit 7dc8a48

Browse files
committed
MNT: Ensure all types from matplotlib.typing are documented
1 parent e6cab33 commit 7dc8a48

File tree

3 files changed

+105
-3
lines changed

3 files changed

+105
-3
lines changed

doc/api/typing_api.rst

Lines changed: 31 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,11 @@
66
:no-members:
77
:no-undoc-members:
88

9+
.. types are written out explicitly as `.. autodata::` directives, so that we
10+
can meaningfully group them in sections.
11+
test_typing.py::test_typing_aliases_documented ensures that the documented
12+
types are in sync with the actual types defined in matplotlib.typing.
13+
914
Color
1015
=====
1116

@@ -16,19 +21,42 @@ Color
1621
.. autodata:: matplotlib.typing.RGBColourType
1722
.. autodata:: matplotlib.typing.RGBAColourType
1823

19-
Styles
20-
======
24+
Artist styles
25+
=============
2126

2227
.. autodata:: matplotlib.typing.LineStyleType
2328
.. autodata:: matplotlib.typing.DrawStyleType
2429
.. autodata:: matplotlib.typing.MarkEveryType
30+
.. autodata:: matplotlib.typing.MarkerType
2531
.. autodata:: matplotlib.typing.FillStyleType
2632
.. autodata:: matplotlib.typing.CapStyleType
2733
.. autodata:: matplotlib.typing.JoinStyleType
2834

35+
Events
36+
======
37+
38+
.. autodata:: matplotlib.typing.MouseEventType
39+
.. autodata:: matplotlib.typing.KeyEventType
40+
.. autodata:: matplotlib.typing.DrawEventType
41+
.. autodata:: matplotlib.typing.PickEventType
42+
.. autodata:: matplotlib.typing.ResizeEventType
43+
.. autodata:: matplotlib.typing.CloseEventType
44+
.. autodata:: matplotlib.typing.EventType
45+
46+
rcParams and stylesheets
47+
========================
48+
.. autodata:: matplotlib.typing.RcKeyType
49+
.. autodata:: matplotlib.typing.RcGroupKeyType
50+
.. autodata:: matplotlib.typing.RcStyleType
51+
2952
Other types
3053
===========
3154

3255
.. autodata:: matplotlib.typing.CoordsType
33-
.. autodata:: matplotlib.typing.RcStyleType
56+
.. autodata:: matplotlib.typing.LegendLocType
57+
.. autodata:: matplotlib.typing.LogLevel
3458
.. autodata:: matplotlib.typing.HashableList
59+
60+
61+
.. intentionally undocumented types (one type per row)
62+
CoordsBaseType

lib/matplotlib/tests/test_typing.py

Lines changed: 64 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,70 @@ def test_cm_stub_matches_runtime_colormaps():
3434
assert runtime_cmaps == stubbed_cmaps
3535

3636

37+
def test_typing_aliases_documented():
38+
"""Every public type in typing.py is documented or intentionally undocumented."""
39+
import ast
40+
41+
typing_py_path = Path(__file__).parent.parent / "typing.py"
42+
assert typing_py_path.exists(), f"{typing_py_path} does not exist"
43+
tree = ast.parse(typing_py_path.read_text(encoding="utf-8"))
44+
45+
# Collect all public module-level assignment names (both annotated and plain).
46+
defined_types = set()
47+
for node in ast.iter_child_nodes(tree):
48+
if isinstance(node, ast.AnnAssign) and isinstance(node.target, ast.Name):
49+
name = node.target.id
50+
elif isinstance(node, ast.Assign) and len(node.targets) == 1:
51+
target = node.targets[0]
52+
name = target.id if isinstance(target, ast.Name) else None
53+
else:
54+
continue
55+
if name is not None and not name.startswith("_"):
56+
defined_types.add(name)
57+
58+
assert defined_types, "No type definitions found in typing.py"
59+
60+
rst_path = (
61+
Path(__file__).parent.parent.parent.parent / "doc" / "api" / "typing_api.rst"
62+
)
63+
assert rst_path.exists(), f"{rst_path} does not exist"
64+
rst_content = rst_path.read_text(encoding="utf-8")
65+
66+
# Collect documented ``.. autodata::`` entries.
67+
documented = set(
68+
re.findall(
69+
r"^\.\.\s+autodata::\s+matplotlib\.typing\.(\w+)",
70+
rst_content,
71+
re.MULTILINE,
72+
)
73+
)
74+
assert documented, "No autodata entries found in typing_api.rst"
75+
76+
# Collect types listed under the comment
77+
# ".. intentionally undocumented types (one type per row)".
78+
# Each type must be indented and an empty line ends the section.
79+
intentionally_undocumented = set()
80+
marker = ".. intentionally undocumented types (one type per row)"
81+
lines_following_marker = rst_content.split(marker, 1)[1].splitlines()[1:]
82+
for line in lines_following_marker:
83+
if not line or not line[0].isspace():
84+
break
85+
intentionally_undocumented.add(line.strip())
86+
87+
accounted_for = documented | intentionally_undocumented
88+
89+
missing = defined_types - accounted_for
90+
assert not missing, (
91+
f"Types defined in typing.py but not in typing_api.rst "
92+
f"(document them or add to 'intentionally undocumented types'): {missing}"
93+
)
94+
95+
extra = accounted_for - defined_types
96+
assert not extra, (
97+
f"Types listed in typing_api.rst but not defined in typing.py: {extra}"
98+
)
99+
100+
37101
def test_rcparam_stubs():
38102
runtime_rc_keys = {
39103
name for name in plt.rcParamsDefault.keys()

lib/matplotlib/typing.py

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -116,6 +116,10 @@
116116
pathlib.Path |
117117
Sequence[str | pathlib.Path | dict[str, Any]]
118118
)
119+
"""
120+
Valid specifiers for styles as used in `matplotlib.style.use` and
121+
`matplotlib.style.context`.
122+
"""
119123

120124
_HT = TypeVar("_HT", bound=Hashable)
121125
HashableList: TypeAlias = list[_HT | "HashableList[_HT]"]
@@ -170,6 +174,12 @@
170174
tuple[float, float] |
171175
int
172176
)
177+
"""
178+
Supported location specifiers for legends.
179+
180+
This is a superset of permissible entries. "best" is only applicable to Axes legends.
181+
All the "outside ..." locations are only applicable to figure legends.
182+
"""
173183

174184
RcKeyType: TypeAlias = Literal[
175185
"agg.path.chunksize",

0 commit comments

Comments
 (0)