1 | /// A stream of tokens |
2 | #[derive (Debug, Clone, PartialEq, Eq, PartialOrd, Ord)] |
3 | pub struct TokenStream(pub String); |
4 | |
5 | impl From<String> for TokenStream { |
6 | fn from(tokens: String) -> Self { |
7 | Self(tokens) |
8 | } |
9 | } |
10 | |
11 | impl From<&String> for TokenStream { |
12 | fn from(tokens: &String) -> Self { |
13 | Self(tokens.to_string()) |
14 | } |
15 | } |
16 | |
17 | impl From<&str> for TokenStream { |
18 | fn from(tokens: &str) -> Self { |
19 | Self(tokens.to_string()) |
20 | } |
21 | } |
22 | |
23 | impl TokenStream { |
24 | pub fn new() -> Self { |
25 | Self(String::new()) |
26 | } |
27 | |
28 | /// Appends another stream to the stream |
29 | /// |
30 | /// note: a space will be inserted before the other stream |
31 | pub fn combine(&mut self, other: &TokenStream) { |
32 | self.push_space(); |
33 | self.0.push_str(&other.0) |
34 | } |
35 | |
36 | #[must_use ] |
37 | pub fn join(&self, value: &str) -> Self { |
38 | Self(format!(" {}{value}" , self.0)) |
39 | } |
40 | |
41 | pub fn is_empty(&self) -> bool { |
42 | self.0.is_empty() |
43 | } |
44 | |
45 | /// View the stream as a string |
46 | pub fn as_str(&self) -> &str { |
47 | &self.0 |
48 | } |
49 | |
50 | /// Convert the stream into a `String` |
51 | pub fn into_string(self) -> String { |
52 | self.0 |
53 | } |
54 | |
55 | /// Parse the token stream as something |
56 | /// |
57 | /// Mostly used with `proc_macro2::TokenStream` or `proc_macro::TokenStream` |
58 | pub fn parse<T: core::str::FromStr>(self) -> Result<T, T::Err> { |
59 | self.into_string().parse() |
60 | } |
61 | |
62 | pub(crate) fn push_space(&mut self) { |
63 | match self.last_char() { |
64 | None | Some(' ' ) => {} |
65 | _ => self.0.push(' ' ), |
66 | } |
67 | } |
68 | |
69 | pub fn push(&mut self, c: char) { |
70 | self.0.push(c) |
71 | } |
72 | |
73 | pub fn push_str(&mut self, str: &str) { |
74 | self.0.push_str(str) |
75 | } |
76 | |
77 | fn last_char(&self) -> Option<char> { |
78 | self.0.chars().last() |
79 | } |
80 | } |
81 | |
82 | impl Default for TokenStream { |
83 | fn default() -> Self { |
84 | Self::new() |
85 | } |
86 | } |
87 | |
88 | impl core::iter::FromIterator<TokenStream> for TokenStream { |
89 | fn from_iter<I: IntoIterator<Item = TokenStream>>(iter: I) -> Self { |
90 | iterOption.into_iter() |
91 | .fold(init:None, |accum: Option<TokenStream>, n: TokenStream| { |
92 | let mut ts: TokenStream = accum.unwrap_or_default(); |
93 | ts.combine(&n); |
94 | Some(ts) |
95 | }) |
96 | .unwrap_or_else(TokenStream::new) |
97 | } |
98 | } |
99 | |
100 | /// A delimiter around a block of code |
101 | #[derive (Copy, Clone)] |
102 | pub enum Delimiter { |
103 | /// `[]` |
104 | Bracket, |
105 | /// `{}` |
106 | Brace, |
107 | /// `()` |
108 | Parenthesis, |
109 | } |
110 | |
111 | impl Delimiter { |
112 | /// The opening delimiter |
113 | pub fn open(self) -> char { |
114 | match self { |
115 | Delimiter::Bracket => '[' , |
116 | Delimiter::Brace => '{' , |
117 | Delimiter::Parenthesis => '(' , |
118 | } |
119 | } |
120 | |
121 | /// The closing delimiter |
122 | pub fn close(self) -> char { |
123 | match self { |
124 | Delimiter::Bracket => ']' , |
125 | Delimiter::Brace => '}' , |
126 | Delimiter::Parenthesis => ')' , |
127 | } |
128 | } |
129 | } |
130 | |
131 | /// A literal of some sort |
132 | pub struct Literal { |
133 | inner: String, |
134 | } |
135 | |
136 | macro_rules! unsuffixed { |
137 | ($ty:ty => $name:ident) => { |
138 | pub fn $name(n: $ty) -> Self { |
139 | Self { inner: n.to_string() } |
140 | } |
141 | }; |
142 | } |
143 | |
144 | impl Literal { |
145 | unsuffixed!(i64 => i64_unsuffixed); |
146 | unsuffixed!(usize => usize_unsuffixed); |
147 | unsuffixed!(u32 => u32_unsuffixed); |
148 | unsuffixed!(u16 => u16_unsuffixed); |
149 | unsuffixed!(u8 => u8_unsuffixed); |
150 | |
151 | pub fn byte_string(s: &[u8]) -> Self { |
152 | Self { inner: format!("b \"{}\"" , core::str::from_utf8(s).expect("Could not turn bytes into byte literal" )) } |
153 | } |
154 | |
155 | pub fn as_str(&self) -> &str { |
156 | &self.inner |
157 | } |
158 | } |
159 | |
160 | impl core::fmt::Display for TokenStream { |
161 | fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result { |
162 | write!(f, " {}" , self.as_str()) |
163 | } |
164 | } |
165 | |