Last active
December 22, 2019 07:41
-
-
Save tk0miya/d7b64291a3fbdf839e20ec507e8287fb to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# extension testbed | |
# autodoc_typehints_docinfo -- typehint をいい感じに表示する拡張 | |
# | |
# * 型情報は typehint を書いておいてね | |
# * conf.py で autodoc_typehints = 'docinfo' と設定する | |
from docutils import nodes | |
from sphinx import addnodes | |
from sphinx.util.docfields import DocFieldTransformer | |
from sphinx.util.inspect import Signature | |
def process_signature(app, objtype, name, obj, options, args, retann): | |
try: | |
if callable(obj): | |
signature = app.env.temp_data.setdefault('signatures', {}).setdefault(name, {}) | |
sig = Signature(obj) | |
for param in sig.parameters.values(): | |
if isinstance(param.annotation, str) and param.name in sig.annotations: | |
annotation = sig.annotations[param.name] | |
else: | |
annotation = param.annotation | |
if annotation is not param.empty: | |
signature[param.name] = sig.format_annotation(param.annotation) | |
except TypeError: | |
pass | |
orig_transform_all = DocFieldTransformer.transform_all | |
def transform_all(self, node): | |
signature = node.parent[0] | |
fullname = '.'.join([signature['module'], signature['fullname']]) | |
signatures = self.directive.env.temp_data.get('signatures', {}) | |
if signatures.get(fullname, {}): | |
field_lists = [n for n in node if isinstance(n, nodes.field_list)] | |
if field_lists == []: | |
insert_field_list(node, signatures[fullname]) | |
else: | |
for field_list in field_lists: | |
modify_field_list(field_list, signatures[fullname]) | |
orig_transform_all(self, node) | |
def insert_field_list(node, signature): | |
field_list = nodes.field_list() | |
for name, annotation in signature.items(): | |
field_name = nodes.field_name("param " + name, "param " + name) | |
field_body = nodes.field_body() | |
field_list += nodes.field("", field_name, field_body) | |
field_name = nodes.field_name("type " + name, "type " + name) | |
field_body = nodes.field_body("", nodes.paragraph(annotation, annotation)) | |
field_list += nodes.field("", field_name, field_body) | |
desc = [n for n in node if isinstance(n, addnodes.desc)] | |
if desc: | |
index = node.index(desc[0]) | |
node.insert(index - 1, [field_list]) | |
else: | |
node += field_list | |
def modify_field_list(node, signature): | |
for name, annotation in signature.items(): | |
field_name = nodes.field_name("type " + name, "type " + name) | |
field_body = nodes.field_body("", nodes.paragraph(annotation, annotation)) | |
node += nodes.field("", field_name, field_body) | |
def config_inited(app, config): | |
if config.autodoc_typehints == 'docinfo': | |
config.autodoc_typehints = 'none' | |
DocFieldTransformer.transform_all = transform_all | |
app.connect('autodoc-process-signature', process_signature) | |
def setup(app): | |
app.setup_extension('sphinx.ext.autodoc') | |
app.config.values['autodoc_typehints'][2].candidates += ('docinfo',) | |
app.connect('config-inited', config_inited) |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
autodoc_typehints = 'signature'
の場合(ext.pyを適用しないデフォルト動作)この拡張を有効化して
autodoc_typehints = 'docinfo'
の場合(ext.pyを適用した動作)autodoc_typehints = 'docinfo'
の場合(ext.pyを適用した動作)で、 'sphinx.ext.intersphinx'も適用設定