Beispiel #1
0
    def get_rst(self):
        env = self.state.document.settings.env
        entries = []
        all_docnames = env.found_docs.copy()
        found = set([env.docname])  # don't include myself
        for entry in self.content:
            if not entry:
                continue
            patname = docname_join(env.docname, entry)
            docnames = sorted(patfilter(all_docnames, patname))
            for docname in docnames:
                if not docname in found:
                    found.add(docname)
                    entries.append(self.entry_class.create(env, docname))
        expr = self.options.get('filter')
        if expr:
            def func(e):
                try:
                    return eval(expr, dict(e=e))
                except Exception as exc:
                    return "{} in {}".format(exc, expr)
            entries = list(filter(func, entries))

        orderby = self.options.get('orderby')
        if orderby:
            def func(a):
                return getattr(a, orderby, '')
            entries = sorted(entries, key=func)

        headers = self.get_headers()
        rows = []
        for e in entries:
            rows.append(self.format_entry(e))
        return rstgen.table(headers, rows)
Beispiel #2
0
    def get_rst(self):
        env = self.state.document.settings.env
        entries = []
        all_docnames = env.found_docs.copy()
        found = set([env.docname])  # don't include myself
        for entry in self.content:
            if not entry:
                continue
            patname = docname_join(env.docname, entry)
            docnames = sorted(patfilter(all_docnames, patname))
            for docname in docnames:
                if not docname in found:
                    found.add(docname)
                    entries.append(self.entry_class.create(env, docname))
        expr = self.options.get('filter')
        if expr:
            def func(e):
                return eval(expr, dict(e=e))
            entries = list(filter(func, entries))

        orderby = self.options.get('orderby')
        if orderby:
            def func(a, b):
                va = getattr(a, orderby, '')
                vb = getattr(b, orderby, '')
                return cmp(va, vb)
            entries = sorted(entries, func)

        headers = self.get_headers()
        rows = []
        for e in entries:
            rows.append(self.format_entry(e))
        return rstgen.table(headers, rows)
Beispiel #3
0
    def parse_content(self, toctree):
        env = self.state.document.settings.env
        suffixes = env.config.source_suffix

        # glob target documents
        all_docnames = env.found_docs.copy()
        all_docnames.remove(env.docname)  # remove current document

        ret = []
        for entry in self.content:
            if not entry:
                continue
            # look for explicit titles ("Some Title <document>")
            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)
                docnames = sorted(patfilter(all_docnames, patname))
                for docname in docnames:
                    all_docnames.remove(docname)  # don't include it again
                    toctree['entries'].append((None, docname))
                    toctree['includefiles'].append(docname)
                if not docnames:
                    ret.append(self.state.document.reporter.warning(
                        'toctree glob pattern %r didn\'t match any documents'
                        % entry, line=self.lineno))
            else:
                if explicit:
                    ref = explicit.group(2)
                    title = explicit.group(1)
                    docname = ref
                else:
                    ref = docname = entry
                    title = None
                # remove suffixes (backwards compatibility)
                for suffix in suffixes:
                    if docname.endswith(suffix):
                        docname = docname[:-len(suffix)]
                        break
                # absolutize filenames
                docname = docname_join(env.docname, docname)
                if url_re.match(ref) or ref == 'self':
                    toctree['entries'].append((title, ref))
                elif docname not in env.found_docs:
                    ret.append(self.state.document.reporter.warning(
                        'toctree contains reference to nonexisting '
                        'document %r' % docname, line=self.lineno))
                    env.note_reread()
                else:
                    all_docnames.discard(docname)
                    toctree['entries'].append((title, docname))
                    toctree['includefiles'].append(docname)

        # entries contains all entries (self references, external links etc.)
        if 'reversed' in self.options:
            toctree['entries'] = list(reversed(toctree['entries']))

        return ret
Beispiel #4
0
    def parse_content(self, toctree):
        suffixes = self.config.source_suffix

        # glob target documents
        all_docnames = self.env.found_docs.copy()
        all_docnames.remove(self.env.docname)  # remove current document

        ret = []
        for entry in self.content:
            if not entry:
                continue
            # look for explicit titles ("Some Title <document>")
            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(self.env.docname, entry)
                docnames = sorted(patfilter(all_docnames, patname))
                for docname in docnames:
                    all_docnames.remove(docname)  # don't include it again
                    toctree['entries'].append((None, docname))
                    toctree['includefiles'].append(docname)
                if not docnames:
                    ret.append(self.state.document.reporter.warning(
                        'toctree glob pattern %r didn\'t match any documents'
                        % entry, line=self.lineno))
            else:
                if explicit:
                    ref = explicit.group(2)
                    title = explicit.group(1)
                    docname = ref
                else:
                    ref = docname = entry
                    title = None
                # remove suffixes (backwards compatibility)
                for suffix in suffixes:
                    if docname.endswith(suffix):
                        docname = docname[:-len(suffix)]
                        break
                # absolutize filenames
                docname = docname_join(self.env.docname, docname)
                if url_re.match(ref) or ref == 'self':
                    toctree['entries'].append((title, ref))
                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))
                    self.env.note_reread()
                else:
                    all_docnames.discard(docname)
                    toctree['entries'].append((title, docname))
                    toctree['includefiles'].append(docname)

        # entries contains all entries (self references, external links etc.)
        if 'reversed' in self.options:
            toctree['entries'] = list(reversed(toctree['entries']))

        return ret
    def parse_iterable(self, references, toctree):
        """Build a TOC from a series of document links.

        Args:
            references: An iterable series of document links
            toctree: The toctree node.
        """

        # glob target documents
        all_docnames = self.env.found_docs.copy()
        all_docnames.remove(self.env.docname)  # remove current document

        warnings = []

        for ref in references:
            if not ref:
                continue
            if toctree['glob'] and glob_re.match(
                    ref) and not url_re.match(ref):
                patname = docname_join(self.env.docname, ref)
                docnames = sorted(patfilter(all_docnames, patname))
                for docname in docnames:
                    all_docnames.remove(docname)  # don't include it again
                    toctree['entries'].append((None, docname))
                    toctree['includefiles'].append(docname)
                if not docnames:
                    warnings.append(
                        self.state.document.reporter.warning(
                            'toctree glob pattern %r didn\'t match any documents'
                            % ref,
                            line=self.lineno))
            else:
                self.make_entry(title=None,
                                ref=ref,
                                toctree=toctree,
                                all_docnames=all_docnames,
                                warnings=warnings)
        return warnings
Beispiel #6
0
    def run(self):
        env = self.state.document.settings.env
        suffixes = env.config.source_suffix
        glob = 'glob' in self.options
        caption = self.options.get('caption')
        if caption:
            self.options.setdefault('name', nodes.fully_normalize_name(caption))

        ret = []
        # (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
        entries = []
        includefiles = []
        all_docnames = env.found_docs.copy()
        # don't add the currently visited file in catch-all patterns
        all_docnames.remove(env.docname)
        for entry in self.content:
            if not entry:
                continue
            if glob and ('*' in entry or '?' in entry or '[' in entry):
                patname = docname_join(env.docname, entry)
                docnames = sorted(patfilter(all_docnames, patname))
                for docname in docnames:
                    all_docnames.remove(docname)  # don't include it again
                    entries.append((None, docname))
                    includefiles.append(docname)
                if not docnames:
                    ret.append(self.state.document.reporter.warning(
                        'toctree glob pattern %r didn\'t match any documents'
                        % entry, line=self.lineno))
            else:
                # look for explicit titles ("Some Title <document>")
                m = explicit_title_re.match(entry)
                if m:
                    ref = m.group(2)
                    title = m.group(1)
                    docname = ref
                else:
                    ref = docname = entry
                    title = None
                # remove suffixes (backwards compatibility)
                for suffix in suffixes:
                    if docname.endswith(suffix):
                        docname = docname[:-len(suffix)]
                        break
                # absolutize filenames
                docname = docname_join(env.docname, docname)
                if url_re.match(ref) or ref == 'self':
                    entries.append((title, ref))
                elif docname not in env.found_docs:
                    ret.append(self.state.document.reporter.warning(
                        'toctree contains reference to nonexisting '
                        'document %r' % docname, line=self.lineno))
                    env.note_reread()
                else:
                    all_docnames.discard(docname)
                    entries.append((title, docname))
                    includefiles.append(docname)
        subnode = addnodes.toctree()
        subnode['parent'] = env.docname
        # entries contains all entries (self references, external links etc.)
        subnode['entries'] = entries
        # includefiles only entries that are documents
        subnode['includefiles'] = includefiles
        subnode['maxdepth'] = self.options.get('maxdepth', -1)
        subnode['caption'] = caption
        subnode['glob'] = glob
        subnode['hidden'] = 'hidden' in self.options
        subnode['includehidden'] = 'includehidden' in self.options
        subnode['numbered'] = self.options.get('numbered', 0)
        subnode['titlesonly'] = 'titlesonly' in self.options
        set_source_info(self, subnode)
        wrappernode = nodes.compound(classes=['toctree-wrapper'])
        wrappernode.append(subnode)
        self.add_name(wrappernode)
        ret.append(wrappernode)
        return ret
Beispiel #7
0
    def run(self):
        env = self.state.document.settings.env
        suffixes = env.config.source_suffix
        glob = 'glob' in self.options

        ret = []
        # (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
        entries = []
        includefiles = []
        all_docnames = env.found_docs.copy()
        # don't add the currently visited file in catch-all patterns
        try:
            all_docnames.remove(env.docname)
        except KeyError:
            if env.docname == "<<string>>":
                # This comes from rst2html.
                pass
            else:
                logger = logging.getLogger("CustomTocTreeCollector")
                logger.warning(
                    "[CustomTocTreeCollector] unable to remove document '{0}' from {1}"
                    .format(env.docname, ", ".join(all_docnames)))

        for entry in self.content:
            if not entry:
                continue
            if glob and ('*' in entry or '?' in entry or '[' in entry):
                patname = docname_join(env.docname, entry)
                docnames = sorted(patfilter(all_docnames, patname))
                for docname in docnames:
                    all_docnames.remove(docname)  # don't include it again
                    entries.append((None, docname))
                    includefiles.append(docname)
                if not docnames:
                    ret.append(
                        self.state.document.reporter.warning(
                            '[CustomTocTree] glob pattern %r didn\'t match any documents'
                            % entry,
                            line=self.lineno))
            else:
                # look for explicit titles ("Some Title <document>")
                m = explicit_title_re.match(entry)
                if m:
                    ref = m.group(2)
                    title = m.group(1)
                    docname = ref
                else:
                    ref = docname = entry
                    title = None
                # remove suffixes (backwards compatibility)
                for suffix in suffixes:
                    if docname.endswith(suffix):
                        docname = docname[:-len(suffix)]
                        break
                # absolutize filenames
                docname = docname_join(env.docname, docname)
                if url_re.match(ref) or ref == 'self':
                    entries.append((title, ref))
                elif docname not in env.found_docs:
                    ret.append(
                        self.state.document.reporter.warning(
                            '[CustomTocTree] contains reference to nonexisting '
                            'document %r' % docname,
                            line=self.lineno))
                    env.note_reread()
                else:
                    all_docnames.discard(docname)
                    entries.append((title, docname))
                    includefiles.append(docname)
        subnode = addnodes.toctree()
        subnode['parent'] = env.docname
        # entries contains all entries (self references, external links etc.)
        if 'reversed' in self.options:
            entries.reverse()
        subnode['entries'] = entries
        # includefiles only entries that are documents
        subnode['includefiles'] = includefiles
        subnode['maxdepth'] = self.options.get('maxdepth', -1)
        subnode['caption'] = self.options.get('caption')
        subnode['glob'] = glob
        subnode['hidden'] = 'hidden' in self.options
        subnode['includehidden'] = 'includehidden' in self.options
        subnode['numbered'] = self.options.get('numbered', 0)
        subnode['titlesonly'] = 'titlesonly' in self.options
        set_source_info(self, subnode)
        wrappernode = nodes.compound(classes=['toctree-wrapper'])
        wrappernode.append(subnode)
        self.add_name(wrappernode)
        ret.append(wrappernode)
        return ret
Beispiel #8
0
    def parse_content(self, toctree: addnodes.toctree) -> List[Node]:
        suffixes = self.config.source_suffix

        # glob target documents
        all_docnames = self.env.found_docs.copy()
        all_docnames.remove(self.env.docname)  # remove current document

        ret: List[Node] = []
        excluded = Matcher(self.config.exclude_patterns)
        for entry in self.content:
            if not entry:
                continue
            # look for explicit titles ("Some Title <document>")
            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(self.env.docname, entry)
                docnames = sorted(patfilter(all_docnames, patname))
                for docname in docnames:
                    all_docnames.remove(docname)  # don't include it again
                    toctree['entries'].append((None, docname))
                    toctree['includefiles'].append(docname)
                if not docnames:
                    logger.warning(__(
                        'toctree glob pattern %r didn\'t match any documents'),
                                   entry,
                                   location=toctree)
            else:
                if explicit:
                    ref = explicit.group(2)
                    title = explicit.group(1)
                    docname = ref
                else:
                    ref = docname = entry
                    title = None
                # remove suffixes (backwards compatibility)
                for suffix in suffixes:
                    if docname.endswith(suffix):
                        docname = docname[:-len(suffix)]
                        break
                # absolutize filenames
                docname = docname_join(self.env.docname, docname)
                if url_re.match(ref) or ref == 'self':
                    toctree['entries'].append((title, ref))
                elif docname not in self.env.found_docs:
                    if excluded(self.env.doc2path(docname, None)):
                        message = __(
                            'toctree contains reference to excluded document %r'
                        )
                        subtype = 'excluded'
                    else:
                        message = __(
                            'toctree contains reference to nonexisting document %r'
                        )
                        subtype = 'not_readable'

                    logger.warning(message,
                                   docname,
                                   type='toc',
                                   subtype=subtype,
                                   location=toctree)
                    self.env.note_reread()
                else:
                    if docname in all_docnames:
                        all_docnames.remove(docname)
                    else:
                        logger.warning(
                            __('duplicated entry found in toctree: %s'),
                            docname,
                            location=toctree)

                    toctree['entries'].append((title, docname))
                    toctree['includefiles'].append(docname)

        # entries contains all entries (self references, external links etc.)
        if 'reversed' in self.options:
            toctree['entries'] = list(reversed(toctree['entries']))
            toctree['includefiles'] = list(reversed(toctree['includefiles']))

        return ret
    def run(self):
        env = self.state.document.settings.env
        suffix = env.config.source_suffix
        glob = 'glob' in self.options
        limit = 'limit' in self.options

        ret = []
        # (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
        entries = []
        includefiles = []
        all_docnames = env.found_docs.copy()
        # don't add the currently visited file in catch-all patterns
        all_docnames.remove(env.docname)
        for entry in self.content:
            if not entry:
                continue
            if not glob:
                # look for explicit titles ("Some Title <document>")
                m = explicit_title_re.match(entry)
                if m:
                    ref = m.group(2)
                    title = m.group(1)
                    docname = ref
                else:
                    ref = docname = entry
                    title = None
                # remove suffixes (backwards compatibility)
                if docname.endswith(suffix):
                    docname = docname[:-len(suffix)]
                # absolutize filenames
                docname = docname_join(env.docname, docname)
                if url_re.match(ref) or ref == 'self':
                    entries.append((title, ref))
                elif docname not in env.found_docs:
                    ret.append(
                        self.state.document.reporter.warning(
                            'toctree contains reference to nonexisting '
                            'document %r' % docname,
                            line=self.lineno))
                    env.note_reread()
                else:
                    entries.append((title, docname))
                    includefiles.append(docname)
            else:
                patname = docname_join(env.docname, entry)
                docnames = sorted(patfilter(all_docnames, patname))
                for docname in docnames:
                    all_docnames.remove(docname)  # don't include it again
                    entries.append((None, docname))
                    includefiles.append(docname)
                if not docnames:
                    ret.append(
                        self.state.document.reporter.warning(
                            'toctree glob pattern %r didn\'t match any documents'
                            % entry,
                            line=self.lineno))

        sorted_entries = {}
        for entry in entries:
            metadata = env.metadata.get(entry[1], {})

            if 'date' not in metadata:
                continue
            try:
                pub_date = parse_date(metadata['date'])
                env.metadata.get(entry[1], {})
            except ValueError, exc:
                continue

            sorted_entries[pub_date.isoformat()] = entry
Beispiel #10
0
    def run(self):
        env = self.state.document.settings.env
        suffix = env.config.source_suffix
        glob = 'glob' in self.options

        ret = []
        # (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
        entries = []
        includefiles = []
        all_docnames = env.found_docs.copy()
        # don't add the currently visited file in catch-all patterns
        all_docnames.remove(env.docname)
        for entry in self.content:
            if not entry:
                continue
            if not glob:
                # look for explicit titles ("Some Title <document>")
                m = explicit_title_re.match(entry)
                if m:
                    ref = m.group(2)
                    title = m.group(1)
                    docname = ref
                else:
                    ref = docname = entry
                    title = None
                # remove suffixes (backwards compatibility)
                if docname.endswith(suffix):
                    docname = docname[:-len(suffix)]
                # absolutize filenames
                docname = docname_join(env.docname, docname)
                if url_re.match(ref) or ref == 'self':
                    entries.append((title, ref))
                elif docname not in env.found_docs:
                    ret.append(
                        self.state.document.reporter.warning(
                            'toctree contains reference to nonexisting '
                            'document %r' % docname,
                            line=self.lineno))
                    env.note_reread()
                else:
                    entries.append((title, docname))
                    includefiles.append(docname)
            else:
                patname = docname_join(env.docname, entry)
                docnames = sorted(patfilter(all_docnames, patname))
                for docname in docnames:
                    all_docnames.remove(docname)  # don't include it again
                    entries.append((None, docname))
                    includefiles.append(docname)
                if not docnames:
                    ret.append(
                        self.state.document.reporter.warning(
                            'toctree glob pattern %r didn\'t match any documents'
                            % entry,
                            line=self.lineno))
        subnode = addnodes.toctree()
        subnode['parent'] = env.docname
        # entries contains all entries (self references, external links etc.)
        subnode['entries'] = entries
        # includefiles only entries that are documents
        subnode['includefiles'] = includefiles
        subnode['maxdepth'] = self.options.get('maxdepth', -1)
        subnode['glob'] = glob
        subnode['hidden'] = 'hidden' in self.options
        subnode['numbered'] = self.options.get('numbered', 0)
        subnode['titlesonly'] = 'titlesonly' in self.options
        set_source_info(self, subnode)
        wrappernode = nodes.compound(classes=['toctree-wrapper'])
        wrappernode.append(subnode)
        ret.append(wrappernode)
        return ret
Beispiel #11
0
 def run(self):
     env = self.state.document.settings.env
     suffix = env.config.source_suffix
     glob = 'glob' in self.options
             
     # (title, ref) pairs, where ref may only be a document
     # external links are forbidden, since we have no way of dating them
     # and title may be None if the document's title is to be used
     entries = []
     includefiles = []
     
     all_docnames = env.found_docs.copy()
     # don't add the currently visited file in catch-all patterns
     all_docnames.remove(env.docname)
     
     ret = []
     
     for entry in self.content:
         if not entry:
             continue
         if not glob:
             # look for explicit titles ("Some Title <document>")
             m = explicit_title_re.match(entry)
             if m:
                 ref = m.group(2)
                 title = m.group(1)
                 docname = ref
             else:
                 ref = docname = entry
                 title = None
             # remove suffixes (backwards compatibility)
             if docname.endswith(suffix):
                 docname = docname[:-len(suffix)]
             # absolutize filenames
             docname = docname_join(env.docname, docname)
             if url_re.match(ref) or ref == 'self':
                 entries.append((title, ref))
             elif docname not in env.found_docs:
                 ret.append(self.state.document.reporter.warning(
                     'toctree contains reference to nonexisting '
                     'document %r' % docname, line=self.lineno))
                 env.note_reread()
             else:
                 entries.append((title, docname))
                 includefiles.append(docname)
         else:
             patname = docname_join(env.docname, entry)
             docnames = patfilter(all_docnames, patname)
             for docname in docnames:
                 all_docnames.remove(docname) # don't include it again
                 entries.append((None, docname))
                 includefiles.append(docname)
             if not docnames:
                 ret.append(self.state.document.reporter.warning(
                     'latest list glob pattern %r didn\'t match any documents'
                     % entry, line=self.lineno))
     
     subnode = latest()
     subnode['parent'] = env.docname
     # entries contains all entries (self references, external links etc.)
     subnode['entries'] = entries
     # includefiles only entries that are documents
     subnode['includefiles'] = includefiles
     subnode['maxdepth'] = self.options.get('maxdepth', -1)
     subnode['glob'] = glob
     subnode['titlesonly'] = 'titlesonly' in self.options
     #what does this do?
     set_source_info(self, subnode)
     wrappernode = nodes.compound(classes=['feed-latest-wrapper'])
     wrappernode.append(subnode)
     ret.append(wrappernode)
     return ret
Beispiel #12
0
    def run(self):
        # type: () -> List[nodes.Node]
        env = self.state.document.settings.env
        suffixes = env.config.source_suffix
        glob = 'glob' in self.options

        ret = []
        # Children of the internal toctree node; these will be rewritten by
        # traversals (and so having other references into these will also
        # get rewritten) but, nicely, are not rendered directly due to the
        # way that the environment code deals with toctrees.
        others = []
        # (title, ref) pairs, where ref may be a document, or an external link,
        # or a node.  title may be None if the document's title is to be used
        # and must be None if a node is given as a ref.
        entries = []  # type: List[Tuple[unicode, Union[unicode,nodes.Node]]]
        includefiles = []
        all_docnames = env.found_docs.copy()
        # don't add the currently visited file in catch-all patterns
        all_docnames.remove(env.docname)
        for entry in self.content:
            if not entry:
                continue
            if entry.startswith("_ "):
                node = nodes.paragraph()
                self.state.nested_parse(ViewList([entry[2:]]), 0, node)
                others.append(node)
                entries.append((None, node))
            elif glob and ('*' in entry or '?' in entry or '[' in entry):
                patname = docname_join(env.docname, entry)
                docnames = sorted(patfilter(all_docnames, patname))
                for docname in docnames:
                    all_docnames.remove(docname)  # don't include it again
                    entries.append((None, docname))
                    includefiles.append(docname)
                if not docnames:
                    ret.append(
                        self.state.document.reporter.warning(
                            'toctree glob pattern %r didn\'t match any documents'
                            % entry,
                            line=self.lineno))
            else:
                # look for explicit titles ("Some Title <document>")
                m = explicit_title_re.match(entry)
                if m:
                    ref = m.group(2)
                    title = m.group(1)
                    docname = ref
                else:
                    ref = docname = entry
                    title = None
                # remove suffixes (backwards compatibility)
                for suffix in suffixes:
                    if docname.endswith(suffix):
                        docname = docname[:-len(suffix)]
                        break
                # absolutize filenames
                docname = docname_join(env.docname, docname)
                if url_re.match(ref) or ref == 'self':
                    entries.append((title, ref))
                elif docname not in env.found_docs:
                    ret.append(
                        self.state.document.reporter.warning(
                            'toctree contains reference to nonexisting '
                            'document %r' % docname,
                            line=self.lineno))
                    env.note_reread()
                else:
                    all_docnames.discard(docname)
                    entries.append((title, docname))
                    includefiles.append(docname)
        subnode = addnodes.toctree()
        subnode['parent'] = env.docname
        # entries contains all entries (self references, external links etc.)
        if 'reversed' in self.options:
            entries.reverse()
        subnode['entries'] = entries
        # includefiles only entries that are documents
        subnode['includefiles'] = includefiles
        subnode['maxdepth'] = self.options.get('maxdepth', -1)
        subnode['caption'] = self.options.get('caption')
        subnode['glob'] = glob
        subnode['hidden'] = 'hidden' in self.options
        subnode['includehidden'] = 'includehidden' in self.options
        subnode['numbered'] = self.options.get('numbered', 0)
        subnode['titlesonly'] = 'titlesonly' in self.options
        subnode.children = others
        set_source_info(self, subnode)
        wrappernode = nodes.compound(classes=['toctree-wrapper'])
        wrappernode.append(subnode)
        self.add_name(wrappernode)
        ret.append(wrappernode)
        return ret
    def run(self):
        env = self.state.document.settings.env
        suffix = env.config.source_suffix
        glob = "glob" in self.options
        limit = "limit" in self.options

        ret = []
        # (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
        entries = []
        includefiles = []
        all_docnames = env.found_docs.copy()
        # don't add the currently visited file in catch-all patterns
        all_docnames.remove(env.docname)
        for entry in self.content:
            if not entry:
                continue
            if not glob:
                # look for explicit titles ("Some Title <document>")
                m = explicit_title_re.match(entry)
                if m:
                    ref = m.group(2)
                    title = m.group(1)
                    docname = ref
                else:
                    ref = docname = entry
                    title = None
                # remove suffixes (backwards compatibility)
                if docname.endswith(suffix):
                    docname = docname[: -len(suffix)]
                # absolutize filenames
                docname = docname_join(env.docname, docname)
                if url_re.match(ref) or ref == "self":
                    entries.append((title, ref))
                elif docname not in env.found_docs:
                    ret.append(
                        self.state.document.reporter.warning(
                            "toctree contains reference to nonexisting " "document %r" % docname, line=self.lineno
                        )
                    )
                    env.note_reread()
                else:
                    entries.append((title, docname))
                    includefiles.append(docname)
            else:
                patname = docname_join(env.docname, entry)
                docnames = sorted(patfilter(all_docnames, patname))
                for docname in docnames:
                    all_docnames.remove(docname)  # don't include it again
                    entries.append((None, docname))
                    includefiles.append(docname)
                if not docnames:
                    ret.append(
                        self.state.document.reporter.warning(
                            "toctree glob pattern %r didn't match any documents" % entry, line=self.lineno
                        )
                    )

        sorted_entries = {}
        for entry in entries:
            metadata = env.metadata.get(entry[1], {})

            if "date" not in metadata:
                continue
            try:
                pub_date = parse_date(metadata["date"])
                env.metadata.get(entry[1], {})
            except ValueError, exc:
                continue

            sorted_entries[pub_date.isoformat()] = entry
Beispiel #14
0
def insert_toctrees(app: Sphinx, doctree: nodes.document) -> None:
    """Create the toctree nodes and add it to the document.

    Adapted from `sphinx/directives/other.py::TocTree`
    """
    # check for existing toctrees and raise warning
    for node in doctree.traverse(toctree_node):
        create_warning(
            app,
            doctree,
            "toctree",
            "toctree directive not expected with external-toc",
            line=node.line,
        )

    toc_placeholders: List[TableOfContentsNode] = list(
        doctree.traverse(TableOfContentsNode)
    )

    site_map: SiteMap = app.env.external_site_map
    doc_item: Optional[Document] = site_map.get(app.env.docname)

    if doc_item is None or not doc_item.subtrees:
        if toc_placeholders:
            create_warning(
                app,
                doctree,
                "tableofcontents",
                "tableofcontents directive in document with no descendants",
            )
        for node in toc_placeholders:
            node.replace_self([])
        return

    # TODO allow for more than one tableofcontents, i.e. per part?
    for node in toc_placeholders[1:]:
        create_warning(
            app,
            doctree,
            "tableofcontents",
            "more than one tableofcontents directive in document",
            line=node.line,
        )
        node.replace_self([])

    # initial variables
    all_docnames = app.env.found_docs.copy()
    all_docnames.remove(app.env.docname)  # remove current document
    excluded = Matcher(app.config.exclude_patterns)

    node_list: List[nodes.Element] = []

    for toctree in doc_item.subtrees:

        subnode = toctree_node()
        subnode["parent"] = app.env.docname
        subnode.source = doctree.source
        subnode["entries"] = []
        subnode["includefiles"] = []
        subnode["maxdepth"] = toctree.maxdepth
        subnode["caption"] = toctree.caption
        # TODO this wasn't in the original code,
        # but alabaster theme intermittently raised `KeyError('rawcaption')`
        subnode["rawcaption"] = toctree.caption or ""
        subnode["glob"] = any(isinstance(entry, GlobItem) for entry in toctree.items)
        subnode["hidden"] = False if toc_placeholders else toctree.hidden
        subnode["includehidden"] = False
        subnode["numbered"] = (
            0
            if toctree.numbered is False
            else (999 if toctree.numbered is True else int(toctree.numbered))
        )
        subnode["titlesonly"] = toctree.titlesonly
        wrappernode = nodes.compound(classes=["toctree-wrapper"])
        wrappernode.append(subnode)

        for entry in toctree.items:

            if isinstance(entry, UrlItem):

                subnode["entries"].append((entry.title, entry.url))

            elif isinstance(entry, FileItem):

                child_doc_item = site_map[entry]
                docname = str(entry)
                title = child_doc_item.title

                docname = remove_suffix(docname, app.config.source_suffix)

                if docname not in app.env.found_docs:
                    if excluded(app.env.doc2path(docname, None)):
                        message = f"toctree contains reference to excluded document {docname!r}"
                    else:
                        message = f"toctree contains reference to nonexisting document {docname!r}"

                    create_warning(app, doctree, "ref", message, append_to=node_list)
                    app.env.note_reread()
                else:
                    subnode["entries"].append((title, docname))
                    subnode["includefiles"].append(docname)

            elif isinstance(entry, GlobItem):
                patname = str(entry)
                docnames = sorted(patfilter(all_docnames, patname))
                for docname in docnames:
                    all_docnames.remove(docname)  # don't include it again
                    subnode["entries"].append((None, docname))
                    subnode["includefiles"].append(docname)
                if not docnames:
                    message = (
                        f"toctree glob pattern '{entry}' didn't match any documents"
                    )
                    create_warning(app, doctree, "glob", message, append_to=node_list)

        # reversing entries can be useful when globbing
        if toctree.reversed:
            subnode["entries"] = list(reversed(subnode["entries"]))
            subnode["includefiles"] = list(reversed(subnode["includefiles"]))

        node_list.append(wrappernode)

    if toc_placeholders:
        toc_placeholders[0].replace_self(node_list)
    else:
        # note here the toctree cannot not just be appended to the end of the doc,
        # since `TocTreeCollector.process_doc` expects it in a section
        # TODO check if there is this is always ok
        doctree.children[-1].extend(node_list)
Beispiel #15
0
    def run(self):
        # type: () -> List[nodes.Node]
        env = self.state.document.settings.env
        suffixes = env.config.source_suffix
        glob = 'glob' in self.options

        ret = []
        # Children of the internal toctree node; these will be rewritten by
        # traversals (and so having other references into these will also
        # get rewritten) but, nicely, are not rendered directly due to the
        # way that the environment code deals with toctrees.
        others = []
        # (title, ref) pairs, where ref may be a document, or an external link,
        # or a node.  title may be None if the document's title is to be used
        # and must be None if a node is given as a ref.
        entries = []        # type: List[Tuple[unicode, Union[unicode,nodes.Node]]]
        includefiles = []
        all_docnames = env.found_docs.copy()
        # don't add the currently visited file in catch-all patterns
        all_docnames.remove(env.docname)
        for entry in self.content:
            if not entry:
                continue
            if entry.startswith("_ "):
                node = nodes.paragraph()
                self.state.nested_parse(ViewList([entry[2:]]), 0, node)
                others.append(node)
                entries.append((None, node))
            elif glob and ('*' in entry or '?' in entry or '[' in entry):
                patname = docname_join(env.docname, entry)
                docnames = sorted(patfilter(all_docnames, patname))
                for docname in docnames:
                    all_docnames.remove(docname)  # don't include it again
                    entries.append((None, docname))
                    includefiles.append(docname)
                if not docnames:
                    ret.append(self.state.document.reporter.warning(
                        'toctree glob pattern %r didn\'t match any documents'
                        % entry, line=self.lineno))
            else:
                # look for explicit titles ("Some Title <document>")
                m = explicit_title_re.match(entry)
                if m:
                    ref = m.group(2)
                    title = m.group(1)
                    docname = ref
                else:
                    ref = docname = entry
                    title = None
                # remove suffixes (backwards compatibility)
                for suffix in suffixes:
                    if docname.endswith(suffix):
                        docname = docname[:-len(suffix)]
                        break
                # absolutize filenames
                docname = docname_join(env.docname, docname)
                if url_re.match(ref) or ref == 'self':
                    entries.append((title, ref))
                elif docname not in env.found_docs:
                    ret.append(self.state.document.reporter.warning(
                        'toctree contains reference to nonexisting '
                        'document %r' % docname, line=self.lineno))
                    env.note_reread()
                else:
                    all_docnames.discard(docname)
                    entries.append((title, docname))
                    includefiles.append(docname)
        subnode = addnodes.toctree()
        subnode['parent'] = env.docname
        # entries contains all entries (self references, external links etc.)
        if 'reversed' in self.options:
            entries.reverse()
        subnode['entries'] = entries
        # includefiles only entries that are documents
        subnode['includefiles'] = includefiles
        subnode['maxdepth'] = self.options.get('maxdepth', -1)
        subnode['caption'] = self.options.get('caption')
        subnode['glob'] = glob
        subnode['hidden'] = 'hidden' in self.options
        subnode['includehidden'] = 'includehidden' in self.options
        subnode['numbered'] = self.options.get('numbered', 0)
        subnode['titlesonly'] = 'titlesonly' in self.options
        subnode.children = others
        set_source_info(self, subnode)
        wrappernode = nodes.compound(classes=['toctree-wrapper'])
        wrappernode.append(subnode)
        self.add_name(wrappernode)
        ret.append(wrappernode)
        return ret