From 1347afdb2e02ef2cb8557978fa39f72930436128 Mon Sep 17 00:00:00 2001 From: Zach Smith Date: Wed, 25 Apr 2018 20:12:20 -0400 Subject: Resolve linter errors/minor cleanup --- pycco/__init__.py | 2 +- pycco/generate_index.py | 4 ++- pycco/main.py | 68 +++++++++++++++++++++++++++---------------------- tests/test_pycco.py | 17 +++++++++---- 4 files changed, 54 insertions(+), 37 deletions(-) diff --git a/pycco/__init__.py b/pycco/__init__.py index 7794314..042afa6 100644 --- a/pycco/__init__.py +++ b/pycco/__init__.py @@ -1,3 +1,3 @@ -from .main import * +from .main import * # noqa __all__ = ("process",) diff --git a/pycco/generate_index.py b/pycco/generate_index.py index ab0ead0..7652466 100644 --- a/pycco/generate_index.py +++ b/pycco/generate_index.py @@ -52,7 +52,9 @@ def generate_tree_html(tree): if 'entry' in subtree: html = u'
  • {}
  • '.format(subtree['entry']['relpath'], node) else: - html = u'
    {}
      {}
    '.format(node, generate_tree_html(subtree)) + html = u'
    {}
      {}
    '.format( + node, generate_tree_html(subtree) + ) items.append(html) diff --git a/pycco/main.py b/pycco/main.py index f0d4fcf..735d7eb 100644 --- a/pycco/main.py +++ b/pycco/main.py @@ -146,7 +146,7 @@ def parse(code, language): line = line.replace(multistart, '') line = line.replace(multiend, '') docs_text += line.strip() + '\n' - indent_level = re.match("\s*", line).group(0) + indent_level = re.match(r"\s*", line).group(0) if has_code and docs_text.strip(): save(docs_text, code_text[:-1]) @@ -229,8 +229,8 @@ def preprocess(comment, preserve_paths=True, outdir=None): name=match.group(2) ) - comment = re.sub('^([=]+)([^=]+)[=]*\s*$', replace_section_name, comment) - comment = re.sub('(?' + l["symbol"] + 'DIVIDER\n*') + r'\n*{}DIVIDER\n*'.format(comment_symbol) + ) # Get the Pygments Lexer for this language. - l["lexer"] = lexers.get_lexer_by_name(l["name"]) + l["lexer"] = lexers.get_lexer_by_name(language_name) def get_language(source, code, language=None): @@ -625,7 +633,7 @@ def main(): if opts.watch: try: import watchdog.events - import watchdog.observers + import watchdog.observers # noqa except ImportError: sys.exit('The -w/--watch option requires the watchdog package.') diff --git a/tests/test_pycco.py b/tests/test_pycco.py index 6db8265..6a98eda 100644 --- a/tests/test_pycco.py +++ b/tests/test_pycco.py @@ -4,7 +4,7 @@ import tempfile import time import os.path import pytest -from hypothesis import given, example, assume +from hypothesis import given, example from hypothesis.strategies import lists, text, booleans, choices, none import pycco.generate_index as generate_index @@ -41,8 +41,8 @@ def test_destination(filepath, preserve_paths, outdir): @given(choices(), text()) def test_parse(choice, source): - l = get_language(choice) - parsed = p.parse(source, l) + lang = get_language(choice) + parsed = p.parse(source, lang) for s in parsed: assert {"code_text", "docs_text"} == set(s.keys()) @@ -63,7 +63,9 @@ def test_multi_line_leading_spaces(): def test_comment_with_only_cross_ref(): - source = '''# ==Link Target==\n\ndef test_link():\n """[[testing.py#link-target]]"""\n pass''' + source = ( + '''# ==Link Target==\n\ndef test_link():\n """[[testing.py#link-target]]"""\n pass''' + ) sections = p.parse(source, PYTHON) p.highlight(sections, PYTHON, outdir=tempfile.gettempdir()) assert sections[1][ @@ -160,7 +162,12 @@ def test_process(preserve_paths, index, choice): language=lang_name) -@given(lists(lists(text(min_size=1), min_size=1, max_size=30), min_size=1), lists(text(min_size=1), min_size=1)) +one_or_more_chars = text(min_size=1) +paths = lists(one_or_more_chars, min_size=1, max_size=30) +@given( + lists(paths, min_size=1), + lists(one_or_more_chars, min_size=1) +) def test_generate_index(path_lists, outdir_list): file_paths = [os.path.join(*path_list) for path_list in path_lists] outdir = os.path.join(*outdir_list) -- cgit v1.2.1 From a761ddff2bc6eb36bf9ef75733bb4dc4177c5d7a Mon Sep 17 00:00:00 2001 From: Zach Smith Date: Wed, 25 Apr 2018 20:21:56 -0400 Subject: Update requirements --- requirements.test.txt | 6 +++--- requirements.txt | 4 ++-- setup.py | 10 +++++++--- 3 files changed, 12 insertions(+), 8 deletions(-) diff --git a/requirements.test.txt b/requirements.test.txt index 5db5948..f8e9871 100644 --- a/requirements.test.txt +++ b/requirements.test.txt @@ -1,3 +1,3 @@ -hypothesis==1.18.1 -pytest-cov==2.2.0 -coveralls==1.1 +hypothesis==3.56.5 +pytest-cov==2.5.1 +coveralls==1.3.0 diff --git a/requirements.txt b/requirements.txt index 38964da..7980f04 100644 --- a/requirements.txt +++ b/requirements.txt @@ -1,3 +1,3 @@ pystache==0.5.4 -Pygments==2.0.2 -markdown==2.6.3 +Pygments==2.2.0 +markdown==2.6.11 diff --git a/setup.py b/setup.py index c9a38e0..8fc15c2 100644 --- a/setup.py +++ b/setup.py @@ -1,11 +1,15 @@ from setuptools import setup, find_packages +description = ( + "A Python port of Docco: the original quick-and-dirty, " + "hundred-line-long, literate-programming-style documentation " + "generator." +) + setup( name="Pycco", version="0.5.1", - description="""A Python port of Docco: the original quick-and-dirty, - hundred-line-long, literate-programming-style documentation generator. - """, + description=description, author="Zach Smith", author_email="subsetpark@gmail.com", url="https://pycco-docs.github.io/pycco/", -- cgit v1.2.1 From bedb3da55d611153388004184222a26190ce3202 Mon Sep 17 00:00:00 2001 From: Zach Smith Date: Wed, 25 Apr 2018 20:25:30 -0400 Subject: Sort imports --- pycco/main.py | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/pycco/main.py b/pycco/main.py index 735d7eb..affd38d 100644 --- a/pycco/main.py +++ b/pycco/main.py @@ -1,21 +1,21 @@ #!/usr/bin/env python from __future__ import print_function -# This module contains all of our static resources. -from pycco_resources import pycco_template, css as pycco_css - # Import our external dependencies. import optparse import os -import pygments import re import sys import time -import pycco.generate_index as generate_index +from os import path +import pycco.generate_index as generate_index +import pygments from markdown import markdown -from os import path -from pygments import lexers, formatters +from pycco_resources import css as pycco_css +# This module contains all of our static resources. +from pycco_resources import pycco_template +from pygments import formatters, lexers """ "**Pycco**" is a Python port of [Docco](http://jashkenas.github.com/docco/): -- cgit v1.2.1 From c815be6017bbe884ce88bb41f7ec0369ca77914d Mon Sep 17 00:00:00 2001 From: Zach Smith Date: Wed, 25 Apr 2018 20:49:46 -0400 Subject: Factor out languages to their own module --- pycco/languages.py | 60 ++++++++++++++++++++++++++++ pycco/main.py | 113 +++++++++++++++++----------------------------------- tests/test_pycco.py | 12 +++--- 3 files changed, 104 insertions(+), 81 deletions(-) create mode 100644 pycco/languages.py diff --git a/pycco/languages.py b/pycco/languages.py new file mode 100644 index 0000000..48288f0 --- /dev/null +++ b/pycco/languages.py @@ -0,0 +1,60 @@ +""" +A list of the languages that Pycco supports, mapping the file extension to +the name of the Pygments lexer and the symbol that indicates a comment. To +add another language to Pycco's repertoire, add it here. +""" + +__all__ = ("supported_languages",) + +HASH = "#" +SLASH_STAR = "/*" +STAR_SLASH = "*/" +SLASH_SLASH = "//" +DASH_DASH = "--" + +def lang(name, comment_symbol, multistart=None, multiend=None): + result = { + "name": name, + "comment_symbol": comment_symbol + } + if multistart is not None and multiend is not None: + result["multistart"] = multistart + result["multiend"] = multiend + return result + + +c_lang = lang("c", SLASH_SLASH, SLASH_STAR, STAR_SLASH) + +supported_languages = { + ".coffee": lang("coffee-script", HASH, "###", "###"), + + ".pl": lang("perl", HASH), + + ".sql": lang("sql", DASH_DASH, SLASH_STAR, STAR_SLASH), + + ".sh": lang("bash", HASH), + + ".c": c_lang, + + ".h": c_lang, + + ".cl": c_lang, + + ".cpp": lang("cpp", SLASH_SLASH), + + ".js": lang("javascript", SLASH_SLASH, SLASH_STAR, STAR_SLASH), + + ".rb": lang("ruby", HASH, "=begin", "=end"), + + ".py": lang("python", HASH, '"""', '""'), + + ".scm": lang("scheme", ";;", "#|", "|#"), + + ".lua": lang("lua", DASH_DASH, "--[[", "--]]"), + + ".erl": lang("erlang", "%%"), + + ".tcl": lang("tcl", HASH), + + ".hs": lang("haskell", DASH_DASH, "{-", "-}"), +} diff --git a/pycco/main.py b/pycco/main.py index affd38d..9e4a3c9 100644 --- a/pycco/main.py +++ b/pycco/main.py @@ -1,5 +1,5 @@ #!/usr/bin/env python -from __future__ import print_function +from __future__ import print_function, absolute_import # Import our external dependencies. import optparse @@ -9,7 +9,8 @@ import sys import time from os import path -import pycco.generate_index as generate_index +from pycco.generate_index import generate_index +from pycco.languages import supported_languages import pygments from markdown import markdown from pycco_resources import css as pycco_css @@ -69,7 +70,7 @@ def _generate_documentation(file_path, code, outdir, preserve_paths, language): """ Helper function to allow documentation generation without file handling. """ - language = get_language(file_path, code, language=language) + language = get_language(file_path, code, language_name=language) sections = parse(code, language) highlight(sections, language, preserve_paths=preserve_paths, outdir=outdir) return generate_html(file_path, sections, preserve_paths=preserve_paths, outdir=outdir) @@ -313,55 +314,10 @@ def generate_html(source, sections, preserve_paths=True, outdir=None): # === Helpers & Setup === -# A list of the languages that Pycco supports, mapping the file extension to -# the name of the Pygments lexer and the symbol that indicates a comment. To -# add another language to Pycco's repertoire, add it here. -languages = { - ".coffee": {"name": "coffee-script", "comment_symbol": "#", - "multistart": '###', "multiend": '###'}, - - ".pl": {"name": "perl", "comment_symbol": "#"}, - - ".sql": {"name": "sql", "comment_symbol": "--"}, - - ".sh": {"name": "bash", "comment_symbol": "#"}, - - ".c": {"name": "c", "comment_symbol": "//", - "multistart": "/*", "multiend": "*/"}, - - ".h": {"name": "c", "comment_symbol": "//", - "multistart": "/*", "multiend": "*/"}, - - ".cpp": {"name": "cpp", "comment_symbol": "//"}, - - ".cl": {"name": "c", "comment_symbol": "//", - "multistart": "/*", "multiend": "*/"}, - - ".js": {"name": "javascript", "comment_symbol": "//", - "multistart": "/*", "multiend": "*/"}, - - ".rb": {"name": "ruby", "comment_symbol": "#", - "multistart": "=begin", "multiend": "=end"}, - - ".py": {"name": "python", "comment_symbol": "#", - "multistart": '"""', "multiend": '"""'}, - - ".scm": {"name": "scheme", "comment_symbol": ";;", - "multistart": "#|", "multiend": "|#"}, - - ".lua": {"name": "lua", "comment_symbol": "--", - "multistart": "--[[", "multiend": "--]]"}, - - ".erl": {"name": "erlang", "comment_symbol": "%%"}, - - ".tcl": {"name": "tcl", "comment_symbol": "#"}, - - ".hs": {"name": "haskell", "comment_symbol": "--", - "multistart": "{-", "multiend": "-}"}, -} - -# Build out the appropriate matchers and delimiters for each language. -for ext, l in languages.items(): +def compile_language(l): + """ + Build out the appropriate matchers and delimiters for each language. + """ language_name = l["name"] comment_symbol = l["comment_symbol"] @@ -382,32 +338,37 @@ for ext, l in languages.items(): l["lexer"] = lexers.get_lexer_by_name(language_name) -def get_language(source, code, language=None): - """Get the current language we're documenting, based on the extension.""" +for entry in supported_languages.values(): + compile_language(entry) - if language is not None: - for l in languages.values(): - if l["name"] == language: - return l +def get_language(source, code, language_name=None): + """ + Get the current language we're documenting, based on the extension. + """ + if language_name is not None: + for entry in supported_languages.values(): + if entry["name"] == language_name: + return entry else: - raise ValueError("Unknown forced language: " + language) + raise ValueError("Unknown forced language: {}".format(language_name)) - m = re.match(r'.*(\..+)', os.path.basename(source)) if source else None - if m and m.group(1) in languages: - return languages[m.group(1)] - else: - try: - lang = lexers.guess_lexer(code).name.lower() - for l in languages.values(): - if l["name"] == lang: - return l - else: - raise ValueError() - except ValueError: - # If pygments can't find any lexers, it will raise its own - # subclass of ValueError. We will catch it and raise ours - # for consistency. - raise ValueError("Can't figure out the language!") + if source: + m = re.match(r'.*(\..+)', os.path.basename(source)) + if m and m.group(1) in supported_languages: + return supported_languages[m.group(1)] + + try: + language_name = lexers.guess_lexer(code).name.lower() + for entry in supported_languages.values(): + if entry["name"] == language_name: + return entry + else: + raise ValueError() + except ValueError: + # If pygments can't find any lexers, it will raise its own + # subclass of ValueError. We will catch it and raise ours + # for consistency. + raise ValueError("Can't figure out the language!") def destination(filepath, preserve_paths=True, outdir=None): @@ -541,7 +502,7 @@ def process(sources, preserve_paths=True, outdir=None, language=None, if index: with open(path.join(outdir, "index.html"), "wb") as f: - f.write(generate_index.generate_index(generated_files, outdir)) + f.write(generate_index(generated_files, outdir)) __all__ = ("process", "generate_documentation") diff --git a/tests/test_pycco.py b/tests/test_pycco.py index 6a98eda..f5ab936 100644 --- a/tests/test_pycco.py +++ b/tests/test_pycco.py @@ -1,3 +1,4 @@ +from __future__ import absolute_import import copy import os import tempfile @@ -8,16 +9,17 @@ from hypothesis import given, example from hypothesis.strategies import lists, text, booleans, choices, none import pycco.generate_index as generate_index +from pycco.languages import supported_languages import pycco.main as p -PYTHON = p.languages['.py'] +PYTHON = supported_languages['.py'] PYCCO_SOURCE = 'pycco/main.py' FOO_FUNCTION = """def foo():\n return True""" def get_language(choice): - return choice(list(p.languages.values())) + return choice(list(supported_languages.values())) @given(lists(text()), text()) @@ -75,10 +77,10 @@ def test_comment_with_only_cross_ref(): @given(text(), text()) def test_get_language_specify_language(source, code): assert p.get_language( - source, code, language="python") == p.languages['.py'] + source, code, language_name="python") == supported_languages['.py'] with pytest.raises(ValueError): - p.get_language(source, code, language="non-existent") + p.get_language(source, code, language_name="non-existent") @given(text() | none()) @@ -155,7 +157,7 @@ def test_generate_documentation(): @given(booleans(), booleans(), choices()) def test_process(preserve_paths, index, choice): - lang_name = choice([l["name"] for l in p.languages.values()]) + lang_name = choice([l["name"] for l in supported_languages.values()]) p.process([PYCCO_SOURCE], preserve_paths=preserve_paths, index=index, outdir=tempfile.gettempdir(), -- cgit v1.2.1 From 1b536d0b910c73ba298587bf28060ef8aaac0403 Mon Sep 17 00:00:00 2001 From: Zach Smith Date: Wed, 25 Apr 2018 21:07:36 -0400 Subject: Fix multicomment Python --- pycco/languages.py | 3 ++- pycco/main.py | 16 +++++++++++----- 2 files changed, 13 insertions(+), 6 deletions(-) diff --git a/pycco/languages.py b/pycco/languages.py index 48288f0..f1ec64b 100644 --- a/pycco/languages.py +++ b/pycco/languages.py @@ -11,6 +11,7 @@ SLASH_STAR = "/*" STAR_SLASH = "*/" SLASH_SLASH = "//" DASH_DASH = "--" +TRIPLE_QUOTE = '"""' def lang(name, comment_symbol, multistart=None, multiend=None): result = { @@ -46,7 +47,7 @@ supported_languages = { ".rb": lang("ruby", HASH, "=begin", "=end"), - ".py": lang("python", HASH, '"""', '""'), + ".py": lang("python", HASH, TRIPLE_QUOTE, TRIPLE_QUOTE), ".scm": lang("scheme", ";;", "#|", "|#"), diff --git a/pycco/main.py b/pycco/main.py index 9e4a3c9..b82cadb 100644 --- a/pycco/main.py +++ b/pycco/main.py @@ -257,19 +257,25 @@ def highlight(sections, language, preserve_paths=True, outdir=None): ) lexer = language["lexer"] html_formatter = formatters.get_formatter_by_name("html") - output = pygments.highlight(joined_text, lexer, html_formatter) + divider_html = language["divider_html"] + + output = pygments.highlight( + joined_text, lexer, html_formatter + ).replace( + highlight_start, "" + ).replace( + highlight_end, "" + ) + fragments = re.split(divider_html, output) - output = output.replace(highlight_start, "").replace(highlight_end, "") - fragments = re.split(language["divider_html"], output) for i, section in enumerate(sections): section["code_html"] = highlight_start + shift(fragments, "") + highlight_end - docs_text = section['docs_text'] try: docs_text = unicode(section["docs_text"]) except UnicodeError: docs_text = unicode(section["docs_text"].decode('utf-8')) except NameError: - pass + docs_text = section['docs_text'] section["docs_html"] = markdown(preprocess(docs_text, preserve_paths=preserve_paths, outdir=outdir)) -- cgit v1.2.1 From 867f3dd1b2af5b6c767e22742453a0b2e87f2a22 Mon Sep 17 00:00:00 2001 From: Zach Smith Date: Wed, 25 Apr 2018 21:11:41 -0400 Subject: Include cython --- pycco/languages.py | 2 ++ 1 file changed, 2 insertions(+) diff --git a/pycco/languages.py b/pycco/languages.py index f1ec64b..f32b231 100644 --- a/pycco/languages.py +++ b/pycco/languages.py @@ -49,6 +49,8 @@ supported_languages = { ".py": lang("python", HASH, TRIPLE_QUOTE, TRIPLE_QUOTE), + ".pyx": lang("cython", HASH, TRIPLE_QUOTE, TRIPLE_QUOTE), + ".scm": lang("scheme", ";;", "#|", "|#"), ".lua": lang("lua", DASH_DASH, "--[[", "--]]"), -- cgit v1.2.1 From 9b6470b2d48b0cf7c5fa7abb66cc9b0009daf272 Mon Sep 17 00:00:00 2001 From: Zach Smith Date: Wed, 25 Apr 2018 21:24:09 -0400 Subject: Minor reorder --- pycco/main.py | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/pycco/main.py b/pycco/main.py index b82cadb..065be25 100644 --- a/pycco/main.py +++ b/pycco/main.py @@ -252,12 +252,13 @@ def highlight(sections, language, preserve_paths=True, outdir=None): raise TypeError("Missing the required 'outdir' keyword argument.") divider_text = language["divider_text"] + lexer = language["lexer"] + divider_html = language["divider_html"] + joined_text = divider_text.join( section["code_text"].rstrip() for section in sections ) - lexer = language["lexer"] html_formatter = formatters.get_formatter_by_name("html") - divider_html = language["divider_html"] output = pygments.highlight( joined_text, lexer, html_formatter -- cgit v1.2.1 From 7ef165234555ed12b45e7489f3fb54adbc291bc9 Mon Sep 17 00:00:00 2001 From: Zach Smith Date: Wed, 25 Apr 2018 21:28:44 -0400 Subject: Comment style fixes --- pycco/main.py | 22 +++++++++++++++------- 1 file changed, 15 insertions(+), 7 deletions(-) diff --git a/pycco/main.py b/pycco/main.py index 065be25..edf9dc2 100644 --- a/pycco/main.py +++ b/pycco/main.py @@ -407,7 +407,6 @@ def shift(list, default): Shift items off the front of the `list` until it is empty, then return `default`. """ - try: return list.pop(0) except IndexError: @@ -461,7 +460,9 @@ def _flatten_sources(sources): def process(sources, preserve_paths=True, outdir=None, language=None, encoding="utf8", index=False, skip=False): - """For each source file passed as argument, generate the documentation.""" + """ + For each source file passed as argument, generate the documentation. + """ if not outdir: raise TypeError("Missing the required 'directory' keyword argument.") @@ -516,7 +517,9 @@ __all__ = ("process", "generate_documentation") def monitor(sources, opts): - """Monitor each source file and re-generate documentation on change.""" + """ + Monitor each source file and re-generate documentation on change. + """ # The watchdog modules are imported in `main()` but we need to re-import # here to bring them into the local namespace. @@ -529,11 +532,14 @@ def monitor(sources, opts): for source in sources) class RegenerateHandler(watchdog.events.FileSystemEventHandler): - - """A handler for recompiling files which triggered watchdog events""" + """ + A handler for recompiling files which triggered watchdog events + """ def on_modified(self, event): - """Regenerate documentation for a file which triggered an event""" + """ + Regenerate documentation for a file which triggered an event + """ # Re-generate documentation from a source file if it was listed on # the command line. Watchdog monitors whole directories, so other # files may cause notifications as well. @@ -561,7 +567,9 @@ def monitor(sources, opts): def main(): - """Hook spot for the console script.""" + """ + Hook spot for the console script. + """ parser = optparse.OptionParser() parser.add_option('-p', '--paths', action='store_true', -- cgit v1.2.1 From 5ef70ef932c37bda68982aa6c35b90a18201cd70 Mon Sep 17 00:00:00 2001 From: Zach Smith Date: Wed, 25 Apr 2018 21:31:17 -0400 Subject: Comment style --- pycco/main.py | 19 ++++++++++--------- 1 file changed, 10 insertions(+), 9 deletions(-) diff --git a/pycco/main.py b/pycco/main.py index edf9dc2..f27420f 100644 --- a/pycco/main.py +++ b/pycco/main.py @@ -191,10 +191,11 @@ def preprocess(comment, preserve_paths=True, outdir=None): """ Add cross-references before having the text processed by markdown. It's possible to reference another file, like this : `[[main.py]]` which renders - [[main.py]]. You can also reference a specific section of another file, like - this: `[[main.py#highlighting-the-source-code]]` which renders as + [[main.py]]. You can also reference a specific section of another file, + like this: `[[main.py#highlighting-the-source-code]]` which renders as [[main.py#highlighting-the-source-code]]. Sections have to be manually - declared; they are written on a single line, and surrounded by equals signs: + declared; they are written on a single line, and surrounded by equals + signs: `=== like this ===` """ @@ -289,8 +290,8 @@ def highlight(sections, language, preserve_paths=True, outdir=None): def generate_html(source, sections, preserve_paths=True, outdir=None): """ - Once all of the code is finished highlighting, we can generate the HTML file - and write out the documentation. Pass the completed sections into the + Once all of the code is finished highlighting, we can generate the HTML + file and write out the documentation. Pass the completed sections into the template found in `resources/pycco.html`. Pystache will attempt to recursively render context variables, so we must @@ -381,7 +382,7 @@ def get_language(source, code, language_name=None): def destination(filepath, preserve_paths=True, outdir=None): """ Compute the destination HTML path for an input source file path. If the - source is `lib/example.py`, the HTML will be at `docs/example.html` + source is `lib/example.py`, the HTML will be at `docs/example.html`. """ dirname, filename = path.split(filepath) @@ -444,7 +445,7 @@ highlight_end = "" def _flatten_sources(sources): """ This function will iterate through the list of sources and if a directory - is encountered it will walk the tree for any files + is encountered it will walk the tree for any files. """ _sources = [] @@ -533,12 +534,12 @@ def monitor(sources, opts): class RegenerateHandler(watchdog.events.FileSystemEventHandler): """ - A handler for recompiling files which triggered watchdog events + A handler for recompiling files which triggered watchdog events. """ def on_modified(self, event): """ - Regenerate documentation for a file which triggered an event + Regenerate documentation for a file which triggered an event. """ # Re-generate documentation from a source file if it was listed on # the command line. Watchdog monitors whole directories, so other -- cgit v1.2.1 From e7c5ba004aae1c065239ea2803a2ed127ff9a54c Mon Sep 17 00:00:00 2001 From: Zach Smith Date: Wed, 25 Apr 2018 21:41:05 -0400 Subject: Add docstring to language entry --- pycco/languages.py | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/pycco/languages.py b/pycco/languages.py index f32b231..cb9edd1 100644 --- a/pycco/languages.py +++ b/pycco/languages.py @@ -14,6 +14,10 @@ DASH_DASH = "--" TRIPLE_QUOTE = '"""' def lang(name, comment_symbol, multistart=None, multiend=None): + """ + Generate a language entry dictionary, given a name and comment symbol and + optional start/end strings for multiline comments. + """ result = { "name": name, "comment_symbol": comment_symbol -- cgit v1.2.1 From c7c4c24f287207342eb48dd15578867a14efa335 Mon Sep 17 00:00:00 2001 From: Zach Smith Date: Wed, 25 Apr 2018 21:55:09 -0400 Subject: Set size limits to avoid data generation errors --- tests/test_pycco.py | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/tests/test_pycco.py b/tests/test_pycco.py index f5ab936..53fa74f 100644 --- a/tests/test_pycco.py +++ b/tests/test_pycco.py @@ -164,11 +164,11 @@ def test_process(preserve_paths, index, choice): language=lang_name) -one_or_more_chars = text(min_size=1) +one_or_more_chars = text(min_size=1, max_size=255) paths = lists(one_or_more_chars, min_size=1, max_size=30) @given( - lists(paths, min_size=1), - lists(one_or_more_chars, min_size=1) + lists(paths, min_size=1, max_size=255), + lists(one_or_more_chars, min_size=1, max_size=255) ) def test_generate_index(path_lists, outdir_list): file_paths = [os.path.join(*path_list) for path_list in path_lists] -- cgit v1.2.1 From f1a50149f96a0ed4c62c3cc7915684ef3e1d263f Mon Sep 17 00:00:00 2001 From: Zach Smith Date: Wed, 25 Apr 2018 21:59:09 -0400 Subject: Very minor style update --- pycco/languages.py | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/pycco/languages.py b/pycco/languages.py index cb9edd1..29bf16d 100644 --- a/pycco/languages.py +++ b/pycco/languages.py @@ -23,8 +23,7 @@ def lang(name, comment_symbol, multistart=None, multiend=None): "comment_symbol": comment_symbol } if multistart is not None and multiend is not None: - result["multistart"] = multistart - result["multiend"] = multiend + result.update(multistart=multistart, multiend=multiend) return result -- cgit v1.2.1 From 178093e84a2a66f39af109f81cbb184c9fe04ef7 Mon Sep 17 00:00:00 2001 From: Zach Smith Date: Wed, 25 Apr 2018 22:37:27 -0400 Subject: Turns out we were advertising smartypants but not making good on it --- pycco/main.py | 11 ++++++++--- 1 file changed, 8 insertions(+), 3 deletions(-) diff --git a/pycco/main.py b/pycco/main.py index f27420f..b49cfb9 100644 --- a/pycco/main.py +++ b/pycco/main.py @@ -278,9 +278,14 @@ def highlight(sections, language, preserve_paths=True, outdir=None): docs_text = unicode(section["docs_text"].decode('utf-8')) except NameError: docs_text = section['docs_text'] - section["docs_html"] = markdown(preprocess(docs_text, - preserve_paths=preserve_paths, - outdir=outdir)) + section["docs_html"] = markdown( + preprocess( + docs_text, + preserve_paths=preserve_paths, + outdir=outdir + ), + extensions=['markdown.extensions.smarty'] + ) section["num"] = i return sections -- cgit v1.2.1 From 185f999fad86967f98926b97a1ef1e220fbce39b Mon Sep 17 00:00:00 2001 From: Zach Smith Date: Wed, 25 Apr 2018 22:41:42 -0400 Subject: Escape double dash in comment --- pycco/main.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pycco/main.py b/pycco/main.py index b49cfb9..c062fbd 100644 --- a/pycco/main.py +++ b/pycco/main.py @@ -609,7 +609,7 @@ def main(): language=opts.language, index=opts.generate_index, skip=opts.skip_bad_files) - # If the -w / --watch option was present, monitor the source directories + # If the -w / \-\-watch option was present, monitor the source directories # for changes and re-generate documentation for source files whenever they # are modified. if opts.watch: -- cgit v1.2.1 From 101b234b180a04a859ebd80db69221ace7de1021 Mon Sep 17 00:00:00 2001 From: Zach Smith Date: Wed, 25 Apr 2018 22:55:52 -0400 Subject: migrate optparse -> argparse --- pycco/main.py | 40 +++++++++++++++++++++------------------- 1 file changed, 21 insertions(+), 19 deletions(-) diff --git a/pycco/main.py b/pycco/main.py index c062fbd..63b6e99 100644 --- a/pycco/main.py +++ b/pycco/main.py @@ -1,18 +1,18 @@ #!/usr/bin/env python -from __future__ import print_function, absolute_import +from __future__ import absolute_import, print_function # Import our external dependencies. -import optparse +import argparse import os import re import sys import time from os import path -from pycco.generate_index import generate_index -from pycco.languages import supported_languages import pygments from markdown import markdown +from pycco.generate_index import generate_index +from pycco.languages import supported_languages from pycco_resources import css as pycco_css # This module contains all of our static resources. from pycco_resources import pycco_template @@ -577,49 +577,51 @@ def main(): Hook spot for the console script. """ - parser = optparse.OptionParser() - parser.add_option('-p', '--paths', action='store_true', + parser = argparse.ArgumentParser() + parser.add_argument('-p', '--paths', action='store_true', help='Preserve path structure of original files') - parser.add_option('-d', '--directory', action='store', type='string', + parser.add_argument('-d', '--directory', action='store', type=str, dest='outdir', default='docs', help='The output directory that the rendered files should go to.') - parser.add_option('-w', '--watch', action='store_true', + parser.add_argument('-w', '--watch', action='store_true', help='Watch original files and re-generate documentation on changes') - parser.add_option('-l', '--force-language', action='store', type='string', + parser.add_argument('-l', '--force-language', action='store', type=str, dest='language', default=None, help='Force the language for the given files') - parser.add_option('-i', '--generate_index', action='store_true', + parser.add_argument('-i', '--generate_index', action='store_true', help='Generate an index.html document with sitemap content') - parser.add_option('-s', '--skip-bad-files', action='store_true', + parser.add_argument('-s', '--skip-bad-files', action='store_true', dest='skip_bad_files', help='Continue processing after hitting a bad file') - opts, sources = parser.parse_args() - if opts.outdir == '': + parser.add_argument('sources', nargs='*') + + args = parser.parse_args() + if args.outdir == '': outdir = '.' else: - outdir = opts.outdir + outdir = args.outdir - process(sources, outdir=outdir, preserve_paths=opts.paths, - language=opts.language, index=opts.generate_index, - skip=opts.skip_bad_files) + process(args.sources, outdir=outdir, preserve_paths=args.paths, + language=args.language, index=args.generate_index, + skip=args.skip_bad_files) # If the -w / \-\-watch option was present, monitor the source directories # for changes and re-generate documentation for source files whenever they # are modified. - if opts.watch: + if args.watch: try: import watchdog.events import watchdog.observers # noqa except ImportError: sys.exit('The -w/--watch option requires the watchdog package.') - monitor(sources, opts) + monitor(args.sources, args) # Run the script. -- cgit v1.2.1 From 57d0aaa4cff222ccd20b7d6f78f96ac6bb2225c0 Mon Sep 17 00:00:00 2001 From: Zach Smith Date: Wed, 25 Apr 2018 23:22:41 -0400 Subject: Use a sensible set of markdown extensions --- pycco/main.py | 29 +++++++++++++++++++++++------ 1 file changed, 23 insertions(+), 6 deletions(-) diff --git a/pycco/main.py b/pycco/main.py index 63b6e99..3e3c174 100644 --- a/pycco/main.py +++ b/pycco/main.py @@ -21,11 +21,24 @@ from pygments import formatters, lexers """ "**Pycco**" is a Python port of [Docco](http://jashkenas.github.com/docco/): the original quick-and-dirty, hundred-line-long, literate-programming-style -documentation generator. It produces HTML that displays your comments -alongside your code. Comments are passed through -[Markdown](http://daringfireball.net/projects/markdown/syntax) and -[SmartyPants](http://daringfireball.net/projects/smartypants), while code is -passed through [Pygments](http://pygments.org/) for syntax highlighting. +documentation generator. It produces HTML that displays your comments alongside +your code. Comments are passed through [Markdown][markdown] and +[SmartyPants][smartypants][^extensions], while code is passed through +[Pygments](http://pygments.org/) for syntax highlighting. + +[markdown]: http://daringfireball.net/projects/markdown/syntax +[smartypants]: https://python-markdown.github.io/extensions/footnotes/ + +[^extensions]: Three extensions to Markdown are available: + + 1. [SmartyPants][smarty] + 2. [Fenced code blocks][fences] + 3. [Footnotes][footnotes] + +[smarty]: https://python-markdown.github.io/extensions/smarty/ +[fences]: https://python-markdown.github.io/extensions/fenced_code_blocks/ +[footnotes]: https://python-markdown.github.io/extensions/footnotes/ + This page is the result of running Pycco against its own source file. If you install Pycco, you can run it from the command-line: @@ -284,7 +297,11 @@ def highlight(sections, language, preserve_paths=True, outdir=None): preserve_paths=preserve_paths, outdir=outdir ), - extensions=['markdown.extensions.smarty'] + extensions=[ + 'markdown.extensions.smarty', + 'markdown.extensions.fenced_code', + 'markdown.extensions.footnotes', + ] ) section["num"] = i -- cgit v1.2.1