0
# Parsing and Execution
1
2
Parse result handling, execution strategies, and exception management for robust command line processing with detailed error reporting and flexible execution models.
3
4
## Capabilities
5
6
### ParseResult Class
7
8
Contains the results of parsing command line arguments with detailed information about matched options, parameters, and subcommands.
9
10
```java { .api }
11
public static class ParseResult {
12
/**
13
* Checks if the specified option was matched during parsing
14
* @param option the option name to check
15
* @return true if the option was matched
16
*/
17
public boolean hasMatchedOption(String option);
18
19
/**
20
* Gets the value of a matched option with default fallback
21
* @param option the option name
22
* @param defaultValue default value if option not matched
23
* @return the option value or default
24
*/
25
public <T> T matchedOptionValue(String option, T defaultValue);
26
27
/**
28
* Gets matched positional parameter values
29
* @param index the parameter index
30
* @param defaultValue default value if not matched
31
* @return list of matched values or default
32
*/
33
public List<String> matchedPositionalValue(int index, List<String> defaultValue);
34
35
/**
36
* Gets all matched options
37
* @return map of option names to matched values
38
*/
39
public Map<String, Object> matchedOptions();
40
41
/**
42
* Gets all matched positional parameters
43
* @return list of matched positional parameters
44
*/
45
public List<String> matchedPositionals();
46
47
/**
48
* Checks if help was requested
49
* @return true if help flag was matched
50
*/
51
public boolean isUsageHelpRequested();
52
53
/**
54
* Checks if version help was requested
55
* @return true if version flag was matched
56
*/
57
public boolean isVersionHelpRequested();
58
59
/**
60
* Gets unmatched arguments
61
* @return list of arguments that couldn't be matched
62
*/
63
public List<String> unmatched();
64
65
/**
66
* Gets the CommandSpec for the parsed command
67
* @return the command specification
68
*/
69
public CommandSpec commandSpec();
70
71
/**
72
* Gets subcommand parse results
73
* @return list of ParseResult for matched subcommands
74
*/
75
public List<ParseResult> subcommands();
76
}
77
```
78
79
**Usage Examples:**
80
81
```java
82
@Command(name = "app")
83
class MyApp {
84
@Option(names = {"-v", "--verbose"}) boolean verbose;
85
@Option(names = {"-f", "--file"}) String filename;
86
@Parameters List<String> files;
87
}
88
89
CommandLine cmd = new CommandLine(new MyApp());
90
ParseResult parseResult = cmd.parseArgs("-v", "--file", "config.xml", "input1.txt", "input2.txt");
91
92
// Check for specific options
93
if (parseResult.hasMatchedOption("-v")) {
94
System.out.println("Verbose mode enabled");
95
}
96
97
// Get option values with defaults
98
String filename = parseResult.matchedOptionValue("--file", "default.xml");
99
List<String> files = parseResult.matchedPositionalValue(0, Collections.emptyList());
100
101
// Handle help requests
102
if (parseResult.isUsageHelpRequested()) {
103
cmd.usage(System.out);
104
return;
105
}
106
```
107
108
### Execution Strategies
109
110
Different strategies for executing parsed commands in complex command hierarchies.
111
112
```java { .api }
113
/**
114
* Interface for command execution strategies
115
*/
116
public interface IExecutionStrategy {
117
/**
118
* Executes the command based on parse results
119
* @param parseResult the parsing results
120
* @return exit code
121
* @throws ExecutionException if execution fails
122
*/
123
int execute(ParseResult parseResult) throws ExecutionException;
124
}
125
126
/**
127
* Executes only the first command in the parse result
128
*/
129
public static class RunFirst extends AbstractParseResultHandler<List<Object>> implements IParseResultHandler {
130
/**
131
* Executes the first command only
132
*/
133
public int execute(ParseResult parseResult) throws ExecutionException;
134
}
135
136
/**
137
* Executes only the last command in the parse result
138
*/
139
public static class RunLast extends AbstractParseResultHandler<List<Object>> implements IParseResultHandler {
140
/**
141
* Executes the last command only
142
*/
143
public int execute(ParseResult parseResult) throws ExecutionException;
144
}
145
146
/**
147
* Executes all commands in the parse result
148
*/
149
public static class RunAll extends AbstractParseResultHandler<List<Object>> implements IParseResultHandler {
150
/**
151
* Executes all commands in order
152
*/
153
public int execute(ParseResult parseResult) throws ExecutionException;
154
}
155
```
156
157
**Usage Examples:**
158
159
```java
160
@Command(name = "parent")
161
class ParentCommand implements Runnable {
162
public void run() { System.out.println("Parent executed"); }
163
}
164
165
@Command(name = "child")
166
class ChildCommand implements Runnable {
167
public void run() { System.out.println("Child executed"); }
168
}
169
170
CommandLine parent = new CommandLine(new ParentCommand());
171
parent.addSubcommand("child", new ChildCommand());
172
173
// Using different execution strategies
174
CommandLine.RunFirst runFirst = new CommandLine.RunFirst();
175
CommandLine.RunLast runLast = new CommandLine.RunLast();
176
CommandLine.RunAll runAll = new CommandLine.RunAll();
177
178
ParseResult parseResult = parent.parseArgs("child");
179
180
// Only executes ParentCommand
181
runFirst.execute(parseResult);
182
183
// Only executes ChildCommand
184
runLast.execute(parseResult);
185
186
// Executes both ParentCommand and ChildCommand
187
runAll.execute(parseResult);
188
```
189
190
### Exception Handling
191
192
Comprehensive exception hierarchy for handling parsing and execution errors.
193
194
```java { .api }
195
/**
196
* Base exception for all picocli exceptions
197
*/
198
public static class PicocliException extends RuntimeException {
199
public PicocliException(String message);
200
public PicocliException(String message, Throwable cause);
201
}
202
203
/**
204
* Exception during command initialization
205
*/
206
public static class InitializationException extends PicocliException {
207
public InitializationException(String message);
208
public InitializationException(String message, Throwable cause);
209
}
210
211
/**
212
* Exception during command execution
213
*/
214
public static class ExecutionException extends PicocliException {
215
public ExecutionException(CommandLine commandLine, String message);
216
public ExecutionException(CommandLine commandLine, String message, Throwable cause);
217
}
218
219
/**
220
* Exception during type conversion
221
*/
222
public static class TypeConversionException extends PicocliException {
223
public TypeConversionException(String message);
224
}
225
226
/**
227
* Base exception for parameter parsing errors
228
*/
229
public static class ParameterException extends PicocliException {
230
public ParameterException(CommandLine commandLine, String message);
231
public ParameterException(CommandLine commandLine, String message, Throwable cause);
232
233
/**
234
* Gets the CommandLine where the error occurred
235
*/
236
public CommandLine getCommandLine();
237
}
238
239
/**
240
* Required parameter was not provided
241
*/
242
public static class MissingParameterException extends ParameterException {
243
public MissingParameterException(CommandLine commandLine, ArgSpec missing, String message);
244
}
245
246
/**
247
* Mutually exclusive arguments were both provided
248
*/
249
public static class MutuallyExclusiveArgsException extends ParameterException {
250
public MutuallyExclusiveArgsException(CommandLine commandLine, String message);
251
}
252
253
/**
254
* Unmatched command line arguments
255
*/
256
public static class UnmatchedArgumentException extends ParameterException {
257
public UnmatchedArgumentException(CommandLine commandLine, List<String> unmatched);
258
259
/**
260
* Gets the unmatched arguments
261
*/
262
public List<String> getUnmatched();
263
}
264
265
/**
266
* Maximum number of values exceeded for an option
267
*/
268
public static class MaxValuesExceededException extends ParameterException {
269
public MaxValuesExceededException(CommandLine commandLine, String message);
270
}
271
272
/**
273
* Option value was overwritten when not allowed
274
*/
275
public static class OverwrittenOptionException extends ParameterException {
276
public OverwrittenOptionException(CommandLine commandLine, ArgSpec overwritten, String message);
277
}
278
279
/**
280
* Type converter missing for parameter type
281
*/
282
public static class MissingTypeConverterException extends ParameterException {
283
public MissingTypeConverterException(CommandLine commandLine, String message);
284
}
285
```
286
287
**Usage Example:**
288
289
```java
290
try {
291
int exitCode = new CommandLine(new MyApp()).execute(args);
292
System.exit(exitCode);
293
} catch (ParameterException ex) {
294
System.err.println("Parameter error: " + ex.getMessage());
295
ex.getCommandLine().usage(System.err);
296
System.exit(2);
297
} catch (ExecutionException ex) {
298
System.err.println("Execution error: " + ex.getMessage());
299
ex.printStackTrace();
300
System.exit(1);
301
}
302
```
303
304
### Exception Handlers
305
306
Interfaces for custom exception handling during parsing and execution.
307
308
```java { .api }
309
/**
310
* Handles parameter parsing exceptions
311
*/
312
public interface IParameterExceptionHandler {
313
/**
314
* Handles a parameter parsing exception
315
* @param ex the parameter exception
316
* @param args the command line arguments
317
* @return exit code
318
* @throws Exception if handling fails
319
*/
320
int handleParseException(ParameterException ex, String[] args) throws Exception;
321
}
322
323
/**
324
* Handles execution exceptions
325
*/
326
public interface IExecutionExceptionHandler {
327
/**
328
* Handles an execution exception
329
* @param ex the execution exception
330
* @param commandLine the CommandLine where the exception occurred
331
* @param parseResult the parse result
332
* @return exit code
333
* @throws Exception if handling fails
334
*/
335
int handleExecutionException(Exception ex, CommandLine commandLine, ParseResult parseResult) throws Exception;
336
}
337
338
/**
339
* Default exception handler implementation
340
*/
341
public static class DefaultExceptionHandler<R> implements IParameterExceptionHandler, IExecutionExceptionHandler {
342
public int handleParseException(ParameterException ex, String[] args);
343
public int handleExecutionException(Exception ex, CommandLine commandLine, ParseResult parseResult);
344
}
345
```
346
347
**Usage Example:**
348
349
```java
350
// Custom parameter exception handler
351
IParameterExceptionHandler paramHandler = (ex, args) -> {
352
System.err.println("Custom parameter error: " + ex.getMessage());
353
ex.getCommandLine().usage(System.err);
354
return 2; // Custom exit code
355
};
356
357
// Custom execution exception handler
358
IExecutionExceptionHandler execHandler = (ex, cmd, parseResult) -> {
359
System.err.println("Custom execution error: " + ex.getMessage());
360
if (ex instanceof FileNotFoundException) {
361
System.err.println("File not found. Please check the file path.");
362
return 3; // File not found exit code
363
}
364
return 1; // General error
365
};
366
367
CommandLine cmd = new CommandLine(new MyApp());
368
cmd.setParameterExceptionHandler(paramHandler);
369
cmd.setExecutionExceptionHandler(execHandler);
370
371
int exitCode = cmd.execute(args);
372
```
373
374
### Exit Code Management
375
376
Interfaces and utilities for managing command exit codes.
377
378
```java { .api }
379
/**
380
* Generates exit codes from command execution results
381
*/
382
public interface IExitCodeGenerator {
383
/**
384
* Generates an exit code for the command result
385
* @return exit code
386
*/
387
int generateExitCode();
388
}
389
390
/**
391
* Maps exceptions to exit codes
392
*/
393
public interface IExitCodeExceptionMapper {
394
/**
395
* Maps an exception to an exit code
396
* @param ex the exception
397
* @return exit code
398
*/
399
int getExitCode(Throwable ex);
400
}
401
402
/**
403
* Standard exit codes
404
*/
405
public static final class ExitCode {
406
public static final int OK = 0; // Success
407
public static final int SOFTWARE = 1; // Software error
408
public static final int USAGE = 2; // Usage error
409
}
410
```
411
412
**Usage Example:**
413
414
```java
415
@Command(name = "processor")
416
class DataProcessor implements Runnable, IExitCodeGenerator {
417
@Option(names = "-f") String filename;
418
419
private int exitCode = 0;
420
421
public void run() {
422
try {
423
processFile(filename);
424
exitCode = ExitCode.OK;
425
} catch (FileNotFoundException e) {
426
System.err.println("File not found: " + filename);
427
exitCode = 3; // Custom file not found exit code
428
} catch (Exception e) {
429
System.err.println("Processing error: " + e.getMessage());
430
exitCode = ExitCode.SOFTWARE;
431
}
432
}
433
434
@Override
435
public int generateExitCode() {
436
return exitCode;
437
}
438
}
439
440
// The exit code will be determined by the IExitCodeGenerator
441
int exitCode = new CommandLine(new DataProcessor()).execute(args);
442
```