1 use expect_test
::{expect, Expect}
;
2 use ide_db
::base_db
::{FileLoader, FileRange}
;
5 use crate::{fixture, hover::HoverDocFormat, HoverConfig}
;
7 fn check_hover_no_result(ra_fixture
: &str) {
8 let (analysis
, position
) = fixture
::position(ra_fixture
);
13 documentation
: Some(HoverDocFormat
::Markdown
),
16 FileRange { file_id: position.file_id, range: TextRange::empty(position.offset) }
,
19 assert
!(hover
.is_none(), "hover not expected but found: {:?}", hover
.unwrap());
23 fn check(ra_fixture
: &str, expect
: Expect
) {
24 let (analysis
, position
) = fixture
::position(ra_fixture
);
29 documentation
: Some(HoverDocFormat
::Markdown
),
32 FileRange { file_id: position.file_id, range: TextRange::empty(position.offset) }
,
37 let content
= analysis
.db
.file_text(position
.file_id
);
38 let hovered_element
= &content
[hover
.range
];
40 let actual
= format
!("*{}*\n{}\n", hovered_element
, hover
.info
.markup
);
41 expect
.assert_eq(&actual
)
44 fn check_hover_no_links(ra_fixture
: &str, expect
: Expect
) {
45 let (analysis
, position
) = fixture
::position(ra_fixture
);
49 links_in_hover
: false,
50 documentation
: Some(HoverDocFormat
::Markdown
),
53 FileRange { file_id: position.file_id, range: TextRange::empty(position.offset) }
,
58 let content
= analysis
.db
.file_text(position
.file_id
);
59 let hovered_element
= &content
[hover
.range
];
61 let actual
= format
!("*{}*\n{}\n", hovered_element
, hover
.info
.markup
);
62 expect
.assert_eq(&actual
)
65 fn check_hover_no_markdown(ra_fixture
: &str, expect
: Expect
) {
66 let (analysis
, position
) = fixture
::position(ra_fixture
);
71 documentation
: Some(HoverDocFormat
::PlainText
),
74 FileRange { file_id: position.file_id, range: TextRange::empty(position.offset) }
,
79 let content
= analysis
.db
.file_text(position
.file_id
);
80 let hovered_element
= &content
[hover
.range
];
82 let actual
= format
!("*{}*\n{}\n", hovered_element
, hover
.info
.markup
);
83 expect
.assert_eq(&actual
)
86 fn check_actions(ra_fixture
: &str, expect
: Expect
) {
87 let (analysis
, file_id
, position
) = fixture
::range_or_position(ra_fixture
);
92 documentation
: Some(HoverDocFormat
::Markdown
),
95 FileRange { file_id, range: position.range_or_empty() }
,
99 expect
.assert_debug_eq(&hover
.info
.actions
)
102 fn check_hover_range(ra_fixture
: &str, expect
: Expect
) {
103 let (analysis
, range
) = fixture
::range(ra_fixture
);
107 links_in_hover
: false,
108 documentation
: Some(HoverDocFormat
::Markdown
),
115 expect
.assert_eq(hover
.info
.markup
.as_str())
118 fn check_hover_range_no_results(ra_fixture
: &str) {
119 let (analysis
, range
) = fixture
::range(ra_fixture
);
123 links_in_hover
: false,
124 documentation
: Some(HoverDocFormat
::Markdown
),
130 assert
!(hover
.is_none());
134 fn hover_descend_macros_avoids_duplicates() {
137 macro_rules! dupe_use {
161 fn hover_shows_all_macro_descends() {
210 fn hover_shows_type_of_an_expression() {
213 pub fn foo() -> u32 { 1 }
216 let foo_test = foo()$0;
229 fn hover_remove_markdown_if_configured() {
230 check_hover_no_markdown(
232 pub fn foo() -> u32 { 1 }
235 let foo_test = foo()$0;
246 fn hover_shows_long_type_of_an_expression() {
249 struct Scan<A, B, C> { a: A, b: B, c: C }
250 struct Iter<I> { inner: I }
251 enum Option<T> { Some(T), None }
253 struct OtherStruct<T> { i: T }
255 fn scan<A, B, C>(a: A, b: B, c: C) -> Iter<Scan<OtherStruct<A>, B, C>> {
256 Iter { inner: Scan { a, b, c } }
261 let closure = |memo: &mut u32, value: &u32, _another: &mut u32| -> Option<u32> {
262 Option::Some(*memo + value)
265 let mut iter$0 = scan(OtherStruct { i: num }, closure, number);
272 let mut iter: Iter<Scan<OtherStruct<OtherStruct<i32>>, |&mut u32, &u32, &mut u32| -> Option<u32>, u32>>
279 fn hover_shows_fn_signature() {
280 // Single file with result
283 pub fn foo() -> u32 { 1 }
285 fn main() { let foo_test = fo$0o(); }
300 // Multiple candidates but results are ambiguous.
304 pub fn foo() -> u32 { 1 }
307 pub fn foo() -> &str { "" }
310 pub fn foo(a: u32, b: u32) {}
317 fn main() { let foo_test = fo$0o(); }
327 // Use literal `crate` in path
332 fn foo() -> crate::X { X }
334 fn main() { f$0oo(); }
349 // Check `super` in path
354 mod m { pub fn foo() -> super::X { super::X } }
356 fn main() { m::f$0oo(); }
366 pub fn foo() -> super::X
373 fn hover_omits_unnamed_where_preds() {
376 pub fn foo(bar: impl T) { }
378 fn main() { fo$0o(); }
388 pub fn foo(bar: impl T)
394 pub fn foo<V: AsRef<str>>(bar: impl T, baz: V) { }
396 fn main() { fo$0o(); }
406 pub fn foo<V>(bar: impl T, baz: V)
415 fn hover_shows_fn_signature_with_type_params() {
418 pub fn foo<'a, T: AsRef<str>>(b: &'a T) -> &'a str { }
420 fn main() { let foo_test = fo$0o(); }
430 pub fn foo<'a, T>(b: &'a T) -> &'a str
439 fn hover_shows_fn_signature_on_fn_name() {
442 pub fn foo$0(a: u32, b: u32) -> u32 {}
454 pub fn foo(a: u32, b: u32) -> u32
461 fn hover_shows_fn_doc() {
466 /// # use std::path::Path;
468 /// foo(Path::new("hello, world!"))
470 pub fn foo$0(_: &Path) {}
490 # use std::path::Path;
492 foo(Path::new("hello, world!"))
499 fn hover_shows_fn_doc_attr_raw_string() {
502 #[doc = r#"Raw string doc attr"#]
503 pub fn foo$0(_: &Path) {}
526 fn hover_shows_struct_field_info() {
527 // Hovering over the field when instantiating
530 struct Foo { field_a: u32 }
533 let foo = Foo { field_a$0: 0, };
549 // Hovering over the field in the definition
552 struct Foo { field_a$0: u32 }
555 let foo = Foo { field_a: 0 };
573 fn hover_const_static() {
575 r
#"const foo$0: u32 = 123;"#,
584 const foo: u32 = 123 (0x7B)
611 r
#"static foo$0: u32 = 456;"#,
620 static foo: u32 = 456
627 fn hover_default_generic_types() {
630 struct Test<K, T = u8> { k: K, t: T }
633 let zz$0 = Test { t: 23u8, k: 33 };
645 struct Test<K, T = u8> { k: K, t: T }
648 let $0zz$0 = Test { t: 23u8, k: 33 };
661 enum Option<T> { Some(T) }
664 fn main() { So$0me(12); }
681 enum Option<T> { Some(T) }
684 fn main() { let b$0ar = Some(12); }
697 fn hover_enum_variant() {
729 let s = Option::Som$0e(12);
751 fn hover_for_local_variable() {
753 r
#"fn func(foo: i32) { fo$0o; }"#,
765 fn hover_for_local_variable_pat() {
767 r
#"fn func(fo$0o: i32) {}"#,
779 fn hover_local_var_edge() {
781 r
#"fn func(foo: i32) { if true { $0foo; }; }"#,
793 fn hover_for_param_edge() {
795 r
#"fn func($0foo: i32) {}"#,
807 fn hover_for_param_with_multiple_traits() {
817 fn f(_x$0: impl Deref<Target=u8> + DerefMut<Target=u8>) {}"#,
822 _x: impl Deref<Target = u8> + DerefMut<Target = u8>
829 fn test_hover_infer_associated_method_result() {
832 struct Thing { x: u32 }
835 fn new() -> Thing { Thing { x: 0 } }
838 fn main() { let foo_$0test = Thing::new(); }
851 fn test_hover_infer_associated_method_exact() {
855 pub struct Thing { x: u32 }
858 pub fn new() -> Thing { Thing { x: 0 } }
862 fn main() { let foo_test = wrapper::Thing::new$0(); }
872 pub fn new() -> Thing
879 fn test_hover_infer_associated_const_in_pattern() {
910 fn test_hover_self() {
913 struct Thing { x: u32 }
915 fn new() -> Self { Self$0 { x: 0 } }
932 struct Thing { x: u32 }
934 fn new() -> Self$0 { Self { x: 0 } }
953 pub fn new() -> Self$0 { Thing::A }
972 pub fn thing(a: Self$0) {}
990 fn test_hover_shadowing_pat() {
1011 fn test_hover_macro_invocation() {
1014 macro_rules! foo { () => {} }
1016 fn f() { fo$0o!(); }
1033 fn test_hover_macro2_invocation() {
1041 fn f() { fo$0o!(); }
1064 fn test_hover_tuple_field() {
1066 r
#"struct TS(String, i32$0);"#,
1078 fn test_hover_through_macro() {
1081 macro_rules! id { ($($tt:tt)*) => { $($tt)* } }
1084 fn bar() { fo$0o(); }
1102 fn test_hover_through_attr() {
1105 //- proc_macros: identity
1106 #[proc_macros::identity]
1124 fn test_hover_through_expr_in_macro() {
1127 macro_rules! id { ($($tt:tt)*) => { $($tt)* } }
1128 fn foo(bar:u32) { let a = id!(ba$0r); }
1141 fn test_hover_through_expr_in_macro_recursive() {
1144 macro_rules! id_deep { ($($tt:tt)*) => { $($tt)* } }
1145 macro_rules! id { ($($tt:tt)*) => { id_deep!($($tt)*) } }
1146 fn foo(bar:u32) { let a = id!(ba$0r); }
1159 fn test_hover_through_func_in_macro_recursive() {
1162 macro_rules! id_deep { ($($tt:tt)*) => { $($tt)* } }
1163 macro_rules! id { ($($tt:tt)*) => { id_deep!($($tt)*) } }
1164 fn bar() -> u32 { 0 }
1165 fn foo() { let a = id!([0u32, bar($0)] ); }
1177 fn test_hover_through_literal_string_in_macro() {
1180 macro_rules! arr { ($($tt:tt)*) => { [$($tt)*] } }
1182 let mastered_for_itunes = "";
1183 let _ = arr!("Tr$0acks", &mastered_for_itunes);
1196 fn test_hover_through_assert_macro() {
1199 #[rustc_builtin_macro]
1200 macro_rules! assert {}
1202 fn bar() -> bool { true }
1222 fn test_hover_multiple_actions() {
1226 struct Foo { bar: Bar }
1228 fn foo(Foo { b$0ar }: &Foo) {}
1235 mod_path: "test::Bar",
1236 nav: NavigationTarget {
1244 description: "struct Bar",
1255 fn test_hover_through_literal_string_in_builtin_macro() {
1256 check_hover_no_result(
1258 #[rustc_builtin_macro]
1259 macro_rules! format {}
1262 format!("hel$0lo {}", 0);
1269 fn test_hover_non_ascii_space_doc() {
1272 /// <- `\u{3000}` here
1275 fn bar() { fo$0o(); }
1296 fn test_hover_function_show_qualifiers() {
1298 r
#"async fn foo$0() {}"#,
1312 r
#"pub const unsafe fn foo$0() {}"#,
1321 pub const unsafe fn foo()
1325 // Top level `pub(crate)` will be displayed as no visibility.
1327 r
#"mod m { pub(crate) async unsafe extern "C" fn foo$0() {} }"#,
1336 pub(crate) async unsafe extern "C" fn foo()
1343 fn test_hover_function_show_types() {
1345 r
#"fn foo$0(a: i32, b:i32) -> i32 { 0 }"#,
1354 fn foo(a: i32, b: i32) -> i32
1361 fn test_hover_function_pointer_show_identifiers() {
1363 r
#"type foo$0 = fn(a: i32, b: i32) -> i32;"#,
1372 type foo = fn(a: i32, b: i32) -> i32
1379 fn test_hover_function_pointer_no_identifier() {
1381 r
#"type foo$0 = fn(i32, _: i32) -> i32;"#,
1390 type foo = fn(i32, i32) -> i32
1397 fn test_hover_trait_show_qualifiers() {
1399 r
"unsafe trait foo$0() {}",
1416 fn test_hover_extern_crate() {
1419 //- /main.rs crate:main deps:std
1421 //- /std/lib.rs crate:std
1422 //! Standard library for this test
1436 Standard library for this test
1444 //- /main.rs crate:main deps:std
1445 extern crate std as ab$0c;
1446 //- /std/lib.rs crate:std
1447 //! Standard library for this test
1461 Standard library for this test
1470 fn test_hover_mod_with_same_name_as_function() {
1473 use self::m$0y::Bar;
1474 mod my { pub struct Bar; }
1493 fn test_hover_struct_doc_comment() {
1496 /// This is an example
1504 /// assert_eq!(6, my_crate::add_one(5));
1508 fn foo() { let bar = Ba$0r; }
1531 assert_eq!(6, my_crate::add_one(5));
1538 fn test_hover_struct_doc_attr() {
1544 fn foo() { let bar = Ba$0r; }
1565 fn test_hover_struct_doc_attr_multiple_and_mixed() {
1569 #[doc = "bar docs 1"]
1570 #[doc = "bar docs 2"]
1573 fn foo() { let bar = Ba$0r; }
1596 fn test_hover_external_url() {
1600 /// [external](https://www.google.com)
1616 [external](https://www.google.com)
1621 // Check that we don't rewrite links which we can't identify
1623 fn test_hover_unknown_target() {
1649 fn test_hover_no_links() {
1650 check_hover_no_links(
1653 /// case 1. bare URL: https://www.example.com/
1654 /// case 2. inline URL with title: [example](https://www.example.com/)
1655 /// case 3. code reference: [`Result`]
1656 /// case 4. code reference but miss footnote: [`String`]
1657 /// case 5. autolink: <http://www.example.com/>
1658 /// case 6. email address: <test@example.com>
1659 /// case 7. reference: [example][example]
1660 /// case 8. collapsed link: [example][]
1661 /// case 9. shortcut link: [example]
1662 /// case 10. inline without URL: [example]()
1663 /// case 11. reference: [foo][foo]
1664 /// case 12. reference: [foo][bar]
1665 /// case 13. collapsed link: [foo][]
1666 /// case 14. shortcut link: [foo]
1667 /// case 15. inline without URL: [foo]()
1668 /// case 16. just escaped text: \[foo]
1669 /// case 17. inline link: [Foo](foo::Foo)
1671 /// [`Result`]: ../../std/result/enum.Result.html
1672 /// [^example]: https://www.example.com/
1689 case 1. bare URL: https://www.example.com/
1690 case 2. inline URL with title: [example](https://www.example.com/)
1691 case 3. code reference: `Result`
1692 case 4. code reference but miss footnote: `String`
1693 case 5. autolink: http://www.example.com/
1694 case 6. email address: test@example.com
1695 case 7. reference: example
1696 case 8. collapsed link: example
1697 case 9. shortcut link: example
1698 case 10. inline without URL: example
1699 case 11. reference: foo
1700 case 12. reference: foo
1701 case 13. collapsed link: foo
1702 case 14. shortcut link: foo
1703 case 15. inline without URL: foo
1704 case 16. just escaped text: \[foo\]
1705 case 17. inline link: Foo
1707 [^example]: https://www.example.com/
1713 fn test_hover_macro_generated_struct_fn_doc_comment() {
1714 cov_mark
::check
!(hover_macro_generated_struct_fn_doc_comment
);
1730 fn foo() { let bar = Bar; bar.fo$0o(); }
1751 fn test_hover_macro_generated_struct_fn_doc_attr() {
1752 cov_mark
::check
!(hover_macro_generated_struct_fn_doc_attr
);
1760 #[doc = "Do the foo"]
1768 fn foo() { let bar = Bar; bar.fo$0o(); }
1789 fn test_hover_variadic_function() {
1793 pub fn foo(bar: i32, ...) -> i32;
1796 fn main() { let foo_test = unsafe { fo$0o(1, 2, 3); } }
1806 pub unsafe fn foo(bar: i32, ...) -> i32
1813 fn test_hover_trait_has_impl_action() {
1815 r
#"trait foo$0() {}"#,
1832 fn test_hover_struct_has_impl_action() {
1834 r
"struct foo$0() {}",
1851 fn test_hover_union_has_impl_action() {
1853 r
#"union foo$0() {}"#,
1870 fn test_hover_enum_has_impl_action() {
1872 r
"enum foo$0() { A, B }",
1889 fn test_hover_self_has_impl_action() {
1891 r
#"struct foo where Self$0:;"#,
1908 fn test_hover_test_has_action() {
1926 use_name_in_title: false,
1927 nav: NavigationTarget {
1932 focus_range: 11..19,
1953 fn test_hover_test_mod_has_action() {
1965 use_name_in_title: false,
1966 nav: NavigationTarget {
1974 description: "mod tests",
1988 fn test_hover_struct_has_goto_type_action() {
1993 fn main() { let s$0t = S{ f1:0 }; }
2000 mod_path: "test::S",
2001 nav: NavigationTarget {
2009 description: "struct S",
2020 fn test_hover_generic_struct_has_goto_type_actions() {
2024 struct S<T>{ f1: T }
2026 fn main() { let s$0t = S{ f1:Arg(0) }; }
2033 mod_path: "test::S",
2034 nav: NavigationTarget {
2039 focus_range: 24..25,
2042 description: "struct S<T>",
2046 mod_path: "test::Arg",
2047 nav: NavigationTarget {
2055 description: "struct Arg",
2066 fn test_hover_generic_struct_has_flattened_goto_type_actions() {
2070 struct S<T>{ f1: T }
2072 fn main() { let s$0t = S{ f1: S{ f1: Arg(0) } }; }
2079 mod_path: "test::S",
2080 nav: NavigationTarget {
2085 focus_range: 24..25,
2088 description: "struct S<T>",
2092 mod_path: "test::Arg",
2093 nav: NavigationTarget {
2101 description: "struct Arg",
2112 fn test_hover_tuple_has_goto_type_actions() {
2121 fn main() { let s$0t = (A(1), B(2), M::C(3) ); }
2128 mod_path: "test::A",
2129 nav: NavigationTarget {
2137 description: "struct A",
2141 mod_path: "test::B",
2142 nav: NavigationTarget {
2147 focus_range: 22..23,
2150 description: "struct B",
2154 mod_path: "test::M::C",
2155 nav: NavigationTarget {
2160 focus_range: 53..54,
2163 description: "pub struct C",
2174 fn test_hover_return_impl_trait_has_goto_type_action() {
2178 fn foo() -> impl Foo {}
2180 fn main() { let s$0t = foo(); }
2187 mod_path: "test::Foo",
2188 nav: NavigationTarget {
2196 description: "trait Foo",
2207 fn test_hover_generic_return_impl_trait_has_goto_type_action() {
2212 fn foo() -> impl Foo<S> {}
2214 fn main() { let s$0t = foo(); }
2221 mod_path: "test::Foo",
2222 nav: NavigationTarget {
2230 description: "trait Foo<T>",
2234 mod_path: "test::S",
2235 nav: NavigationTarget {
2240 focus_range: 23..24,
2243 description: "struct S",
2254 fn test_hover_return_impl_traits_has_goto_type_action() {
2259 fn foo() -> impl Foo + Bar {}
2261 fn main() { let s$0t = foo(); }
2268 mod_path: "test::Foo",
2269 nav: NavigationTarget {
2277 description: "trait Foo",
2281 mod_path: "test::Bar",
2282 nav: NavigationTarget {
2287 focus_range: 19..22,
2290 description: "trait Bar",
2301 fn test_hover_generic_return_impl_traits_has_goto_type_action() {
2309 fn foo() -> impl Foo<S1> + Bar<S2> {}
2311 fn main() { let s$0t = foo(); }
2318 mod_path: "test::Foo",
2319 nav: NavigationTarget {
2327 description: "trait Foo<T>",
2331 mod_path: "test::Bar",
2332 nav: NavigationTarget {
2337 focus_range: 22..25,
2340 description: "trait Bar<T>",
2344 mod_path: "test::S1",
2345 nav: NavigationTarget {
2350 focus_range: 39..41,
2353 description: "struct S1",
2357 mod_path: "test::S2",
2358 nav: NavigationTarget {
2363 focus_range: 52..54,
2366 description: "struct S2",
2377 fn test_hover_arg_impl_trait_has_goto_type_action() {
2381 fn foo(ar$0g: &impl Foo) {}
2388 mod_path: "test::Foo",
2389 nav: NavigationTarget {
2397 description: "trait Foo",
2408 fn test_hover_arg_impl_traits_has_goto_type_action() {
2415 fn foo(ar$0g: &impl Foo + Bar<S>) {}
2422 mod_path: "test::Foo",
2423 nav: NavigationTarget {
2431 description: "trait Foo",
2435 mod_path: "test::Bar",
2436 nav: NavigationTarget {
2441 focus_range: 19..22,
2444 description: "trait Bar<T>",
2448 mod_path: "test::S",
2449 nav: NavigationTarget {
2454 focus_range: 36..37,
2457 description: "struct S",
2468 fn test_hover_async_block_impl_trait_has_goto_type_action() {
2471 //- /main.rs crate:main deps:core
2472 // we don't use minicore here so that this test doesn't randomly fail
2473 // when someone edits minicore
2476 let fo$0o = async { S };
2478 //- /core.rs crate:core
2480 #[lang = "future_trait"]
2489 mod_path: "core::future::Future",
2490 nav: NavigationTarget {
2495 focus_range: 60..66,
2498 description: "pub trait Future",
2502 mod_path: "main::S",
2503 nav: NavigationTarget {
2508 focus_range: 108..109,
2511 description: "struct S",
2522 fn test_hover_arg_generic_impl_trait_has_goto_type_action() {
2527 fn foo(ar$0g: &impl Foo<S>) {}
2534 mod_path: "test::Foo",
2535 nav: NavigationTarget {
2543 description: "trait Foo<T>",
2547 mod_path: "test::S",
2548 nav: NavigationTarget {
2553 focus_range: 23..24,
2556 description: "struct S",
2567 fn test_hover_dyn_return_has_goto_type_action() {
2575 fn foo() -> B<dyn Foo> {}
2577 fn main() { let s$0t = foo(); }
2584 mod_path: "test::B",
2585 nav: NavigationTarget {
2590 focus_range: 49..50,
2593 description: "struct B<T>",
2597 mod_path: "test::Foo",
2598 nav: NavigationTarget {
2606 description: "trait Foo",
2617 fn test_hover_dyn_arg_has_goto_type_action() {
2621 fn foo(ar$0g: &dyn Foo) {}
2628 mod_path: "test::Foo",
2629 nav: NavigationTarget {
2637 description: "trait Foo",
2648 fn test_hover_generic_dyn_arg_has_goto_type_action() {
2653 fn foo(ar$0g: &dyn Foo<S>) {}
2660 mod_path: "test::Foo",
2661 nav: NavigationTarget {
2669 description: "trait Foo<T>",
2673 mod_path: "test::S",
2674 nav: NavigationTarget {
2679 focus_range: 23..24,
2682 description: "struct S",
2693 fn test_hover_goto_type_action_links_order() {
2696 trait ImplTrait<T> {}
2697 trait DynTrait<T> {}
2701 fn foo(a$0rg: &impl ImplTrait<B<dyn DynTrait<B<S>>>>) {}
2708 mod_path: "test::ImplTrait",
2709 nav: NavigationTarget {
2717 description: "trait ImplTrait<T>",
2721 mod_path: "test::B",
2722 nav: NavigationTarget {
2727 focus_range: 50..51,
2730 description: "struct B<T>",
2734 mod_path: "test::DynTrait",
2735 nav: NavigationTarget {
2740 focus_range: 28..36,
2743 description: "trait DynTrait<T>",
2747 mod_path: "test::S",
2748 nav: NavigationTarget {
2753 focus_range: 65..66,
2756 description: "struct S",
2767 fn test_hover_associated_type_has_goto_type_action() {
2772 fn get(self) -> Self::Item {}
2778 impl Foo for S { type Item = Bar; }
2780 fn test() -> impl Foo { S {} }
2782 fn main() { let s$0t = test().get(); }
2789 mod_path: "test::Foo",
2790 nav: NavigationTarget {
2798 description: "trait Foo",
2809 fn test_hover_const_param_has_goto_type_action() {
2813 struct Foo<const BAR: Bar>;
2815 impl<const BAR: Bar> Foo<BAR$0> {}
2822 mod_path: "test::Bar",
2823 nav: NavigationTarget {
2831 description: "struct Bar",
2842 fn test_hover_type_param_has_goto_type_action() {
2847 fn foo<T: Foo>(t: T$0){}
2854 mod_path: "test::Foo",
2855 nav: NavigationTarget {
2863 description: "trait Foo",
2874 fn test_hover_self_has_go_to_type() {
2887 mod_path: "test::Foo",
2888 nav: NavigationTarget {
2896 description: "struct Foo",
2907 fn hover_displays_normalized_crate_names() {
2910 //- /lib.rs crate:name-with-dashes
2912 pub struct Thing { x: u32 }
2915 pub fn new() -> Thing { Thing { x: 0 } }
2919 //- /main.rs crate:main deps:name-with-dashes
2920 fn main() { let foo_test = name_with_dashes::wrapper::Thing::new$0(); }
2926 name_with_dashes::wrapper::Thing
2930 pub fn new() -> Thing
2937 fn hover_field_pat_shorthand_ref_match_ergonomics() {
2969 fn const_generic_order() {
2973 struct S$0T<const C: usize = 1, T = Foo>(T);
2983 struct ST<const C: usize, T = Foo>
2990 fn const_generic_positive_i8_literal() {
2993 struct Const<const N: i8>;
2996 let v$0alue = Const::<1>;
3010 fn const_generic_zero_i8_literal() {
3013 struct Const<const N: i8>;
3016 let v$0alue = Const::<0>;
3030 fn const_generic_negative_i8_literal() {
3033 struct Const<const N: i8>;
3036 let v$0alue = Const::<-1>;
3043 let value: Const<-1>
3050 fn const_generic_bool_literal() {
3053 struct Const<const F: bool>;
3056 let v$0alue = Const::<true>;
3063 let value: Const<true>
3070 fn const_generic_char_literal() {
3073 struct Const<const C: char>;
3076 let v$0alue = Const::<'🦀'>;
3083 let value: Const<'🦀'>
3090 fn hover_self_param_shows_type() {
3109 fn hover_self_param_shows_type_for_arbitrary_self_type() {
3115 fn bar(sel$0f: Arc<Foo>) {}
3129 fn hover_doc_outer_inner() {
3136 /// This comment belongs to the function
3160 fn hover_doc_outer_inner_attribue() {
3163 #[doc = "Be quick;"]
3165 #![doc = "time is mana"]
3167 #[doc = "This comment belongs to the function"]
3191 fn hover_doc_block_style_indentend() {
3225 fn hover_comments_dont_highlight_parent() {
3226 cov_mark
::check
!(no_highlight_on_comment_hover
);
3227 check_hover_no_result(
3255 fn hover_lifetime() {
3257 r
#"fn foo<'lifetime>(_: &'lifetime$0 ()) {}"#,
3269 fn hover_type_param() {
3276 impl<T: TraitA + TraitB> Foo<T$0> where T: Sized {}
3300 // lifetimes bounds arent being tracked yet
3305 impl<T: 'static> Foo<T$0> {}
3318 fn hover_type_param_sized_bounds() {
3319 // implicit `: Sized` bound
3325 impl<T: Trait> Foo<T$0> {}
3340 impl<T: Trait + ?Sized> Foo<T$0> {}
3352 mod type_param_sized_bounds
{
3356 fn single_implicit() {
3373 fn single_explicit() {
3377 fn foo<T$0: Sized>() {}
3390 fn single_relaxed() {
3394 fn foo<T$0: ?Sized>() {}
3407 fn multiple_implicit() {
3412 fn foo<T$0: Trait>() {}
3425 fn multiple_explicit() {
3430 fn foo<T$0: Trait + Sized>() {}
3443 fn multiple_relaxed() {
3448 fn foo<T$0: Trait + ?Sized>() {}
3465 fn foo<T$0: ?Sized + Sized + Sized>() {}
3479 fn foo<T$0: Sized + ?Sized + Sized + Trait>() {}
3493 fn hover_const_generic_type_alias() {
3496 struct Foo<const LEN: usize>;
3497 type Fo$0o2 = Foo<2>;
3514 fn hover_const_param() {
3517 struct Foo<const LEN: usize>;
3518 impl<const LEN: usize> Foo<LEN$0> {}
3531 fn hover_const_eval() {
3536 const FOO$0: usize = 1 << 3;
3546 const FOO: usize = 8
3558 const FOO$0: usize = (1 << 3) + (1 << 2);
3568 const FOO: usize = 12 (0xC)
3576 // show original body when const eval fails
3580 const FOO$0: usize = 2 - 3;
3590 const FOO: usize = 2 - 3
3598 // don't show hex for negatives
3602 const FOO$0: i32 = 2 - 3;
3623 const FOO$0: &str = "bar";
3633 const FOO: &str = "bar"
3641 // show char literal
3645 const FOO$0: char = 'a';
3655 const FOO: char = 'a'
3663 // show escaped char literal
3667 const FOO$0: char = '\x61';
3677 const FOO: char = 'a'
3685 // show byte literal
3689 const FOO$0: u8 = b'a';
3699 const FOO: u8 = 97 (0x61)
3707 // show escaped byte literal
3711 const FOO$0: u8 = b'\x61';
3721 const FOO: u8 = 97 (0x61)
3729 // show float literal
3733 const FOO$0: f64 = 1.0234;
3743 const FOO: f64 = 1.0234
3751 //show float typecasted from int
3755 const FOO$0: f32 = 1f32;
3765 const FOO: f32 = 1.0
3773 //show f64 typecasted from float
3777 const FOO$0: f64 = 1.0f64;
3787 const FOO: f64 = 1.0
3798 fn hover_const_pat() {
3802 const FOO: usize = 3;
3818 const FOO: usize = 3
3829 fn array_repeat_exp() {
3833 let til$0e4 = [0_u32; (4 * 8 * 8) / 32];
3847 fn hover_mod_def() {
3874 fn hover_self_in_use() {
3877 //! This should not appear
3879 /// But this should appear
3882 use foo::bar::{self$0};
3897 But this should appear
3903 fn hover_keyword() {
3906 //- /main.rs crate:main deps:std
3907 fn f() { retur$0n; }
3908 //- /libstd.rs crate:std
3909 /// Docs for return_keyword
3910 mod return_keyword {}
3921 Docs for return_keyword
3927 fn hover_keyword_doc() {
3930 //- /main.rs crate:main deps:std
3932 let bar = mov$0e || {};
3934 //- /libstd.rs crate:std
3935 #[doc(keyword = "move")]
3937 /// [closures][closure]
3939 /// <https://doc.rust-lang.org/nightly/book/ch13-01-closures.html>
3941 /// [closure]: ../book/ch13-01-closures.html
3942 /// [threads]: ../book/ch16-01-threads.html#using-move-closures-with-threads
3954 [closure](https://doc.rust-lang.org/nightly/book/ch13-01-closures.html)
3955 [closures](https://doc.rust-lang.org/nightly/book/ch13-01-closures.html)
3956 [threads](https://doc.rust-lang.org/nightly/book/ch16-01-threads.html#using-move-closures-with-threads)
3957 <https://doc.rust-lang.org/nightly/book/ch13-01-closures.html>
3963 fn hover_keyword_as_primitive() {
3966 //- /main.rs crate:main deps:std
3967 type F = f$0n(i32) -> i32;
3968 //- /libstd.rs crate:std
3969 /// Docs for prim_fn
3987 fn hover_builtin() {
3990 //- /main.rs crate:main deps:std
3991 cosnt _: &str$0 = ""; }
3993 //- /libstd.rs crate:std
3994 /// Docs for prim_str
3995 /// [`foo`](../std/keyword.foo.html)
4008 [`foo`](https://doc.rust-lang.org/nightly/std/keyword.foo.html)
4014 fn hover_macro_expanded_function() {
4017 struct S<'a, T>(&'a T);
4021 fn bar<'t, T: Clone + 't>(s: &mut S<'t, T>, t: u32) -> *mut u32 where
4023 for<'a> T: Clone + 'a
4042 fn bar<'t, T>(s: &mut S<'t, T>, t: u32) -> *mut u32
4046 for<'a> T: Clone + 'a,
4053 fn hover_intra_doc_links() {
4058 /// This is the item. Cool!
4062 /// Gives you a [`TheItem$0`].
4064 /// [`TheItem`]: theitem::TheItem
4065 pub fn gimme() -> theitem::TheItem {
4082 This is the item. Cool!
4088 fn test_hover_trait_assoc_typealias() {
4113 type Bar = <Foo as t2::T2>::Ba$0r;
4114 // ^^^ unresolvedReference
4131 fn hover_generic_assoc() {
4134 fn foo<T: A>() where T::Assoc$0: {}
4154 let _: <T>::Assoc$0;
4194 fn string_shadowed_with_inner_items() {
4197 //- /main.rs crate:main deps:alloc
4199 /// Custom `String` type.
4208 //- /alloc.rs crate:alloc
4213 /// This is `alloc::String`.
4230 Custom `String` type.
4236 fn function_doesnt_shadow_crate_in_use_tree() {
4239 //- /main.rs crate:main deps:foo
4242 //- /foo.rs crate:foo
4256 fn hover_feature() {
4258 r
#"#![feature(box_syntax$0)]"#,
4268 The tracking issue for this feature is: [#49733]
4270 [#49733]: https://github.com/rust-lang/rust/issues/49733
4272 See also [`box_patterns`](box-patterns.md)
4274 ------------------------
4276 Currently the only stable way to create a `Box` is via the `Box::new` method.
4277 Also it is not possible in stable Rust to destructure a `Box` in a match
4278 pattern. The unstable `box` keyword can be used to create a `Box`. An example
4282 #![feature(box_syntax)]
4296 r
#"#![allow(arithmetic_overflow$0)]"#,
4298 *arithmetic_overflow*
4304 arithmetic operation overflows
4310 fn hover_clippy_lint() {
4312 r
#"#![allow(clippy::almost_swapped$0)]"#,
4316 clippy::almost_swapped
4320 Checks for `foo = bar; bar = foo` sequences.
4326 fn hover_attr_path_qualifier() {
4329 //- /foo.rs crate:foo
4331 //- /lib.rs crate:main.rs deps:foo
4362 use bar::{self as foo$0};
4405 fn hover_attribute_in_macro() {
4409 macro_rules! identity {
4414 #[rustc_builtin_macro]
4436 fn hover_derive_input() {
4440 #[rustc_builtin_macro]
4461 #[rustc_builtin_macro]
4464 #[derive(foo::Copy$0)]
4482 fn hover_range_math() {
4485 fn f() { let expr = $01 + 2 * 3$0 }
4495 fn f() { let expr = 1 $0+ 2 * $03 }
4505 fn f() { let expr = 1 + $02 * 3$0 }
4515 fn hover_range_arrays() {
4518 fn f() { let expr = $0[1, 2, 3, 4]$0 }
4528 fn f() { let expr = [1, 2, $03, 4]$0 }
4538 fn f() { let expr = [1, 2, $03$0, 4] }
4548 fn hover_range_functions() {
4551 fn f<T>(a: &[T]) { }
4552 fn b() { $0f$0(&[1, 2, 3, 4, 5]); }
4562 fn f<T>(a: &[T]) { }
4563 fn b() { f($0&[1, 2, 3, 4, 5]$0); }
4573 fn hover_range_shows_nothing_when_invalid() {
4574 check_hover_range_no_results(
4576 fn f<T>(a: &[T]) { }
4577 fn b()$0 { f(&[1, 2, 3, 4, 5]); }$0
4581 check_hover_range_no_results(
4583 fn f<T>$0(a: &[T]) { }
4584 fn b() { f(&[1, 2, 3,$0 4, 5]); }
4588 check_hover_range_no_results(
4590 fn $0f() { let expr = [1, 2, 3, 4]$0 }
4596 fn hover_range_shows_unit_for_statements() {
4599 fn f<T>(a: &[T]) { }
4600 fn b() { $0f(&[1, 2, 3, 4, 5]); }$0
4610 fn f() { let expr$0 = $0[1, 2, 3, 4] }
4620 fn hover_range_for_pat() {
4647 fn hover_range_shows_coercions_if_applicable_expr() {
4651 let x: &u32 = $0&&&&&0$0;
4664 let x: *const u32 = $0&0$0;
4670 Coerced to: *const u32
4677 fn hover_range_shows_type_actions() {
4682 let x: &Foo = $0&&&&&Foo$0;
4690 mod_path: "test::Foo",
4691 nav: NavigationTarget {
4699 description: "struct Foo",
4710 fn hover_try_expr_res() {
4716 fn foo() -> Result<(), FooError> {
4717 Ok($0Result::<(), FooError>::Ok(())?$0)
4731 fn foo() -> Result<(), FooError> {
4732 Ok($0Result::<(), BarError>::Ok(())?$0)
4737 Try Error Type: BarError
4738 Propagated as: FooError
4745 fn hover_try_expr() {
4748 struct NotResult<T, U>(T, U);
4752 fn foo() -> NotResult<(), Looooong> {
4753 $0NotResult((), Short)?$0;
4758 Try Target Type: NotResult<(), Short>
4759 Propagated as: NotResult<(), Looooong>
4765 struct NotResult<T, U>(T, U);
4769 fn foo() -> NotResult<(), Short> {
4770 $0NotResult((), Looooong)?$0;
4775 Try Target Type: NotResult<(), Looooong>
4776 Propagated as: NotResult<(), Short>
4783 fn hover_try_expr_option() {
4784 cov_mark
::check
!(hover_try_expr_opt_opt
);
4787 //- minicore: option, try
4789 fn foo() -> Option<()> {
4796 <Option<i32> as Try>::Output
4802 fn hover_deref_expr() {
4806 use core::ops::Deref;
4808 struct DerefExample<T> {
4812 impl<T> Deref for DerefExample<T> {
4815 fn deref(&self) -> &Self::Target {
4821 let x = DerefExample { value: 0 };
4822 let y: i32 = $0*x$0;
4827 Dereferenced from: DerefExample<i32>
4835 fn hover_deref_expr_with_coercion() {
4839 use core::ops::Deref;
4841 struct DerefExample<T> {
4845 impl<T> Deref for DerefExample<T> {
4848 fn deref(&self) -> &Self::Target {
4854 let x = DerefExample { value: &&&&&0 };
4855 let y: &i32 = $0*x$0;
4860 Dereferenced from: DerefExample<&&&&&i32>
4869 fn hover_intra_in_macro() {
4872 macro_rules! foo_macro {
4873 ($(#[$attr:meta])* $name:ident) => {
4880 /// Doc comment for [`Foo$0`]
4897 Doc comment for [`Foo`](https://docs.rs/test/*/test/struct.Foo.html)
4903 fn hover_intra_in_attr() {
4906 #[doc = "Doc comment for [`Foo$0`]"]
4922 Doc comment for [`Foo`](https://docs.rs/test/*/test/struct.Foo.html)
4928 fn hover_inert_attr() {
4945 * \#\[doc(hidden|inline|...)\]
4946 * \#\[doc = string\]
4965 * \#\[allow(lint1, lint2, ..., /\*opt\*/ reason = "...")\]
4971 fn hover_dollar_crate() {
4972 // $crate should be resolved to the right crate name.
4976 //- /main.rs crate:main deps:dep
4978 //- /dep.rs crate:dep
4981 ( $name:ident ) => { const $name: $crate::Type = $crate::Type; };
4994 const KONST: dep::Type = $crate::Type
5001 fn hover_record_variant() {
5005 RecordV$0 { field: u32 }
5016 RecordV { field: u32 }
5023 fn hover_trait_impl_assoc_item_def_doc_forwarding() {
5053 fn hover_ranged_macro_call() {
5056 macro_rules! __rust_force_expr {
5063 __rust_force_expr!($elem)
5089 struct Struct(usize);
5091 impl core::ops::Deref for Struct {
5092 type Target = usize;
5094 fn deref(&self) -> &Self::Target {
5111 fn deref(&self) -> &Self::Target
5118 fn static_const_macro_expanded_body() {
5125 f(e) // Prevent const eval from evaluating this constant, we want to print the body's code.
5151 pub static V: i8 = {
5167 pub static V: i8 = {