about summary refs log tree commit diff
path: root/src/librustdoc/html/render
diff options
context:
space:
mode:
authorbinarycat <binarycat@envs.net>2025-08-26 13:41:33 -0500
committerbinarycat <binarycat@envs.net>2025-10-02 15:27:40 -0500
commitc407d340de1717a88537725c899c153c6fdda051 (patch)
treef4dacce2e88b1cd2461c1d7c8d39194f3ef735ac /src/librustdoc/html/render
parent6710835ae739ca326441ff6c63d24fb123858300 (diff)
downloadrust-c407d340de1717a88537725c899c153c6fdda051.tar.gz
rust-c407d340de1717a88537725c899c153c6fdda051.zip
if a trait item is shown in search results, hide the impl item
for example, if we're showing `Iterator::next`,
we don't need to also show `Range::next` in the results.

Co-authored-by: Michael Howell <michael@notriddle.com>
Diffstat (limited to 'src/librustdoc/html/render')
-rw-r--r--src/librustdoc/html/render/mod.rs2
-rw-r--r--src/librustdoc/html/render/search_index.rs78
2 files changed, 51 insertions, 29 deletions
diff --git a/src/librustdoc/html/render/mod.rs b/src/librustdoc/html/render/mod.rs
index 6d684449b6d..88184c9611f 100644
--- a/src/librustdoc/html/render/mod.rs
+++ b/src/librustdoc/html/render/mod.rs
@@ -134,6 +134,8 @@ pub(crate) struct IndexItem {
     pub(crate) desc: String,
     pub(crate) parent: Option<DefId>,
     pub(crate) parent_idx: Option<usize>,
+    pub(crate) trait_parent: Option<DefId>,
+    pub(crate) trait_parent_idx: Option<usize>,
     pub(crate) exact_module_path: Option<Vec<Symbol>>,
     pub(crate) impl_id: Option<DefId>,
     pub(crate) search_type: Option<IndexItemFunctionType>,
diff --git a/src/librustdoc/html/render/search_index.rs b/src/librustdoc/html/render/search_index.rs
index 2984f3ab50e..81b38d157a8 100644
--- a/src/librustdoc/html/render/search_index.rs
+++ b/src/librustdoc/html/render/search_index.rs
@@ -580,6 +580,7 @@ impl SerializedSearchIndex {
                          module_path,
                          exact_module_path,
                          parent,
+                         trait_parent,
                          deprecated,
                          associated_item_disambiguator,
                      }| EntryData {
@@ -589,6 +590,7 @@ impl SerializedSearchIndex {
                         exact_module_path: exact_module_path
                             .and_then(|path_id| map.get(&path_id).copied()),
                         parent: parent.and_then(|path_id| map.get(&path_id).copied()),
+                        trait_parent: trait_parent.and_then(|path_id| map.get(&path_id).copied()),
                         deprecated: *deprecated,
                         associated_item_disambiguator: associated_item_disambiguator.clone(),
                     },
@@ -870,6 +872,7 @@ struct EntryData {
     module_path: Option<usize>,
     exact_module_path: Option<usize>,
     parent: Option<usize>,
+    trait_parent: Option<usize>,
     deprecated: bool,
     associated_item_disambiguator: Option<String>,
 }
@@ -885,6 +888,7 @@ impl Serialize for EntryData {
         seq.serialize_element(&self.module_path.map(|id| id + 1).unwrap_or(0))?;
         seq.serialize_element(&self.exact_module_path.map(|id| id + 1).unwrap_or(0))?;
         seq.serialize_element(&self.parent.map(|id| id + 1).unwrap_or(0))?;
+        seq.serialize_element(&self.trait_parent.map(|id| id + 1).unwrap_or(0))?;
         seq.serialize_element(&if self.deprecated { 1 } else { 0 })?;
         if let Some(disambig) = &self.associated_item_disambiguator {
             seq.serialize_element(&disambig)?;
@@ -916,6 +920,9 @@ impl<'de> Deserialize<'de> for EntryData {
                     .ok_or_else(|| A::Error::missing_field("exact_module_path"))?;
                 let parent: SerializedOptional32 =
                     v.next_element()?.ok_or_else(|| A::Error::missing_field("parent"))?;
+                let trait_parent: SerializedOptional32 =
+                    v.next_element()?.ok_or_else(|| A::Error::missing_field("trait_parent"))?;
+
                 let deprecated: u32 = v.next_element()?.unwrap_or(0);
                 let associated_item_disambiguator: Option<String> = v.next_element()?;
                 Ok(EntryData {
@@ -925,6 +932,7 @@ impl<'de> Deserialize<'de> for EntryData {
                     exact_module_path: Option::<i32>::from(exact_module_path)
                         .map(|path| path as usize),
                     parent: Option::<i32>::from(parent).map(|path| path as usize),
+                    trait_parent: Option::<i32>::from(trait_parent).map(|path| path as usize),
                     deprecated: deprecated != 0,
                     associated_item_disambiguator,
                 })
@@ -1275,7 +1283,8 @@ pub(crate) fn build_index(
 
     // Attach all orphan items to the type's definition if the type
     // has since been learned.
-    for &OrphanImplItem { impl_id, parent, ref item, ref impl_generics } in &cache.orphan_impl_items
+    for &OrphanImplItem { impl_id, parent, trait_parent, ref item, ref impl_generics } in
+        &cache.orphan_impl_items
     {
         if let Some((fqp, _)) = cache.paths.get(&parent) {
             let desc = short_markdown_summary(&item.doc_value(), &item.link_names(cache));
@@ -1287,6 +1296,8 @@ pub(crate) fn build_index(
                 desc,
                 parent: Some(parent),
                 parent_idx: None,
+                trait_parent,
+                trait_parent_idx: None,
                 exact_module_path: None,
                 impl_id,
                 search_type: get_function_type_for_search(
@@ -1391,6 +1402,7 @@ pub(crate) fn build_index(
                         module_path: None,
                         exact_module_path: None,
                         parent: None,
+                        trait_parent: None,
                         deprecated: false,
                         associated_item_disambiguator: None,
                     }),
@@ -1404,39 +1416,46 @@ pub(crate) fn build_index(
         }
     };
 
-    // First, populate associated item parents
+    // First, populate associated item parents and trait parents
     let crate_items: Vec<&mut IndexItem> = search_index
         .iter_mut()
         .map(|item| {
-            item.parent_idx = item.parent.and_then(|defid| {
-                cache.paths.get(&defid).map(|&(ref fqp, ty)| {
-                    let pathid = serialized_index.names.len();
-                    match serialized_index.crate_paths_index.entry((ty, fqp.clone())) {
-                        Entry::Occupied(entry) => *entry.get(),
-                        Entry::Vacant(entry) => {
-                            entry.insert(pathid);
-                            let (name, path) = fqp.split_last().unwrap();
-                            serialized_index.push_path(
-                                name.as_str().to_string(),
-                                PathData {
-                                    ty,
-                                    module_path: path.to_vec(),
-                                    exact_module_path: if let Some(exact_path) =
-                                        cache.exact_paths.get(&defid)
-                                        && let Some((name2, exact_path)) = exact_path.split_last()
-                                        && name == name2
-                                    {
-                                        Some(exact_path.to_vec())
-                                    } else {
-                                        None
+            let mut defid_to_rowid = |defid, check_external: bool| {
+                cache
+                    .paths
+                    .get(&defid)
+                    .or_else(|| check_external.then(|| cache.external_paths.get(&defid)).flatten())
+                    .map(|&(ref fqp, ty)| {
+                        let pathid = serialized_index.names.len();
+                        match serialized_index.crate_paths_index.entry((ty, fqp.clone())) {
+                            Entry::Occupied(entry) => *entry.get(),
+                            Entry::Vacant(entry) => {
+                                entry.insert(pathid);
+                                let (name, path) = fqp.split_last().unwrap();
+                                serialized_index.push_path(
+                                    name.as_str().to_string(),
+                                    PathData {
+                                        ty,
+                                        module_path: path.to_vec(),
+                                        exact_module_path: if let Some(exact_path) =
+                                            cache.exact_paths.get(&defid)
+                                            && let Some((name2, exact_path)) =
+                                                exact_path.split_last()
+                                            && name == name2
+                                        {
+                                            Some(exact_path.to_vec())
+                                        } else {
+                                            None
+                                        },
                                     },
-                                },
-                            );
-                            usize::try_from(pathid).unwrap()
+                                );
+                                usize::try_from(pathid).unwrap()
+                            }
                         }
-                    }
-                })
-            });
+                    })
+            };
+            item.parent_idx = item.parent.and_then(|p| defid_to_rowid(p, false));
+            item.trait_parent_idx = item.trait_parent.and_then(|p| defid_to_rowid(p, true));
 
             if let Some(defid) = item.defid
                 && item.parent_idx.is_none()
@@ -1519,6 +1538,7 @@ pub(crate) fn build_index(
             Some(EntryData {
                 ty: item.ty,
                 parent: item.parent_idx,
+                trait_parent: item.trait_parent_idx,
                 module_path,
                 exact_module_path,
                 deprecated: item.deprecation.is_some(),