docs/qapidoc: add intermediate output debugger

Add debugging output for the qapidoc transmogrifier - setting DEBUG=1
will produce .ir files (one for each qapidoc directive) that write the
generated rst file to disk to allow for easy debugging and verification
of the generated document.

Signed-off-by: John Snow <jsnow@redhat.com>
Message-ID: <20250311034303.75779-57-jsnow@redhat.com>
Acked-by: Markus Armbruster <armbru@redhat.com>
Signed-off-by: Markus Armbruster <armbru@redhat.com>
This commit is contained in:
John Snow 2025-03-10 23:42:54 -04:00 committed by Markus Armbruster
parent c9b6f98803
commit 7f6f24aaf5

View file

@ -37,7 +37,7 @@ import sys
from typing import TYPE_CHECKING from typing import TYPE_CHECKING
from docutils import nodes from docutils import nodes
from docutils.parsers.rst import Directive, directives from docutils.parsers.rst import directives
from docutils.statemachine import StringList from docutils.statemachine import StringList
from qapi.error import QAPIError from qapi.error import QAPIError
from qapi.parser import QAPIDoc from qapi.parser import QAPIDoc
@ -60,7 +60,7 @@ from sphinx import addnodes
from sphinx.directives.code import CodeBlock from sphinx.directives.code import CodeBlock
from sphinx.errors import ExtensionError from sphinx.errors import ExtensionError
from sphinx.util import logging from sphinx.util import logging
from sphinx.util.docutils import switch_source_input from sphinx.util.docutils import SphinxDirective, switch_source_input
from sphinx.util.nodes import nested_parse_with_titles from sphinx.util.nodes import nested_parse_with_titles
@ -414,7 +414,7 @@ class QAPISchemaGenDepVisitor(QAPISchemaVisitor):
super().visit_module(name) super().visit_module(name)
class NestedDirective(Directive): class NestedDirective(SphinxDirective):
def run(self) -> Sequence[nodes.Node]: def run(self) -> Sequence[nodes.Node]:
raise NotImplementedError raise NotImplementedError
@ -483,10 +483,43 @@ class QAPIDocDirective(NestedDirective):
node.document = self.state.document node.document = self.state.document
self.state.nested_parse(content, 0, contentnode) self.state.nested_parse(content, 0, contentnode)
logger.info("Transmogrifier's nested parse completed.") logger.info("Transmogrifier's nested parse completed.")
sys.stdout.flush()
if self.env.app.verbosity >= 2 or os.environ.get("DEBUG"):
argname = "_".join(Path(self.arguments[0]).parts)
name = Path(argname).stem + ".ir"
self.write_intermediate(content, name)
sys.stdout.flush()
return contentnode return contentnode
def write_intermediate(self, content: StringList, filename: str) -> None:
logger.info(
"writing intermediate rST for '%s' to '%s'",
self.arguments[0],
filename,
)
srctree = Path(self.env.app.config.qapidoc_srctree).resolve()
outlines = []
lcol_width = 0
for i, line in enumerate(content):
src, lineno = content.info(i)
srcpath = Path(src).resolve()
srcpath = srcpath.relative_to(srctree)
lcol = f"{srcpath}:{lineno:04d}"
lcol_width = max(lcol_width, len(lcol))
outlines.append((lcol, line))
with open(filename, "w", encoding="UTF-8") as outfile:
for lcol, rcol in outlines:
outfile.write(lcol.rjust(lcol_width))
outfile.write(" |")
if rcol:
outfile.write(f" {rcol}")
outfile.write("\n")
def legacy(self, schema: QAPISchema) -> nodes.Element: def legacy(self, schema: QAPISchema) -> nodes.Element:
vis = QAPISchemaGenRSTVisitor(self) vis = QAPISchemaGenRSTVisitor(self)
vis.visit_begin(schema) vis.visit_begin(schema)