@@ -442,7 +442,9 @@ impl<'a, 'tcx> DocFolder for CacheBuilder<'a, 'tcx> {
442442}
443443
444444fn add_item_to_search_index ( tcx : TyCtxt < ' _ > , cache : & mut Cache , item : & clean:: Item , name : Symbol ) {
445- let ( ( parent_did, parent_path) , is_impl_child) = match * item. kind {
445+ // Item has a name, so it must also have a DefId (can't be an impl, let alone a blanket or auto impl).
446+ let item_def_id = item. item_id . as_def_id ( ) . unwrap ( ) ;
447+ let ( parent_did, parent_path) = match * item. kind {
446448 clean:: StrippedItem ( ..) => return ,
447449 clean:: AssocConstItem ( ..) | clean:: AssocTypeItem ( ..)
448450 if cache. parent_stack . last ( ) . is_some_and ( |parent| parent. is_trait_impl ( ) ) =>
@@ -454,123 +456,114 @@ fn add_item_to_search_index(tcx: TyCtxt<'_>, cache: &mut Cache, item: &clean::It
454456 | clean:: TyAssocConstItem ( ..)
455457 | clean:: TyAssocTypeItem ( ..)
456458 | clean:: StructFieldItem ( ..)
457- | clean:: VariantItem ( ..) => (
458- (
459- Some (
460- cache
461- . parent_stack
462- . last ( )
463- . expect ( "parent_stack is empty" )
464- . item_id ( )
465- . expect_def_id ( ) ,
466- ) ,
467- Some ( & cache. stack [ ..cache . stack . len ( ) - 1 ] ) ,
468- ) ,
469- false ,
470- ) ,
459+ | clean:: VariantItem ( ..) => {
460+ // Don't index if containing module is stripped (i.e., private),
461+ // or if item is tuple struct/variant field (name is a number -> not useful for search).
462+ if cache. stripped_mod
463+ || item . type_ ( ) == ItemType :: StructField
464+ && name . as_str ( ) . chars ( ) . all ( |c| c . is_digit ( 10 ) )
465+ {
466+ return ;
467+ }
468+ let parent_did =
469+ cache. parent_stack . last ( ) . expect ( "parent_stack is empty" ) . item_id ( ) . expect_def_id ( ) ;
470+ let parent_path = & cache . stack [ ..cache . stack . len ( ) - 1 ] ;
471+ ( Some ( parent_did ) , parent_path )
472+ }
471473 clean:: MethodItem ( ..) | clean:: AssocConstItem ( ..) | clean:: AssocTypeItem ( ..) => {
472474 let last = cache. parent_stack . last ( ) . expect ( "parent_stack is empty 2" ) ;
473- let did = match & * last {
474- ParentStackItem :: Impl {
475- // impl Trait for &T { fn method(self); }
476- //
477- // When generating a function index with the above shape, we want it
478- // associated with `T`, not with the primitive reference type. It should
479- // show up as `T::method`, rather than `reference::method`, in the search
480- // results page.
481- for_ : clean:: Type :: BorrowedRef { type_, .. } ,
482- ..
483- } => type_. def_id ( & cache) ,
475+ let parent_did = match & * last {
476+ // impl Trait for &T { fn method(self); }
477+ //
478+ // When generating a function index with the above shape, we want it
479+ // associated with `T`, not with the primitive reference type. It should
480+ // show up as `T::method`, rather than `reference::method`, in the search
481+ // results page.
482+ ParentStackItem :: Impl { for_ : clean:: Type :: BorrowedRef { type_, .. } , .. } => {
483+ type_. def_id ( & cache)
484+ }
484485 ParentStackItem :: Impl { for_, .. } => for_. def_id ( & cache) ,
485486 ParentStackItem :: Type ( item_id) => item_id. as_def_id ( ) ,
486487 } ;
487- let path = did
488- . and_then ( |did| cache. paths . get ( & did) )
489- // The current stack not necessarily has correlation
490- // for where the type was defined. On the other
491- // hand, `paths` always has the right
492- // information if present.
493- . map ( |( fqp, _) | & fqp[ ..fqp. len ( ) - 1 ] ) ;
494- ( ( did, path) , true )
488+ let Some ( parent_did) = parent_did else { return } ;
489+ // The current stack not necessarily has correlation
490+ // for where the type was defined. On the other
491+ // hand, `paths` always has the right
492+ // information if present.
493+ match cache. paths . get ( & parent_did) {
494+ Some ( ( fqp, _) ) => ( Some ( parent_did) , & fqp[ ..fqp. len ( ) - 1 ] ) ,
495+ None => {
496+ handle_orphan_impl_child ( cache, item, parent_did) ;
497+ return ;
498+ }
499+ }
500+ }
501+ _ => {
502+ // Don't index if item is crate root, which is inserted later on when serializing the index.
503+ if item_def_id. is_crate_root ( ) {
504+ return ;
505+ }
506+ ( None , & * cache. stack )
495507 }
496- _ => ( ( None , Some ( & * cache. stack ) ) , false ) ,
497508 } ;
498509
499- if let Some ( parent_did) = parent_did
500- && parent_path. is_none ( )
501- && is_impl_child
502- {
503- // We have a parent, but we don't know where they're
504- // defined yet. Wait for later to index this item.
505- let impl_generics = clean_impl_generics ( cache. parent_stack . last ( ) ) ;
506- let impl_id = if let Some ( ParentStackItem :: Impl { item_id, .. } ) = cache. parent_stack . last ( )
507- {
508- item_id. as_def_id ( )
509- } else {
510- None
511- } ;
512- let orphan_item =
513- OrphanImplItem { parent : parent_did, item : item. clone ( ) , impl_generics, impl_id } ;
514- cache. orphan_impl_items . push ( orphan_item) ;
515- } else if let Some ( path) = parent_path
516- && ( is_impl_child || !cache. stripped_mod )
517- {
518- debug_assert ! ( !item. is_stripped( ) ) ;
519-
520- // A crate has a module at its root, containing all items,
521- // which should not be indexed. The crate-item itself is
522- // inserted later on when serializing the search-index.
523- if item. item_id . as_def_id ( ) . is_some_and ( |idx| !idx. is_crate_root ( ) )
524- && let ty = item. type_ ( )
525- && ( ty != ItemType :: StructField || u16:: from_str_radix ( name. as_str ( ) , 10 ) . is_err ( ) )
526- {
527- let desc = short_markdown_summary ( & item. doc_value ( ) , & item. link_names ( cache) ) ;
528- // For searching purposes, a re-export is a duplicate if:
529- //
530- // - It's either an inline, or a true re-export
531- // - It's got the same name
532- // - Both of them have the same exact path
533- let defid = ( match & * item. kind {
534- & clean:: ItemKind :: ImportItem ( ref import) => import. source . did ,
535- _ => None ,
536- } )
537- . or_else ( || item. item_id . as_def_id ( ) ) ;
538- // In case this is a field from a tuple struct, we don't add it into
539- // the search index because its name is something like "0", which is
540- // not useful for rustdoc search.
541- let path = join_with_double_colon ( path) ;
542- let impl_id =
543- if let Some ( ParentStackItem :: Impl { item_id, .. } ) = cache. parent_stack . last ( ) {
544- item_id. as_def_id ( )
545- } else {
546- None
547- } ;
548- let search_type = get_function_type_for_search (
549- & item,
550- tcx,
551- clean_impl_generics ( cache. parent_stack . last ( ) ) . as_ref ( ) ,
552- parent_did,
553- cache,
554- ) ;
555- let aliases = item. attrs . get_doc_aliases ( ) ;
556- let deprecation = item. deprecation ( tcx) ;
557- let index_item = IndexItem {
558- ty,
559- defid,
560- name,
561- path,
562- desc,
563- parent : parent_did,
564- parent_idx : None ,
565- exact_path : None ,
566- impl_id,
567- search_type,
568- aliases,
569- deprecation,
570- } ;
571- cache. search_index . push ( index_item) ;
572- }
573- }
510+ debug_assert ! ( !item. is_stripped( ) ) ;
511+
512+ let desc = short_markdown_summary ( & item. doc_value ( ) , & item. link_names ( cache) ) ;
513+ // For searching purposes, a re-export is a duplicate if:
514+ //
515+ // - It's either an inline, or a true re-export
516+ // - It's got the same name
517+ // - Both of them have the same exact path
518+ let defid = match & * item. kind {
519+ clean:: ItemKind :: ImportItem ( import) => import. source . did . unwrap_or ( item_def_id) ,
520+ _ => item_def_id,
521+ } ;
522+ let path = join_with_double_colon ( parent_path) ;
523+ let impl_id = if let Some ( ParentStackItem :: Impl { item_id, .. } ) = cache. parent_stack . last ( ) {
524+ item_id. as_def_id ( )
525+ } else {
526+ None
527+ } ;
528+ let search_type = get_function_type_for_search (
529+ & item,
530+ tcx,
531+ clean_impl_generics ( cache. parent_stack . last ( ) ) . as_ref ( ) ,
532+ parent_did,
533+ cache,
534+ ) ;
535+ let aliases = item. attrs . get_doc_aliases ( ) ;
536+ let deprecation = item. deprecation ( tcx) ;
537+ let index_item = IndexItem {
538+ ty : item. type_ ( ) ,
539+ defid : Some ( defid) ,
540+ name,
541+ path,
542+ desc,
543+ parent : parent_did,
544+ parent_idx : None ,
545+ exact_path : None ,
546+ impl_id,
547+ search_type,
548+ aliases,
549+ deprecation,
550+ } ;
551+ cache. search_index . push ( index_item) ;
552+ }
553+
554+ /// We have a parent, but we don't know where they're
555+ /// defined yet. Wait for later to index this item.
556+ /// See [`Cache::orphan_impl_items`].
557+ fn handle_orphan_impl_child ( cache : & mut Cache , item : & clean:: Item , parent_did : DefId ) {
558+ let impl_generics = clean_impl_generics ( cache. parent_stack . last ( ) ) ;
559+ let impl_id = if let Some ( ParentStackItem :: Impl { item_id, .. } ) = cache. parent_stack . last ( ) {
560+ item_id. as_def_id ( )
561+ } else {
562+ None
563+ } ;
564+ let orphan_item =
565+ OrphanImplItem { parent : parent_did, item : item. clone ( ) , impl_generics, impl_id } ;
566+ cache. orphan_impl_items . push ( orphan_item) ;
574567}
575568
576569pub ( crate ) struct OrphanImplItem {
0 commit comments