1
+ from __future__ import annotations
2
+
1
3
from pathlib import Path
2
4
3
5
from docutils import nodes
@@ -14,21 +16,20 @@ class PEPContents(transforms.Transform):
14
16
def apply (self ) -> None :
15
17
if not Path (self .document ["source" ]).match ("pep-*" ):
16
18
return # not a PEP file, exit early
17
-
18
19
# Create the contents placeholder section
19
- title = nodes .title ("" , "Contents" )
20
- contents_topic = nodes .topic ("" , title , classes = [ "contents" ] )
20
+ title = nodes .title ("" , "" , nodes . Text ( " Contents") )
21
+ contents_section = nodes .section ("" , title )
21
22
if not self .document .has_name ("contents" ):
22
- contents_topic ["names" ].append ("contents" )
23
- self .document .note_implicit_target (contents_topic )
23
+ contents_section ["names" ].append ("contents" )
24
+ self .document .note_implicit_target (contents_section )
24
25
25
26
# Add a table of contents builder
26
27
pending = nodes .pending (Contents )
27
- contents_topic += pending
28
+ contents_section += pending
28
29
self .document .note_pending (pending )
29
30
30
31
# Insert the toc after title and PEP headers
31
- self .document .children [0 ].insert (2 , contents_topic )
32
+ self .document .children [0 ].insert (2 , contents_section )
32
33
33
34
# Add a horizontal rule before contents
34
35
transition = nodes .transition ()
@@ -37,27 +38,42 @@ def apply(self) -> None:
37
38
38
39
class Contents (parts .Contents ):
39
40
"""Build Table of Contents from document."""
40
- def __init__ (self , document , startnode = None ):
41
+ def __init__ (self , document : nodes . document , startnode : nodes . Node | None = None ):
41
42
super ().__init__ (document , startnode )
42
43
43
44
# used in parts.Contents.build_contents
44
45
self .toc_id = None
45
46
self .backlinks = None
46
47
47
48
def apply (self ) -> None :
48
- # used in parts.Contents.build_contents
49
- self .toc_id = self .startnode .parent ["ids" ][0 ]
50
- self .backlinks = self .document .settings .toc_backlinks
51
-
52
- # let the writer (or output software) build the contents list?
53
- if getattr (self .document .settings , "use_latex_toc" , False ):
54
- # move customisation settings to the parent node
55
- self .startnode .parent .attributes .update (self .startnode .details )
56
- self .startnode .parent .remove (self .startnode )
49
+ contents = self .build_contents (self .document [0 ][4 :]) # skip PEP title, headers, <hr/>, and contents
50
+ if contents :
51
+ self .startnode .replace_self (contents )
57
52
else :
58
- contents = self .build_contents (self .document [0 ])
59
- if contents :
60
- self .startnode .replace_self (contents )
61
- else :
62
- # if no contents, remove the empty placeholder
63
- self .startnode .parent .parent .remove (self .startnode .parent )
53
+ # if no contents, remove the empty placeholder
54
+ self .startnode .parent .parent .remove (self .startnode .parent )
55
+
56
+ def build_contents (self , node : nodes .Node | list [nodes .Node ], _level : None = None ):
57
+ entries = []
58
+ children = getattr (node , "children" , node )
59
+
60
+ for section in children :
61
+ if not isinstance (section , nodes .section ):
62
+ continue
63
+
64
+ title = section [0 ]
65
+
66
+ # remove all pre-existing hyperlinks in the title (e.g. PEP references)
67
+ while (link_node := title .next_node (nodes .reference )) is not None :
68
+ link_node .replace_self (link_node [0 ])
69
+ ref_id = section ['ids' ][0 ]
70
+ title ["refid" ] = ref_id # Add a link to self
71
+ entry_text = self .copy_and_filter (title )
72
+ reference = nodes .reference ("" , "" , refid = ref_id , * entry_text )
73
+ item = nodes .list_item ("" , nodes .paragraph ("" , "" , reference ))
74
+
75
+ item += self .build_contents (section ) # recurse to add sub-sections
76
+ entries .append (item )
77
+ if entries :
78
+ return nodes .bullet_list ('' , * entries )
79
+ return []
0 commit comments