1 /*
2 * Licensed to the Apache Software Foundation (ASF) under one or more
3 * contributor license agreements. See the NOTICE file distributed with
4 * this work for additional information regarding copyright ownership.
5 * The ASF licenses this file to You under the Apache License, Version 2.0
6 * (the "License"); you may not use this file except in compliance with
7 * the License. You may obtain a copy of the License at
8 *
9 * http://www.apache.org/licenses/LICENSE-2.0
10 *
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
16 */
17 package org.apache.commons.cli2.builder;
18
19 import java.util.ArrayList;
20 import java.util.List;
21
22 import org.apache.commons.cli2.Argument;
23 import org.apache.commons.cli2.option.ArgumentImpl;
24 import org.apache.commons.cli2.resource.ResourceConstants;
25 import org.apache.commons.cli2.resource.ResourceHelper;
26 import org.apache.commons.cli2.validation.Validator;
27
28 /**
29 * Builds Argument instances.
30 */
31 public class ArgumentBuilder {
32
33 /** i18n */
34 private final static ResourceHelper resources = ResourceHelper.getResourceHelper();
35
36 /** name of the argument. Used for display and lookups in CommandLine */
37 private String name;
38
39 /** description of the argument. Used in the automated online help */
40 private String description;
41
42 /** minimum number of values required */
43 private int minimum;
44
45 /** maximum number of values permitted */
46 private int maximum;
47
48 /** character used to separate the values from the option */
49 private char initialSeparator;
50
51 /** character used to separate the values from each other */
52 private char subsequentSeparator;
53
54 /** object that should be used to ensure the values are valid */
55 private Validator validator;
56
57 /** used to identify the consume remaining option, typically "--" */
58 private String consumeRemaining;
59
60 /** default values for argument */
61 private List defaultValues;
62
63 /** id of the argument */
64 private int id;
65
66 /**
67 * Creates a new ArgumentBuilder instance
68 */
69 public ArgumentBuilder() {
70 reset();
71 }
72
73 /**
74 * Creates a new Argument instance using the options specified in this
75 * ArgumentBuilder.
76 *
77 * @return A new Argument instance using the options specified in this
78 * ArgumentBuilder.
79 */
80 public final Argument create() {
81 final Argument argument =
82 new ArgumentImpl(
83 name,
84 description,
85 minimum,
86 maximum,
87 initialSeparator,
88 subsequentSeparator,
89 validator,
90 consumeRemaining,
91 defaultValues,
92 id);
93
94 reset();
95
96 return argument;
97 }
98
99 /**
100 * Resets the ArgumentBuilder to the defaults for a new Argument. The
101 * method is called automatically at the end of a create() call.
102 * @return this ArgumentBuilder
103 */
104 public final ArgumentBuilder reset() {
105 name = "arg";
106 description = null;
107 minimum = 0;
108 maximum = Integer.MAX_VALUE;
109 initialSeparator = ArgumentImpl.DEFAULT_INITIAL_SEPARATOR;
110 subsequentSeparator = ArgumentImpl.DEFAULT_SUBSEQUENT_SEPARATOR;
111 validator = null;
112 consumeRemaining = "--";
113 defaultValues = null;
114 id = 0;
115 return this;
116 }
117
118 /**
119 * Sets the name of the argument. The name is used when displaying usage
120 * information and to allow lookups in the CommandLine object.
121 *
122 * @see org.apache.commons.cli2.CommandLine#getValue(String)
123 *
124 * @param newName the name of the argument
125 * @return this ArgumentBuilder
126 */
127 public final ArgumentBuilder withName(final String newName) {
128 if (newName == null) {
129 throw new IllegalArgumentException(resources.getMessage(ResourceConstants.ARGUMENT_BUILDER_NULL_NAME));
130 }
131 if ("".equals(newName)) {
132 throw new IllegalArgumentException(resources.getMessage(ResourceConstants.ARGUMENT_BUILDER_EMPTY_NAME));
133 }
134 this.name = newName;
135 return this;
136 }
137
138 /**
139 * Sets the description of the argument.
140 *
141 * The description is used when displaying online help.
142 *
143 * @param newDescription a description of the argument
144 * @return this ArgumentBuilder
145 */
146 public final ArgumentBuilder withDescription(final String newDescription) {
147 this.description = newDescription;
148 return this;
149 }
150
151 /**
152 * Sets the minimum number of values needed for the argument to be valid.
153 *
154 * @param newMinimum the number of values needed
155 * @return this ArgumentBuilder
156 */
157 public final ArgumentBuilder withMinimum(final int newMinimum) {
158 if (newMinimum < 0) {
159 throw new IllegalArgumentException(resources.getMessage(ResourceConstants.ARGUMENT_BUILDER_NEGATIVE_MINIMUM));
160 }
161 this.minimum = newMinimum;
162 return this;
163 }
164
165 /**
166 * Sets the maximum number of values allowed for the argument to be valid.
167 *
168 * @param newMaximum the number of values allowed
169 * @return this ArgumentBuilder
170 */
171 public final ArgumentBuilder withMaximum(final int newMaximum) {
172 if (newMaximum < 0) {
173 throw new IllegalArgumentException(resources.getMessage(ResourceConstants.ARGUMENT_BUILDER_NEGATIVE_MAXIMUM));
174 }
175 this.maximum = newMaximum;
176 return this;
177 }
178
179 /**
180 * Sets the character used to separate the values from the option. When an
181 * argument is of the form -libs:dir1,dir2,dir3 the initialSeparator would
182 * be ':'.
183 *
184 * @param newInitialSeparator the character used to separate the values
185 * from the option
186 * @return this ArgumentBuilder
187 */
188 public final ArgumentBuilder withInitialSeparator(
189 final char newInitialSeparator) {
190
191 this.initialSeparator = newInitialSeparator;
192 return this;
193 }
194
195 /**
196 * Sets the character used to separate the values from each other. When an
197 * argument is of the form -libs:dir1,dir2,dir3 the subsequentSeparator
198 * would be ','.
199 *
200 * @param newSubsequentSeparator the character used to separate the values
201 * from each other
202 * @return this ArgumentBuilder
203 */
204 public final ArgumentBuilder withSubsequentSeparator(
205 final char newSubsequentSeparator) {
206
207 this.subsequentSeparator = newSubsequentSeparator;
208 return this;
209 }
210
211 /**
212 * Sets the validator instance used to perform validation on the Argument
213 * values.
214 *
215 * @param newValidator a Validator instance
216 * @return this ArgumentBuilder
217 */
218 public final ArgumentBuilder withValidator(final Validator newValidator) {
219 if (newValidator == null) {
220 throw new IllegalArgumentException(resources.getMessage(ResourceConstants.ARGUMENT_BUILDER_NULL_VALIDATOR));
221 }
222 this.validator = newValidator;
223 return this;
224 }
225
226 /**
227 * Sets the "consume remaining" option, defaults to "--". Use this if you
228 * want to allow values that might be confused with option strings.
229 *
230 * @param newConsumeRemaining the string to use for the consume
231 * remaining option
232 * @return this ArgumentBuilder
233 */
234 public final ArgumentBuilder withConsumeRemaining(final String newConsumeRemaining) {
235 if (newConsumeRemaining == null) {
236 throw new IllegalArgumentException(resources.getMessage(ResourceConstants.ARGUMENT_BUILDER_NULL_CONSUME_REMAINING));
237 }
238 if ( "".equals(newConsumeRemaining)) {
239 throw new IllegalArgumentException(resources.getMessage(ResourceConstants.ARGUMENT_BUILDER_EMPTY_CONSUME_REMAINING));
240 }
241 this.consumeRemaining = newConsumeRemaining;
242 return this;
243 }
244
245 /**
246 * Sets the default value.
247 *
248 * @param defaultValue the default value for the Argument
249 * @return this ArgumentBuilder
250 */
251 public final ArgumentBuilder withDefault(final Object defaultValue) {
252 if (defaultValue == null) {
253 throw new IllegalArgumentException(resources.getMessage(ResourceConstants.ARGUMENT_BUILDER_NULL_DEFAULT));
254 }
255
256 if (this.defaultValues == null) {
257 this.defaultValues = new ArrayList(1);
258 }
259 this.defaultValues.add(defaultValue);
260 return this;
261 }
262
263 /**
264 * Sets the default values.
265 *
266 * @param newDefaultValues the default values for the Argument
267 * @return this ArgumentBuilder
268 */
269 public final ArgumentBuilder withDefaults(final List newDefaultValues) {
270 if (newDefaultValues == null) {
271 throw new IllegalArgumentException(resources.getMessage(ResourceConstants.ARGUMENT_BUILDER_NULL_DEFAULTS));
272 }
273 this.defaultValues = newDefaultValues;
274 return this;
275 }
276
277 /**
278 * Sets the id
279 *
280 * @param newId the id of the Argument
281 * @return this ArgumentBuilder
282 */
283 public final ArgumentBuilder withId(final int newId) {
284 this.id = newId;
285 return this;
286 }
287 }