4 # Copyright (C) 2009 Google Inc.
6 # This program is free software; you can redistribute it and/or modify
7 # it under the terms of the GNU General Public License as published by
8 # the Free Software Foundation; either version 2 of the License, or
9 # (at your option) any later version.
11 # This program is distributed in the hope that it will be useful, but
12 # WITHOUT ANY WARRANTY; without even the implied warranty of
13 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 # General Public License for more details.
16 # You should have received a copy of the GNU General Public License
17 # along with this program; if not, write to the Free Software
18 # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
22 """Script for unittesting documentation"""
27 from ganeti import _autoconf
28 from ganeti import utils
29 from ganeti import cmdlib
30 from ganeti import build
31 from ganeti.rapi import connector
36 class TestDocs(unittest.TestCase):
37 """Documentation tests"""
40 def _ReadDocFile(filename):
41 return utils.ReadFile("%s/doc/%s" %
42 (testutils.GetSourceDir(), filename))
44 def testHookDocs(self):
45 """Check whether all hooks are documented.
48 hooksdoc = self._ReadDocFile("hooks.rst")
50 for name in dir(cmdlib):
51 obj = getattr(cmdlib, name)
53 if (isinstance(obj, type) and
54 issubclass(obj, cmdlib.LogicalUnit) and
55 hasattr(obj, "HPATH")):
56 self._CheckHook(name, obj, hooksdoc)
58 def _CheckHook(self, name, lucls, hooksdoc):
59 if lucls.HTYPE is None:
62 # TODO: Improve this test (e.g. find hooks documented but no longer
65 pattern = r"^:directory:\s*%s\s*$" % re.escape(lucls.HPATH)
67 self.assert_(re.findall(pattern, hooksdoc, re.M),
68 msg=("Missing documentation for hook %s/%s" %
69 (lucls.HTYPE, lucls.HPATH)))
72 def testRapiDocs(self):
73 """Check whether all RAPI resources are documented.
76 rapidoc = self._ReadDocFile("rapi.rst")
78 node_name = "[node_name]"
79 instance_name = "[instance_name]"
82 resources = connector.GetHandlers(re.escape(node_name),
83 re.escape(instance_name),
89 for line in rapidoc.splitlines():
90 if re.match(r"^\++$", line):
91 titles.append(prevline)
97 for key, handler in resources.iteritems():
99 if hasattr(key, "match"):
102 if (title.startswith("``") and
103 title.endswith("``") and
104 key.match(title[2:-2])):
109 # TODO: Find better way of identifying resource
110 undocumented.append(str(handler))
112 elif ("``%s``" % key) not in titles:
113 undocumented.append(key)
115 self.failIf(undocumented,
116 msg=("Missing RAPI resource documentation for %s" %
117 utils.CommaJoin(undocumented)))
120 class TestManpages(unittest.TestCase):
124 def _ReadManFile(name):
125 return utils.ReadFile("%s/man/%s.sgml" %
126 (testutils.GetSourceDir(), name))
129 def _LoadScript(name):
130 return build.LoadModule("scripts/%s" % name)
133 for script in _autoconf.GNT_SCRIPTS:
134 self._CheckManpage(script,
135 self._ReadManFile(script),
136 self._LoadScript(script).commands.keys())
138 def _CheckManpage(self, script, mantext, commands):
142 pattern = "<cmdsynopsis>\s*<command>%s</command>" % re.escape(cmd)
143 if not re.findall(pattern, mantext, re.S):
147 msg=("Manpage for '%s' missing documentation for %s" %
148 (script, utils.CommaJoin(missing))))
151 if __name__ == "__main__":
152 testutils.GanetiTestProgram()