Example #1
0
def test_missing_reference_pydomain(tempdir, app, status, warning):
    inv_file = tempdir / 'inventory'
    inv_file.write_bytes(inventory_v2)
    app.config.intersphinx_mapping = {
        'https://docs.python.org/': inv_file,
    }
    app.config.intersphinx_cache_limit = 0

    # load the inventory and check if it's done correctly
    normalize_intersphinx_mapping(app, app.config)
    load_mappings(app)

    # no context data
    kwargs = {}
    node, contnode = fake_node('py', 'func', 'func', 'func()', **kwargs)
    rn = missing_reference(app, app.env, node, contnode)
    assert rn is None

    # py:module context helps to search objects
    kwargs = {'py:module': 'module1'}
    node, contnode = fake_node('py', 'func', 'func', 'func()', **kwargs)
    rn = missing_reference(app, app.env, node, contnode)
    assert rn.astext() == 'func()'

    # py:attr context helps to search objects
    kwargs = {'py:module': 'module1'}
    node, contnode = fake_node('py', 'attr', 'Foo.bar', 'Foo.bar', **kwargs)
    rn = missing_reference(app, app.env, node, contnode)
    assert rn.astext() == 'Foo.bar'
Example #2
0
def test_missing_reference_stddomain(tempdir, app, status, warning):
    inv_file = tempdir / 'inventory'
    inv_file.write_bytes(inventory_v2)
    app.config.intersphinx_mapping = {
        'cmd': ('https://docs.python.org/', inv_file),
    }
    app.config.intersphinx_cache_limit = 0

    # load the inventory and check if it's done correctly
    normalize_intersphinx_mapping(app, app.config)
    load_mappings(app)

    # no context data
    kwargs = {}
    node, contnode = fake_node('std', 'option', '-l', '-l', **kwargs)
    rn = missing_reference(app, app.env, node, contnode)
    assert rn is None

    # std:program context helps to search objects
    kwargs = {'std:program': 'ls'}
    node, contnode = fake_node('std', 'option', '-l', 'ls -l', **kwargs)
    rn = missing_reference(app, app.env, node, contnode)
    assert rn.astext() == 'ls -l'

    # refers inventory by name
    kwargs = {}
    node, contnode = fake_node('std', 'option', 'cmd:ls -l', '-l', **kwargs)
    rn = missing_reference(app, app.env, node, contnode)
    assert rn.astext() == '-l'
Example #3
0
def test_missing_reference_stddomain(tempdir, app, status, warning):
    inv_file = tempdir / 'inventory'
    inv_file.write_bytes(inventory_v2)
    app.config.intersphinx_mapping = {
        'cmd': ('https://docs.python.org/', inv_file),
    }
    app.config.intersphinx_cache_limit = 0

    # load the inventory and check if it's done correctly
    load_mappings(app)

    # no context data
    kwargs = {}
    node, contnode = fake_node('std', 'option', '-l', '-l', **kwargs)
    rn = missing_reference(app, app.env, node, contnode)
    assert rn is None

    # std:program context helps to search objects
    kwargs = {'std:program': 'ls'}
    node, contnode = fake_node('std', 'option', '-l', 'ls -l', **kwargs)
    rn = missing_reference(app, app.env, node, contnode)
    assert rn.astext() == 'ls -l'

    # refers inventory by name
    kwargs = {}
    node, contnode = fake_node('std', 'option', 'cmd:ls -l', '-l', **kwargs)
    rn = missing_reference(app, app.env, node, contnode)
    assert rn.astext() == '-l'
def replace_target_intersphinx(app, env, node, contnode):
    reftarget_replace = app.config.reftarget_replace
    target = node.get("reftarget", None)
    if target:
        for old, new in reftarget_replace.items():
            node["reftarget"] = target.replace(old, new)
    return missing_reference(app, env, node, contnode)
Example #5
0
def call_intersphinx(app, env, node, contnode):
    """
    Call intersphinx and make links between Sage manuals relative.

    TESTS:

    Check that the link from the thematic tutorials to the reference
    manual is relative, see :trac:`20118`::

        sage: from sage.env import SAGE_DOC  # optional - dochtml
        sage: thematic_index = os.path.join(SAGE_DOC, "html", "en", "thematic_tutorials", "index.html")  # optional - dochtml
        sage: for line in open(thematic_index).readlines():  # optional - dochtml
        ....:     if "padics" in line:
        ....:         _ = sys.stdout.write(line)
        <li><p><a class="reference external" href="../reference/padics/sage/rings/padics/tutorial.html#sage-rings-padics-tutorial" title="(in Sage... Reference Manual: p-Adics v...)"><span>Introduction to the p-adics</span></a></p></li>
    """
    debug_inf(app, "???? Trying intersphinx for %s" % node['reftarget'])
    builder = app.builder
    res = intersphinx.missing_reference(app, env, node, contnode)
    if res:
        # Replace absolute links to $SAGE_DOC by relative links: this
        # allows to copy the whole documentation tree somewhere else
        # without breaking links, see Trac #20118.
        if res['refuri'].startswith(SAGE_DOC):
            here = os.path.dirname(os.path.join(builder.outdir,
                                                node['refdoc']))
            res['refuri'] = os.path.relpath(res['refuri'], here)
            debug_inf(app, "++++ Found at %s" % res['refuri'])
    else:
        debug_inf(app, "---- Intersphinx: %s not Found" % node['reftarget'])
    return res
Example #6
0
def missing_reference(app, env, node, contnode):
    """Search the index for missing references.
    For example, resolve :class:`Event` to :class:`Event <gevent.event.Event>`"""
    # XXX methods and functions resolved by this function miss their ()

    if intersphinx.missing_reference(app, env, node, contnode) is not None:
        # is there a better way to give intersphinx a bigger priority?
        return

    env = app.builder.env

    type = node['reftype']
    target = node['reftarget']
    modname = node.get('py:module')
    classname = node.get('py:class')

    if modname and classname:
        return

    def new_reference(refuri, reftitle):
        newnode = nodes.reference('', '')
        newnode['refuri'] = refuri
        newnode['reftitle'] = reftitle
        newnode['py:class'] = 'external-xref'
        newnode['classname'] = 'external-xref'
        newnode.append(contnode)
        msg = 'Resolved missing-reference: :%5s:`%s` -> %s' % (type, target, refuri)
        if noisy >= 1 or msg not in message_cache:
            print(msg)
            message_cache.add(msg)
        return newnode

    if noisy >= 1:
        print('Looking for %s' % [type, target, modname, classname])
        print(node)

    for docname, items in env.indexentries.items():
        if noisy >= 2:
            print(docname)
        for _x in items:
            if noisy >= 4:
                print(_x)
            (i_type, i_string, i_target, i_aliasname) = _x[:4]
            if noisy >= 3:
                print('---', [i_type, i_string, i_target, i_aliasname])
            if i_aliasname.endswith(target):
                stripped_aliasname = i_aliasname[len(docname):]
                if stripped_aliasname:
                    assert stripped_aliasname[0] == '.', repr(stripped_aliasname)
                    stripped_aliasname = stripped_aliasname[1:]
                    if stripped_aliasname == target:
                        if noisy >= 1:
                            print('--- found %s %s in %s' % (type, target, i_aliasname))
                        return new_reference(docname + '.html#' + i_aliasname, i_aliasname)

    if type == 'mod':
        modules = [x for x in env.indexentries.keys() if x.startswith('gevent.')]
        target = 'gevent.' + target
        if target in modules:
            return new_reference(target + '.html', target)
def resolve_intersphinx_aliases(app, env, node, contnode):
    alias = node.get('reftarget')
    if alias is not None and alias in reftarget_aliases:
        resolved_ref, text = reftarget_aliases[alias]
        node['reftarget'] = resolved_ref
        text_node = next(iter(
            contnode.traverse(lambda n: n.tagname == '#text')))
        text_node.parent.replace(text, Text(text, ''))
        return missing_reference(app, env, node, contnode)
    return None
Example #8
0
def __sphinx_issue_8127(app, env, node, contnode):
    reftarget = node.get("reftarget", None)
    if reftarget == "..":
        node["reftype"] = "data"
        node["reftarget"] = "Ellipsis"
        text_node = next(iter(contnode.traverse(lambda n: n.tagname == "#text")))
        replacement_node = Text("...", "")
        if text_node.parent is not None:
            text_node.parent.replace(text_node, replacement_node)
        else:  # e.g. happens in rtype fields
            contnode = replacement_node
        return missing_reference(app, env, node, contnode)
Example #9
0
def test_missing_reference_jsdomain(tempdir, app, status, warning):
    inv_file = tempdir / 'inventory'
    inv_file.write_bytes(inventory_v2)
    app.config.intersphinx_mapping = {
        'https://docs.python.org/': inv_file,
    }
    app.config.intersphinx_cache_limit = 0

    # load the inventory and check if it's done correctly
    load_mappings(app)

    # no context data
    kwargs = {}
    node, contnode = fake_node('js', 'meth', 'baz', 'baz()', **kwargs)
    rn = missing_reference(app, app.env, node, contnode)
    assert rn is None

    # js:module and js:object context helps to search objects
    kwargs = {'js:module': 'foo', 'js:object': 'bar'}
    node, contnode = fake_node('js', 'meth', 'baz', 'baz()', **kwargs)
    rn = missing_reference(app, app.env, node, contnode)
    assert rn.astext() == 'baz()'
Example #10
0
def test_missing_reference_jsdomain(tempdir, app, status, warning):
    inv_file = tempdir / 'inventory'
    inv_file.write_bytes(inventory_v2)
    app.config.intersphinx_mapping = {
        'https://docs.python.org/': inv_file,
    }
    app.config.intersphinx_cache_limit = 0

    # load the inventory and check if it's done correctly
    load_mappings(app)

    # no context data
    kwargs = {}
    node, contnode = fake_node('js', 'meth', 'baz', 'baz()', **kwargs)
    rn = missing_reference(app, app.env, node, contnode)
    assert rn is None

    # js:module and js:object context helps to search objects
    kwargs = {'js:module': 'foo', 'js:object': 'bar'}
    node, contnode = fake_node('js', 'meth', 'baz', 'baz()', **kwargs)
    rn = missing_reference(app, app.env, node, contnode)
    assert rn.astext() == 'baz()'
Example #11
0
def test_missing_reference_pydomain(tempdir, app, status, warning):
    inv_file = tempdir / 'inventory'
    inv_file.write_bytes(inventory_v2)
    app.config.intersphinx_mapping = {
        'https://docs.python.org/': inv_file,
    }
    app.config.intersphinx_cache_limit = 0

    # load the inventory and check if it's done correctly
    normalize_intersphinx_mapping(app, app.config)
    load_mappings(app)

    # no context data
    kwargs = {}
    node, contnode = fake_node('py', 'func', 'func', 'func()', **kwargs)
    rn = missing_reference(app, app.env, node, contnode)
    assert rn is None

    # py:module context helps to search objects
    kwargs = {'py:module': 'module1'}
    node, contnode = fake_node('py', 'func', 'func', 'func()', **kwargs)
    rn = missing_reference(app, app.env, node, contnode)
    assert rn.astext() == 'func()'

    # py:attr context helps to search objects
    kwargs = {'py:module': 'module1'}
    node, contnode = fake_node('py', 'attr', 'Foo.bar', 'Foo.bar', **kwargs)
    rn = missing_reference(app, app.env, node, contnode)
    assert rn.astext() == 'Foo.bar'

    # pending_xref_condition="resolved"
    node = addnodes.pending_xref('', reftarget='Foo.bar', refdomain='py', reftype='attr')
    node['py:module'] = 'module1'
    node += addnodes.pending_xref_condition('', 'Foo.bar', condition='resolved')
    node += addnodes.pending_xref_condition('', 'module1.Foo.bar', condition='*')
    rn = missing_reference(app, app.env, node, nodes.Text('dummy-cont-node'))
    assert rn.astext() == 'Foo.bar'
Example #12
0
def resolve_intersphinx_aliases(app, env, node, contnode):
    reftarget_aliases = app.config.ref_aliases
    alias = node.get("reftarget", None)
    if alias is not None and alias in reftarget_aliases:
        real_ref, text_to_render = reftarget_aliases[alias]
        # this will resolve the ref
        node["reftarget"] = real_ref

        # this will rewrite the rendered text:
        # find the text node child
        text_node = next(iter(contnode.traverse(lambda n: n.tagname == "#text")))
        # remove the old text node, add new text node with custom text
        text_node.parent.replace(text_node, Text(text_to_render, ""))

        # delegate all the rest of dull work to intersphinx
        return missing_reference(app, env, node, contnode)
Example #13
0
    def case(*, term, doc, py):
        def assert_(rn, expected):
            if expected is None:
                assert rn is None
            else:
                assert rn.astext() == expected

        kwargs = {}

        node, contnode = fake_node('std', 'term', 'a term', 'a term', **kwargs)
        rn = missing_reference(app, app.env, node, contnode)
        assert_(rn, 'a term' if term else None)

        node, contnode = fake_node('std', 'term', 'inv:a term', 'a term',
                                   **kwargs)
        rn = missing_reference(app, app.env, node, contnode)
        assert_(rn, 'a term')

        node, contnode = fake_node('std', 'doc', 'docname', 'docname',
                                   **kwargs)
        rn = missing_reference(app, app.env, node, contnode)
        assert_(rn, 'docname' if doc else None)

        node, contnode = fake_node('std', 'doc', 'inv:docname', 'docname',
                                   **kwargs)
        rn = missing_reference(app, app.env, node, contnode)
        assert_(rn, 'docname')

        # an arbitrary ref in another domain
        node, contnode = fake_node('py', 'func', 'module1.func', 'func()',
                                   **kwargs)
        rn = missing_reference(app, app.env, node, contnode)
        assert_(rn, 'func()' if py else None)

        node, contnode = fake_node('py', 'func', 'inv:module1.func', 'func()',
                                   **kwargs)
        rn = missing_reference(app, app.env, node, contnode)
        assert_(rn, 'func()')
Example #14
0
def test_missing_reference(tempdir, app, status, warning):
    inv_file = tempdir / 'inventory'
    inv_file.write_bytes(inventory_v2)
    app.config.intersphinx_mapping = {
        'https://docs.python.org/': inv_file,
        'py3k': ('https://docs.python.org/py3k/', inv_file),
        'py3krel': ('py3k', inv_file),  # relative path
        'py3krelparent': ('../../py3k', inv_file),  # relative path, parent dir
    }
    app.config.intersphinx_cache_limit = 0

    # load the inventory and check if it's done correctly
    normalize_intersphinx_mapping(app, app.config)
    load_mappings(app)
    inv = app.env.intersphinx_inventory

    assert inv['py:module']['module2'] == \
        ('foo', '2.0', 'https://docs.python.org/foo.html#module-module2', '-')

    # check resolution when a target is found
    rn = reference_check(app, 'py', 'func', 'module1.func', 'foo')
    assert isinstance(rn, nodes.reference)
    assert rn['refuri'] == 'https://docs.python.org/sub/foo.html#module1.func'
    assert rn['reftitle'] == '(in foo v2.0)'
    assert rn[0].astext() == 'foo'

    # create unresolvable nodes and check None return value
    assert reference_check(app, 'py', 'foo', 'module1.func', 'foo') is None
    assert reference_check(app, 'py', 'func', 'foo', 'foo') is None
    assert reference_check(app, 'py', 'func', 'foo', 'foo') is None

    # check handling of prefixes

    # prefix given, target found: prefix is stripped
    rn = reference_check(app, 'py', 'mod', 'py3k:module2', 'py3k:module2')
    assert rn[0].astext() == 'module2'

    # prefix given, but not in title: nothing stripped
    rn = reference_check(app, 'py', 'mod', 'py3k:module2', 'module2')
    assert rn[0].astext() == 'module2'

    # prefix given, but explicit: nothing stripped
    rn = reference_check(app,
                         'py',
                         'mod',
                         'py3k:module2',
                         'py3k:module2',
                         refexplicit=True)
    assert rn[0].astext() == 'py3k:module2'

    # prefix given, target not found and nonexplicit title: prefix is stripped
    node, contnode = fake_node('py',
                               'mod',
                               'py3k:unknown',
                               'py3k:unknown',
                               refexplicit=False)
    rn = missing_reference(app, app.env, node, contnode)
    assert rn is None
    assert contnode[0].astext() == 'unknown'

    # prefix given, target not found and explicit title: nothing is changed
    node, contnode = fake_node('py',
                               'mod',
                               'py3k:unknown',
                               'py3k:unknown',
                               refexplicit=True)
    rn = missing_reference(app, app.env, node, contnode)
    assert rn is None
    assert contnode[0].astext() == 'py3k:unknown'

    # check relative paths
    rn = reference_check(app, 'py', 'mod', 'py3krel:module1', 'foo')
    assert rn['refuri'] == 'py3k/foo.html#module-module1'

    rn = reference_check(app, 'py', 'mod', 'py3krelparent:module1', 'foo')
    assert rn['refuri'] == '../../py3k/foo.html#module-module1'

    rn = reference_check(app,
                         'py',
                         'mod',
                         'py3krel:module1',
                         'foo',
                         refdoc='sub/dir/test')
    assert rn['refuri'] == '../../py3k/foo.html#module-module1'

    rn = reference_check(app,
                         'py',
                         'mod',
                         'py3krelparent:module1',
                         'foo',
                         refdoc='sub/dir/test')
    assert rn['refuri'] == '../../../../py3k/foo.html#module-module1'

    # check refs of standard domain
    rn = reference_check(app, 'std', 'doc', 'docname', 'docname')
    assert rn['refuri'] == 'https://docs.python.org/docname.html'
Example #15
0
def reference_check(app, *args, **kwds):
    node, contnode = fake_node(*args, **kwds)
    return missing_reference(app, app.env, node, contnode)
Example #16
0
def test_missing_reference(tempdir, app, status, warning):
    inv_file = tempdir / 'inventory'
    inv_file.write_bytes(inventory_v2)
    app.config.intersphinx_mapping = {
        'https://docs.python.org/': inv_file,
        'py3k': ('https://docs.python.org/py3k/', inv_file),
    }
    app.config.intersphinx_cache_limit = 0

    # load the inventory and check if it's done correctly
    load_mappings(app)
    inv = app.env.intersphinx_inventory

    assert inv['py:module']['module2'] == \
        ('foo', '2.0', 'https://docs.python.org/foo.html#module-module2', '-')

    # create fake nodes and check referencing

    def fake_node(domain, type, target, content, **attrs):
        contnode = nodes.emphasis(content, content)
        node = addnodes.pending_xref('')
        node['reftarget'] = target
        node['reftype'] = type
        node['refdomain'] = domain
        node.attributes.update(attrs)
        node += contnode
        return node, contnode

    def reference_check(*args, **kwds):
        node, contnode = fake_node(*args, **kwds)
        return missing_reference(app, app.env, node, contnode)

    # check resolution when a target is found
    rn = reference_check('py', 'func', 'module1.func', 'foo')
    assert isinstance(rn, nodes.reference)
    assert rn['refuri'] == 'https://docs.python.org/sub/foo.html#module1.func'
    assert rn['reftitle'] == '(in foo v2.0)'
    assert rn[0].astext() == 'foo'

    # create unresolvable nodes and check None return value
    assert reference_check('py', 'foo', 'module1.func', 'foo') is None
    assert reference_check('py', 'func', 'foo', 'foo') is None
    assert reference_check('py', 'func', 'foo', 'foo') is None

    # check handling of prefixes

    # prefix given, target found: prefix is stripped
    rn = reference_check('py', 'mod', 'py3k:module2', 'py3k:module2')
    assert rn[0].astext() == 'module2'

    # prefix given, but not in title: nothing stripped
    rn = reference_check('py', 'mod', 'py3k:module2', 'module2')
    assert rn[0].astext() == 'module2'

    # prefix given, but explicit: nothing stripped
    rn = reference_check('py',
                         'mod',
                         'py3k:module2',
                         'py3k:module2',
                         refexplicit=True)
    assert rn[0].astext() == 'py3k:module2'

    # prefix given, target not found and nonexplicit title: prefix is stripped
    node, contnode = fake_node('py',
                               'mod',
                               'py3k:unknown',
                               'py3k:unknown',
                               refexplicit=False)
    rn = missing_reference(app, app.env, node, contnode)
    assert rn is None
    assert contnode[0].astext() == 'unknown'

    # prefix given, target not found and explicit title: nothing is changed
    node, contnode = fake_node('py',
                               'mod',
                               'py3k:unknown',
                               'py3k:unknown',
                               refexplicit=True)
    rn = missing_reference(app, app.env, node, contnode)
    assert rn is None
    assert contnode[0].astext() == 'py3k:unknown'
Example #17
0
def test_missing_reference(tempdir, app, status, warning):
    inv_file = tempdir / 'inventory'
    inv_file.write_bytes(inventory_v2)
    app.config.intersphinx_mapping = {
        'https://docs.python.org/': inv_file,
        'py3k': ('https://docs.python.org/py3k/', inv_file),
    }
    app.config.intersphinx_cache_limit = 0

    # load the inventory and check if it's done correctly
    load_mappings(app)
    inv = app.env.intersphinx_inventory

    assert inv['py:module']['module2'] == \
        ('foo', '2.0', 'https://docs.python.org/foo.html#module-module2', '-')

    # create fake nodes and check referencing

    def fake_node(domain, type, target, content, **attrs):
        contnode = nodes.emphasis(content, content)
        node = addnodes.pending_xref('')
        node['reftarget'] = target
        node['reftype'] = type
        node['refdomain'] = domain
        node.attributes.update(attrs)
        node += contnode
        return node, contnode

    def reference_check(*args, **kwds):
        node, contnode = fake_node(*args, **kwds)
        return missing_reference(app, app.env, node, contnode)

    # check resolution when a target is found
    rn = reference_check('py', 'func', 'module1.func', 'foo')
    assert isinstance(rn, nodes.reference)
    assert rn['refuri'] == 'https://docs.python.org/sub/foo.html#module1.func'
    assert rn['reftitle'] == '(in foo v2.0)'
    assert rn[0].astext() == 'foo'

    # create unresolvable nodes and check None return value
    assert reference_check('py', 'foo', 'module1.func', 'foo') is None
    assert reference_check('py', 'func', 'foo', 'foo') is None
    assert reference_check('py', 'func', 'foo', 'foo') is None

    # check handling of prefixes

    # prefix given, target found: prefix is stripped
    rn = reference_check('py', 'mod', 'py3k:module2', 'py3k:module2')
    assert rn[0].astext() == 'module2'

    # prefix given, but not in title: nothing stripped
    rn = reference_check('py', 'mod', 'py3k:module2', 'module2')
    assert rn[0].astext() == 'module2'

    # prefix given, but explicit: nothing stripped
    rn = reference_check('py', 'mod', 'py3k:module2', 'py3k:module2',
                         refexplicit=True)
    assert rn[0].astext() == 'py3k:module2'

    # prefix given, target not found and nonexplicit title: prefix is stripped
    node, contnode = fake_node('py', 'mod', 'py3k:unknown', 'py3k:unknown',
                               refexplicit=False)
    rn = missing_reference(app, app.env, node, contnode)
    assert rn is None
    assert contnode[0].astext() == 'unknown'

    # prefix given, target not found and explicit title: nothing is changed
    node, contnode = fake_node('py', 'mod', 'py3k:unknown', 'py3k:unknown',
                               refexplicit=True)
    rn = missing_reference(app, app.env, node, contnode)
    assert rn is None
    assert contnode[0].astext() == 'py3k:unknown'
Example #18
0
def missing_reference(app, env, node, contnode):
    """Search the index for missing references.
    For example, resolve :class:`Event` to :class:`Event <gevent.event.Event>`"""
    # XXX methods and functions resolved by this function miss their ()

    if intersphinx.missing_reference(app, env, node, contnode) is not None:
        # is there a better way to give intersphinx a bigger priority?
        return

    env = app.builder.env

    type = node['reftype']
    target = node['reftarget']
    modname = node.get('py:module')
    classname = node.get('py:class')

    if modname and classname:
        return

    def new_reference(refuri, reftitle):
        newnode = nodes.reference('', '')
        newnode['refuri'] = refuri
        newnode['reftitle'] = reftitle
        newnode['py:class'] = 'external-xref'
        newnode['classname'] = 'external-xref'
        newnode.append(contnode)
        msg = 'Resolved missing-reference: :%5s:`%s` -> %s' % (type, target,
                                                               refuri)
        if noisy >= 1 or msg not in message_cache:
            print(msg)
            message_cache.add(msg)
        return newnode

    if noisy >= 1:
        print('Looking for %s' % [type, target, modname, classname])
        print(node)

    for docname, items in env.indexentries.items():
        if noisy >= 2:
            print(docname)
        for (i_type, i_string, i_target, i_aliasname) in items:
            if noisy >= 3:
                print('---', [i_type, i_string, i_target, i_aliasname])
            if i_aliasname.endswith(target):
                stripped_aliasname = i_aliasname[len(docname):]
                if stripped_aliasname:
                    assert stripped_aliasname[0] == '.', repr(
                        stripped_aliasname)
                    stripped_aliasname = stripped_aliasname[1:]
                    if stripped_aliasname == target:
                        if noisy >= 1:
                            print('--- found %s %s in %s' %
                                  (type, target, i_aliasname))
                        return new_reference(docname + '.html#' + i_aliasname,
                                             i_aliasname)

    if type == 'mod':
        modules = [
            x for x in env.indexentries.keys() if x.startswith('gevent.')
        ]
        target = 'gevent.' + target
        if target in modules:
            return new_reference(target + '.html', target)
def _on_missing_reference(app, env, node, contnode):
    """Handler for missing references.

    This will attempt to fix references to options and then attempt to
    apply default intersphinx prefixes (if needed) before resolving a
    reference using intersphinx.

    Args:
        app (sphinx.application.Sphinx):
            The Sphinx application processing the document.

        env (sphinx.environment.BuildEnvironment):
            The environment for this doc build.

        node (sphinx.addnodes.pending_xref):
            The pending reference to resolve.

        contnode (docutils.nodes.literal):
            The context for the reference.

    Returns:
        list:
        The list of any reference nodes, as created by intersphinx.
    """
    orig_target = node['reftarget']
    target = orig_target
    domain = node.get('refdomain')

    # See if we're referencing a std:option. Sphinx (as of 1.6.1) does not
    # properly link these. A pull request has been opened to fix this
    # (https://github.com/sphinx-doc/sphinx/pull/3769). Until we can make
    # use of that, we're including the workaround here.
    if domain == 'std' and node['reftype'] == 'option':
        # Options are stored in the inventory as "program-name.--option".
        # In order to look up the option, the target will need to be
        # converted to this format.
        #
        # Ideally, we'd be able to utilize the same logic as found in
        # StandardDomain._resolve_option_xref, but we don't have any
        # information on the progoptions data stored there. Instead, we
        # try to determine if the target already has a program name or
        # an intersphinx doc set and normalize the contents to match the
        # option reference name format.
        i = target.rfind(' ')

        if i != -1:
            # The option target contains a program name and an option
            # name. We can easily normalize this to be in
            # <progname>.<option> format.
            target = '%s.%s' % (target[:i], target[i + 1:])
            target = target.replace(' ', '-')
        else:
            # Since a space was not found, and a program name is needed
            # to complete the reference, we'll see if a ".. program::"
            # has been set in this file. If so, we'll put that into the
            # target name (being careful to consider any intersphinx doc
            # set name that may be prefixed).
            progname = node.get('std:program')

            if progname:
                if ':' in target:
                    setname, newtarget = target.split(':', 1)
                    target = '%s:%s.%s' % (setname, progname, newtarget)
                else:
                    target = '%s.%s' % (progname, target)

    if ':' not in target:
        prefixes = \
            env.metadata[env.docname].get('default-intersphinx-prefixes')

        if prefixes:
            # Try all supported prefixes in order. These are the only allowed
            # to be inferred.
            for prefix in prefixes:
                old_content = contnode[0]
                node['reftarget'] = '%s:%s' % (prefix, target)
                result = intersphinx.missing_reference(app, env, node,
                                                       contnode)

                if result:
                    return result

                # Couldn't find it. Go back to the original target and try
                # again.
                node['reftarget'] = orig_target
                contnode[0] = old_content

            return None

    return intersphinx.missing_reference(app, env, node, contnode)
Example #20
0
 def reference_check(*args, **kwds):
     node, contnode = fake_node(*args, **kwds)
     return missing_reference(app, app.env, node, contnode)
Example #21
0
def test_missing_reference(tempdir, app, status, warning):
    inv_file = tempdir / "inventory"
    inv_file.write_bytes(inventory_v2)
    app.config.intersphinx_mapping = {
        "https://docs.python.org/": inv_file,
        "py3k": ("https://docs.python.org/py3k/", inv_file),
    }
    app.config.intersphinx_cache_limit = 0

    # load the inventory and check if it's done correctly
    load_mappings(app)
    inv = app.env.intersphinx_inventory

    assert inv["py:module"]["module2"] == ("foo", "2.0", "https://docs.python.org/foo.html#module-module2", "-")

    # create fake nodes and check referencing

    def fake_node(domain, type, target, content, **attrs):
        contnode = nodes.emphasis(content, content)
        node = addnodes.pending_xref("")
        node["reftarget"] = target
        node["reftype"] = type
        node["refdomain"] = domain
        node.attributes.update(attrs)
        node += contnode
        return node, contnode

    def reference_check(*args, **kwds):
        node, contnode = fake_node(*args, **kwds)
        return missing_reference(app, app.env, node, contnode)

    # check resolution when a target is found
    rn = reference_check("py", "func", "module1.func", "foo")
    assert isinstance(rn, nodes.reference)
    assert rn["refuri"] == "https://docs.python.org/sub/foo.html#module1.func"
    assert rn["reftitle"] == "(in foo v2.0)"
    assert rn[0].astext() == "foo"

    # create unresolvable nodes and check None return value
    assert reference_check("py", "foo", "module1.func", "foo") is None
    assert reference_check("py", "func", "foo", "foo") is None
    assert reference_check("py", "func", "foo", "foo") is None

    # check handling of prefixes

    # prefix given, target found: prefix is stripped
    rn = reference_check("py", "mod", "py3k:module2", "py3k:module2")
    assert rn[0].astext() == "module2"

    # prefix given, but not in title: nothing stripped
    rn = reference_check("py", "mod", "py3k:module2", "module2")
    assert rn[0].astext() == "module2"

    # prefix given, but explicit: nothing stripped
    rn = reference_check("py", "mod", "py3k:module2", "py3k:module2", refexplicit=True)
    assert rn[0].astext() == "py3k:module2"

    # prefix given, target not found and nonexplicit title: prefix is stripped
    node, contnode = fake_node("py", "mod", "py3k:unknown", "py3k:unknown", refexplicit=False)
    rn = missing_reference(app, app.env, node, contnode)
    assert rn is None
    assert contnode[0].astext() == "unknown"

    # prefix given, target not found and explicit title: nothing is changed
    node, contnode = fake_node("py", "mod", "py3k:unknown", "py3k:unknown", refexplicit=True)
    rn = missing_reference(app, app.env, node, contnode)
    assert rn is None
    assert contnode[0].astext() == "py3k:unknown"
Example #22
0
def test_missing_reference(tempdir, app, status, warning):
    inv_file = tempdir / 'inventory'
    inv_file.write_bytes(inventory_v2)
    app.config.intersphinx_mapping = {
        'https://docs.python.org/': inv_file,
        'py3k': ('https://docs.python.org/py3k/', inv_file),
        'py3krel': ('py3k', inv_file),  # relative path
        'py3krelparent': ('../../py3k', inv_file),  # relative path, parent dir
    }
    app.config.intersphinx_cache_limit = 0

    # load the inventory and check if it's done correctly
    load_mappings(app)
    inv = app.env.intersphinx_inventory

    assert inv['py:module']['module2'] == \
        ('foo', '2.0', 'https://docs.python.org/foo.html#module-module2', '-')

    # check resolution when a target is found
    rn = reference_check(app, 'py', 'func', 'module1.func', 'foo')
    assert isinstance(rn, nodes.reference)
    assert rn['refuri'] == 'https://docs.python.org/sub/foo.html#module1.func'
    assert rn['reftitle'] == '(in foo v2.0)'
    assert rn[0].astext() == 'foo'

    # create unresolvable nodes and check None return value
    assert reference_check(app, 'py', 'foo', 'module1.func', 'foo') is None
    assert reference_check(app, 'py', 'func', 'foo', 'foo') is None
    assert reference_check(app, 'py', 'func', 'foo', 'foo') is None

    # check handling of prefixes

    # prefix given, target found: prefix is stripped
    rn = reference_check(app, 'py', 'mod', 'py3k:module2', 'py3k:module2')
    assert rn[0].astext() == 'module2'

    # prefix given, but not in title: nothing stripped
    rn = reference_check(app, 'py', 'mod', 'py3k:module2', 'module2')
    assert rn[0].astext() == 'module2'

    # prefix given, but explicit: nothing stripped
    rn = reference_check(app, 'py', 'mod', 'py3k:module2', 'py3k:module2',
                         refexplicit=True)
    assert rn[0].astext() == 'py3k:module2'

    # prefix given, target not found and nonexplicit title: prefix is stripped
    node, contnode = fake_node('py', 'mod', 'py3k:unknown', 'py3k:unknown',
                               refexplicit=False)
    rn = missing_reference(app, app.env, node, contnode)
    assert rn is None
    assert contnode[0].astext() == 'unknown'

    # prefix given, target not found and explicit title: nothing is changed
    node, contnode = fake_node('py', 'mod', 'py3k:unknown', 'py3k:unknown',
                               refexplicit=True)
    rn = missing_reference(app, app.env, node, contnode)
    assert rn is None
    assert contnode[0].astext() == 'py3k:unknown'

    # check relative paths
    rn = reference_check(app, 'py', 'mod', 'py3krel:module1', 'foo')
    assert rn['refuri'] == 'py3k/foo.html#module-module1'

    rn = reference_check(app, 'py', 'mod', 'py3krelparent:module1', 'foo')
    assert rn['refuri'] == '../../py3k/foo.html#module-module1'

    rn = reference_check(app, 'py', 'mod', 'py3krel:module1', 'foo', refdoc='sub/dir/test')
    assert rn['refuri'] == '../../py3k/foo.html#module-module1'

    rn = reference_check(app, 'py', 'mod', 'py3krelparent:module1', 'foo',
                         refdoc='sub/dir/test')
    assert rn['refuri'] == '../../../../py3k/foo.html#module-module1'

    # check refs of standard domain
    rn = reference_check(app, 'std', 'doc', 'docname', 'docname')
    assert rn['refuri'] == 'https://docs.python.org/docname.html'