1 use crate::ascii::dec_uint;
2 use crate::combinator::dispatch;
3 use crate::combinator::empty;
4 use crate::combinator::fail;
5 use crate::combinator::seq;
6 use crate::error::ErrMode;
7 use crate::error::ErrorKind;
8 use crate::error::ParserError;
9 use crate::prelude::*;
10 use crate::token::any;
11
12 #[test]
dispatch_basics()13 fn dispatch_basics() {
14 fn escape_seq_char(input: &mut &str) -> PResult<char> {
15 dispatch! {any;
16 'b' => empty.value('\u{8}'),
17 'f' => empty.value('\u{c}'),
18 'n' => empty.value('\n'),
19 'r' => empty.value('\r'),
20 't' => empty.value('\t'),
21 '\\' => empty.value('\\'),
22 '"' => empty.value('"'),
23 _ => fail::<_, char, _>,
24 }
25 .parse_next(input)
26 }
27 assert_eq!(escape_seq_char.parse_peek("b123"), Ok(("123", '\u{8}')));
28 assert_eq!(
29 escape_seq_char.parse_peek("error"),
30 Err(ErrMode::Backtrack(ParserError::from_error_kind(
31 &"rror",
32 ErrorKind::Fail
33 )))
34 );
35 assert_eq!(
36 escape_seq_char.parse_peek(""),
37 Err(ErrMode::Backtrack(ParserError::from_error_kind(
38 &"",
39 ErrorKind::Fail
40 )))
41 );
42 }
43
44 #[test]
seq_struct_basics()45 fn seq_struct_basics() {
46 #[derive(Debug, PartialEq)]
47 struct Point {
48 x: u32,
49 y: u32,
50 }
51
52 fn parser(input: &mut &str) -> PResult<Point> {
53 seq! {
54 Point {
55 x: dec_uint,
56 _: ',',
57 y: dec_uint,
58 }
59 }
60 .parse_next(input)
61 }
62 assert_eq!(
63 parser.parse_peek("123,4 remaining"),
64 Ok((" remaining", Point { x: 123, y: 4 },)),
65 );
66 assert_eq!(
67 parser.parse_peek("123, remaining"),
68 Err(ErrMode::Backtrack(ParserError::from_error_kind(
69 &" remaining",
70 ErrorKind::Fail
71 )))
72 );
73 assert_eq!(
74 parser.parse_peek(""),
75 Err(ErrMode::Backtrack(ParserError::from_error_kind(
76 &"",
77 ErrorKind::Fail
78 )))
79 );
80 }
81
82 #[test]
seq_struct_default_init()83 fn seq_struct_default_init() {
84 #[derive(Debug, PartialEq, Default)]
85 struct Point {
86 x: u32,
87 y: u32,
88 z: u32,
89 }
90
91 fn parser(input: &mut &str) -> PResult<Point> {
92 seq! {
93 Point {
94 x: dec_uint,
95 _: ',',
96 y: dec_uint,
97 ..Default::default()
98 }
99 }
100 .parse_next(input)
101 }
102 assert_eq!(
103 parser.parse_peek("123,4 remaining"),
104 Ok((" remaining", Point { x: 123, y: 4, z: 0 },)),
105 );
106 assert_eq!(
107 parser.parse_peek("123, remaining"),
108 Err(ErrMode::Backtrack(ParserError::from_error_kind(
109 &" remaining",
110 ErrorKind::Fail
111 )))
112 );
113 assert_eq!(
114 parser.parse_peek(""),
115 Err(ErrMode::Backtrack(ParserError::from_error_kind(
116 &"",
117 ErrorKind::Fail
118 )))
119 );
120 }
121
122 #[test]
seq_struct_trailing_comma_elided()123 fn seq_struct_trailing_comma_elided() {
124 #![allow(dead_code)]
125
126 #[derive(Debug, PartialEq)]
127 struct Point {
128 x: u32,
129 y: u32,
130 }
131
132 fn parser(input: &mut &str) -> PResult<Point> {
133 seq! {
134 Point {
135 x: dec_uint,
136 _: ',',
137 y: dec_uint,
138 _: empty,
139 }
140 }
141 .parse_next(input)
142 }
143 }
144
145 #[test]
seq_struct_no_trailing_comma()146 fn seq_struct_no_trailing_comma() {
147 #![allow(dead_code)]
148
149 #[derive(Debug, PartialEq)]
150 struct Point {
151 x: u32,
152 y: u32,
153 }
154
155 fn parser(input: &mut &str) -> PResult<Point> {
156 seq! {
157 Point {
158 x: dec_uint,
159 _: ',',
160 y: dec_uint
161 }
162 }
163 .parse_next(input)
164 }
165 }
166
167 #[test]
seq_struct_no_trailing_comma_elided()168 fn seq_struct_no_trailing_comma_elided() {
169 #![allow(dead_code)]
170
171 #[derive(Debug, PartialEq)]
172 struct Point {
173 x: u32,
174 y: u32,
175 }
176
177 fn parser(input: &mut &str) -> PResult<Point> {
178 seq! {
179 Point {
180 x: dec_uint,
181 _: ',',
182 y: dec_uint,
183 _: empty
184 }
185 }
186 .parse_next(input)
187 }
188 }
189
190 #[test]
seq_enum_struct_variant()191 fn seq_enum_struct_variant() {
192 #[derive(Debug, PartialEq, Eq)]
193 enum Expr {
194 Add { lhs: u32, rhs: u32 },
195 Mul(u32, u32),
196 }
197
198 fn add(input: &mut &[u8]) -> PResult<Expr> {
199 seq! {Expr::Add {
200 lhs: dec_uint::<_, u32, _>,
201 _: b" + ",
202 rhs: dec_uint::<_, u32, _>,
203 }}
204 .parse_next(input)
205 }
206
207 fn mul(input: &mut &[u8]) -> PResult<Expr> {
208 seq!(Expr::Mul(
209 dec_uint::<_, u32, _>,
210 _: b" * ",
211 dec_uint::<_, u32, _>,
212 ))
213 .parse_next(input)
214 }
215
216 assert_eq!(
217 add.parse_peek(&b"1 + 2"[..]),
218 Ok((&b""[..], Expr::Add { lhs: 1, rhs: 2 })),
219 );
220
221 assert_eq!(
222 mul.parse_peek(&b"3 * 4"[..]),
223 Ok((&b""[..], Expr::Mul(3, 4))),
224 );
225 }
226
227 #[test]
seq_tuple_struct_basics()228 fn seq_tuple_struct_basics() {
229 #[derive(Debug, PartialEq)]
230 struct Point(u32, u32);
231
232 fn parser(input: &mut &str) -> PResult<Point> {
233 seq! {
234 Point(
235 dec_uint,
236 _: ',',
237 dec_uint,
238 )
239 }
240 .parse_next(input)
241 }
242 assert_eq!(
243 parser.parse_peek("123,4 remaining"),
244 Ok((" remaining", Point(123, 4),)),
245 );
246 assert_eq!(
247 parser.parse_peek("123, remaining"),
248 Err(ErrMode::Backtrack(ParserError::from_error_kind(
249 &" remaining",
250 ErrorKind::Fail
251 )))
252 );
253 assert_eq!(
254 parser.parse_peek(""),
255 Err(ErrMode::Backtrack(ParserError::from_error_kind(
256 &"",
257 ErrorKind::Fail
258 )))
259 );
260 }
261
262 #[test]
seq_tuple_struct_trailing_comma_elided()263 fn seq_tuple_struct_trailing_comma_elided() {
264 #![allow(dead_code)]
265
266 #[derive(Debug, PartialEq)]
267 struct Point(u32, u32);
268
269 fn parser(input: &mut &str) -> PResult<Point> {
270 seq! {
271 Point(
272 dec_uint,
273 _: ',',
274 dec_uint,
275 _: empty,
276 )
277 }
278 .parse_next(input)
279 }
280 }
281
282 #[test]
seq_tuple_struct_no_trailing_comma()283 fn seq_tuple_struct_no_trailing_comma() {
284 #![allow(dead_code)]
285
286 #[derive(Debug, PartialEq)]
287 struct Point(u32, u32);
288
289 fn parser(input: &mut &str) -> PResult<Point> {
290 seq! {
291 Point(
292 dec_uint,
293 _: ',',
294 dec_uint
295 )
296 }
297 .parse_next(input)
298 }
299 }
300
301 #[test]
seq_tuple_struct_no_trailing_comma_elided()302 fn seq_tuple_struct_no_trailing_comma_elided() {
303 #![allow(dead_code)]
304
305 #[derive(Debug, PartialEq)]
306 struct Point(u32, u32);
307
308 fn parser(input: &mut &str) -> PResult<Point> {
309 seq! {
310 Point(
311 dec_uint,
312 _: ',',
313 dec_uint,
314 _: empty
315 )
316 }
317 .parse_next(input)
318 }
319 }
320
321 #[test]
seq_tuple_basics()322 fn seq_tuple_basics() {
323 fn parser(input: &mut &str) -> PResult<(u32, u32)> {
324 seq! {
325 (
326 dec_uint,
327 _: ',',
328 dec_uint,
329 )
330 }
331 .parse_next(input)
332 }
333 assert_eq!(
334 parser.parse_peek("123,4 remaining"),
335 Ok((" remaining", (123, 4),)),
336 );
337 assert_eq!(
338 parser.parse_peek("123, remaining"),
339 Err(ErrMode::Backtrack(ParserError::from_error_kind(
340 &" remaining",
341 ErrorKind::Fail
342 )))
343 );
344 assert_eq!(
345 parser.parse_peek(""),
346 Err(ErrMode::Backtrack(ParserError::from_error_kind(
347 &"",
348 ErrorKind::Fail
349 )))
350 );
351 }
352
353 #[test]
seq_tuple_trailing_comma_elided()354 fn seq_tuple_trailing_comma_elided() {
355 #![allow(dead_code)]
356
357 fn parser(input: &mut &str) -> PResult<(u32, u32)> {
358 seq! {
359 (
360 dec_uint,
361 _: ',',
362 dec_uint,
363 _: empty,
364 )
365 }
366 .parse_next(input)
367 }
368 }
369
370 #[test]
seq_tuple_no_trailing_comma()371 fn seq_tuple_no_trailing_comma() {
372 #![allow(dead_code)]
373
374 fn parser(input: &mut &str) -> PResult<(u32, u32)> {
375 seq! {
376 (
377 dec_uint,
378 _: ',',
379 dec_uint
380 )
381 }
382 .parse_next(input)
383 }
384 }
385
386 #[test]
seq_tuple_no_trailing_comma_elided()387 fn seq_tuple_no_trailing_comma_elided() {
388 #![allow(dead_code)]
389
390 fn parser(input: &mut &str) -> PResult<(u32, u32)> {
391 seq! {
392 (
393 dec_uint,
394 _: ',',
395 dec_uint,
396 _: empty
397 )
398 }
399 .parse_next(input)
400 }
401 }
402
403 #[test]
seq_tuple_no_parens()404 fn seq_tuple_no_parens() {
405 #![allow(dead_code)]
406
407 fn parser(input: &mut &str) -> PResult<(u32, u32)> {
408 seq! (
409 dec_uint,
410 _: ',',
411 dec_uint,
412 )
413 .parse_next(input)
414 }
415 }
416