1. Qiita
  2. 投稿
  3. Python

Sphinxのドキュメント作成を便利にする「sphinx-quickstart-plus」を作りました

  • 8
    いいね
  • 0
    コメント

前記事:Sphinxを便利にして、みんなに使ってもらいたい

Sphinxは非常に便利なのですが、ドキュメント作成の手順が非常に煩雑でした。
そこで、Sphinxを拡張するモジュール「sphinx-quickstart-plus」を作りました。

https://github.com/pashango2/sphinx-qsp

インストール方法

pipで簡単にインストールできます。
Sphinxモジュールに依存していますので、あらかじめSphinxをインストールしておいてください。

$ pip install sphinx-quickstart-plus

追記:
version0.4ではパッケージチェック時にデバッグ用のprintが出ていました。
version0.4.1で修正しました、Pypiに反映されるまでしばらくお待ち下さい。

使い方

今まで、ドキュメント作成はsphinx-quickstartと打っていましたが、sphinx-quickstart-plusと打つだけです。

$ sphinx-quickstart-plus

すると、以下のようなメッセージが流れてきます。

出力
Welcome to the Sphinx 1.5.1 quickstart utility.

Please enter values for the following settings (just press Enter to
accept a default value, if one is given in brackets).

Enter the root path for documentation.
> Root path for the documentation [.]: document_path

You have two options for placing the build directory for Sphinx output.
Either, you use a directory "_build" within the root path, or you separate
"source" and "build" directories within the root path.
> Separate source and build directories (y/n) [n]: y

...

今までのsphinx-quickstartと全く同じ出力が出ます。
「何も変わってねーじゃん」と思われるかもしれませんが、もう少しお付き合いください。

出力
...
A Makefile and a Windows command file can be generated for you so that you
only have to run e.g. `make html' instead of invoking sphinx-build
directly.
> Create Makefile? (y/n) [y]: 
> Create Windows command file? (y/n) [y]: 

> ext_commonmark:use CommonMark and AutoStructify (y/n) [n]: y
> ext_nbshpinx:provides a source parser for *.ipynb files (y/n) [n]: y
> ext_blockdiag:Sphinx extension for embedding blockdiag diagrams (y/n) [n]: y
> ext_fontawesome:use font awesome (y/n) [n]: y
> ext_rtd_theme:use Read the Doc theme (y/n) [n]: y
> ext_autobuild:autobuild: Watch a directory and rebuild the documentation (y/n) [n]: y

最後にsphinx-quickstartになかった設問が出てきます。
今現在の拡張と説明は以下のとおりです。

拡張名 説明
ext_commonmark .rstだけでなく.md(CommonMark)が使えるようになります
ext_nbshpinx Jupyter Notebookが取り込めるようになります
ext_blockdiag ブロック図が書けるようになります
ext_fontawesome Font AwesomeがreSTから使えるようになります
ext_rtd_theme Read the Docsのテーマを使えるようになります
ext_autobuild オートビルドが使えるようになります

これらのSphinx拡張がconf.pyを編集することなく使えるようになります。

それだけではありません、ふたたびsphinx-quickstart-plusを起動すると、冒頭の設問が変わります。

出力
> Use latest setting? (y/n) [y]: y

'y'とタイプすると、PathProject nameAuthorVersionReleaseの5項目を答えるだけで、前回のドキュメントと同じ設定のドキュメントが作成されます。
前回のsphinx-quickstart-plusで作成したドキュメント設定を記憶しています。

ちなみに'n'とタイプした場合は、通常のsphinx-quickstartの設問が流れますが、デフォルト設定が最後の設定になっていますので、変更箇所以外はEnterキーの連打でよいので楽ちんです。

$ sphinx-quickstart-plus

> Use latest setting? (y/n) [y]: n

...

You have two options for placing the build directory for Sphinx output.
Either, you use a directory "_build" within the root path, or you separate
"source" and "build" directories within the root path.
> Separate source and build directories (y/n) [y]: <-デフォルトが最後の入力になってる

各拡張選択時にconf.pyに追加されるコード

ext_commonmark

conf.py
# ----- CommonMark
source_suffix = [source_suffix, '.md']

from recommonmark.parser import CommonMarkParser
source_parsers = {
    '.md': CommonMarkParser,
}

from recommonmark.transform import AutoStructify

github_doc_root = 'https://github.com/rtfd/recommonmark/tree/master/doc/'
def setup(app):
    app.add_config_value('recommonmark_config', {
            'url_resolver': lambda url: github_doc_root + url,
            'auto_toc_tree_section': 'Contents',
            }, True)
    app.add_transform(AutoStructify)

ext_nbshpinx

conf.py
# ----- Jupyter Notebook nbsphinx
extensions.append('nbsphinx')
exclude_patterns.append('**.ipynb_checkpoints')

ext_blockdiag

conf.py
# ----- blockdiag settings
extensions.extend([
    'sphinxcontrib.blockdiag',
    'sphinxcontrib.seqdiag',
    'sphinxcontrib.actdiag',
    'sphinxcontrib.nwdiag',
    'sphinxcontrib.rackdiag',
    'sphinxcontrib.packetdiag',
])
blockdiag_html_image_format = 'SVG'
seqdiag_html_image_format = 'SVG'
actdiag_html_image_format = 'SVG'
nwdiag_html_image_format = 'SVG'
rackiag_html_image_format = 'SVG'
packetdiag_html_image_format = 'SVG'

ext_fontawesome

conf.py
# ----- sphinx-fontawesome
import sphinx_fontawesome
extensions.append('sphinx_fontawesome')

ext_rtd_theme

conf.py
# ----- Read the Docs Theme
html_theme = "sphinx_rtd_theme"

ext_autobuild

auto_buildはconf.pyを書き換えませんが、Makefileを書き換えます。

$ make livehtml

と打つと、オートビルドが始まります。
Windowsの人はauto_build.batが生成されるので、それを実行してください。

$ auto_build.bat

PyCharmなどの.mdを編集していると一時ファイルが作成されてしまい、それもビルドしてしまうので、いくつかの一時ファイルをビルド無視する設定も含まれています。

ライセンスについて

「sphinx-quickstart-plus」はライセンスフリーです、ご自由にお使いください。
なお、このモジュールを使っていかなる不利益が生じても責任は負いませんので、ご理解ください。

https://github.com/pashango2/sphinx-qsp

また、私の環境はUbuntuなのでWindowsとMacの環境ではテストできていません。
バグなどはあるかと思います。
問題がありましたら、GitHubのイシューかコメント欄におねがいします。

コード解説

このモジュール本体はコメントを合わせて400行もない小さなモジュールです、作成期間も6時間程度で殆どがデバッグ作業です。
ですが、sphinx-quickstartの豊富な引数や機能をフルサポートしています。

どうしてこんな事ができるかというと、モンキーパッチという技術を使っているからです。

モンキーパッチとは?

モンキーパッチとは既存のライブラリの動作を乗っ取って、動的に書き換えてしまうパッチです。
これは動的言語の特性を活かした離れ業であり、コンパイル言語では真似できない手法です。1

補足
モンキーパッチは既存のライブラリのファイルを書き換えるものではありません。
あくまで既存ライブラリのファイルを変更することなく、動的に動作を変える手法です。
sphinx-quickstart-plusをインストールしても、元となるSphinxライブラリの動作は一切変わりません。

参考

モンキーパッチ Wikipedia

sphinx-quickstartsphinx.quickstart.pyというモジュールに処理が書かれています。
ですので、普通にsphinx.quickstartをインポートしますが、ask_user関数はモンキーパッチで書き換えてしまいますので、オリジナル処理の関数ポインタを忘れないよう、別途にfrom .. import ask_userでインポートしています。

from sphinx import quickstart
from sphinx.quickstart import ask_user, generate, do_prompt, nonempty, boolean

quickstart.ask_user関数をmonkey_patch_ask_user関数で上書きして乗っ取ります。

    # monkey patch
    quickstart.ask_user = monkey_patch_ask_user

monkey_patch_ask_user関数で独自の処理を行った後、オリジナルのquickstart.ask_user関数を呼び出しています。

def monkey_patch_ask_user(d):
    ... 独自処理

    # オリジナルの ask_user呼び出し
    ask_user(d)

    ... 独自処理

他にも色んな関数をモンキーパッチで乗っ取っているのですが、基本的にやっている事は一緒です。

最後にquickstart.mainを呼びます。

    quickstart.main(argv)

あとがき

個人的にいくつかのドキュメントを作成しましたが、めっちゃ便利です。