@@ -38,7 +38,7 @@ impl JsonRenderer<'_> {
3838 Some ( UrlFragment :: UserWritten ( _) ) | None => * page_id,
3939 } ;
4040
41- ( link. clone ( ) , from_item_id ( id. into ( ) , self . tcx ) )
41+ ( link. clone ( ) , id_from_item_inner ( id. into ( ) , self . tcx , None ) )
4242 } )
4343 . collect ( ) ;
4444 let docs = item. attrs . collapsed_doc_value ( ) ;
@@ -50,7 +50,8 @@ impl JsonRenderer<'_> {
5050 . collect ( ) ;
5151 let span = item. span ( self . tcx ) ;
5252 let visibility = item. visibility ( self . tcx ) ;
53- let clean:: Item { name, attrs : _, kind : _, item_id, cfg : _, .. } = item;
53+ let clean:: Item { name, item_id, .. } = item;
54+ let id = id_from_item ( & item, self . tcx ) ;
5455 let inner = match * item. kind {
5556 clean:: KeywordItem => return None ,
5657 clean:: StrippedItem ( ref inner) => {
@@ -69,7 +70,7 @@ impl JsonRenderer<'_> {
6970 _ => from_clean_item ( item, self . tcx ) ,
7071 } ;
7172 Some ( Item {
72- id : from_item_id_with_name ( item_id , self . tcx , name ) ,
73+ id,
7374 crate_id : item_id. krate ( ) . as_u32 ( ) ,
7475 name : name. map ( |sym| sym. to_string ( ) ) ,
7576 span : span. and_then ( |span| self . convert_span ( span) ) ,
@@ -107,7 +108,7 @@ impl JsonRenderer<'_> {
107108 Some ( ty:: Visibility :: Public ) => Visibility :: Public ,
108109 Some ( ty:: Visibility :: Restricted ( did) ) if did. is_crate_root ( ) => Visibility :: Crate ,
109110 Some ( ty:: Visibility :: Restricted ( did) ) => Visibility :: Restricted {
110- parent : from_item_id ( did. into ( ) , self . tcx ) ,
111+ parent : id_from_item_inner ( did. into ( ) , self . tcx , None ) ,
111112 path : self . tcx . def_path ( did) . to_string_no_crate_verbose ( ) ,
112113 } ,
113114 }
@@ -207,51 +208,58 @@ impl FromWithTcx<clean::TypeBindingKind> for TypeBindingKind {
207208/// It generates an ID as follows:
208209///
209210/// `CRATE_ID:ITEM_ID[:NAME_ID]` (if there is no name, NAME_ID is not generated).
210- pub ( crate ) fn from_item_id ( item_id : ItemId , tcx : TyCtxt < ' _ > ) -> Id {
211- from_item_id_with_name ( item_id, tcx, None )
212- }
213-
214- // FIXME: this function (and appending the name at the end of the ID) should be removed when
215- // reexports are not inlined anymore for json format. It should be done in #93518.
216- pub ( crate ) fn from_item_id_with_name ( item_id : ItemId , tcx : TyCtxt < ' _ > , name : Option < Symbol > ) -> Id {
217- struct DisplayDefId < ' a > ( DefId , TyCtxt < ' a > , Option < Symbol > ) ;
211+ pub ( crate ) fn id_from_item_inner ( item_id : ItemId , tcx : TyCtxt < ' _ > , extra : Option < & Id > ) -> Id {
212+ struct DisplayDefId < ' a , ' b > ( DefId , TyCtxt < ' a > , Option < & ' b Id > ) ;
218213
219- impl < ' a > fmt:: Display for DisplayDefId < ' a > {
214+ impl < ' a , ' b > fmt:: Display for DisplayDefId < ' a , ' b > {
220215 fn fmt ( & self , f : & mut fmt:: Formatter < ' _ > ) -> fmt:: Result {
221- let DisplayDefId ( def_id, tcx, name) = self ;
222- let name = match name {
223- Some ( name) => format ! ( ":{}" , name. as_u32( ) ) ,
224- None => {
225- // We need this workaround because primitive types' DefId actually refers to
226- // their parent module, which isn't present in the output JSON items. So
227- // instead, we directly get the primitive symbol and convert it to u32 to
228- // generate the ID.
229- if matches ! ( tcx. def_kind( def_id) , DefKind :: Mod ) &&
230- let Some ( prim) = tcx. get_attrs ( * def_id, sym:: doc)
231- . flat_map ( |attr| attr. meta_item_list ( ) . unwrap_or_default ( ) )
232- . filter ( |attr| attr. has_name ( sym:: primitive) )
233- . find_map ( |attr| attr. value_str ( ) ) {
234- format ! ( ":{}" , prim. as_u32( ) )
235- } else {
236- tcx
237- . opt_item_name ( * def_id)
238- . map ( |n| format ! ( ":{}" , n. as_u32( ) ) )
239- . unwrap_or_default ( )
240- }
241- }
216+ let DisplayDefId ( def_id, tcx, extra) = self ;
217+ // We need this workaround because primitive types' DefId actually refers to
218+ // their parent module, which isn't present in the output JSON items. So
219+ // instead, we directly get the primitive symbol and convert it to u32 to
220+ // generate the ID.
221+ let s;
222+ let extra = if let Some ( e) = extra {
223+ s = format ! ( "-{}" , e. 0 ) ;
224+ & s
225+ } else {
226+ ""
227+ } ;
228+ let name = if matches ! ( tcx. def_kind( def_id) , DefKind :: Mod ) &&
229+ let Some ( prim) = tcx. get_attrs ( * def_id, sym:: doc)
230+ . flat_map ( |attr| attr. meta_item_list ( ) . unwrap_or_default ( ) )
231+ . filter ( |attr| attr. has_name ( sym:: primitive) )
232+ . find_map ( |attr| attr. value_str ( ) ) {
233+ format ! ( ":{}" , prim. as_u32( ) )
234+ } else {
235+ tcx
236+ . opt_item_name ( * def_id)
237+ . map ( |n| format ! ( ":{}" , n. as_u32( ) ) )
238+ . unwrap_or_default ( )
242239 } ;
243- write ! ( f, "{}:{}{} " , self . 0 . krate. as_u32( ) , u32 :: from( self . 0 . index) , name )
240+ write ! ( f, "{}:{}{name}{extra} " , self . 0 . krate. as_u32( ) , u32 :: from( self . 0 . index) )
244241 }
245242 }
246243
247244 match item_id {
248- ItemId :: DefId ( did) => Id ( format ! ( "{}" , DisplayDefId ( did, tcx, name ) ) ) ,
245+ ItemId :: DefId ( did) => Id ( format ! ( "{}" , DisplayDefId ( did, tcx, extra ) ) ) ,
249246 ItemId :: Blanket { for_, impl_id } => {
250- Id ( format ! ( "b:{}-{}" , DisplayDefId ( impl_id, tcx, None ) , DisplayDefId ( for_, tcx, name ) ) )
247+ Id ( format ! ( "b:{}-{}" , DisplayDefId ( impl_id, tcx, None ) , DisplayDefId ( for_, tcx, extra ) ) )
251248 }
252249 ItemId :: Auto { for_, trait_ } => {
253- Id ( format ! ( "a:{}-{}" , DisplayDefId ( trait_, tcx, None ) , DisplayDefId ( for_, tcx, name) ) )
250+ Id ( format ! ( "a:{}-{}" , DisplayDefId ( trait_, tcx, None ) , DisplayDefId ( for_, tcx, extra) ) )
251+ }
252+ }
253+ }
254+
255+ pub ( crate ) fn id_from_item ( item : & clean:: Item , tcx : TyCtxt < ' _ > ) -> Id {
256+ match * item. kind {
257+ clean:: ItemKind :: ImportItem ( ref import) => {
258+ let extra =
259+ import. source . did . map ( ItemId :: from) . map ( |i| id_from_item_inner ( i, tcx, None ) ) ;
260+ id_from_item_inner ( item. item_id , tcx, extra. as_ref ( ) )
254261 }
262+ _ => id_from_item_inner ( item. item_id , tcx, None ) ,
255263 }
256264}
257265
@@ -525,7 +533,7 @@ impl FromWithTcx<clean::Path> for Path {
525533 fn from_tcx ( path : clean:: Path , tcx : TyCtxt < ' _ > ) -> Path {
526534 Path {
527535 name : path. whole_name ( ) ,
528- id : from_item_id ( path. def_id ( ) . into ( ) , tcx) ,
536+ id : id_from_item_inner ( path. def_id ( ) . into ( ) , tcx, None ) ,
529537 args : path. segments . last ( ) . map ( |args| Box :: new ( args. clone ( ) . args . into_tcx ( tcx) ) ) ,
530538 }
531539 }
@@ -702,7 +710,7 @@ impl FromWithTcx<clean::Import> for Import {
702710 Import {
703711 source : import. source . path . whole_name ( ) ,
704712 name,
705- id : import. source . did . map ( ItemId :: from) . map ( |i| from_item_id ( i, tcx) ) ,
713+ id : import. source . did . map ( ItemId :: from) . map ( |i| id_from_item_inner ( i, tcx, None ) ) ,
706714 glob,
707715 }
708716 }
@@ -791,7 +799,7 @@ fn ids(items: impl IntoIterator<Item = clean::Item>, tcx: TyCtxt<'_>) -> Vec<Id>
791799 items
792800 . into_iter ( )
793801 . filter ( |x| !x. is_stripped ( ) && !x. is_keyword ( ) )
794- . map ( |i| from_item_id_with_name ( i . item_id , tcx, i . name ) )
802+ . map ( |i| id_from_item ( & i , tcx) )
795803 . collect ( )
796804}
797805
@@ -801,12 +809,10 @@ fn ids_keeping_stripped(
801809) -> Vec < Option < Id > > {
802810 items
803811 . into_iter ( )
804- . map ( |i| {
805- if !i. is_stripped ( ) && !i. is_keyword ( ) {
806- Some ( from_item_id_with_name ( i. item_id , tcx, i. name ) )
807- } else {
808- None
809- }
810- } )
812+ . map (
813+ |i| {
814+ if !i. is_stripped ( ) && !i. is_keyword ( ) { Some ( id_from_item ( & i, tcx) ) } else { None }
815+ } ,
816+ )
811817 . collect ( )
812818}
0 commit comments