| //! Tests that don't fit into a specific category. | 
 |  | 
 | use expect_test::{Expect, expect}; | 
 | use ide_db::SymbolKind; | 
 |  | 
 | use crate::{ | 
 |     CompletionItemKind, | 
 |     tests::{ | 
 |         TEST_CONFIG, check, check_edit, check_no_kw, check_with_trigger_character, | 
 |         do_completion_with_config, | 
 |     }, | 
 | }; | 
 |  | 
 | #[test] | 
 | fn completes_if_prefix_is_keyword() { | 
 |     check_edit( | 
 |         "wherewolf", | 
 |         r#" | 
 | fn main() { | 
 |     let wherewolf = 92; | 
 |     drop(where$0) | 
 | } | 
 | "#, | 
 |         r#" | 
 | fn main() { | 
 |     let wherewolf = 92; | 
 |     drop(wherewolf) | 
 | } | 
 | "#, | 
 |     ) | 
 | } | 
 |  | 
 | /// Regression test for issue #6091. | 
 | #[test] | 
 | fn correctly_completes_module_items_prefixed_with_underscore() { | 
 |     check_edit( | 
 |         "_alpha", | 
 |         r#" | 
 | fn main() { | 
 |     _$0 | 
 | } | 
 | fn _alpha() {} | 
 | "#, | 
 |         r#" | 
 | fn main() { | 
 |     _alpha();$0 | 
 | } | 
 | fn _alpha() {} | 
 | "#, | 
 |     ) | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_prelude() { | 
 |     check_no_kw( | 
 |         r#" | 
 | //- /main.rs edition:2018 crate:main deps:std | 
 | fn foo() { let x: $0 } | 
 |  | 
 | //- /std/lib.rs crate:std | 
 | pub mod prelude { | 
 |     pub mod rust_2018 { | 
 |         pub struct Option; | 
 |     } | 
 | } | 
 | "#, | 
 |         expect![[r#" | 
 |             md std | 
 |             st Option Option | 
 |             bt u32       u32 | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_prelude_macros() { | 
 |     check_no_kw( | 
 |         r#" | 
 | //- /main.rs edition:2018 crate:main deps:std | 
 | fn f() {$0} | 
 |  | 
 | //- /std/lib.rs crate:std | 
 | pub mod prelude { | 
 |     pub mod rust_2018 { | 
 |         pub use crate::concat; | 
 |     } | 
 | } | 
 |  | 
 | mod macros { | 
 |     #[rustc_builtin_macro] | 
 |     #[macro_export] | 
 |     macro_rules! concat { } | 
 | } | 
 | "#, | 
 |         expect![[r#" | 
 |             fn f()                       fn() | 
 |             ma concat!(…) macro_rules! concat | 
 |             md std | 
 |             bt u32                        u32 | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_std_prelude_if_core_is_defined() { | 
 |     check_no_kw( | 
 |         r#" | 
 | //- /main.rs crate:main deps:core,std edition:2021 | 
 | fn foo() { let x: $0 } | 
 |  | 
 | //- /core/lib.rs crate:core | 
 | pub mod prelude { | 
 |     pub mod rust_2021 { | 
 |         pub struct Option; | 
 |     } | 
 | } | 
 |  | 
 | //- /std/lib.rs crate:std deps:core | 
 | pub mod prelude { | 
 |     pub mod rust_2021 { | 
 |         pub struct String; | 
 |     } | 
 | } | 
 | "#, | 
 |         expect![[r#" | 
 |             md core | 
 |             md std | 
 |             st String String | 
 |             bt u32       u32 | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn respects_doc_hidden() { | 
 |     check_no_kw( | 
 |         r#" | 
 | //- /lib.rs crate:lib deps:std | 
 | fn f() { | 
 |     format_$0 | 
 | } | 
 |  | 
 | //- /std.rs crate:std | 
 | #[doc(hidden)] | 
 | #[macro_export] | 
 | macro_rules! format_args_nl { | 
 |     () => {} | 
 | } | 
 |  | 
 | pub mod prelude { | 
 |     pub mod rust_2018 {} | 
 | } | 
 |             "#, | 
 |         expect![[r#" | 
 |             fn f() fn() | 
 |             md std | 
 |             bt u32  u32 | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn respects_doc_hidden_in_assoc_item_list() { | 
 |     check_no_kw( | 
 |         r#" | 
 | //- /lib.rs crate:lib deps:std | 
 | struct S; | 
 | impl S { | 
 |     format_$0 | 
 | } | 
 |  | 
 | //- /std.rs crate:std | 
 | #[doc(hidden)] | 
 | #[macro_export] | 
 | macro_rules! format_args_nl { | 
 |     () => {} | 
 | } | 
 |  | 
 | pub mod prelude { | 
 |     pub mod rust_2018 {} | 
 | } | 
 |             "#, | 
 |         expect![[r#" | 
 |                 md std | 
 |             "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn associated_item_visibility() { | 
 |     check_no_kw( | 
 |         r#" | 
 | //- /lib.rs crate:lib new_source_root:library | 
 | pub struct S; | 
 |  | 
 | impl S { | 
 |     pub fn public_method() { } | 
 |     fn private_method() { } | 
 |     pub type PublicType = u32; | 
 |     type PrivateType = u32; | 
 |     pub const PUBLIC_CONST: u32 = 1; | 
 |     const PRIVATE_CONST: u32 = 1; | 
 | } | 
 |  | 
 | //- /main.rs crate:main deps:lib new_source_root:local | 
 | fn foo() { let _ = lib::S::$0 } | 
 | "#, | 
 |         expect![[r#" | 
 |             ct PUBLIC_CONST pub const PUBLIC_CONST: u32 | 
 |             fn public_method()                     fn() | 
 |             ta PublicType     pub type PublicType = u32 | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_union_associated_method() { | 
 |     check_no_kw( | 
 |         r#" | 
 | union U {}; | 
 | impl U { fn m() { } } | 
 |  | 
 | fn foo() { let _ = U::$0 } | 
 | "#, | 
 |         expect![[r#" | 
 |             fn m() fn() | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_trait_associated_method_1() { | 
 |     check_no_kw( | 
 |         r#" | 
 | trait Trait { fn m(); } | 
 |  | 
 | fn foo() { let _ = Trait::$0 } | 
 | "#, | 
 |         expect![[r#" | 
 |             fn m() (as Trait) fn() | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_trait_associated_method_2() { | 
 |     check_no_kw( | 
 |         r#" | 
 | trait Trait { fn m(); } | 
 |  | 
 | struct S; | 
 | impl Trait for S {} | 
 |  | 
 | fn foo() { let _ = S::$0 } | 
 | "#, | 
 |         expect![[r#" | 
 |             fn m() (as Trait) fn() | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_trait_associated_method_3() { | 
 |     check_no_kw( | 
 |         r#" | 
 | trait Trait { fn m(); } | 
 |  | 
 | struct S; | 
 | impl Trait for S {} | 
 |  | 
 | fn foo() { let _ = <S as Trait>::$0 } | 
 | "#, | 
 |         expect![[r#" | 
 |             fn m() (as Trait) fn() | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_ty_param_assoc_ty() { | 
 |     check_no_kw( | 
 |         r#" | 
 | trait Super { | 
 |     type Ty; | 
 |     const CONST: u8; | 
 |     fn func() {} | 
 |     fn method(&self) {} | 
 | } | 
 |  | 
 | trait Sub: Super { | 
 |     type SubTy; | 
 |     const C2: (); | 
 |     fn subfunc() {} | 
 |     fn submethod(&self) {} | 
 | } | 
 |  | 
 | fn foo<T: Sub>() { T::$0 } | 
 | "#, | 
 |         expect![[r#" | 
 |             ct C2 (as Sub)         const C2: () | 
 |             ct CONST (as Super) const CONST: u8 | 
 |             fn func() (as Super)           fn() | 
 |             fn subfunc() (as Sub)          fn() | 
 |             me method(…) (as Super)   fn(&self) | 
 |             me submethod(…) (as Sub)  fn(&self) | 
 |             ta SubTy (as Sub)        type SubTy | 
 |             ta Ty (as Super)            type Ty | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_self_param_assoc_ty() { | 
 |     check_no_kw( | 
 |         r#" | 
 | trait Super { | 
 |     type Ty; | 
 |     const CONST: u8 = 0; | 
 |     fn func() {} | 
 |     fn method(&self) {} | 
 | } | 
 |  | 
 | trait Sub: Super { | 
 |     type SubTy; | 
 |     const C2: () = (); | 
 |     fn subfunc() {} | 
 |     fn submethod(&self) {} | 
 | } | 
 |  | 
 | struct Wrap<T>(T); | 
 | impl<T> Super for Wrap<T> {} | 
 | impl<T> Sub for Wrap<T> { | 
 |     fn subfunc() { | 
 |         // Should be able to assume `Self: Sub + Super` | 
 |         Self::$0 | 
 |     } | 
 | } | 
 | "#, | 
 |         expect![[r#" | 
 |             ct C2 (as Sub)         const C2: () | 
 |             ct CONST (as Super) const CONST: u8 | 
 |             fn func() (as Super)           fn() | 
 |             fn subfunc() (as Sub)          fn() | 
 |             me method(…) (as Super)   fn(&self) | 
 |             me submethod(…) (as Sub)  fn(&self) | 
 |             ta SubTy (as Sub)        type SubTy | 
 |             ta Ty (as Super)            type Ty | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_type_alias() { | 
 |     check_no_kw( | 
 |         r#" | 
 | struct S; | 
 | impl S { fn foo() {} } | 
 | type T = S; | 
 | impl T { fn bar() {} } | 
 |  | 
 | fn main() { T::$0; } | 
 | "#, | 
 |         expect![[r#" | 
 |             fn bar() fn() | 
 |             fn foo() fn() | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_qualified_macros() { | 
 |     check_no_kw( | 
 |         r#" | 
 | #[macro_export] | 
 | macro_rules! foo { () => {} } | 
 |  | 
 | fn main() { let _ = crate::$0 } | 
 | "#, | 
 |         expect![[r#" | 
 |             fn main()              fn() | 
 |             ma foo!(…) macro_rules! foo | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn does_not_complete_non_fn_macros() { | 
 |     check_no_kw( | 
 |         r#" | 
 | mod m { | 
 |     #[rustc_builtin_macro] | 
 |     pub macro Clone {} | 
 | } | 
 |  | 
 | fn f() {m::$0} | 
 | "#, | 
 |         expect![[r#""#]], | 
 |     ); | 
 |     check_no_kw( | 
 |         r#" | 
 | mod m { | 
 |     #[rustc_builtin_macro] | 
 |     pub macro bench {} | 
 | } | 
 |  | 
 | fn f() {m::$0} | 
 | "#, | 
 |         expect![[r#""#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_reexported_items_under_correct_name() { | 
 |     check_no_kw( | 
 |         r#" | 
 | fn foo() { self::m::$0 } | 
 |  | 
 | mod m { | 
 |     pub use super::p::wrong_fn as right_fn; | 
 |     pub use super::p::WRONG_CONST as RIGHT_CONST; | 
 |     pub use super::p::WrongType as RightType; | 
 | } | 
 | mod p { | 
 |     pub fn wrong_fn() {} | 
 |     pub const WRONG_CONST: u32 = 1; | 
 |     pub struct WrongType {}; | 
 | } | 
 | "#, | 
 |         expect![[r#" | 
 |             ct RIGHT_CONST     u32 | 
 |             fn right_fn()     fn() | 
 |             st RightType WrongType | 
 |         "#]], | 
 |     ); | 
 |  | 
 |     check_edit( | 
 |         "RightType", | 
 |         r#" | 
 | fn foo() { self::m::$0 } | 
 |  | 
 | mod m { | 
 |     pub use super::p::wrong_fn as right_fn; | 
 |     pub use super::p::WRONG_CONST as RIGHT_CONST; | 
 |     pub use super::p::WrongType as RightType; | 
 | } | 
 | mod p { | 
 |     pub fn wrong_fn() {} | 
 |     pub const WRONG_CONST: u32 = 1; | 
 |     pub struct WrongType {}; | 
 | } | 
 | "#, | 
 |         r#" | 
 | fn foo() { self::m::RightType } | 
 |  | 
 | mod m { | 
 |     pub use super::p::wrong_fn as right_fn; | 
 |     pub use super::p::WRONG_CONST as RIGHT_CONST; | 
 |     pub use super::p::WrongType as RightType; | 
 | } | 
 | mod p { | 
 |     pub fn wrong_fn() {} | 
 |     pub const WRONG_CONST: u32 = 1; | 
 |     pub struct WrongType {}; | 
 | } | 
 | "#, | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_in_simple_macro_call() { | 
 |     check_no_kw( | 
 |         r#" | 
 | macro_rules! m { ($e:expr) => { $e } } | 
 | fn main() { m!(self::f$0); } | 
 | fn foo() {} | 
 | "#, | 
 |         expect![[r#" | 
 |             fn foo()  fn() | 
 |             fn main() fn() | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn function_mod_share_name() { | 
 |     check_no_kw( | 
 |         r#" | 
 | fn foo() { self::m::$0 } | 
 |  | 
 | mod m { | 
 |     pub mod z {} | 
 |     pub fn z() {} | 
 | } | 
 | "#, | 
 |         expect![[r#" | 
 |             fn z() fn() | 
 |             md z | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_hashmap_new() { | 
 |     check_no_kw( | 
 |         r#" | 
 | struct RandomState; | 
 | struct HashMap<K, V, S = RandomState> {} | 
 |  | 
 | impl<K, V> HashMap<K, V, RandomState> { | 
 |     pub fn new() -> HashMap<K, V, RandomState> { } | 
 | } | 
 | fn foo() { | 
 |     HashMap::$0 | 
 | } | 
 | "#, | 
 |         expect![[r#" | 
 |             fn new() fn() -> HashMap<K, V, RandomState> | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_variant_through_self() { | 
 |     cov_mark::check!(completes_variant_through_self); | 
 |     check_no_kw( | 
 |         r#" | 
 | enum Foo { | 
 |     Bar, | 
 |     Baz, | 
 | } | 
 |  | 
 | impl Foo { | 
 |     fn foo(self) { | 
 |         Self::$0 | 
 |     } | 
 | } | 
 | "#, | 
 |         expect![[r#" | 
 |             me foo(…) fn(self) | 
 |             ev Bar         Bar | 
 |             ev Baz         Baz | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_non_exhaustive_variant_within_the_defining_crate() { | 
 |     check_no_kw( | 
 |         r#" | 
 | enum Foo { | 
 |     #[non_exhaustive] | 
 |     Bar, | 
 |     Baz, | 
 | } | 
 |  | 
 | fn foo(self) { | 
 |     Foo::$0 | 
 | } | 
 | "#, | 
 |         expect![[r#" | 
 |             ev Bar Bar | 
 |             ev Baz Baz | 
 |         "#]], | 
 |     ); | 
 |  | 
 |     check_no_kw( | 
 |         r#" | 
 | //- /main.rs crate:main deps:e | 
 | fn foo(self) { | 
 |     e::Foo::$0 | 
 | } | 
 |  | 
 | //- /e.rs crate:e | 
 | enum Foo { | 
 |     #[non_exhaustive] | 
 |     Bar, | 
 |     Baz, | 
 | } | 
 | "#, | 
 |         expect![[r#" | 
 |             ev Baz Baz | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_primitive_assoc_const() { | 
 |     cov_mark::check!(completes_primitive_assoc_const); | 
 |     check_no_kw( | 
 |         r#" | 
 | //- /lib.rs crate:lib deps:core | 
 | fn f() { | 
 |     u8::$0 | 
 | } | 
 |  | 
 | //- /core.rs crate:core | 
 | #![rustc_coherence_is_core] | 
 | #[lang = "u8"] | 
 | impl u8 { | 
 |     pub const MAX: Self = 255; | 
 |  | 
 |     pub fn func(self) {} | 
 | } | 
 | "#, | 
 |         expect![[r#" | 
 |             ct MAX pub const MAX: Self | 
 |             me func(…)        fn(self) | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_variant_through_alias() { | 
 |     cov_mark::check!(completes_variant_through_alias); | 
 |     check_no_kw( | 
 |         r#" | 
 | enum Foo { | 
 |     Bar | 
 | } | 
 | type Foo2 = Foo; | 
 | fn main() { | 
 |     Foo2::$0 | 
 | } | 
 | "#, | 
 |         expect![[r#" | 
 |             ev Bar Bar | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn respects_doc_hidden2() { | 
 |     check_no_kw( | 
 |         r#" | 
 | //- /lib.rs crate:lib deps:dep | 
 | fn f() { | 
 |     dep::$0 | 
 | } | 
 |  | 
 | //- /dep.rs crate:dep | 
 | #[doc(hidden)] | 
 | #[macro_export] | 
 | macro_rules! m { | 
 |     () => {} | 
 | } | 
 |  | 
 | #[doc(hidden)] | 
 | pub fn f() {} | 
 |  | 
 | #[doc(hidden)] | 
 | pub struct S; | 
 |  | 
 | #[doc(hidden)] | 
 | pub mod m {} | 
 |             "#, | 
 |         expect![[r#""#]], | 
 |     ) | 
 | } | 
 |  | 
 | #[test] | 
 | fn type_anchor_empty() { | 
 |     check_no_kw( | 
 |         r#" | 
 | trait Foo { | 
 |     fn foo() -> Self; | 
 | } | 
 | struct Bar; | 
 | impl Foo for Bar { | 
 |     fn foo() -> { | 
 |         Bar | 
 |     } | 
 | } | 
 | fn bar() -> Bar { | 
 |     <_>::$0 | 
 | } | 
 | "#, | 
 |         expect![[r#" | 
 |             fn foo() (as Foo) fn() -> Self | 
 |             ex Bar | 
 |             ex bar() | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn type_anchor_type() { | 
 |     check_no_kw( | 
 |         r#" | 
 | trait Foo { | 
 |     fn foo() -> Self; | 
 | } | 
 | struct Bar; | 
 | impl Bar { | 
 |     fn bar() {} | 
 | } | 
 | impl Foo for Bar { | 
 |     fn foo() -> { | 
 |         Bar | 
 |     } | 
 | } | 
 | fn bar() -> Bar { | 
 |     <Bar>::$0 | 
 | } | 
 | "#, | 
 |         expect![[r#" | 
 |             fn bar()                  fn() | 
 |             fn foo() (as Foo) fn() -> Self | 
 |             ex Bar | 
 |             ex bar() | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn type_anchor_type_trait() { | 
 |     check_no_kw( | 
 |         r#" | 
 | trait Foo { | 
 |     fn foo() -> Self; | 
 | } | 
 | struct Bar; | 
 | impl Bar { | 
 |     fn bar() {} | 
 | } | 
 | impl Foo for Bar { | 
 |     fn foo() -> { | 
 |         Bar | 
 |     } | 
 | } | 
 | fn bar() -> Bar { | 
 |     <Bar as Foo>::$0 | 
 | } | 
 | "#, | 
 |         expect![[r#" | 
 |             fn foo() (as Foo) fn() -> Self | 
 |             ex Bar | 
 |             ex bar() | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_fn_in_pub_trait_generated_by_macro() { | 
 |     check_no_kw( | 
 |         r#" | 
 | mod other_mod { | 
 |     macro_rules! make_method { | 
 |         ($name:ident) => { | 
 |             fn $name(&self) {} | 
 |         }; | 
 |     } | 
 |  | 
 |     pub trait MyTrait { | 
 |         make_method! { by_macro } | 
 |         fn not_by_macro(&self) {} | 
 |     } | 
 |  | 
 |     pub struct Foo {} | 
 |  | 
 |     impl MyTrait for Foo {} | 
 | } | 
 |  | 
 | fn main() { | 
 |     use other_mod::{Foo, MyTrait}; | 
 |     let f = Foo {}; | 
 |     f.$0 | 
 | } | 
 | "#, | 
 |         expect![[r#" | 
 |             me by_macro() (as MyTrait)     fn(&self) | 
 |             me not_by_macro() (as MyTrait) fn(&self) | 
 |         "#]], | 
 |     ) | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_fn_in_pub_trait_generated_by_recursive_macro() { | 
 |     check_no_kw( | 
 |         r#" | 
 | mod other_mod { | 
 |     macro_rules! make_method { | 
 |         ($name:ident) => { | 
 |             fn $name(&self) {} | 
 |         }; | 
 |     } | 
 |  | 
 |     macro_rules! make_trait { | 
 |         () => { | 
 |             pub trait MyTrait { | 
 |                 make_method! { by_macro } | 
 |                 fn not_by_macro(&self) {} | 
 |             } | 
 |         } | 
 |     } | 
 |  | 
 |     make_trait!(); | 
 |  | 
 |     pub struct Foo {} | 
 |  | 
 |     impl MyTrait for Foo {} | 
 | } | 
 |  | 
 | fn main() { | 
 |     use other_mod::{Foo, MyTrait}; | 
 |     let f = Foo {}; | 
 |     f.$0 | 
 | } | 
 | "#, | 
 |         expect![[r#" | 
 |             me by_macro() (as MyTrait)     fn(&self) | 
 |             me not_by_macro() (as MyTrait) fn(&self) | 
 |         "#]], | 
 |     ) | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_const_in_pub_trait_generated_by_macro() { | 
 |     check_no_kw( | 
 |         r#" | 
 | mod other_mod { | 
 |     macro_rules! make_const { | 
 |         ($name:ident) => { | 
 |             const $name: u8 = 1; | 
 |         }; | 
 |     } | 
 |  | 
 |     pub trait MyTrait { | 
 |         make_const! { by_macro } | 
 |     } | 
 |  | 
 |     pub struct Foo {} | 
 |  | 
 |     impl MyTrait for Foo {} | 
 | } | 
 |  | 
 | fn main() { | 
 |     use other_mod::{Foo, MyTrait}; | 
 |     let f = Foo {}; | 
 |     Foo::$0 | 
 | } | 
 | "#, | 
 |         expect![[r#" | 
 |             ct by_macro (as MyTrait) pub const by_macro: u8 | 
 |         "#]], | 
 |     ) | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_locals_from_macros() { | 
 |     check_no_kw( | 
 |         r#" | 
 |  | 
 | macro_rules! x { | 
 |     ($x:ident, $expr:expr) => { | 
 |         let $x = 0; | 
 |         $expr | 
 |     }; | 
 | } | 
 | fn main() { | 
 |     x! { | 
 |         foobar, { | 
 |             f$0 | 
 |         } | 
 |     }; | 
 | } | 
 | "#, | 
 |         expect![[r#" | 
 |             fn main()          fn() | 
 |             lc foobar           i32 | 
 |             ma x!(…) macro_rules! x | 
 |             bt u32              u32 | 
 |         "#]], | 
 |     ) | 
 | } | 
 |  | 
 | #[test] | 
 | fn regression_12644() { | 
 |     check_no_kw( | 
 |         r#" | 
 | macro_rules! __rust_force_expr { | 
 |     ($e:expr) => { | 
 |         $e | 
 |     }; | 
 | } | 
 | macro_rules! vec { | 
 |     ($elem:expr) => { | 
 |         __rust_force_expr!($elem) | 
 |     }; | 
 | } | 
 |  | 
 | struct Struct; | 
 | impl Struct { | 
 |     fn foo(self) {} | 
 | } | 
 |  | 
 | fn f() { | 
 |     vec![Struct].$0; | 
 | } | 
 | "#, | 
 |         expect![[r#" | 
 |             me foo() fn(self) | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_after_colon_with_trigger() { | 
 |     check_with_trigger_character( | 
 |         r#" | 
 | //- minicore: option | 
 | fn foo { ::$0 } | 
 | "#, | 
 |         Some(':'), | 
 |         expect![[r#" | 
 |             md core | 
 |         "#]], | 
 |     ); | 
 |     check_with_trigger_character( | 
 |         r#" | 
 | //- minicore: option | 
 | fn foo { /* test */::$0 } | 
 | "#, | 
 |         Some(':'), | 
 |         expect![[r#" | 
 |             md core | 
 |         "#]], | 
 |     ); | 
 |  | 
 |     check_with_trigger_character( | 
 |         r#" | 
 | fn foo { crate::$0 } | 
 | "#, | 
 |         Some(':'), | 
 |         expect![[r#" | 
 |             fn foo() fn() | 
 |         "#]], | 
 |     ); | 
 |  | 
 |     check_with_trigger_character( | 
 |         r#" | 
 | fn foo { crate:$0 } | 
 | "#, | 
 |         Some(':'), | 
 |         expect![""], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_after_colon_without_trigger() { | 
 |     check_with_trigger_character( | 
 |         r#" | 
 | fn foo { crate::$0 } | 
 | "#, | 
 |         None, | 
 |         expect![[r#" | 
 |             fn foo() fn() | 
 |         "#]], | 
 |     ); | 
 |  | 
 |     check_with_trigger_character( | 
 |         r#" | 
 | fn foo { crate:$0 } | 
 | "#, | 
 |         None, | 
 |         expect![""], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn no_completions_in_invalid_path() { | 
 |     check( | 
 |         r#" | 
 | fn foo { crate:::$0 } | 
 | "#, | 
 |         expect![""], | 
 |     ); | 
 |     check_no_kw( | 
 |         r#" | 
 | fn foo { crate::::$0 } | 
 | "#, | 
 |         expect![""], | 
 |     ) | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_struct_via_doc_alias_in_fn_body() { | 
 |     check( | 
 |         r#" | 
 | #[doc(alias = "Bar")] | 
 | struct Foo; | 
 |  | 
 | fn here_we_go() { | 
 |     $0 | 
 | } | 
 | "#, | 
 |         expect![[r#" | 
 |             fn here_we_go()   fn() | 
 |             st Foo (alias Bar) Foo | 
 |             bt u32             u32 | 
 |             kw async | 
 |             kw const | 
 |             kw crate:: | 
 |             kw enum | 
 |             kw extern | 
 |             kw false | 
 |             kw fn | 
 |             kw for | 
 |             kw if | 
 |             kw if let | 
 |             kw impl | 
 |             kw impl for | 
 |             kw let | 
 |             kw letm | 
 |             kw loop | 
 |             kw match | 
 |             kw mod | 
 |             kw return | 
 |             kw self:: | 
 |             kw static | 
 |             kw struct | 
 |             kw trait | 
 |             kw true | 
 |             kw type | 
 |             kw union | 
 |             kw unsafe | 
 |             kw use | 
 |             kw while | 
 |             kw while let | 
 |             sn macro_rules | 
 |             sn pd | 
 |             sn ppd | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_struct_via_multiple_doc_aliases_in_fn_body() { | 
 |     check( | 
 |         r#" | 
 | #[doc(alias("Bar", "Qux"))] | 
 | #[doc(alias = "Baz")] | 
 | struct Foo; | 
 |  | 
 | fn here_we_go() { | 
 |     B$0 | 
 | } | 
 | "#, | 
 |         expect![[r#" | 
 |             fn here_we_go()             fn() | 
 |             st Foo (alias Bar, Qux, Baz) Foo | 
 |             bt u32                       u32 | 
 |             kw async | 
 |             kw const | 
 |             kw crate:: | 
 |             kw enum | 
 |             kw extern | 
 |             kw false | 
 |             kw fn | 
 |             kw for | 
 |             kw if | 
 |             kw if let | 
 |             kw impl | 
 |             kw impl for | 
 |             kw let | 
 |             kw letm | 
 |             kw loop | 
 |             kw match | 
 |             kw mod | 
 |             kw return | 
 |             kw self:: | 
 |             kw static | 
 |             kw struct | 
 |             kw trait | 
 |             kw true | 
 |             kw type | 
 |             kw union | 
 |             kw unsafe | 
 |             kw use | 
 |             kw while | 
 |             kw while let | 
 |             sn macro_rules | 
 |             sn pd | 
 |             sn ppd | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_field_name_via_doc_alias_in_fn_body() { | 
 |     check( | 
 |         r#" | 
 | struct Foo { | 
 |     #[doc(alias = "qux")] | 
 |     bar: u8 | 
 | }; | 
 |  | 
 | fn here_we_go() { | 
 |     let foo = Foo { q$0 } | 
 | } | 
 | "#, | 
 |         expect![[r#" | 
 |             fd bar (alias qux) u8 | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_struct_fn_name_via_doc_alias_in_fn_body() { | 
 |     check( | 
 |         r#" | 
 | struct Foo; | 
 | impl Foo { | 
 |     #[doc(alias = "qux")] | 
 |     fn bar() -> u8 { 1 } | 
 | } | 
 |  | 
 | fn here_we_go() { | 
 |     Foo::q$0 | 
 | } | 
 | "#, | 
 |         expect![[r#" | 
 |             fn bar() (alias qux) fn() -> u8 | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_method_name_via_doc_alias_in_fn_body() { | 
 |     check( | 
 |         r#" | 
 | struct Foo { | 
 |     bar: u8 | 
 | } | 
 | impl Foo { | 
 |     #[doc(alias = "qux")] | 
 |     fn baz(&self) -> u8 { | 
 |         self.bar | 
 |     } | 
 | } | 
 |  | 
 | fn here_we_go() { | 
 |     let foo = Foo { field: 42 }; | 
 |     foo.q$0 | 
 | } | 
 | "#, | 
 |         expect![[r#" | 
 |             fd bar                            u8 | 
 |             me baz() (alias qux) fn(&self) -> u8 | 
 |             sn box                Box::new(expr) | 
 |             sn call               function(expr) | 
 |             sn const                    const {} | 
 |             sn dbg                    dbg!(expr) | 
 |             sn dbgr                  dbg!(&expr) | 
 |             sn deref                       *expr | 
 |             sn let                           let | 
 |             sn letm                      let mut | 
 |             sn match               match expr {} | 
 |             sn ref                         &expr | 
 |             sn refm                    &mut expr | 
 |             sn return                return expr | 
 |             sn unsafe                  unsafe {} | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_fn_name_via_doc_alias_in_fn_body() { | 
 |     check( | 
 |         r#" | 
 | #[doc(alias = "qux")] | 
 | fn foo() {} | 
 | fn bar() { qu$0 } | 
 | "#, | 
 |         expect![[r#" | 
 |             fn bar()             fn() | 
 |             fn foo() (alias qux) fn() | 
 |             bt u32                u32 | 
 |             kw async | 
 |             kw const | 
 |             kw crate:: | 
 |             kw enum | 
 |             kw extern | 
 |             kw false | 
 |             kw fn | 
 |             kw for | 
 |             kw if | 
 |             kw if let | 
 |             kw impl | 
 |             kw impl for | 
 |             kw let | 
 |             kw letm | 
 |             kw loop | 
 |             kw match | 
 |             kw mod | 
 |             kw return | 
 |             kw self:: | 
 |             kw static | 
 |             kw struct | 
 |             kw trait | 
 |             kw true | 
 |             kw type | 
 |             kw union | 
 |             kw unsafe | 
 |             kw use | 
 |             kw while | 
 |             kw while let | 
 |             sn macro_rules | 
 |             sn pd | 
 |             sn ppd | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_struct_name_via_doc_alias_in_another_mod() { | 
 |     check( | 
 |         r#" | 
 | mod foo { | 
 |     #[doc(alias = "Qux")] | 
 |     pub struct Bar(u8); | 
 | } | 
 |  | 
 | fn here_we_go() { | 
 |     use foo; | 
 |     let foo = foo::Q$0 | 
 | } | 
 | "#, | 
 |         expect![[r#" | 
 |             st Bar (alias Qux) Bar | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_use_via_doc_alias_in_another_mod() { | 
 |     check( | 
 |         r#" | 
 | mod foo { | 
 |     #[doc(alias = "Qux")] | 
 |     pub struct Bar(u8); | 
 | } | 
 |  | 
 | fn here_we_go() { | 
 |     use foo::Q$0; | 
 | } | 
 | "#, | 
 |         expect![[r#" | 
 |             st Bar (alias Qux) Bar | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_flyimport_with_doc_alias_in_another_mod() { | 
 |     check( | 
 |         r#" | 
 | mod foo { | 
 |     #[doc(alias = "Qux")] | 
 |     pub struct Bar(); | 
 | } | 
 |  | 
 | fn here_we_go() { | 
 |     let foo = Bar$0 | 
 | } | 
 | "#, | 
 |         expect![[r#" | 
 |             fn here_we_go()                  fn() | 
 |             md foo | 
 |             st Bar (alias Qux) (use foo::Bar) Bar | 
 |             bt u32                            u32 | 
 |             kw const | 
 |             kw crate:: | 
 |             kw false | 
 |             kw for | 
 |             kw if | 
 |             kw if let | 
 |             kw loop | 
 |             kw match | 
 |             kw return | 
 |             kw self:: | 
 |             kw true | 
 |             kw unsafe | 
 |             kw while | 
 |             kw while let | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn completes_only_public() { | 
 |     check( | 
 |         r#" | 
 | //- /e.rs | 
 | pub(self) fn i_should_be_hidden() {} | 
 | pub(in crate::e) fn i_should_also_be_hidden() {} | 
 | pub fn i_am_public () {} | 
 |  | 
 | //- /lib.rs crate:krate | 
 | pub mod e; | 
 |  | 
 | //- /main.rs deps:krate crate:main | 
 | use krate::e; | 
 | fn main() { | 
 |     e::$0 | 
 | }"#, | 
 |         expect![[r#" | 
 |             fn i_am_public() fn() | 
 |         "#]], | 
 |     ) | 
 | } | 
 |  | 
 | #[test] | 
 | fn completion_filtering_excludes_non_identifier_doc_aliases() { | 
 |     check_edit( | 
 |         "PartialOrdcmporder", | 
 |         r#" | 
 | #[doc(alias = ">")] | 
 | #[doc(alias = "cmp")] | 
 | #[doc(alias = "order")] | 
 | trait PartialOrd {} | 
 |  | 
 | struct Foo<T: Partial$0 | 
 | "#, | 
 |         r#" | 
 | #[doc(alias = ">")] | 
 | #[doc(alias = "cmp")] | 
 | #[doc(alias = "order")] | 
 | trait PartialOrd {} | 
 |  | 
 | struct Foo<T: PartialOrd | 
 | "#, | 
 |     ); | 
 | } | 
 |  | 
 | fn check_signatures(src: &str, kind: CompletionItemKind, reduced: Expect, full: Expect) { | 
 |     const FULL_SIGNATURES_CONFIG: crate::CompletionConfig<'_> = { | 
 |         let mut x = TEST_CONFIG; | 
 |         x.full_function_signatures = true; | 
 |         x | 
 |     }; | 
 |  | 
 |     // reduced signature | 
 |     let completion = do_completion_with_config(TEST_CONFIG, src, kind); | 
 |     assert!(completion[0].detail.is_some()); | 
 |     reduced.assert_eq(completion[0].detail.as_ref().unwrap()); | 
 |  | 
 |     // full signature | 
 |     let completion = do_completion_with_config(FULL_SIGNATURES_CONFIG, src, kind); | 
 |     assert!(completion[0].detail.is_some()); | 
 |     full.assert_eq(completion[0].detail.as_ref().unwrap()); | 
 | } | 
 |  | 
 | #[test] | 
 | fn respects_full_function_signatures() { | 
 |     check_signatures( | 
 |         r#" | 
 | pub fn foo<'x, T>(x: &'x mut T) -> u8 where T: Clone, { 0u8 } | 
 | fn main() { fo$0 } | 
 | "#, | 
 |         CompletionItemKind::SymbolKind(ide_db::SymbolKind::Function), | 
 |         expect!("fn(&'x mut T) -> u8"), | 
 |         expect!("pub fn foo<'x, T>(x: &'x mut T) -> u8 where T: Clone,"), | 
 |     ); | 
 |  | 
 |     check_signatures( | 
 |         r#" | 
 | struct Foo; | 
 | struct Bar; | 
 | impl Bar { | 
 |     pub const fn baz(x: Foo) -> ! { loop {} }; | 
 | } | 
 |  | 
 | fn main() { Bar::b$0 } | 
 | "#, | 
 |         CompletionItemKind::SymbolKind(ide_db::SymbolKind::Function), | 
 |         expect!("const fn(Foo) -> !"), | 
 |         expect!("pub const fn baz(x: Foo) -> !"), | 
 |     ); | 
 |  | 
 |     check_signatures( | 
 |         r#" | 
 | struct Foo; | 
 | struct Bar; | 
 | impl Bar { | 
 |     pub const fn baz<'foo>(&'foo mut self, x: &'foo Foo) -> ! { loop {} }; | 
 | } | 
 |  | 
 | fn main() { | 
 |     let mut bar = Bar; | 
 |     bar.b$0 | 
 | } | 
 | "#, | 
 |         CompletionItemKind::SymbolKind(SymbolKind::Method), | 
 |         expect!("const fn(&'foo mut self, &'foo Foo) -> !"), | 
 |         expect!("pub const fn baz<'foo>(&'foo mut self, x: &'foo Foo) -> !"), | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn skips_underscore() { | 
 |     check_with_trigger_character( | 
 |         r#" | 
 | fn foo(_$0) { } | 
 | "#, | 
 |         Some('_'), | 
 |         expect![[r#""#]], | 
 |     ); | 
 |     check_with_trigger_character( | 
 |         r#" | 
 | fn foo(_: _$0) { } | 
 | "#, | 
 |         Some('_'), | 
 |         expect![[r#""#]], | 
 |     ); | 
 |     check_with_trigger_character( | 
 |         r#" | 
 | fn foo<T>() { | 
 |     foo::<_$0>(); | 
 | } | 
 | "#, | 
 |         Some('_'), | 
 |         expect![[r#""#]], | 
 |     ); | 
 |     // underscore expressions are fine, they are invalid so the user definitely meant to type an | 
 |     // underscored name here | 
 |     check_with_trigger_character( | 
 |         r#" | 
 | fn foo() { | 
 |     _$0 | 
 | } | 
 | "#, | 
 |         Some('_'), | 
 |         expect![[r#" | 
 |             fn foo()  fn() | 
 |             bt u32     u32 | 
 |             kw async | 
 |             kw const | 
 |             kw crate:: | 
 |             kw enum | 
 |             kw extern | 
 |             kw false | 
 |             kw fn | 
 |             kw for | 
 |             kw if | 
 |             kw if let | 
 |             kw impl | 
 |             kw impl for | 
 |             kw let | 
 |             kw letm | 
 |             kw loop | 
 |             kw match | 
 |             kw mod | 
 |             kw return | 
 |             kw self:: | 
 |             kw static | 
 |             kw struct | 
 |             kw trait | 
 |             kw true | 
 |             kw type | 
 |             kw union | 
 |             kw unsafe | 
 |             kw use | 
 |             kw while | 
 |             kw while let | 
 |             sn macro_rules | 
 |             sn pd | 
 |             sn ppd | 
 |         "#]], | 
 |     ); | 
 | } | 
 |  | 
 | #[test] | 
 | fn no_skip_underscore_ident() { | 
 |     check_with_trigger_character( | 
 |         r#" | 
 | fn foo(a_$0) { } | 
 | "#, | 
 |         Some('_'), | 
 |         expect![[r#" | 
 |             kw mut | 
 |             kw ref | 
 |         "#]], | 
 |     ); | 
 |     check_with_trigger_character( | 
 |         r#" | 
 | fn foo(_: a_$0) { } | 
 | "#, | 
 |         Some('_'), | 
 |         expect![[r#" | 
 |             bt u32 u32 | 
 |             kw crate:: | 
 |             kw self:: | 
 |         "#]], | 
 |     ); | 
 |     check_with_trigger_character( | 
 |         r#" | 
 | fn foo<T>() { | 
 |     foo::<a_$0>(); | 
 | } | 
 | "#, | 
 |         Some('_'), | 
 |         expect![[r#" | 
 |             tp T | 
 |             bt u32 u32 | 
 |             kw crate:: | 
 |             kw self:: | 
 |         "#]], | 
 |     ); | 
 | } |