Инструмент для автоматического контроля стиля docstring в соответствии с PEP257

Такие инструменты, как pep8, могут проверять стиль исходного кода, но они не проверяют, не установлены ли docstrings в соответствии с pep257, pep287. Существуют ли такие инструменты?

Обновление

Я решил реализовать такой инструмент статического анализа самостоятельно, см.

https://github.com/GreenSteam/pep257

В настоящий момент распространяется большинство pep257. На дизайн в значительной степени повлиял упомянутый pep8 инструмент.

Ответ 1

Я не знаю какого-либо инструмента статического анализа для строк python doc. Я фактически начал строить один вскоре после начала работы с PyLint, но быстро сдался.

PyLint имеет плагиновую систему, и плагин doc-строки можно сделать, если вы хотите включить работу, чтобы сделать исполняемые файлы PEP.

Плагины PyLint называются шашками и представлены в двух формах: те, которые работают с исходным файлом как текстовый документ, и те, которые работают с ним как AST. Я сделал попытку, начиная с АСТ. Возможно, это была ошибка в ретроспективе.

Вот что у меня было:

class DocStringChecker(BaseChecker):
    """
    PyLint AST based checker to eval compliance with PEP 257-ish conventions.
    """
    __implements__ = IASTNGChecker

    name = 'doc_string_checker'
    priority = -1
    msgs = {'W9001': ('One line doc string on >1 lines',
                     ('Used when a short doc string is on multiple lines')),
            'W9002': ('Doc string does not end with "." period',
                     ('Used when a doc string does not end with a period')),
            'W9003': ('Not all args mentioned in doc string',
                     ('Used when not all arguments are in the doc string ')),
            'W9004': ('triple quotes',
                     ('Used when doc string does not use """')),
           }
    options = ()

    def visit_function(self, node):
        if node.doc: self._check_doc_string(node)

    def visit_module(self, node):
        if node.doc: self._check_doc_string(node)

    def visit_class(self, node):
        if node.doc: self._check_doc_string(node)

    def _check_doc_string(self, node):
        self.one_line_one_one_line(node)
        self.has_period(node)
        self.all_args_in_doc(node)

    def one_line_one_one_line(self,node):
        """One line docs (len < 80) are on one line"""
        doc = node.doc
        if len(doc) > 80: return True
        elif sum(doc.find(nl) for nl in ('\n', '\r', '\n\r')) == -3: return True
        else:
            self.add_message('W9001', node=node, line=node.tolineno)

    def has_period(self,node):
        """Doc ends in a period"""
        if not node.doc.strip().endswith('.'):
            self.add_message('W9002', node=node, line=node.tolineno)

    def all_args_in_doc(self,node):
        """All function arguments are mentioned in doc"""
        if not hasattr(node, 'argnames'): return True
        for arg in node.argnames:
            if arg != 'self' and arg in node.doc: continue
            else: break
        else: return True
        self.add_message('W9003', node=node, line=node.tolineno)

    def triple_quotes(self,node): #This would need a raw checker to work b/c the AST doesn't use """
        """Doc string uses tripple quotes"""
        doc = node.doc.strip()
        if doc.endswith('"""') and doc.startswith('"""'): return True
        else: self.add_message('W9004', node=node, line=node.tolineno)


def register(linter):
    """required method to auto register this checker"""
    linter.register_checker(DocStringChecker(linter))

Как я помню, у этой системы нет отличных документов (которые могли измениться в прошлом году). Это по крайней мере дает вам возможность начать взлом/действительно простой код вместо документов.

Ответ 2

Я не думаю, что он валидирует против любых PEP, но Epydoc будет проверять, чтобы все указанные параметры и объекты в docstrmap действительные параметры и объекты.