• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 #![allow(clippy::uninlined_format_args)]
2 
3 #[macro_use]
4 mod macros;
5 
6 use proc_macro2::{Delimiter, Group, Ident, Punct, Spacing, Span, TokenStream, TokenTree};
7 use quote::{quote, ToTokens};
8 use syn::{parse_quote, Expr, Type, TypePath};
9 
10 #[test]
parse_interpolated_leading_component()11 fn parse_interpolated_leading_component() {
12     // mimics the token stream corresponding to `$mod::rest`
13     let tokens = TokenStream::from_iter(vec![
14         TokenTree::Group(Group::new(Delimiter::None, quote! { first })),
15         TokenTree::Punct(Punct::new(':', Spacing::Joint)),
16         TokenTree::Punct(Punct::new(':', Spacing::Alone)),
17         TokenTree::Ident(Ident::new("rest", Span::call_site())),
18     ]);
19 
20     snapshot!(tokens.clone() as Expr, @r###"
21     Expr::Path {
22         path: Path {
23             segments: [
24                 PathSegment {
25                     ident: "first",
26                 },
27                 Token![::],
28                 PathSegment {
29                     ident: "rest",
30                 },
31             ],
32         },
33     }
34     "###);
35 
36     snapshot!(tokens as Type, @r###"
37     Type::Path {
38         path: Path {
39             segments: [
40                 PathSegment {
41                     ident: "first",
42                 },
43                 Token![::],
44                 PathSegment {
45                     ident: "rest",
46                 },
47             ],
48         },
49     }
50     "###);
51 }
52 
53 #[test]
print_incomplete_qpath()54 fn print_incomplete_qpath() {
55     // qpath with `as` token
56     let mut ty: TypePath = parse_quote!(<Self as A>::Q);
57     snapshot!(ty.to_token_stream(), @r###"
58     TokenStream(`< Self as A > :: Q`)
59     "###);
60     assert!(ty.path.segments.pop().is_some());
61     snapshot!(ty.to_token_stream(), @r###"
62     TokenStream(`< Self as A > ::`)
63     "###);
64     assert!(ty.path.segments.pop().is_some());
65     snapshot!(ty.to_token_stream(), @r###"
66     TokenStream(`< Self >`)
67     "###);
68     assert!(ty.path.segments.pop().is_none());
69 
70     // qpath without `as` token
71     let mut ty: TypePath = parse_quote!(<Self>::A::B);
72     snapshot!(ty.to_token_stream(), @r###"
73     TokenStream(`< Self > :: A :: B`)
74     "###);
75     assert!(ty.path.segments.pop().is_some());
76     snapshot!(ty.to_token_stream(), @r###"
77     TokenStream(`< Self > :: A ::`)
78     "###);
79     assert!(ty.path.segments.pop().is_some());
80     snapshot!(ty.to_token_stream(), @r###"
81     TokenStream(`< Self > ::`)
82     "###);
83     assert!(ty.path.segments.pop().is_none());
84 
85     // normal path
86     let mut ty: TypePath = parse_quote!(Self::A::B);
87     snapshot!(ty.to_token_stream(), @r###"
88     TokenStream(`Self :: A :: B`)
89     "###);
90     assert!(ty.path.segments.pop().is_some());
91     snapshot!(ty.to_token_stream(), @r###"
92     TokenStream(`Self :: A ::`)
93     "###);
94     assert!(ty.path.segments.pop().is_some());
95     snapshot!(ty.to_token_stream(), @r###"
96     TokenStream(`Self ::`)
97     "###);
98     assert!(ty.path.segments.pop().is_some());
99     snapshot!(ty.to_token_stream(), @r###"
100     TokenStream(``)
101     "###);
102     assert!(ty.path.segments.pop().is_none());
103 }
104 
105 #[test]
parse_parenthesized_path_arguments_with_disambiguator()106 fn parse_parenthesized_path_arguments_with_disambiguator() {
107     #[rustfmt::skip]
108     let tokens = quote!(dyn FnOnce::() -> !);
109     snapshot!(tokens as Type, @r###"
110     Type::TraitObject {
111         dyn_token: Some,
112         bounds: [
113             TypeParamBound::Trait(TraitBound {
114                 path: Path {
115                     segments: [
116                         PathSegment {
117                             ident: "FnOnce",
118                             arguments: PathArguments::Parenthesized {
119                                 output: ReturnType::Type(
120                                     Type::Never,
121                                 ),
122                             },
123                         },
124                     ],
125                 },
126             }),
127         ],
128     }
129     "###);
130 }
131