]> git.ipfire.org Git - thirdparty/samba.git/commitdiff
python:getopt: hack to generate docbook stubs from --help
authorDouglas Bagnall <douglas.bagnall@catalyst.net.nz>
Thu, 27 Feb 2025 04:42:08 +0000 (17:42 +1300)
committerDouglas Bagnall <dbagnall@samba.org>
Wed, 12 Mar 2025 19:57:34 +0000 (19:57 +0000)
We have many many samba-tool subcommands that are not documented in
the manpage. Often the --help text is a good place to start, but doing
it entirely manually is VERY tedious.

This automates some of the process.

Signed-off-by: Douglas Bagnall <douglas.bagnall@catalyst.net.nz>
Reviewed-by: Rowland Penny <rpenny@samba.org>
python/samba/getopt.py

index b810e5ac797bd2112235d6a11e44a68a96252065..30ecb6c745a5b969a9478405ba555b02b7531c14 100644 (file)
@@ -171,6 +171,58 @@ class OptionParser(optparse.OptionParser):
 
         return super().check_values(values, args)
 
+    def format_help(self, formatter=None):
+        # if a magic environment variable is set, we print a docbook
+        # template to add to the samba-tool manpage. Otherwise, we do
+        # normal help.
+        if not os.getenv("SAMBATOOL_HELP_IS_XML"):
+            return super().format_help(formatter=None)
+
+        formatter = SambaDocBookFormatter(1, 9999, 999, True)
+        result = []
+        if self.usage:
+            result.append(self.get_usage() + "\n")
+        if self.description:
+            result.append(self.format_description(formatter) + "\n")
+        result.append("<variablelist>\n")
+        result.append(self.format_option_help(formatter))
+        result.append("</variablelist>\n")
+        result.append(self.format_epilog(formatter))
+        return "".join(result)
+
+
+class SambaDocBookFormatter(optparse.HelpFormatter):
+
+    def _indent(self, s):
+        return '\t' * self.current_indent + s
+
+    def format_usage(self, usage):
+        return self._indent(f"<constant>{usage}</constant>\n")
+
+    def format_heading(self, heading):
+        return self._indent(f"<!--{heading}-->\n")
+
+    def _format_text(self, text):
+        """
+        Format a paragraph of free-form text for inclusion in the
+        help output at the current indentation level.
+        """
+        return self._indent(f"<para>{text}</para>")
+
+    def format_option(self, option):
+        # we don't worry about width (man handles that),
+        # but we try to indent the xml a bit
+        indent = self._indent('  ')
+        result = [indent]
+        result.append('<varlistentry>\n')
+        opts = self.option_strings[option]
+        result.append(f"{indent}  <term>{opts}</term>\n")
+        if option.help:
+            help_text = self.expand_default(option)
+            result.append(f"{indent}  <listitem><para>{help_text}</para></listitem>\n")
+        result.append(f'{indent}</varlistentry>\n')
+        return "".join(result)
+
 
 class OptionGroup(optparse.OptionGroup):
     """Samba OptionGroup base class.