Skip to content

intra-doc links: crate means something different when an item is re-exported #77193

Closed

Description

@dylni

Crate quit exports main from quit_macros. main is documented in quit and has no documentation in quit_macros.

When that documentation has a link to [with_code], which is only in crate quit, it is unresolved. However, [crate::with_code] is resolved.

Rustdoc gives no warnings with either.

You can see the result with quit version 1.1.1 here.

cc @jyn514
cc #76106 (comment)

Activity

  1. added
    A-intra-doc-linksArea: Intra-doc links, the ability to link to items in docs by name
    T-rustdocRelevant to the rustdoc team, which will review and decide on the PR/issue.
    on Sep 25, 2020
  2. changed the title [-]Relative intra-rustdoc links are not resolved when documenting re-exported types[/-] [+]Relative intra-rustdoc links are not resolved when documenting re-exported items[/+] on Sep 25, 2020
  3. jyn514 commented on Sep 25, 2020

    @jyn514
    Member
    All of this was wrong, I forgot to use +nightly

    This isn't related to scopes, rustdoc will also fail to resolve these links:

    /// [crate::process::Command]
    ///
    /// [Vec]
    pub use std::string::String;

    Something about the re-export itself is messing it up.

  4. jyn514 commented on Sep 25, 2020

    @jyn514
    Member

    The good news is this is unrelated to proc-macros. Here's what I found:

    /// [std::process::Command] // works
    ///
    /// [Vec] // works
    /// [with_code] // silently breaks
    /// [crate::with_code] // works
    pub use std::string::String;

    This is really strange. I would have expected it to resolve relative to std::string, not relative to the current crate.

  5. jyn514 commented on Sep 25, 2020

    @jyn514
    Member

    Ok, I found the issue: rustdoc and resolve disagree about which crate this is in 🤦

    Sep 25 13:38:39.133 DEBUG rustdoc::passes::collect_intra_doc_links: resolving with_code as a macro in the module DefId(5:3806 ~ alloc[e7ed]::string[0])
    Sep 25 13:38:39.133 DEBUG rustdoc::passes::collect_intra_doc_links: with_code resolved to Err(()) in namespace ValueNS
    Sep 25 13:38:39.133 DEBUG rustdoc::passes::collect_intra_doc_links: resolving crate::with_code as a macro in the module DefId(5:3806 ~ alloc[e7ed]::string[0])
    Sep 25 13:38:39.133 DEBUG rustdoc::passes::collect_intra_doc_links: crate::with_code resolved to Ok((Path { span: re-export.rs:1:1: 1:1 (#0), segments: [PathSegment { ident: crate#0, id: NodeId(28), args: None }, PathSegment { ident: with_code#0, id: NodeId(29), args: None }], tokens: None }, Def(Fn, DefId(0:4 ~ re_export[8787]::with_code[0])))) in namespace ValueNS
    Sep 25 13:38:39.133 DEBUG rustdoc::passes::collect_intra_doc_links: intra-doc link to crate::with_code resolved to Def(Fn, DefId(0:4 ~ re_export[8787]::with_code[0]))
    

    For with_code, rustdoc passes the original module of String, alloc::string, and resolve correctly says there's no item named alloc::string::with_code. But for crate::with_code, resolve thinks that crate refers to the current crate, not to alloc.

    This explains a lot of other broken links I've been seeing actually: anything that has crate:: will be wrong. So you were actually correct to start that this was the same issue as #76106 ;)

    The fix will be a little tricky ... there's no 'change crate' button for resolve. There are a few things rustdoc can do:

    1. Resolve all links relative to the current module (the status quo before Resolve items for cross-crate imports relative to the original module #73101). This is a no-go, because it means links will break on re-exports (Support intra-doc links on cross-crate reexports #65983).
    2. Resolve all links relative to the original module. This is what I thought was the current behavior. It means that additional documentation can't refer to things in the current lexical scope, which is non-intuitive (cc [rustdoc] intra-doc links for macros always resolve relative to the crate root #72243).
    3. Resolve links in lexical scope: the original docs get resolved in the original module; the new docs get resolved in the module with the re-export. This is the ideal fix but somewhat hard to do because rustdoc doesn't distinguish between the two internally.

    A possible way to implement 2. is by stripping crate:: wherever we see it and resolving relative to the crate root instead of the current module. This is slightly hacky but should work fairly reliably.

  6. changed the title [-]Relative intra-rustdoc links are not resolved when documenting re-exported items[/-] [+]intra-doc links: `crate` means something different when an item is re-exported[/+] on Sep 25, 2020
  7. self-assigned this
    on Sep 25, 2020
  8. jyn514 commented on Sep 25, 2020

    @jyn514
    Member

    Marking as P-high after discussing with @GuillaumeGomez ; it would be unfortunate to still have this bug on the first release after stabilization.

  9. added a commit that references this issue on Sep 28, 2020
  10. added a commit that references this issue on Sep 29, 2020
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

Labels

A-intra-doc-linksArea: Intra-doc links, the ability to link to items in docs by nameC-bugCategory: This is a bug.P-highHigh priorityT-rustdocRelevant to the rustdoc team, which will review and decide on the PR/issue.

Type

No type

Projects

No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions