doc: lot of fixes to make cython class look like python documentation. Closes #17

This commit is contained in:
Mathieu Virbel 2011-06-28 12:06:26 +02:00
parent f06deb3d43
commit 3e2fc4c745
2 changed files with 76 additions and 17 deletions

View File

@ -11,6 +11,7 @@ ignore_list = (
'kivy.graphics.buffer',
'kivy.graphics.vbo',
'kivy.graphics.vertex',
'kivy.lib.osc'
)
import os
@ -127,10 +128,22 @@ Examples
template_examples_ref = \
'''# :ref:`Jump directly to Examples <example-reference%d>`'''
def extract_summary_line(doc):
if doc is None:
return
for line in doc.split('\n'):
line = line.strip()
# don't take empty line
if len(line) < 1:
continue
# ref mark
if line.startswith('.. _'):
continue
return line
for package in packages:
try:
summary = [x for x in sys.modules[package].__doc__.split("\n") if len(x) > 1][0]
except:
summary = extract_summary_line(sys.modules[package].__doc__)
if summary is None:
summary = 'NO DOCUMENTATION (package %s)' % package
t = template.replace('$SUMMARY', summary)
t = t.replace('$PACKAGE', package)
@ -161,10 +174,9 @@ m = modules.keys()
m.sort()
refid = 0
for module in m:
try:
summary = [x for x in sys.modules[module].__doc__.split("\n") if len(x) > 1][0]
except:
summary = 'NO DOCUMENTATION (module %s)' % module
summary = extract_summary_line(sys.modules[module].__doc__)
if summary is None:
summary = 'NO DOCUMENTATION (module %s)' % package
# search examples
example_output = []

View File

@ -2,6 +2,16 @@
Extension for enhancing sphinx documentation generation for cython module
'''
import re
import types
from sphinx.ext.autodoc import MethodDocumenter
class CythonMethodDocumenter(MethodDocumenter):
# XXX i don't understand the impact of having a priority more than the
# attribute or instance method but the things is, if it's a cython module,
# the attribute will be prefer over method.
priority = 12
def is_cython_extension(what, obj):
# try to check if the first line of the doc is a signature
doc = obj.__doc__
@ -11,20 +21,30 @@ def is_cython_extension(what, obj):
if not len(doc):
return False
doc = doc[0]
if not '(' in doc or doc[-1] != ')':
return False
# check more if it's an extension
if what == 'attribute' and hasattr(obj, '__objclass__') and \
hasattr(obj.__objclass__, '__pyx_vtable__'):
# test for cython cpdef
if what in ('attribute', 'method') and hasattr(obj, '__objclass__'):
if not re.match('^([a-zA-Z_][a-zA-Z0-9_]*)\.([a-zA-Z_][a-zA-Z0-9_]*)\((.*)\)', doc):
return False
return True
# test for cython class
if what == 'class' and hasattr(obj, '__pyx_vtable__'):
if not re.match('^([a-zA-Z_][a-zA-Z0-9_]*)\((.*)\)', doc):
return False
return True
# test for python method in cython class
if what == 'method' and obj.__class__ == types.BuiltinFunctionType:
if not re.match('^([a-zA-Z_][a-zA-Z0-9_]*)\((.*)\)', doc):
return False
return True
def callback_docstring(app, what, name, obj, options, lines):
if what == 'module':
# remove empty lines
while len(lines) and lines[0].strip() == '':
while len(lines):
line = lines[0].strip()
if not line.startswith('.. _') and line != '':
break
lines.pop(0)
# if we still have lines, remove the title
@ -37,13 +57,37 @@ def callback_docstring(app, what, name, obj, options, lines):
elif is_cython_extension(what, obj):
lines.pop(0)
for idx in xrange(len(lines)):
line = lines[idx]
if line.startswith(' '):
lines[idx] = line[4:]
line = lines.pop(0)
# trick to realign the first line to the second one.
# FIXME: fail if we finishing with ::
if line is not None and len(lines):
l = len(lines[0]) - len(lines[0].lstrip())
else:
l = 0
lines.insert(0, ' ' * l + line)
# calculate the minimum space available
min_space = 999
for line in lines:
if not line.strip():
continue
min_space = min(min_space, len(line) - len(line.lstrip()))
# remove that kind of space now.
if min_space > 0:
spaces = ' ' * min_space
for idx, line in enumerate(lines):
if not line.strip():
continue
if not line.startswith(spaces):
continue
lines[idx] = line[min_space:]
def callback_signature(app, what, name, obj, options, signature,
return_annotation):
# remove the first 'self' argument, because python autodoc don't
# add it for python method class. So do the same for cython class.
if is_cython_extension(what, obj):
try:
doc = obj.__doc__.split('\n').pop(0)
@ -51,10 +95,13 @@ def callback_signature(app, what, name, obj, options, signature,
doc = doc.replace('(self, ', '(')
doc = doc.replace('(self)', '( )')
return (doc, None)
except AttributeError:
pass
except IndexError:
pass
def setup(app):
app.add_autodocumenter(CythonMethodDocumenter)
app.connect('autodoc-process-docstring', callback_docstring)
app.connect('autodoc-process-signature', callback_signature)