Skip to content

Commit 8f3538f

Browse files
authored
sphinxdocs: fix rendering of args in directives with empty doc (bazel-contrib#2313)
This fixes a bug where tag-classes/functions that didn't have a doc string, but did have arguments/attributes, would render the args/attrs immediately after the directive line, which made them get interpreter as direction options (settings that apply to the overall directive) instead of doc fields nested within the directive (separate block-level elements that get rendered). To fix, update the code to ensure there's a newline between the directive line and subsequent arg/attr lines. Also adds tests for this.
1 parent 0e60058 commit 8f3538f

File tree

2 files changed

+69
-3
lines changed

2 files changed

+69
-3
lines changed

sphinxdocs/private/proto_to_markdown.py

Lines changed: 13 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -182,7 +182,7 @@ def _render_module_extension(self, mod_ext: stardoc_output_pb2.ModuleExtensionIn
182182
for tag in mod_ext.tag_class:
183183
tag_name = f"{mod_ext.extension_name}.{tag.tag_name}"
184184
tag_name = f"{tag.tag_name}"
185-
self._write(":::::{bzl:tag-class} ", tag_name, "\n\n")
185+
self._write(":::::{bzl:tag-class} ")
186186

187187
_sort_attributes_inplace(tag.attribute)
188188
self._render_signature(
@@ -192,7 +192,12 @@ def _render_module_extension(self, mod_ext: stardoc_output_pb2.ModuleExtensionIn
192192
get_default=lambda a: a.default_value,
193193
)
194194

195-
self._write(tag.doc_string.strip(), "\n\n")
195+
if doc_string := tag.doc_string.strip():
196+
self._write(doc_string, "\n\n")
197+
# Ensure a newline between the directive and the doc fields,
198+
# otherwise they get parsed as directive options instead.
199+
if not doc_string and tag.attribute:
200+
self.write("\n")
196201
self._render_attributes(tag.attribute)
197202
self._write(":::::\n")
198203
self._write("::::::\n")
@@ -292,10 +297,15 @@ def _render_func(self, func: stardoc_output_pb2.StarlarkFunctionInfo):
292297

293298
parameters = self._render_func_signature(func)
294299

295-
if doc_string := func.doc_string.strip():
300+
doc_string = func.doc_string.strip()
301+
if doc_string:
296302
self._write(doc_string, "\n\n")
297303

298304
if parameters:
305+
# Ensure a newline between the directive and the doc fields,
306+
# otherwise they get parsed as directive options instead.
307+
if not doc_string:
308+
self._write("\n")
299309
for param in parameters:
300310
self._write(f":arg {param.name}:\n")
301311
if param.default_value:

sphinxdocs/tests/proto_to_markdown/proto_to_markdown_test.py

Lines changed: 56 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -209,6 +209,62 @@ def test_render_typedefs(self):
209209
self.assertIn("\n::::::::::::{bzl:typedef} Carl.ns.Alpha\n", actual)
210210
self.assertIn("\n:::::::::::::{bzl:typedef} Zeta\n", actual)
211211

212+
def test_render_func_no_doc_with_args(self):
213+
proto_text = """
214+
file: "@repo//pkg:foo.bzl"
215+
func_info: {
216+
function_name: "func"
217+
parameter: {
218+
name: "param"
219+
doc_string: "param_doc"
220+
}
221+
}
222+
"""
223+
actual = self._render(proto_text)
224+
expected = """
225+
:::::::::::::{bzl:function} func(*param)
226+
227+
:arg param:
228+
param_doc
229+
230+
:::::::::::::
231+
"""
232+
self.assertIn(expected, actual)
233+
234+
def test_render_module_extension(self):
235+
proto_text = """
236+
file: "@repo//pkg:foo.bzl"
237+
module_extension_info: {
238+
extension_name: "bzlmod_ext"
239+
tag_class: {
240+
tag_name: "bzlmod_ext_tag_a"
241+
doc_string: "BZLMOD_EXT_TAG_A_DOC_STRING"
242+
attribute: {
243+
name: "attr1",
244+
doc_string: "attr1doc"
245+
type: STRING_LIST
246+
}
247+
}
248+
}
249+
"""
250+
actual = self._render(proto_text)
251+
expected = """
252+
:::::{bzl:tag-class} bzlmod_ext_tag_a(attr1)
253+
254+
BZLMOD_EXT_TAG_A_DOC_STRING
255+
256+
:attr attr1:
257+
{type}`list[str]`
258+
attr1doc
259+
:::{bzl:attr-info} Info
260+
:::
261+
262+
263+
:::::
264+
::::::
265+
"""
266+
self.assertIn(expected, actual)
267+
212268

213269
if __name__ == "__main__":
214270
absltest.main()

0 commit comments

Comments
 (0)