Source code for coalib.settings.DocstringMetadata
import inspect
from collections import OrderedDict
from coalib.misc.Enum import enum
[docs]class DocstringMetadata:
_ParseMode = enum('DESCRIPTION', 'PARAM', 'RETVAL')
def __init__(self, desc, param_dict, retval_desc):
"""
Represents a docstring of a python class or function.
:param desc: A description as string.
:param param_dict: A dictionary containing parameter names as key and
their description as value. To preserve the order,
use OrderedDict.
:param retval_desc: A string describing the return value.
"""
self.desc = desc
self.param_dict = param_dict
self.retval_desc = retval_desc
@classmethod
[docs] def from_docstring(cls, docstring):
"""
Parses a python docstring. Usable attributes are:
:param
@param
:return
@return
"""
lines = inspect.cleandoc(docstring).split('\n')
parse_mode = cls._ParseMode.DESCRIPTION
cur_param = ''
desc = ''
param_dict = OrderedDict()
retval_desc = ''
for line in lines:
line = line.strip()
if line.startswith(':param ') or line.startswith('@param '):
parse_mode = cls._ParseMode.PARAM
splitted = line[7:].split(':', 1)
cur_param = splitted[0]
param_dict[cur_param] = splitted[1].strip()
continue
if line.startswith(':return: ') or line.startswith('@return: '):
parse_mode = cls._ParseMode.RETVAL
retval_desc = line[9:].strip()
continue
def concat_doc_parts(old: str, new: str):
if new != '' and not old.endswith('\n'):
return (old + ' ' + new).strip()
return old + (new if new != '' else '\n')
if parse_mode == cls._ParseMode.RETVAL:
retval_desc = concat_doc_parts(retval_desc, line)
elif parse_mode == cls._ParseMode.PARAM:
param_dict[cur_param] = concat_doc_parts(param_dict[cur_param],
line)
else:
desc = concat_doc_parts(desc, line)
return (cls(desc=desc.strip(),
param_dict=param_dict,
retval_desc=retval_desc.strip()))
def __str__(self):
return str(self.desc)