From 6d24579f400c735c1c999fdc602ebc9316b5ced8 Mon Sep 17 00:00:00 2001 From: Takeshi KOMIYA Date: Sun, 29 Nov 2020 02:22:29 +0900 Subject: [PATCH] Fix #8352: std domain: Failed to parse an option that starts with bracket --- CHANGES | 1 + sphinx/domains/std.py | 7 ++++++- tests/test_domain_std.py | 22 ++++++++++++++++++++++ 3 files changed, 29 insertions(+), 1 deletion(-) diff --git a/CHANGES b/CHANGES index 2aea31967..e1b2af1d7 100644 --- a/CHANGES +++ b/CHANGES @@ -70,6 +70,7 @@ Bugs fixed * #8131: linkcheck: Use GET when HEAD requests cause Too Many Redirects, to accommodate infinite redirect loops on HEAD * #8437: Makefile: ``make clean`` with empty BUILDDIR is dangerous +* #8352: std domain: Failed to parse an option that starts with bracket Testing -------- diff --git a/sphinx/domains/std.py b/sphinx/domains/std.py index c87217c56..e4285b1ae 100644 --- a/sphinx/domains/std.py +++ b/sphinx/domains/std.py @@ -43,7 +43,7 @@ logger = logging.getLogger(__name__) # RE for option descriptions -option_desc_re = re.compile(r'((?:/|--|-|\+)?[^\s=[]+)(=?\s*.*)') +option_desc_re = re.compile(r'((?:/|--|-|\+)?[^\s=]+)(=?\s*.*)') # RE for grammar tokens token_re = re.compile(r'`(\w+)`', re.U) @@ -197,6 +197,11 @@ class Cmdoption(ObjectDescription): location=signode) continue optname, args = m.groups() + if optname.endswith('[') and args.endswith(']'): + # optional value surrounded by brackets (ex. foo[=bar]) + optname = optname[:-1] + args = '[' + args + if count: signode += addnodes.desc_addname(', ', ', ') signode += addnodes.desc_name(optname, optname) diff --git a/tests/test_domain_std.py b/tests/test_domain_std.py index 7ee1d6c07..1b3682ee6 100644 --- a/tests/test_domain_std.py +++ b/tests/test_domain_std.py @@ -91,6 +91,28 @@ def test_get_full_qualified_name(): assert domain.get_full_qualified_name(node) == 'ls.-l' +def test_cmd_option_with_optional_value(app): + text = ".. option:: -j[=N]" + doctree = restructuredtext.parse(app, text) + assert_node(doctree, (index, + [desc, ([desc_signature, ([desc_name, '-j'], + [desc_addname, '[=N]'])], + [desc_content, ()])])) + objects = list(app.env.get_domain("std").get_objects()) + assert ('-j', '-j', 'cmdoption', 'index', 'cmdoption-j', 1) in objects + + +def test_cmd_option_starting_with_bracket(app): + text = ".. option:: [enable=]PATTERN" + doctree = restructuredtext.parse(app, text) + assert_node(doctree, (index, + [desc, ([desc_signature, ([desc_name, '[enable'], + [desc_addname, '=]PATTERN'])], + [desc_content, ()])])) + objects = list(app.env.get_domain("std").get_objects()) + assert ('[enable', '[enable', 'cmdoption', 'index', 'cmdoption-arg-enable', 1) in objects + + def test_glossary(app): text = (".. glossary::\n" "\n"