1use crate::{
2 Context, FlagValue,
3 vector::flag::{FlagSearch, LongFound},
4};
5use std::collections::VecDeque;
6
7pub struct Parser {
9 pub flag_pattern: char,
11 pub long_flag_prefix: String,
13 pub eq: char,
15}
16
17impl Default for Parser {
18 fn default() -> Self {
19 Parser {
20 flag_pattern: '-',
21 long_flag_prefix: String::from("--"),
22 eq: '=',
23 }
24 }
25}
26
27impl From<char> for Parser {
28 fn from(flag_pattern: char) -> Self {
29 Parser {
30 flag_pattern,
31 long_flag_prefix: flag_pattern.to_string().repeat(2),
32 eq: '=',
33 }
34 }
35}
36
37impl From<(char, char)> for Parser {
38 fn from((flag_pattern, eq): (char, char)) -> Self {
39 Parser {
40 flag_pattern,
41 long_flag_prefix: flag_pattern.to_string().repeat(2),
42 eq,
43 }
44 }
45}
46
47macro_rules! str_char {
49 ($str:expr, $char:expr) => {{
50 let mut s: String = $str.clone();
51 s.push($char);
52 s
53 }};
54}
55
56macro_rules! arg_match {
58 ($self:ident, $arg:expr,long_flag=>$long_flag:ident{$($lp:tt)*}$(,)?short_flag=>$short_flag:ident{$($sp:tt)*}$(,)?non_flag=>$non_flag:ident{$($nfp:tt)*}$(,)?rest_opt=>$rest_opt:ident{$($ot:tt)*}) =>{
59 match $arg {
60 Some(arg) if $self.long_flag(&arg)=>{
61 match arg {
62 $non_flag if $non_flag.len() < 2 => {
63 $($nfp)*
64 }
65 $long_flag=>{
66 $($lp)*
67 }
68 }
69 }
70 Some(arg) if $self.flag(&arg)=>{
71 match arg {
72 $non_flag if $non_flag.len() < 1 =>{
73 $($nfp)*
74 }
75 $short_flag=>{
76 $($sp)*
77 }
78 }
79 }
80 $rest_opt =>{
81 $($ot)*
82 }
83 }
84 };
85 ($self:ident, $arg:expr,long_flag=>$long_flag:ident{$($lp:tt)*}$(,)?short_flag=>$short_flag:ident{$($sp:tt)*}$(,)?normal_arg=>$normal_arg:ident{$($ap:tt)*}$(,)?none=>{$($np:tt)*}) => {
86 match $arg {
87 None=>{
88 $($np)*
89 }
90 Some(arg) if $self.long_flag(&arg)=>{
91 match arg {
92 $normal_arg if $normal_arg.len() < 2 => {
93 $($ap)*
94 }
95 $long_flag=>{
96 $($lp)*
97 }
98 }
99 }
100 Some(arg) if $self.flag(&arg)=>{
101 match arg {
102 $normal_arg if $normal_arg.len() < 1 =>{
103 $($ap)*
104 }
105 $short_flag=>{
106 $($sp)*
107 }
108 }
109 }
110 Some($normal_arg)=>{
111 $($ap)*
112 }
113 }
114 };
115 ($self:ident, $arg:expr,long_flag=>$long_flag:ident{$($lp:tt)*}$(,)?short_flag=>$short_flag:ident{$($sp:tt)*}$(,)?normal_arg=>$normal_arg:ident{$($ap:tt)*}$(,)?none=>$none:ident{$($np:tt)*}) => {
116 match $arg {
117 Some(arg) if $self.long_flag(&arg)=>{
118 match arg {
119 $normal_arg if $normal_arg.len() < 2 => {
120 $($ap)*
121 }
122 $long_flag=>{
123 $($lp)*
124 }
125 }
126 }
127 Some(arg) if $self.flag(&arg)=>{
128 match arg {
129 $normal_arg if $normal_arg.len() < 1 =>{
130 $($ap)*
131 }
132 $short_flag=>{
133 $($sp)*
134 }
135 }
136 }
137 Some($normal_arg)=>{
138 $($ap)*
139 }
140 $none=>{
141 $($np)*
142 }
143 }
144 };
145}
146
147type ParseMiddleFlagResult = (
149 VecDeque<(String, FlagValue)>,
150 VecDeque<(String, FlagValue)>,
151 VecDeque<ErrorInfo>,
152);
153
154type ParseMiddleArgResult = (
156 Context,
157 VecDeque<MiddleArg>,
158 VecDeque<String>,
159 VecDeque<(String, FlagValue)>,
160 VecDeque<(String, FlagValue)>,
161 VecDeque<ErrorInfo>,
162);
163
164impl Parser {
165 pub fn new(flag_pattern: char, long_flag_prefix: &str) -> Parser {
167 Parser {
168 flag_pattern,
169 long_flag_prefix: String::from(long_flag_prefix),
170 eq: '=',
171 }
172 }
173
174 pub fn long_flag(&self, str: &str) -> bool {
177 str.starts_with(&self.long_flag_prefix)
178 }
179
180 pub fn flag(&self, str: &str) -> bool {
183 str.starts_with(self.flag_pattern)
184 }
185
186 pub fn with_all_field(flag_pattern: char, long_flag_prefix: String, eq: char) -> Parser {
188 Parser {
189 flag_pattern,
190 long_flag_prefix,
191 eq,
192 }
193 }
194
195 pub fn remove_long_flag_prefix(&self, mut arg: String) -> String {
197 match arg.find(|c| c != self.flag_pattern) {
198 Some(index) => arg.split_off(index),
199 None => String::default(),
200 }
201 }
202
203 pub fn get_short_flag_name(&self, mut arg: String) -> String {
205 arg.split_off(1)
206 }
207
208 pub fn middle_parse(
210 &self,
211 mut args: VecDeque<String>,
212 mut inter_mediate_args: VecDeque<MiddleArg>,
213 mut last: MiddleArg,
214 ) -> (
215 Option<String>,
216 VecDeque<String>,
217 VecDeque<MiddleArg>,
218 MiddleArg,
219 ) {
220 loop {
221 arg_match!(
222 self,
223 args.pop_front(),
224 long_flag=>long_flag{
225 inter_mediate_args.push_back(last);
226 last = self.long_middle(long_flag);
227 },
228 short_flag=>short_flag{
229 inter_mediate_args.push_back(last);
230 last = self.short_middle(short_flag);
231 },
232 non_flag=>arg{
233 break (Some(arg), args, inter_mediate_args, last);
234 },
235 rest_opt=>next{
236 break (next, args, inter_mediate_args, last);
237 })
238 }
239 }
240
241 pub fn long_middle(&self, mut long_flag: String) -> MiddleArg {
243 match &long_flag.find(self.eq) {
244 Some(index) => {
245 let after_eq = long_flag.split_off(index + 1);
246 long_flag.pop();
247 MiddleArg::LongFlag(
248 self.remove_long_flag_prefix(long_flag),
249 FlagValue::String(after_eq),
250 )
251 }
252 None => MiddleArg::LongFlag(self.remove_long_flag_prefix(long_flag), FlagValue::None),
253 }
254 }
255
256 pub fn short_middle(&self, mut short_flag: String) -> MiddleArg {
258 match &short_flag.find(self.eq) {
259 Some(index) => {
260 let after_eq = short_flag.split_off(index + 1);
261 short_flag.pop();
262 MiddleArg::ShortFlag(
263 self.get_short_flag_name(short_flag),
264 FlagValue::String(after_eq),
265 )
266 }
267 None => MiddleArg::ShortFlag(self.remove_long_flag_prefix(short_flag), FlagValue::None),
268 }
269 }
270
271 pub fn parse_inter_mediate_args<T: FlagSearch, S: FlagSearch>(
273 &self,
274 local_flags: &T,
275 current_common_flags: &S,
276 mut c: Context,
277 flag_only: bool,
278 ) -> (Context, Option<VecDeque<String>>) {
279 match c.parsing_args {
280 None => (c, None),
281 Some(inter_middle_args) => {
282 let non_flag_args = VecDeque::<String>::new();
283 c.parsing_args = None;
284 let l_flags = VecDeque::new();
285 let c_flags = VecDeque::new();
286 let e_list = VecDeque::new();
287 let (_c, _, non_flag_args, l_flags, c_flags, e_list) = self.parse_next_if_middle_arg(
288 inter_middle_args,
289 non_flag_args,
290 local_flags,
291 current_common_flags,
292 c,
293 l_flags,
294 c_flags,
295 e_list,
296 flag_only,
297 );
298 c = _c;
299 c.local_flags_values.prepend_vec(l_flags.into());
300 c.common_flags_values.prepend_vec(c_flags.into());
301 c.error_info_list.prepend_vec(e_list.into());
302 (c, { if flag_only { None } else { Some(non_flag_args) } })
303 }
304 }
305 }
306
307 pub fn parse_middle_long_flag<T: FlagSearch, S: FlagSearch>(
309 &self,
310 name_or_alias: String,
311 val: FlagValue,
312 local_flags: &T,
313 current_common_flags: &S,
314 c: &Context,
315 mut l_flags: VecDeque<(String, FlagValue)>,
316 mut c_flags: VecDeque<(String, FlagValue)>,
317 mut e_list: VecDeque<ErrorInfo>,
318 ) -> ParseMiddleFlagResult {
319 match local_flags.find_long_flag(&name_or_alias) {
320 LongFound::Name(l_flag) => {
321 match val {
322 FlagValue::String(_) if l_flag.flag_type.is_string() => {
323 l_flags.push_front((name_or_alias, val));
324 }
325 FlagValue::String(val) => match l_flag.derive_flag_value_from_string(val) {
326 FlagValue::Invalid(val) => {
327 let flag_arg =
328 MiddleArg::LongFlag(name_or_alias.clone(), FlagValue::String(val));
329 e_list.push_front((
330 flag_arg,
331 ParseError::InvalidLong(name_or_alias),
332 ParseError::NotParsed,
333 ));
334 }
335 val => {
336 l_flags.push_front((name_or_alias, val));
337 }
338 },
339 FlagValue::None => {
340 l_flags.push_front((name_or_alias, FlagValue::None));
341 }
342 val => l_flags.push_front((name_or_alias, val)),
343 };
344 }
345 LongFound::Long(l_flag) => match val {
346 FlagValue::String(_) if l_flag.flag_type.is_string() => {
347 l_flags.push_front((l_flag.get_name_clone(), val));
348 }
349 FlagValue::String(val) => match l_flag.derive_flag_value_from_string(val) {
350 FlagValue::Invalid(val) => e_list.push_front((
351 MiddleArg::LongFlag(name_or_alias, FlagValue::String(val)),
352 ParseError::InvalidLong(l_flag.get_name_clone()),
353 ParseError::NotParsed,
354 )),
355 val => {
356 l_flags.push_front((l_flag.get_name_clone(), val));
357 }
358 },
359 FlagValue::None => {
360 l_flags.push_front((l_flag.get_name_clone(), FlagValue::None));
361 }
362 val => {
363 l_flags.push_front((l_flag.get_name_clone(), val));
364 }
365 },
366 LongFound::None => {
367 match (current_common_flags, &c.common_flags).find_long_flag(&name_or_alias) {
368 LongFound::Name(c_flag) => match val {
369 FlagValue::None => {
370 c_flags.push_front((name_or_alias, FlagValue::None));
371 }
372 FlagValue::String(_) if c_flag.flag_type.is_string() => {
373 c_flags.push_front((name_or_alias, val));
374 }
375 FlagValue::String(val) => match c_flag.derive_flag_value_from_string(val) {
376 FlagValue::Invalid(val) => {
377 e_list.push_front((
378 MiddleArg::LongFlag(name_or_alias.clone(), FlagValue::String(val)),
379 ParseError::NoExistLong,
380 ParseError::InvalidLong(name_or_alias),
381 ));
382 }
383 val => {
384 c_flags.push_front((name_or_alias, val));
385 }
386 },
387 val => c_flags.push_front((name_or_alias, val)),
388 },
389 LongFound::Long(c_flag) => match val {
390 FlagValue::None => c_flags.push_front((c_flag.get_name_clone(), FlagValue::None)),
391 FlagValue::String(_) if c_flag.flag_type.is_string() => {
392 c_flags.push_front((c_flag.get_name_clone(), val));
393 }
394 FlagValue::String(val) => match c_flag.derive_flag_value_from_string(val) {
395 FlagValue::Invalid(val) => {
396 e_list.push_front((
397 MiddleArg::LongFlag(name_or_alias, FlagValue::String(val)),
398 ParseError::NoExistLong,
399 ParseError::InvalidLong(c_flag.get_name_clone()),
400 ));
401 }
402 val => {
403 c_flags.push_front((c_flag.get_name_clone(), val));
404 }
405 },
406 val => {
407 c_flags.push_front((c_flag.get_name_clone(), val));
408 }
409 },
410 LongFound::None => {
411 e_list.push_front((
412 MiddleArg::LongFlag(name_or_alias, val),
413 ParseError::NoExistLong,
414 ParseError::NoExistLong,
415 ));
416 }
417 }
418 }
419 }
420 (l_flags, c_flags, e_list)
421 }
422
423 pub fn parse_middle_short_flag<T: FlagSearch, S: FlagSearch>(
425 &self,
426 mut short_alias: String,
427 flag_val: FlagValue,
428 local_flags: &T,
429 current_common_flags: &S,
430 c: &Context,
431 mut l_flags: VecDeque<(String, FlagValue)>,
432 mut c_flags: VecDeque<(String, FlagValue)>,
433 mut e_list: VecDeque<ErrorInfo>,
434 ) -> ParseMiddleFlagResult {
435 match short_alias.pop() {
436 Some(last) => match local_flags.find_short_flag(&last) {
437 Some(l_flag) => match flag_val {
438 FlagValue::String(_) if l_flag.flag_type.is_string() => {
439 l_flags.push_front((l_flag.get_name_clone(), flag_val));
440 }
441 FlagValue::String(val) => match l_flag.derive_flag_value_from_string(val) {
442 FlagValue::Invalid(val) => {
443 let i = short_alias.len();
444 e_list.push_front((
445 MiddleArg::ShortFlag(
446 {
447 let mut s = short_alias.clone();
448 s.push(last);
449 s
450 },
451 FlagValue::String(val),
452 ),
453 ParseError::InvalidShort(i, l_flag.get_name_clone()),
454 ParseError::NotParsed,
455 ));
456 }
457 val => {
458 l_flags.push_front((l_flag.get_name_clone(), val));
459 }
460 },
461 FlagValue::None => {
462 l_flags.push_front((l_flag.get_name_clone(), FlagValue::None));
463 }
464 val => {
465 l_flags.push_front((l_flag.get_name_clone(), val));
466 }
467 },
468 None => match (current_common_flags, &c.common_flags).find_short_flag(&last) {
469 Some(c_flag) => match flag_val {
470 FlagValue::String(_) if c_flag.flag_type.is_string() => {
471 c_flags.push_front((c_flag.get_name_clone(), flag_val));
472 }
473 FlagValue::String(val) => match c_flag.derive_flag_value_from_string(val) {
474 FlagValue::Invalid(val) => {
475 let i = short_alias.len();
476 e_list.push_front((
477 MiddleArg::ShortFlag(
478 {
479 let mut s = short_alias.clone();
480 s.push(last);
481 s
482 },
483 FlagValue::String(val),
484 ),
485 ParseError::NoExistShort(i),
486 ParseError::InvalidShort(i, c_flag.get_name_clone()),
487 ));
488 }
489 val => {
490 c_flags.push_front((c_flag.get_name_clone(), val));
491 }
492 },
493 FlagValue::None => {
494 c_flags.push_front((c_flag.get_name_clone(), FlagValue::None));
495 }
496 val => {
497 c_flags.push_front((c_flag.get_name_clone(), val));
498 }
499 },
500 None => e_list.push_front((
501 MiddleArg::ShortFlag(str_char!(short_alias, last), flag_val),
502 ParseError::NoExistShort(short_alias.len()),
503 ParseError::NoExistShort(short_alias.len()),
504 )),
505 },
506 },
507 None => {
508 panic!("invalid short flag");
509 }
510 }
511
512 (l_flags, c_flags, e_list)
513 }
514
515 #[allow(clippy::too_many_arguments)]
517 pub fn parse_middle_normal_arg<T: FlagSearch, S: FlagSearch>(
518 &self,
519 mut inter_mediate_args: VecDeque<MiddleArg>,
520 normal_arg: String,
521 local_flags: &T,
522 current_common_flags: &S,
523 mut c: Context,
524 mut non_flag_args: VecDeque<String>,
525 mut l_flags: VecDeque<(String, FlagValue)>,
526 mut c_flags: VecDeque<(String, FlagValue)>,
527 mut e_list: VecDeque<ErrorInfo>,
528 flag_only: bool,
529 ) -> ParseMiddleArgResult {
530 match inter_mediate_args.pop_back() {
531 Some(MiddleArg::LongFlag(long_flag_name, FlagValue::None)) => {
533 match local_flags.find_long_flag(&long_flag_name) {
534 LongFound::Name(l_flag) => match l_flag.derive_flag_value_from_string(normal_arg) {
535 FlagValue::Invalid(normal_arg) => {
536 if flag_only {
537 c = self.push_normal_arg_in_flag_only_error(c, normal_arg);
538 } else {
539 non_flag_args.push_front(normal_arg);
540 }
541 l_flags.push_front((long_flag_name, FlagValue::None));
542 self.parse_next_if_middle_arg(
543 inter_mediate_args,
544 non_flag_args,
545 local_flags,
546 current_common_flags,
547 c,
548 l_flags,
549 c_flags,
550 e_list,
551 flag_only,
552 )
553 }
554 val => {
555 l_flags.push_front((long_flag_name, val));
556 self.parse_next_if_middle_arg(
557 inter_mediate_args,
558 non_flag_args,
559 local_flags,
560 current_common_flags,
561 c,
562 l_flags,
563 c_flags,
564 e_list,
565 flag_only,
566 )
567 }
568 },
569 LongFound::Long(l_flag) => match l_flag.derive_flag_value_from_string(normal_arg) {
570 FlagValue::Invalid(normal_arg) => {
571 l_flags.push_front((l_flag.get_name_clone(), FlagValue::None));
572 if flag_only {
573 c = self.push_normal_arg_in_flag_only_error(c, normal_arg);
574 } else {
575 non_flag_args.push_front(normal_arg);
576 }
577 self.parse_next_if_middle_arg(
578 inter_mediate_args,
579 non_flag_args,
580 local_flags,
581 current_common_flags,
582 c,
583 l_flags,
584 c_flags,
585 e_list,
586 flag_only,
587 )
588 }
589 val => {
590 l_flags.push_front((l_flag.get_name_clone(), val));
591 self.parse_next_if_middle_arg(
592 inter_mediate_args,
593 non_flag_args,
594 local_flags,
595 current_common_flags,
596 c,
597 l_flags,
598 c_flags,
599 e_list,
600 flag_only,
601 )
602 }
603 },
604 LongFound::None => {
605 match (current_common_flags, &c.common_flags).find_long_flag(&long_flag_name) {
606 LongFound::Name(c_flag) => {
607 match c_flag.derive_flag_value_from_string(normal_arg) {
608 FlagValue::Invalid(normal_arg) => {
609 if flag_only {
610 c = self.push_normal_arg_in_flag_only_error(c, normal_arg);
611 } else {
612 non_flag_args.push_front(normal_arg);
613 }
614 c_flags.push_front((long_flag_name, FlagValue::None));
615 self.parse_next_if_middle_arg(
616 inter_mediate_args,
617 non_flag_args,
618 local_flags,
619 current_common_flags,
620 c,
621 l_flags,
622 c_flags,
623 e_list,
624 flag_only,
625 )
626 }
627 val => {
628 c_flags.push_front((long_flag_name, val));
629 self.parse_next_if_middle_arg(
630 inter_mediate_args,
631 non_flag_args,
632 local_flags,
633 current_common_flags,
634 c,
635 l_flags,
636 c_flags,
637 e_list,
638 flag_only,
639 )
640 }
641 }
642 }
643 LongFound::Long(c_flag) => {
644 match c_flag.derive_flag_value_from_string(normal_arg) {
645 FlagValue::Invalid(normal_arg) => {
646 if flag_only {
647 non_flag_args.push_front(normal_arg);
648 } else {
649 c_flags.push_front((c_flag.get_name_clone(), FlagValue::None));
650 }
651 self.parse_next_if_middle_arg(
652 inter_mediate_args,
653 non_flag_args,
654 local_flags,
655 current_common_flags,
656 c,
657 l_flags,
658 c_flags,
659 e_list,
660 flag_only,
661 )
662 }
663 val => {
664 c_flags.push_front((c_flag.get_name_clone(), val));
665 self.parse_next_if_middle_arg(
666 inter_mediate_args,
667 non_flag_args,
668 local_flags,
669 current_common_flags,
670 c,
671 l_flags,
672 c_flags,
673 e_list,
674 flag_only,
675 )
676 }
677 }
678 }
679 LongFound::None => {
680 non_flag_args.push_front(normal_arg);
681 e_list.push_front((
682 MiddleArg::LongFlag(long_flag_name, FlagValue::None),
683 ParseError::NoExistLong,
684 ParseError::NoExistLong,
685 ));
686 self.parse_next_if_middle_arg(
687 inter_mediate_args,
688 non_flag_args,
689 local_flags,
690 current_common_flags,
691 c,
692 l_flags,
693 c_flags,
694 e_list,
695 flag_only,
696 )
697 }
698 }
699 }
700 }
701 }
702 Some(MiddleArg::LongFlag(name_or_alias, val)) => {
704 if flag_only {
705 c = self.push_normal_arg_in_flag_only_error(c, normal_arg);
706 } else {
707 non_flag_args.push_front(normal_arg);
708 }
709 let (l_flags, c_flags, e_list) = self.parse_middle_long_flag(
710 name_or_alias,
711 val,
712 local_flags,
713 current_common_flags,
714 &c,
715 l_flags,
716 c_flags,
717 e_list,
718 );
719 self.parse_next_if_middle_arg(
720 inter_mediate_args,
721 non_flag_args,
722 local_flags,
723 current_common_flags,
724 c,
725 l_flags,
726 c_flags,
727 e_list,
728 flag_only,
729 )
730 }
731 Some(MiddleArg::ShortFlag(mut short_str, FlagValue::None)) => {
733 let short_alias = short_str.pop();
734 if let Some(short_alias) = short_alias {
735 match local_flags.find_short_flag(&short_alias) {
736 Some(l_flag) => match l_flag.derive_flag_value_from_string(normal_arg) {
737 FlagValue::Invalid(normal_arg) => {
738 non_flag_args.push_front(normal_arg);
739 l_flags.push_front((l_flag.get_name_clone(), FlagValue::None));
740 }
741 val => {
742 l_flags.push_front((l_flag.get_name_clone(), val));
743 }
744 },
745 None => {
746 match (current_common_flags, &c.common_flags).find_short_flag(&short_alias) {
747 Some(c_flag) => match c_flag.derive_flag_value_from_string(normal_arg) {
748 FlagValue::Invalid(normal_arg) => {
749 non_flag_args.push_front(normal_arg);
750 c_flags.push_front((c_flag.get_name_clone(), FlagValue::None));
751 }
752 val => {
753 c_flags.push_front((c_flag.get_name_clone(), val));
754 }
755 },
756 None => {
757 non_flag_args.push_front(normal_arg);
758 let i = short_str.len() - 1;
759 e_list.push_back((
760 MiddleArg::ShortFlag(short_str, FlagValue::None),
761 ParseError::NoExistShort(i),
762 ParseError::NoExistShort(i),
763 ));
764 }
765 }
766 }
767 };
768
769 self.parse_next_if_middle_arg(
770 inter_mediate_args,
771 non_flag_args,
772 local_flags,
773 current_common_flags,
774 c,
775 l_flags,
776 c_flags,
777 e_list,
778 flag_only,
779 )
780 } else {
781 panic!("short alias is not existed")
782 }
783 }
784 Some(MiddleArg::ShortFlag(short_str, val)) => {
785 let (l_flags, c_flags, e_list) = self.parse_middle_short_flag(
786 short_str,
787 val,
788 local_flags,
789 current_common_flags,
790 &c,
791 l_flags,
792 c_flags,
793 e_list,
794 );
795 self.parse_next_if_middle_arg(
796 inter_mediate_args,
797 non_flag_args,
798 local_flags,
799 current_common_flags,
800 c,
801 l_flags,
802 c_flags,
803 e_list,
804 flag_only,
805 )
806 }
807 Some(MiddleArg::Normal(prev_arg)) => {
808 if flag_only {
809 c = self.push_normal_arg_in_flag_only_error(c, normal_arg);
810 } else {
811 non_flag_args.push_front(normal_arg);
812 }
813
814 self.parse_middle_normal_arg(
815 inter_mediate_args,
816 prev_arg,
817 local_flags,
818 current_common_flags,
819 c,
820 non_flag_args,
821 l_flags,
822 c_flags,
823 e_list,
824 flag_only,
825 )
826 }
827 None => {
828 non_flag_args.push_front(normal_arg);
829 (
830 c,
831 inter_mediate_args,
832 non_flag_args,
833 l_flags,
834 c_flags,
835 e_list,
836 )
837 }
838 }
839 }
840
841 fn push_normal_arg_in_flag_only_error(&self, mut c: Context, normal_arg: String) -> Context {
843 let val = MiddleArg::Normal(normal_arg);
844 c.error_info_list
845 .push((val.clone(), ParseError::NotExist, ParseError::NotExist));
846 c.push_front_to_parsing_args(val);
847 c
848 }
849
850 pub fn parse_next_if_middle_arg<T: FlagSearch, S: FlagSearch>(
852 &self,
853 mut inter_mediate_args: VecDeque<MiddleArg>,
854 non_flag_args: VecDeque<String>,
855 local_flags: &T,
856 current_common_flags: &S,
857 c: Context,
858 l_flags: VecDeque<(String, FlagValue)>,
859 c_flags: VecDeque<(String, FlagValue)>,
860 e_list: VecDeque<ErrorInfo>,
861 flag_only: bool,
862 ) -> ParseMiddleArgResult {
863 match inter_mediate_args.pop_back() {
864 Some(MiddleArg::LongFlag(long_flag, flag_val)) => {
865 let (l_flags, c_flags, e_list) = self.parse_middle_long_flag(
866 long_flag,
867 flag_val,
868 local_flags,
869 current_common_flags,
870 &c,
871 l_flags,
872 c_flags,
873 e_list,
874 );
875 self.parse_next_if_middle_arg(
876 inter_mediate_args,
877 non_flag_args,
878 local_flags,
879 current_common_flags,
880 c,
881 l_flags,
882 c_flags,
883 e_list,
884 flag_only,
885 )
886 }
887 Some(MiddleArg::ShortFlag(short_flag, flag_val)) => {
888 let (l_flags, c_flags, e_list) = self.parse_middle_short_flag(
889 short_flag,
890 flag_val,
891 local_flags,
892 current_common_flags,
893 &c,
894 l_flags,
895 c_flags,
896 e_list,
897 );
898 self.parse_next_if_middle_arg(
899 inter_mediate_args,
900 non_flag_args,
901 local_flags,
902 current_common_flags,
903 c,
904 l_flags,
905 c_flags,
906 e_list,
907 flag_only,
908 )
909 }
910 Some(MiddleArg::Normal(arg)) => self.parse_middle_normal_arg(
911 inter_mediate_args,
912 arg,
913 local_flags,
914 current_common_flags,
915 c,
916 non_flag_args,
917 l_flags,
918 c_flags,
919 e_list,
920 flag_only,
921 ),
922 None => (
923 c,
924 inter_mediate_args,
925 non_flag_args,
926 l_flags,
927 c_flags,
928 e_list,
929 ),
930 }
931 }
932
933 pub fn parse_args_until_end<T: FlagSearch, S: FlagSearch>(
935 self,
936 local_flags: &T,
937 current_common_flags: &S,
938 mut c: Context,
939 ) -> Context {
940 let mut non_flag_args = VecDeque::<String>::new();
941 loop {
942 arg_match!(self, c.args.pop_front(),
943 long_flag=>long_flag{
944 let (next, _c) = self.parse_flags_start_with_long_flag(
945 long_flag,
946 local_flags,
947 current_common_flags,
948 c,
949 );
950 c = _c;
951 if let Some(arg) = next {
952 non_flag_args.push_back(arg);
953 } else {
954 break;
955 }
956 },
957 short_flag=>short_flag{
958 let (next, _c) = self.parse_flags_start_with_short_flag(
959 short_flag,
960 local_flags,
961 current_common_flags,
962 c,
963 );
964 c = _c;
965 if let Some(arg) = next {
966 non_flag_args.push_back(arg);
967 } else {
968 break;
969 }
970 },
971 normal_arg=>arg{
972 non_flag_args.push_back(arg);
973 },
974 none=>{
975 break;
976 }
977 )
978 }
979 c.args = non_flag_args;
980 c
981 }
982
983 pub fn parse_flags_start_with_long_flag<T: FlagSearch, S: FlagSearch>(
985 &self,
986 mut long_flag: String,
987 local_flags: &T,
988 current_common_flags: &S,
989 mut c: Context,
990 ) -> (Option<String>, Context) {
991 long_flag = self.remove_long_flag_prefix(long_flag);
992 match long_flag.find(self.eq) {
993 Some(index) => {
994 let after_eq = long_flag.split_off(index + 1);
995 long_flag.pop();
996 match local_flags.find_long_flag(&long_flag) {
997 LongFound::Name(l_flag) => match l_flag.derive_flag_value_from_string(after_eq) {
998 FlagValue::Invalid(after_eq) => {
999 let flag_arg =
1000 MiddleArg::LongFlag(long_flag.clone(), FlagValue::Invalid(after_eq));
1001 c.push_back_to_parsing_args(flag_arg.clone());
1002 c.error_info_list.push((
1003 flag_arg,
1004 ParseError::InvalidLong(long_flag),
1005 ParseError::NotParsed,
1006 ));
1007 }
1008 val => {
1009 c.local_flags_values.push((long_flag, val));
1010 }
1011 },
1012 LongFound::Long(l_flag) => match l_flag.flag_type.get_value_from_string(after_eq) {
1013 FlagValue::Invalid(after_eq) => {
1014 let flag_arg = MiddleArg::LongFlag(long_flag, FlagValue::Invalid(after_eq));
1015 let l_flag_name = l_flag.get_name_clone();
1016 c.error_info_list.push((
1017 flag_arg.clone(),
1018 ParseError::InvalidLong(l_flag_name),
1019 ParseError::NotParsed,
1020 ));
1021 c.push_back_to_parsing_args(flag_arg);
1022 }
1023 val => {
1024 let l_flag = l_flag.get_name_clone();
1025 c.local_flags_values.push((l_flag, val));
1026 }
1027 },
1028 _ => match (current_common_flags, &c.common_flags).find_long_flag(&long_flag) {
1029 LongFound::Name(c_flag) => match c_flag.flag_type.get_value_from_string(after_eq)
1030 {
1031 FlagValue::Invalid(after_eq) => {
1032 let flag_arg = MiddleArg::LongFlag(long_flag, FlagValue::String(after_eq));
1033 c.error_info_list.push((
1034 flag_arg.clone(),
1035 ParseError::NoExistLong,
1036 ParseError::InvalidLong(c_flag.get_name_clone()),
1037 ));
1038 c.push_back_to_parsing_args(flag_arg)
1039 }
1040 val => c.common_flags_values.push((long_flag, val)),
1041 },
1042 LongFound::Long(c_flag) => match c_flag.flag_type.get_value_from_string(after_eq)
1043 {
1044 FlagValue::Invalid(after_eq) => {
1045 let flag_arg = MiddleArg::LongFlag(long_flag, FlagValue::String(after_eq));
1046 c.error_info_list.push((
1047 flag_arg.clone(),
1048 ParseError::NoExistLong,
1049 ParseError::InvalidLong(c_flag.get_name_clone()),
1050 ));
1051 c.push_back_to_parsing_args(flag_arg)
1052 }
1053 val => c.common_flags_values.push((c_flag.get_name_clone(), val)),
1054 },
1055 _ => {
1056 let flag_arg = MiddleArg::LongFlag(long_flag, FlagValue::String(after_eq));
1057 c.error_info_list.push((
1058 flag_arg.clone(),
1059 ParseError::NoExistLong,
1060 ParseError::NoExistLong,
1061 ));
1062 c.push_back_to_parsing_args(flag_arg)
1063 }
1064 },
1065 }
1066 self.parse_next_if_flag(local_flags, current_common_flags, c)
1067 }
1068 None => match local_flags.find_long_flag(&long_flag) {
1069 LongFound::Name(l_flag) => {
1070 arg_match!(self, c.args.pop_front(),long_flag=>next_long_flag{
1071 c.local_flags_values.push((long_flag, FlagValue::None));
1072 self.parse_flags_start_with_long_flag(
1073 next_long_flag,
1074 local_flags,
1075 current_common_flags,
1076 c,
1077 )
1078 },
1079 short_flag=>next_short_flag{
1080 c.local_flags_values.push((long_flag, FlagValue::None));
1081 self.parse_flags_start_with_short_flag(
1082 next_short_flag,
1083 local_flags,
1084 current_common_flags,
1085 c,
1086 )
1087 },
1088 normal_arg=>next_arg{
1089 match l_flag.derive_flag_value_from_string(next_arg) {
1090 FlagValue::Invalid(next_arg) => {
1091 c.local_flags_values.push((long_flag, FlagValue::None));
1092 (Some(next_arg), c)
1093 }
1094 val => {
1095 c.local_flags_values.push((long_flag, val));
1096 self.parse_next_if_flag(local_flags, current_common_flags, c)
1097 }
1098 }
1099 },
1100 none=>{
1101 c.local_flags_values.push((long_flag, FlagValue::None));
1102 (None, c)
1103 })
1104 }
1105 LongFound::Long(l_flag) => arg_match!(
1106 self,c.args.pop_front(),
1107 long_flag=>next_long_flag{
1108 c.local_flags_values
1109 .push((l_flag.get_name_clone(), FlagValue::None));
1110 self.parse_flags_start_with_long_flag(
1111 next_long_flag,
1112 local_flags,
1113 current_common_flags,
1114 c,
1115 )
1116 }
1117 short_flag=>next_short_flag{
1118 c.local_flags_values
1119 .push((l_flag.get_name_clone(), FlagValue::None));
1120 self.parse_flags_start_with_short_flag(
1121 next_short_flag,
1122 local_flags,
1123 current_common_flags,
1124 c,
1125 )
1126 }
1127 normal_arg=>next_arg{
1128 match l_flag.derive_flag_value_from_string(next_arg) {
1129 FlagValue::Invalid(next_arg) => {
1130 c.local_flags_values
1131 .push((l_flag.get_name_clone(), FlagValue::None));
1132 (Some(next_arg), c)
1133 }
1134 val => {
1135 c.local_flags_values.push((long_flag, val));
1136 self.parse_next_if_flag(local_flags, current_common_flags, c)
1137 }
1138 }
1139 }
1140 none=>{
1141 c.local_flags_values
1142 .push((l_flag.get_name_clone(), FlagValue::None));
1143 (None, c)
1144 }
1145 ),
1146 _ => match (current_common_flags, &c.common_flags).find_long_flag(&long_flag) {
1147 LongFound::Name(c_flag) => {
1148 arg_match!(self,c.args.pop_front(), long_flag=>next_long_flag{
1149 c.common_flags_values.push((long_flag, FlagValue::None));
1150 self.parse_flags_start_with_long_flag(
1151 next_long_flag,
1152 local_flags,
1153 current_common_flags,
1154 c,
1155 )
1156 },
1157 short_flag=>next_short_flag{
1158 c.common_flags_values.push((long_flag, FlagValue::None));
1159 self.parse_flags_start_with_short_flag(
1160 next_short_flag,
1161 local_flags,
1162 current_common_flags,
1163 c,
1164 )
1165 }
1166 normal_arg=>next_arg{
1167 match c_flag.flag_type.get_value_from_string(next_arg) {
1168 FlagValue::Invalid(next_arg) => {
1169 c.common_flags_values.push((long_flag, FlagValue::None));
1170 (Some(next_arg), c)
1171 }
1172 val => {
1173 c.common_flags_values.push((long_flag, val));
1174 self.parse_next_if_flag(local_flags, current_common_flags, c)
1175 }
1176 }
1177 }
1178 none=>next_none{
1179 c.common_flags_values.push((long_flag, FlagValue::None));
1180 (next_none, c)
1181 }
1182 )
1183 }
1184 LongFound::Long(c_flag) => {
1185 arg_match!(self,c.args.pop_front(),
1186 long_flag=>next_long_flag{
1187 c.common_flags_values
1188 .push((c_flag.get_name_clone(), FlagValue::None));
1189 self.parse_flags_start_with_long_flag(
1190 next_long_flag,
1191 local_flags,
1192 current_common_flags,
1193 c,
1194 )
1195 },
1196 short_flag=>next_short_flag{
1197 c.common_flags_values
1198 .push((c_flag.get_name_clone(), FlagValue::None));
1199 self.parse_flags_start_with_short_flag(
1200 next_short_flag,
1201 local_flags,
1202 current_common_flags,
1203 c,
1204 )
1205 },
1206 normal_arg=>next_arg{
1207 match c_flag.flag_type.get_value_from_string(next_arg) {
1208 FlagValue::Invalid(next_arg) => {
1209 c.common_flags_values
1210 .push((c_flag.get_name_clone(), FlagValue::None));
1211 (Some(next_arg), c)
1212 }
1213 val => {
1214 c.common_flags_values.push((c_flag.get_name_clone(), val));
1215 self.parse_next_if_flag(local_flags, current_common_flags, c)
1216 }
1217 }
1218 },
1219 none=>next_none{
1220 c.common_flags_values
1221 .push((c_flag.get_name_clone(), FlagValue::None));
1222 (next_none, c)
1223 })
1224 }
1225 _ => {
1226 let flag_arg = MiddleArg::LongFlag(long_flag, FlagValue::None);
1227 c.error_info_list.push((
1228 flag_arg.clone(),
1229 ParseError::NoExistLong,
1230 ParseError::NoExistLong,
1231 ));
1232 c.push_back_to_parsing_args(flag_arg);
1233 self.parse_next_if_flag(local_flags, current_common_flags, c)
1234 }
1235 },
1236 },
1237 }
1238 }
1239
1240 pub fn parse_flags_start_with_short_flag<T: FlagSearch, S: FlagSearch>(
1242 &self,
1243 mut short_flag: String,
1244 local_flags: &T,
1245 current_common_flags: &S,
1246 mut c: Context,
1247 ) -> (Option<String>, Context) {
1248 match short_flag.find(self.eq) {
1249 Some(index) => {
1250 let after_eq = short_flag.split_off(index + 1);
1251 short_flag.pop();
1252 short_flag = self.get_short_flag_name(short_flag);
1253 match short_flag.pop() {
1254 None => {
1255 let record = MiddleArg::ShortFlag(short_flag, FlagValue::String(after_eq));
1256 c.error_info_list
1257 .push((record.clone(), ParseError::Empty, ParseError::Empty));
1258 c.push_back_to_parsing_args(record);
1259 self.parse_next_if_flag(local_flags, current_common_flags, c)
1260 }
1261 Some(before_eq) => {
1262 let mut i = 0;
1263 for s in short_flag.chars() {
1264 match local_flags.find_short_flag(&s) {
1265 Some(l_flag) => {
1266 let record = (l_flag.get_name_clone(), FlagValue::None);
1267 c.local_flags_values.push(record);
1268 }
1269 _ => match (current_common_flags, &c.common_flags).find_short_flag(&s) {
1270 Some(c_flag) => {
1271 let record = (c_flag.get_name_clone(), FlagValue::None);
1272 c.common_flags_values.push(record);
1273 }
1274 _ => {
1275 c.push_back_to_parsing_args(MiddleArg::ShortFlag(
1276 s.to_string(),
1277 FlagValue::None,
1278 ));
1279 let mut short_flag = short_flag.clone();
1280 short_flag.push(before_eq);
1281
1282 c.error_info_list.push((
1283 MiddleArg::ShortFlag(short_flag, FlagValue::None),
1284 ParseError::NoExistShort(i),
1285 ParseError::NoExistShort(i),
1286 ));
1287 }
1288 },
1289 }
1290 i += 1;
1291 }
1292 match local_flags.find_short_flag(&before_eq) {
1294 Some(l_flag) => {
1295 match l_flag.derive_flag_value_from_string(after_eq) {
1296 FlagValue::Invalid(after_eq) => {
1297 let l_flag = l_flag.get_name_clone();
1298 c.error_info_list.push((
1299 MiddleArg::ShortFlag(
1300 {
1301 short_flag.push(before_eq);
1302 short_flag
1303 },
1304 FlagValue::String(after_eq.clone()),
1305 ),
1306 ParseError::InvalidShort(i, l_flag),
1307 ParseError::None,
1308 ));
1309 c.push_back_to_parsing_args(MiddleArg::ShortFlag(
1310 before_eq.to_string(),
1311 FlagValue::String(after_eq),
1312 ));
1313 }
1314 val => {
1315 let l_flag = l_flag.get_name_clone();
1316 c.local_flags_values.push((l_flag, val));
1317 }
1318 };
1319 }
1320 _ => {
1321 match c.common_flags.find_short_flag(&before_eq) {
1323 Some(c_flag) => match c_flag.derive_flag_value_from_string(after_eq) {
1324 FlagValue::Invalid(after_eq) => {
1325 c.error_info_list.push((
1326 MiddleArg::ShortFlag(
1327 {
1328 short_flag.push(before_eq);
1329 short_flag
1330 },
1331 FlagValue::String(after_eq.clone()),
1332 ),
1333 ParseError::NoExistShort(i),
1334 ParseError::InvalidShort(i, c_flag.get_name_clone()),
1335 ));
1336 c.push_back_to_parsing_args(MiddleArg::ShortFlag(
1337 before_eq.to_string(),
1338 FlagValue::String(after_eq),
1339 ));
1340 }
1341 val => {
1342 c.local_flags_values.push((c_flag.get_name_clone(), val));
1343 }
1344 },
1345 _ => {
1346 let f_val = FlagValue::String(after_eq);
1347 c.error_info_list.push((
1348 MiddleArg::ShortFlag(
1349 {
1350 short_flag.push(before_eq);
1351 short_flag
1352 },
1353 f_val.clone(),
1354 ),
1355 ParseError::NoExistShort(i),
1356 ParseError::NoExistShort(i),
1357 ));
1358 c.push_back_to_parsing_args(MiddleArg::ShortFlag(
1359 before_eq.to_string(),
1360 f_val,
1361 ))
1362 }
1363 }
1364 }
1365 }
1366 self.parse_next_if_flag(local_flags, current_common_flags, c)
1367 }
1368 }
1369 }
1370 None => {
1371 short_flag = self.get_short_flag_name(short_flag);
1372 let mut i: Index = 0;
1373 let last = short_flag.pop();
1374 match last {
1375 Some(last) => {
1376 for s in short_flag.chars() {
1377 match local_flags.find_short_flag(&s) {
1378 Some(l_flag) => {
1379 let record = (l_flag.get_name_clone(), FlagValue::None);
1380 c.local_flags_values.push(record);
1381 }
1382 _ => match (current_common_flags, &c.common_flags).find_short_flag(&s) {
1383 Some(c_flag) => {
1384 let record = (c_flag.get_name_clone(), FlagValue::None);
1385 c.common_flags_values.push(record);
1386 }
1387 _ => {
1388 c.push_back_to_parsing_args(MiddleArg::ShortFlag(
1389 s.to_string(),
1390 FlagValue::None,
1391 ));
1392 c.error_info_list.push((
1393 MiddleArg::ShortFlag(short_flag.clone(), FlagValue::None),
1394 ParseError::NoExistShort(i),
1395 ParseError::NoExistShort(i),
1396 ));
1397 }
1398 },
1399 };
1400 i += 1;
1401 }
1402 match local_flags.find_short_flag(&last) {
1404 Some(l_flag) => {
1405 arg_match!(self,c.args.pop_front(),
1406 long_flag=>next_long_flag{
1407 c.local_flags_values
1408 .push((l_flag.get_name_clone(), FlagValue::None));
1409 self.parse_flags_start_with_long_flag(
1410 next_long_flag,
1411 local_flags,
1412 current_common_flags,
1413 c,
1414 )
1415 },
1416 short_flag=>next_short_flag{
1417 c.local_flags_values
1418 .push((l_flag.get_name_clone(), FlagValue::None));
1419 self.parse_flags_start_with_short_flag(
1420 next_short_flag,
1421 local_flags,
1422 current_common_flags,
1423 c,
1424 )
1425 },
1426 normal_arg=>next_arg{
1427 match l_flag.derive_flag_value_from_string(next_arg) {
1428 FlagValue::Invalid(next_arg) => {
1429 c.local_flags_values
1431 .push((l_flag.get_name_clone(), FlagValue::None));
1432 (Some(next_arg), c)
1433 }
1434 val => {
1435 c.local_flags_values.push((l_flag.get_name_clone(), val));
1436 self.parse_next_if_flag(local_flags, current_common_flags, c)
1437 }
1438 }
1439 },
1440 none=>next_none{
1441 c.local_flags_values
1442 .push((l_flag.get_name_clone(), FlagValue::None));
1443 (next_none, c)
1444 })
1445 }
1446 _ => match (current_common_flags, &c.common_flags).find_short_flag(&last) {
1447 Some(c_flag) => arg_match!(self, c.args.pop_front(),
1448 long_flag=>next_long_flag {
1449 c.common_flags_values
1450 .push((c_flag.get_name_clone(), FlagValue::None));
1451 self.parse_flags_start_with_long_flag(
1452 next_long_flag,
1453 local_flags,
1454 current_common_flags,
1455 c,
1456 )
1457 },
1458 short_flag=>next_short_flag{
1459 c.common_flags_values
1460 .push((c_flag.get_name_clone(), FlagValue::None));
1461 self.parse_flags_start_with_short_flag(
1462 next_short_flag,
1463 local_flags,
1464 current_common_flags,
1465 c,
1466 )
1467 },
1468 normal_arg=>next_arg{
1469 match c_flag.derive_flag_value_from_string(next_arg) {
1470 FlagValue::Invalid(next_arg) => {
1471 c.common_flags_values
1472 .push((c_flag.get_name_clone(), FlagValue::None));
1473 (Some(next_arg), c)
1474 }
1475 val => {
1476 c.common_flags_values.push((c_flag.get_name_clone(), val));
1477 self.parse_next_if_flag(local_flags, current_common_flags, c)
1478 }
1479 }
1480 },
1481 none=>next_none{
1482 c.common_flags_values
1483 .push((c_flag.get_name_clone(), FlagValue::None));
1484 (next_none, c)
1485 }
1486 ),
1487 _ => {
1488 let flag_arg = MiddleArg::ShortFlag(
1489 {
1490 short_flag.push(last);
1491 short_flag
1492 },
1493 FlagValue::None,
1494 );
1495 println!("{:?}", flag_arg);
1496 c.error_info_list.push((
1497 flag_arg.clone(),
1498 ParseError::NoExistShort(i),
1499 ParseError::NoExistShort(i),
1500 ));
1501 c.push_back_to_parsing_args(flag_arg);
1502 self.parse_next_if_flag(local_flags, current_common_flags, c)
1503 }
1504 },
1505 }
1506 }
1507 None => {
1508 c.push_back_to_parsing_args(MiddleArg::ShortFlag(
1509 short_flag.clone(),
1510 FlagValue::String(String::new()),
1511 ));
1512 c.error_info_list.push((
1513 MiddleArg::ShortFlag(short_flag, FlagValue::String(String::new())),
1514 ParseError::NotExist,
1515 ParseError::NotExist,
1516 ));
1517 self.parse_next_if_flag(local_flags, current_common_flags, c)
1518 }
1519 }
1520 }
1521 }
1522 }
1523
1524 pub fn parse_next_if_flag<T: FlagSearch, S: FlagSearch>(
1526 &self,
1527 local_flags: &T,
1528 current_common_flags: &S,
1529 mut c: Context,
1530 ) -> (Option<String>, Context) {
1531 arg_match!(self,
1532 c.args.pop_front(),
1533 long_flag=>long_flag{
1534 self.parse_flags_start_with_long_flag(
1535 long_flag,
1536 local_flags,
1537 current_common_flags,
1538 c,
1539 )
1540 },
1541 short_flag=>short_flag{
1542 self.parse_flags_start_with_short_flag(
1543 short_flag,
1544 local_flags,
1545 current_common_flags,
1546 c,
1547 )
1548 },
1549 non_flag=>non_flag{
1550 (Some(non_flag),c)
1551 },
1552 rest_opt=>val{
1553 (val,c)
1554 })
1555 }
1556}
1557
1558#[derive(Debug, Clone, PartialOrd, PartialEq)]
1560pub enum MiddleArg {
1561 Normal(String),
1563 LongFlag(String, FlagValue),
1565 ShortFlag(String, FlagValue),
1567}
1568
1569impl MiddleArg {
1570 pub fn name(&self) -> &str {
1572 match &self {
1573 MiddleArg::LongFlag(name, _) => name,
1574 MiddleArg::ShortFlag(name, _) => name,
1575 MiddleArg::Normal(name) => name,
1576 }
1577 }
1578
1579 pub fn val_if_string(&self) -> Option<&String> {
1581 match self {
1582 MiddleArg::LongFlag(_, FlagValue::String(val)) => Some(val),
1583 MiddleArg::ShortFlag(_, FlagValue::String(val)) => Some(val),
1584 MiddleArg::LongFlag(_, FlagValue::Invalid(val)) => Some(val),
1585 MiddleArg::ShortFlag(_, FlagValue::Invalid(val)) => Some(val),
1586 _ => None,
1587 }
1591 }
1592
1593 pub fn inner_if_string_val(&self) -> Option<(&str, &str)> {
1595 match &self {
1596 MiddleArg::LongFlag(name, FlagValue::String(val)) => Some((name, val)),
1597 MiddleArg::ShortFlag(name, FlagValue::String(val)) => Some((name, val)),
1598 MiddleArg::LongFlag(name, FlagValue::Invalid(val)) => Some((name, val)),
1599 MiddleArg::ShortFlag(name, FlagValue::Invalid(val)) => Some((name, val)),
1600 _ => None,
1601 }
1605 }
1606
1607 pub fn set_val(mut self, value: FlagValue) -> Self {
1609 match self {
1610 MiddleArg::LongFlag(_, ref mut val) => {
1611 (*val) = value;
1612 self
1613 }
1614 MiddleArg::ShortFlag(_, ref mut val) => {
1615 (*val) = value;
1616 self
1617 }
1618 MiddleArg::Normal(ref mut val) => {
1619 (*val) = value.get_string_value();
1620 self
1621 }
1622 }
1623 }
1624
1625 pub fn get_flag_type_str<'a>(&self) -> &'a str {
1627 match self {
1628 MiddleArg::LongFlag(_, _) => "long",
1629 MiddleArg::ShortFlag(_, _) => "short",
1630 MiddleArg::Normal(_) => "normal",
1631 }
1632 }
1633}
1634
1635type Index = usize;
1637#[derive(Debug, Clone, PartialEq, PartialOrd)]
1639pub enum ParseError {
1640 NoExistLong,
1642 NoExistShort(Index),
1644 InvalidShort(Index, String),
1646 InvalidLong(String),
1648 NotExist,
1650 NotParsed,
1652 Empty,
1654 None,
1656}
1657
1658pub type ErrorInfo = (MiddleArg, ParseError, ParseError);
1660
1661pub mod preset {
1663 use super::{ErrorInfo, MiddleArg, ParseError};
1664
1665 pub fn gen_error_description(err_info: &ErrorInfo) -> String {
1667 let mut description = String::from("Parse error: ");
1668 match &err_info.0 {
1669 MiddleArg::Normal(name) => {
1670 description.push_str("arg:");
1671 description.push_str(name);
1672 }
1673 MiddleArg::LongFlag(name, _) => {
1674 description.push_str("flag: --");
1675 description.push_str(name)
1676 }
1677 MiddleArg::ShortFlag(name, _) => {
1678 description.push_str("short flag: -");
1679 description.push_str(name);
1680 }
1681 }
1682 description.push_str(".\n");
1683 match err_info {
1684 (flag_arg, ParseError::NoExistShort(i), ParseError::NoExistShort(_)) => {
1685 let name = flag_arg.name();
1686 description = format!(
1687 "{}The short flag {} is an unknown short flag.",
1688 description,
1689 match name.len() {
1690 1 => {
1691 let mut s = String::from("-");
1692 s.push(name.chars().nth(*i).unwrap());
1693 s
1694 }
1695 _ => {
1696 let mut s = String::from("\"");
1697 s.push(name.chars().nth(*i).unwrap());
1698 s.push('"');
1699 s.push_str(" in ");
1700 s.push_str(name);
1701 s
1702 }
1703 },
1704 );
1705 }
1706 (flag_arg, ParseError::NoExistLong, ParseError::NoExistLong) => {
1707 description = format!("The flag --{} is an unknown flag.", flag_arg.name());
1708 }
1709 (flag_arg, ParseError::NoExistShort(_), ParseError::InvalidShort(i, c_flag)) => {
1710 let (name, val) = flag_arg.inner_if_string_val().unwrap();
1711 description = format!(
1712 "{}The value of short flag {} in {} - {} is not valid for a common flag {}.",
1713 description,
1714 name.chars().nth(*i).unwrap(),
1715 name,
1716 val,
1717 c_flag
1718 );
1719 }
1720 (flag_arg, ParseError::NoExistLong, ParseError::InvalidLong(chit)) => {
1721 let (name, val) = flag_arg.inner_if_string_val().unwrap();
1722 description = format!(
1723 "{}The flag {} matches a common flag {}. But its value {} is invalid for {}.",
1724 description,
1725 name,
1726 chit,
1727 val,
1728 flag_arg.get_flag_type_str()
1729 );
1730 }
1731 (flag_arg, ParseError::InvalidShort(i, l_flag), _) => {
1732 let (name, val) = flag_arg.inner_if_string_val().unwrap();
1733 description = format!(
1734 "{}The flag {}{}'s value {} is not valid for a local flag {}.",
1735 description,
1736 name.chars().nth(*i).unwrap(),
1737 { if name.chars().count() < 2 { "" } else { name } },
1738 val,
1739 l_flag
1740 );
1741 }
1742 (_, _, _) => {}
1743 };
1744 description
1745 }
1746
1747 #[cfg(test)]
1748 mod tests {
1749 use crate::{Command, done, parser::preset::gen_error_description};
1750
1751 #[test]
1752 fn test_error_description() {
1753 let arg: Vec<String> = vec![
1754 "exe_path".to_string(),
1755 "test".to_string(),
1756 "test".to_string(),
1757 "-d".to_string(),
1758 "dir".to_string(),
1759 ];
1760 let test = Command::new().action(|mut _cmd, c| {
1761 println!("test_action: {c:?}");
1762 if let Some(err) = c.first_error() {
1763 let description = gen_error_description(err);
1764 println!("{}", description);
1765 }
1766 done!()
1767 });
1768 let r = test.run_from_args(arg);
1769 assert!(r.is_ok());
1770 }
1771 }
1772}