]> git.proxmox.com Git - rustc.git/blob - src/vendor/clap/src/args/arg_builder/option.rs
67abb2b106136502a0d674d2fba0f597e41b38b4
[rustc.git] / src / vendor / clap / src / args / arg_builder / option.rs
1 // Std
2 use std::fmt::{Display, Formatter, Result};
3 use std::rc::Rc;
4 use std::result::Result as StdResult;
5 use std::ffi::{OsStr, OsString};
6 use std::mem;
7
8 // Third Party
9 use vec_map::{self, VecMap};
10
11 // Internal
12 use args::{ArgSettings, AnyArg, Base, Switched, Valued, Arg, DispOrder};
13
14 #[allow(missing_debug_implementations)]
15 #[doc(hidden)]
16 #[derive(Default, Clone)]
17 pub struct OptBuilder<'n, 'e>
18 where 'n: 'e
19 {
20 pub b: Base<'n, 'e>,
21 pub s: Switched<'e>,
22 pub v: Valued<'n, 'e>,
23 }
24
25 impl<'n, 'e> OptBuilder<'n, 'e> {
26 pub fn new(name: &'n str) -> Self { OptBuilder { b: Base::new(name), ..Default::default() } }
27 }
28
29 impl<'n, 'e, 'z> From<&'z Arg<'n, 'e>> for OptBuilder<'n, 'e> {
30 fn from(a: &'z Arg<'n, 'e>) -> Self {
31 OptBuilder {
32 b: Base::from(a),
33 s: Switched::from(a),
34 v: Valued::from(a),
35 }
36 }
37 }
38
39 impl<'n, 'e> From<Arg<'n, 'e>> for OptBuilder<'n, 'e> {
40 fn from(mut a: Arg<'n, 'e>) -> Self {
41 a.v.fill_in();
42 OptBuilder {
43 b: mem::replace(&mut a.b, Base::default()),
44 s: mem::replace(&mut a.s, Switched::default()),
45 v: mem::replace(&mut a.v, Valued::default()),
46 }
47 }
48 }
49
50 impl<'n, 'e> Display for OptBuilder<'n, 'e> {
51 fn fmt(&self, f: &mut Formatter) -> Result {
52 debugln!("OptBuilder::fmt:{}", self.b.name);
53 let sep = if self.b.is_set(ArgSettings::RequireEquals) {
54 "="
55 } else {
56 " "
57 };
58 // Write the name such --long or -l
59 if let Some(l) = self.s.long {
60 write!(f, "--{}{}", l, sep)?;
61 } else {
62 write!(f, "-{}{}", self.s.short.unwrap(), sep)?;
63 }
64
65 // Write the values such as <name1> <name2>
66 if let Some(ref vec) = self.v.val_names {
67 let mut it = vec.iter().peekable();
68 while let Some((_, val)) = it.next() {
69 write!(f, "<{}>", val)?;
70 if it.peek().is_some() {
71 write!(f, " ")?;
72 }
73 }
74 let num = vec.len();
75 if self.is_set(ArgSettings::Multiple) && num == 1 {
76 write!(f, "...")?;
77 }
78 } else if let Some(num) = self.v.num_vals {
79 let mut it = (0..num).peekable();
80 while let Some(_) = it.next() {
81 write!(f, "<{}>", self.b.name)?;
82 if it.peek().is_some() {
83 write!(f, " ")?;
84 }
85 }
86 if self.is_set(ArgSettings::Multiple) && num == 1 {
87 write!(f, "...")?;
88 }
89 } else {
90 write!(f,
91 "<{}>{}",
92 self.b.name,
93 if self.is_set(ArgSettings::Multiple) {
94 "..."
95 } else {
96 ""
97 })?;
98 }
99
100 Ok(())
101 }
102 }
103
104 impl<'n, 'e> AnyArg<'n, 'e> for OptBuilder<'n, 'e> {
105 fn name(&self) -> &'n str { self.b.name }
106 fn overrides(&self) -> Option<&[&'e str]> { self.b.overrides.as_ref().map(|o| &o[..]) }
107 fn requires(&self) -> Option<&[(Option<&'e str>, &'n str)]> {
108 self.b.requires.as_ref().map(|o| &o[..])
109 }
110 fn blacklist(&self) -> Option<&[&'e str]> { self.b.blacklist.as_ref().map(|o| &o[..]) }
111 fn required_unless(&self) -> Option<&[&'e str]> { self.b.r_unless.as_ref().map(|o| &o[..]) }
112 fn val_names(&self) -> Option<&VecMap<&'e str>> { self.v.val_names.as_ref() }
113 fn is_set(&self, s: ArgSettings) -> bool { self.b.settings.is_set(s) }
114 fn has_switch(&self) -> bool { true }
115 fn set(&mut self, s: ArgSettings) { self.b.settings.set(s) }
116 fn max_vals(&self) -> Option<u64> { self.v.max_vals }
117 fn val_terminator(&self) -> Option<&'e str> { self.v.terminator }
118 fn num_vals(&self) -> Option<u64> { self.v.num_vals }
119 fn possible_vals(&self) -> Option<&[&'e str]> { self.v.possible_vals.as_ref().map(|o| &o[..]) }
120 fn validator(&self) -> Option<&Rc<Fn(String) -> StdResult<(), String>>> {
121 self.v.validator.as_ref()
122 }
123 fn validator_os(&self) -> Option<&Rc<Fn(&OsStr) -> StdResult<(), OsString>>> {
124 self.v.validator_os.as_ref()
125 }
126 fn min_vals(&self) -> Option<u64> { self.v.min_vals }
127 fn short(&self) -> Option<char> { self.s.short }
128 fn long(&self) -> Option<&'e str> { self.s.long }
129 fn val_delim(&self) -> Option<char> { self.v.val_delim }
130 fn takes_value(&self) -> bool { true }
131 fn help(&self) -> Option<&'e str> { self.b.help }
132 fn long_help(&self) -> Option<&'e str> { self.b.long_help }
133 fn default_val(&self) -> Option<&'e OsStr> { self.v.default_val }
134 fn default_vals_ifs(&self) -> Option<vec_map::Values<(&'n str, Option<&'e OsStr>, &'e OsStr)>> {
135 self.v.default_vals_ifs.as_ref().map(|vm| vm.values())
136 }
137 fn longest_filter(&self) -> bool { true }
138 fn aliases(&self) -> Option<Vec<&'e str>> {
139 if let Some(ref aliases) = self.s.aliases {
140 let vis_aliases: Vec<_> = aliases.iter()
141 .filter_map(|&(n, v)| if v { Some(n) } else { None })
142 .collect();
143 if vis_aliases.is_empty() {
144 None
145 } else {
146 Some(vis_aliases)
147 }
148 } else {
149 None
150 }
151 }
152 }
153
154 impl<'n, 'e> DispOrder for OptBuilder<'n, 'e> {
155 fn disp_ord(&self) -> usize { self.s.disp_ord }
156 }
157
158 impl<'n, 'e> PartialEq for OptBuilder<'n, 'e> {
159 fn eq(&self, other: &OptBuilder<'n, 'e>) -> bool {
160 self.b == other.b
161 }
162 }
163
164 #[cfg(test)]
165 mod test {
166 use args::settings::ArgSettings;
167 use super::OptBuilder;
168 use vec_map::VecMap;
169
170 #[test]
171 fn optbuilder_display1() {
172 let mut o = OptBuilder::new("opt");
173 o.s.long = Some("option");
174 o.b.settings.set(ArgSettings::Multiple);
175
176 assert_eq!(&*format!("{}", o), "--option <opt>...");
177 }
178
179 #[test]
180 fn optbuilder_display2() {
181 let mut v_names = VecMap::new();
182 v_names.insert(0, "file");
183 v_names.insert(1, "name");
184
185 let mut o2 = OptBuilder::new("opt");
186 o2.s.short = Some('o');
187 o2.v.val_names = Some(v_names);
188
189 assert_eq!(&*format!("{}", o2), "-o <file> <name>");
190 }
191
192 #[test]
193 fn optbuilder_display3() {
194 let mut v_names = VecMap::new();
195 v_names.insert(0, "file");
196 v_names.insert(1, "name");
197
198 let mut o2 = OptBuilder::new("opt");
199 o2.s.short = Some('o');
200 o2.v.val_names = Some(v_names);
201 o2.b.settings.set(ArgSettings::Multiple);
202
203 assert_eq!(&*format!("{}", o2), "-o <file> <name>");
204 }
205
206 #[test]
207 fn optbuilder_display_single_alias() {
208 let mut o = OptBuilder::new("opt");
209 o.s.long = Some("option");
210 o.s.aliases = Some(vec![("als", true)]);
211
212 assert_eq!(&*format!("{}", o), "--option <opt>");
213 }
214
215 #[test]
216 fn optbuilder_display_multiple_aliases() {
217 let mut o = OptBuilder::new("opt");
218 o.s.long = Some("option");
219 o.s.aliases =
220 Some(vec![("als_not_visible", false), ("als2", true), ("als3", true), ("als4", true)]);
221 assert_eq!(&*format!("{}", o), "--option <opt>");
222 }
223 }