diff options
Diffstat (limited to 'sphinx/directives/other.py')
-rw-r--r-- | sphinx/directives/other.py | 96 |
1 files changed, 64 insertions, 32 deletions
diff --git a/sphinx/directives/other.py b/sphinx/directives/other.py index e9a3864ab..41b21f917 100644 --- a/sphinx/directives/other.py +++ b/sphinx/directives/other.py @@ -8,17 +8,20 @@ """ import re +from contextlib import contextmanager from docutils import nodes -from docutils.parsers.rst import Directive, directives +from docutils.parsers.rst import directives from docutils.parsers.rst.directives.admonitions import BaseAdmonition from docutils.parsers.rst.directives.misc import Class from docutils.parsers.rst.directives.misc import Include as BaseInclude from six.moves import range -from sphinx import addnodes -from sphinx.locale import versionlabels, _ +from sphinx import addnodes, locale +from sphinx.deprecation import DeprecatedDict, RemovedInSphinx30Warning +from sphinx.locale import _ from sphinx.util import url_re, docname_join +from sphinx.util.docutils import SphinxDirective from sphinx.util.matching import patfilter from sphinx.util.nodes import explicit_title_re, set_source_info, \ process_index_entry @@ -29,6 +32,19 @@ if False: from sphinx.application import Sphinx # NOQA +versionlabels = { + 'versionadded': _('New in version %s'), + 'versionchanged': _('Changed in version %s'), + 'deprecated': _('Deprecated since version %s'), +} # type: Dict[unicode, unicode] + +locale.versionlabels = DeprecatedDict( + versionlabels, + 'sphinx.locale.versionlabels is deprecated. ' + 'Please use sphinx.directives.other.versionlabels instead.', + RemovedInSphinx30Warning +) + glob_re = re.compile('.*[*?\[].*') @@ -39,7 +55,7 @@ def int_or_nothing(argument): return int(argument) -class TocTree(Directive): +class TocTree(SphinxDirective): """ Directive to notify Sphinx about the hierarchical structure of the docs, and to include a table-of-contents like tree in the current document. @@ -63,7 +79,7 @@ class TocTree(Directive): def run(self): # type: () -> List[nodes.Node] subnode = addnodes.toctree() - subnode['parent'] = self.state.document.settings.env.docname + subnode['parent'] = self.env.docname # (title, ref) pairs, where ref may be a document, or an external link, # and title may be None if the document's title is to be used @@ -86,12 +102,11 @@ class TocTree(Directive): return ret def parse_content(self, toctree): - env = self.state.document.settings.env - suffixes = env.config.source_suffix + suffixes = self.config.source_suffix # glob target documents - all_docnames = env.found_docs.copy() - all_docnames.remove(env.docname) # remove current document + all_docnames = self.env.found_docs.copy() + all_docnames.remove(self.env.docname) # remove current document ret = [] for entry in self.content: @@ -101,7 +116,7 @@ class TocTree(Directive): explicit = explicit_title_re.match(entry) if (toctree['glob'] and glob_re.match(entry) and not explicit and not url_re.match(entry)): - patname = docname_join(env.docname, entry) + patname = docname_join(self.env.docname, entry) docnames = sorted(patfilter(all_docnames, patname)) for docname in docnames: all_docnames.remove(docname) # don't include it again @@ -125,14 +140,14 @@ class TocTree(Directive): docname = docname[:-len(suffix)] break # absolutize filenames - docname = docname_join(env.docname, docname) + docname = docname_join(self.env.docname, docname) if url_re.match(ref) or ref == 'self': toctree['entries'].append((title, ref)) - elif docname not in env.found_docs: + elif docname not in self.env.found_docs: ret.append(self.state.document.reporter.warning( 'toctree contains reference to nonexisting ' 'document %r' % docname, line=self.lineno)) - env.note_reread() + self.env.note_reread() else: all_docnames.discard(docname) toctree['entries'].append((title, docname)) @@ -145,7 +160,7 @@ class TocTree(Directive): return ret -class Author(Directive): +class Author(SphinxDirective): """ Directive to give the name of the author of the current document or section. Shown in the output only if the show_authors option is on. @@ -158,8 +173,7 @@ class Author(Directive): def run(self): # type: () -> List[nodes.Node] - env = self.state.document.settings.env - if not env.config.show_authors: + if not self.config.show_authors: return [] para = nodes.paragraph(translatable=False) emph = nodes.emphasis() @@ -179,7 +193,7 @@ class Author(Directive): return [para] + messages -class Index(Directive): +class Index(SphinxDirective): """ Directive to add entries to the index. """ @@ -192,8 +206,7 @@ class Index(Directive): def run(self): # type: () -> List[nodes.Node] arguments = self.arguments[0].split('\n') - env = self.state.document.settings.env - targetid = 'index-%s' % env.new_serialno('index') + targetid = 'index-%s' % self.env.new_serialno('index') targetnode = nodes.target('', '', ids=[targetid]) self.state.document.note_explicit_target(targetnode) indexnode = addnodes.index() @@ -205,7 +218,7 @@ class Index(Directive): return [indexnode, targetnode] -class VersionChange(Directive): +class VersionChange(SphinxDirective): """ Directive to describe a change/addition/deprecation in a specific version. """ @@ -248,9 +261,8 @@ class VersionChange(Directive): classes=['versionmodified']), translatable=False) node.append(para) - env = self.state.document.settings.env # XXX should record node.source as well - env.note_versionchange(node['type'], node['version'], node, node.line) + self.env.note_versionchange(node['type'], node['version'], node, node.line) return [node] + messages @@ -261,7 +273,7 @@ class SeeAlso(BaseAdmonition): node_class = addnodes.seealso -class TabularColumns(Directive): +class TabularColumns(SphinxDirective): """ Directive to give an explicit tabulary column definition to LaTeX. """ @@ -279,7 +291,7 @@ class TabularColumns(Directive): return [node] -class Centered(Directive): +class Centered(SphinxDirective): """ Directive to create a centered line of bold text. """ @@ -300,7 +312,7 @@ class Centered(Directive): return [subnode] + messages -class Acks(Directive): +class Acks(SphinxDirective): """ Directive for a list of names. """ @@ -322,7 +334,7 @@ class Acks(Directive): return [node] -class HList(Directive): +class HList(SphinxDirective): """ Directive for a list that gets compacted horizontally. """ @@ -359,7 +371,7 @@ class HList(Directive): return [newnode] -class Only(Directive): +class Only(SphinxDirective): """ Directive to only include text if the given tag(s) are enabled. """ @@ -417,7 +429,7 @@ class Only(Directive): self.state.memo.section_level = surrounding_section_level -class Include(BaseInclude): +class Include(BaseInclude, SphinxDirective): """ Like the standard "Include" directive, but interprets absolute paths "correctly", i.e. relative to source directory. @@ -425,15 +437,35 @@ class Include(BaseInclude): def run(self): # type: () -> List[nodes.Node] - env = self.state.document.settings.env + current_filename = self.env.doc2path(self.env.docname) if self.arguments[0].startswith('<') and \ self.arguments[0].endswith('>'): # docutils "standard" includes, do not do path processing return BaseInclude.run(self) - rel_filename, filename = env.relfn2path(self.arguments[0]) + rel_filename, filename = self.env.relfn2path(self.arguments[0]) self.arguments[0] = filename - env.note_included(filename) - return BaseInclude.run(self) + self.env.note_included(filename) + with patched_warnings(self, current_filename): + return BaseInclude.run(self) + + +@contextmanager +def patched_warnings(directive, parent_filename): + # type: (BaseInclude, unicode) -> Generator[None, None, None] + """Add includee filename to the warnings during inclusion.""" + try: + original = directive.state_machine.insert_input + + def insert_input(input_lines, source): + # type: (Any, unicode) -> None + source += ' <included from %s>' % parent_filename + original(input_lines, source) + + # patch insert_input() temporarily + directive.state_machine.insert_input = insert_input + yield + finally: + directive.state_machine.insert_input = original def setup(app): |