1use std::fmt::{Display, Formatter, Result};
2
3#[derive(Debug, Clone)]
4pub enum Argument {
5 FunctionDefinition {
6 name: String,
7 default: Option<String>,
8 help: Option<String>,
9 arg_type: Option<String>
10 },
11 Variable ( String ),
12 Unnamed ( String )
13}
14
15#[cfg(test)]
16mod tests {
17 mod definition {
18 use Argument;
19
20 #[test]
21 fn it_prints_an_argument_with_no_default() {
22 let arg = Argument::new("test", None, None, None);
23 assert_eq!("test", format!("{}", arg));
24 }
25
26 #[test]
27 fn it_prints_an_argument_with_a_default() {
28 let arg = Argument::new("test", Some(r#""value""#), None, None);
29 assert_eq!(r#"test="value""#, format!("{}", arg));
30 }
31 }
32
33 mod bare_argument {
34 use Argument;
35 #[test]
36 fn it_prints_an_argument() {
37 let arg = Argument::unnamed("world");
38 assert_eq!("\"world\"", format!("{}", arg));
39 }
40 }
41
42 mod function_argument {
43 use Argument;
44 #[test]
45 fn it_prints_an_argument() {
46 let arg = Argument::variable("name");
47 assert_eq!("name", format!("{}", arg));
48 }
49 }
50
51}
52
53impl Argument {
54 pub fn new<T: Display>(name: T,
55 default: Option<T>,
56 arg_type: Option<T>,
57 help: Option<T>)
58 -> Argument {
59 Argument::FunctionDefinition {
60 name: name.to_string(),
61 default: default.map(|s| s.to_string()),
62 arg_type: arg_type.map(|s| s.to_string()),
63 help: help.map(|s| s.to_string())
64 }
65 }
66
67 pub fn unnamed<T: Display>(value: T) -> Argument {
72 Argument::Unnamed(value.to_string())
73 }
74
75 pub fn variable<T: Display>(name: T) -> Argument {
80 Argument::Variable (name.to_string())
81 }
82
83 pub fn has_help(&self) -> bool {
84 match self {
85 &Argument::FunctionDefinition{ref help, .. } => help.is_some(),
86 _ => false,
87 }
88 }
89
90 pub fn help_string(&self) -> Option<String> {
91 match self {
92 &Argument::FunctionDefinition{ref help, ref name, ..} => {
93 let mut formatted_help = format!(":param {}:", name);
94
95 if let &Some(ref help_str) = help {
96 formatted_help.push_str(&format!(" {}", help_str)[..]);
97 Some(formatted_help)
98 } else {
99 None
100 }
101 },
102 _ => None,
103 }
104 }
105
106 pub fn type_string(&self) -> Option<String> {
107 match self {
108 &Argument::FunctionDefinition{ref arg_type, ref name, ..} => {
109 let mut help = format!(":type {}:", name);
110 if let &Some(ref t) = arg_type {
111 help.push_str(&format!(" {}", t)[..]);
112 Some(help)
113 } else {
114 None
115 }
116 },
117 _ => None,
118 }
119 }
120}
121
122impl Display for Argument {
123 fn fmt(&self, f: &mut Formatter) -> Result {
124 let mut output = String::new();
125 match self {
126 &Argument::FunctionDefinition{ref name, ref default, ..} => {
127 output.push_str(&name[..]);
128 if let &Some(ref default) = default {
129 output.push_str(&format!("={}", default));
130 }
131 },
132 &Argument::Unnamed(ref value) => {
133 output.push_str(&format!("\"{}\"", value)[..]);
134 },
135 &Argument::Variable(ref name) => {
136 output.push_str(&format!("{}", name)[..]);
137 },
138 }
139 write!(f, "{}", output)
140 }
141}
142
143#[derive(Debug, Clone)]
144pub struct KeywordArgument {
145 pub keyword: String,
146 pub argument: String,
147}
148
149impl KeywordArgument {
150 pub fn new<T: Display>(name: T, arg: T) -> KeywordArgument {
151 KeywordArgument {
152 keyword: name.to_string(),
153 argument: arg.to_string(),
154 }
155 }
156}
157
158impl Display for KeywordArgument {
159 fn fmt(&self, f: &mut Formatter) -> Result {
160 write!(f, "{}={}", self.keyword, self.argument)
161 }
162}