0
# Arguments
1
2
Positional argument parsing with type conversion and validation. Arguments are processed in order and support optional, multiple, and paired value patterns.
3
4
## Capabilities
5
6
### Argument Declaration
7
8
Create positional arguments using the `argument()` function with support for help text and completion.
9
10
```kotlin { .api }
11
/**
12
* Create a positional argument
13
* @param name Argument name for help display
14
* @param help Help text for the argument
15
* @param helpTags Extra help formatter information
16
* @param completionCandidates Completion candidates
17
*/
18
fun CliktCommand.argument(
19
name: String = "",
20
help: String = "",
21
helpTags: Map<String, String> = emptyMap(),
22
completionCandidates: CompletionCandidates? = null
23
): RawArgument
24
```
25
26
**Usage Examples:**
27
28
```kotlin
29
class MyCommand : CliktCommand() {
30
// Basic argument
31
private val filename by argument(name = "FILE", help = "Input file to process")
32
33
// Argument with completion
34
private val hostname by argument(
35
name = "HOST",
36
help = "Target hostname",
37
completionCandidates = CompletionCandidates.Hostname
38
)
39
}
40
```
41
42
### Type Conversion
43
44
Convert argument values to specific types with built-in converters.
45
46
```kotlin { .api }
47
/**
48
* Convert argument value using custom conversion function
49
*/
50
fun <T : Any> RawArgument.convert(
51
conversion: ArgValueConverter<String, T>
52
): ProcessedArgument<T, T>
53
54
/** Convert to Int */
55
fun RawArgument.int(): ProcessedArgument<Int, Int>
56
57
/** Convert to Long */
58
fun RawArgument.long(): ProcessedArgument<Long, Long>
59
60
/** Convert to Float */
61
fun RawArgument.float(): ProcessedArgument<Float, Float>
62
63
/** Convert to Double */
64
fun RawArgument.double(): ProcessedArgument<Double, Double>
65
66
/** Convert to Boolean */
67
fun RawArgument.boolean(): ProcessedArgument<Boolean, Boolean>
68
69
/** Convert to Enum */
70
fun <T : Enum<T>> RawArgument.enum(): ProcessedArgument<T, T>
71
72
/** Convert using choice map */
73
fun <T : Any> RawArgument.choice(choices: Map<String, T>): ProcessedArgument<T, T>
74
75
/** Convert using string choices */
76
fun RawArgument.choice(vararg choices: String): ProcessedArgument<String, String>
77
```
78
79
**Usage Examples:**
80
81
```kotlin
82
class MyCommand : CliktCommand() {
83
// Numeric arguments
84
private val port by argument(name = "PORT", help = "Port number").int()
85
private val ratio by argument(name = "RATIO", help = "Ratio value").double()
86
87
// Enum argument
88
enum class Operation { ADD, SUBTRACT, MULTIPLY, DIVIDE }
89
private val operation by argument(name = "OP", help = "Operation to perform").enum<Operation>()
90
91
// Choice argument
92
private val format by argument(name = "FORMAT", help = "Output format")
93
.choice("json", "xml", "yaml")
94
95
// Custom conversion
96
private val date by argument(name = "DATE", help = "Date in ISO format")
97
.convert { LocalDate.parse(it) }
98
99
override fun run() {
100
echo("Port: $port")
101
echo("Operation: $operation")
102
echo("Format: $format")
103
echo("Date: $date")
104
}
105
}
106
```
107
108
### Value Processing
109
110
Process argument values with optional, multiple, and paired value patterns.
111
112
```kotlin { .api }
113
/** Make argument optional */
114
fun <T : Any> ProcessedArgument<T, T>.optional(): ProcessedArgument<T?, T>
115
116
/** Accept multiple values */
117
fun <T : Any> ProcessedArgument<T, T>.multiple(): ProcessedArgument<List<T>, T>
118
119
/** Convert multiple values to Set */
120
fun <T : Any> ProcessedArgument<List<T>, T>.unique(): ProcessedArgument<Set<T>, T>
121
122
/** Accept exactly 2 values */
123
fun <T : Any> ProcessedArgument<T, T>.pair(): ProcessedArgument<Pair<T, T>, T>
124
125
/** Accept exactly 3 values */
126
fun <T : Any> ProcessedArgument<T, T>.triple(): ProcessedArgument<Triple<T, T, T>, T>
127
128
/** Provide default value */
129
fun <T : Any> ProcessedArgument<T, T>.default(value: T): ArgumentDelegate<T>
130
131
/** Provide lazy default value */
132
fun <T : Any> ProcessedArgument<T, T>.defaultLazy(value: () -> T): ArgumentDelegate<T>
133
```
134
135
**Usage Examples:**
136
137
```kotlin
138
class MyCommand : CliktCommand() {
139
// Optional argument
140
private val inputFile by argument(name = "INPUT", help = "Input file").optional()
141
142
// Multiple arguments
143
private val files by argument(name = "FILES", help = "Files to process").multiple()
144
private val uniqueNames by argument(name = "NAMES", help = "Unique names").multiple().unique()
145
146
// Paired arguments
147
private val coordinates by argument(name = "X Y", help = "X Y coordinates").int().pair()
148
149
// Triple arguments
150
private val rgb by argument(name = "R G B", help = "RGB color values").int().triple()
151
152
// Default value
153
private val outputFile by argument(name = "OUTPUT", help = "Output file")
154
.default("output.txt")
155
156
override fun run() {
157
echo("Input file: $inputFile")
158
echo("Files: $files")
159
echo("Coordinates: $coordinates")
160
echo("RGB: $rgb")
161
echo("Output file: $outputFile")
162
}
163
}
164
```
165
166
### Validation
167
168
Validate argument values with custom validators and built-in checks.
169
170
```kotlin { .api }
171
/**
172
* Validate argument value
173
* @param validator Custom validation function
174
*/
175
fun <AllT, ValueT> ProcessedArgument<AllT, ValueT>.validate(
176
validator: ArgValidator<AllT>
177
): ArgumentDelegate<AllT>
178
179
/**
180
* Check argument value with boolean condition
181
* @param message Error message if check fails
182
* @param validator Boolean check function
183
*/
184
fun <AllT, ValueT> ProcessedArgument<AllT, ValueT>.check(
185
message: String,
186
validator: (AllT) -> Boolean
187
): ArgumentDelegate<AllT>
188
```
189
190
**Usage Examples:**
191
192
```kotlin
193
class MyCommand : CliktCommand() {
194
// Custom validation
195
private val port by argument(name = "PORT", help = "Port number").int().validate {
196
require(it in 1..65535) { "Port must be between 1 and 65535" }
197
}
198
199
// Boolean check
200
private val percentage by argument(name = "PERCENT", help = "Percentage value")
201
.int().check("Must be 0-100") { it in 0..100 }
202
203
// Validate multiple values
204
private val files by argument(name = "FILES", help = "Input files").multiple()
205
.validate { fileList ->
206
require(fileList.isNotEmpty()) { "At least one file must be specified" }
207
}
208
209
override fun run() {
210
echo("Port: $port")
211
echo("Percentage: $percentage")
212
echo("Files: $files")
213
}
214
}
215
```
216
217
### Help Text
218
219
Add or modify help text for arguments.
220
221
```kotlin { .api }
222
/**
223
* Add help text to processed argument
224
* @param help Help text for the argument
225
*/
226
fun <AllT, ValueT> ProcessedArgument<AllT, ValueT>.help(help: String): ProcessedArgument<AllT, ValueT>
227
```
228
229
**Usage Examples:**
230
231
```kotlin
232
class MyCommand : CliktCommand() {
233
private val count by argument()
234
.int()
235
.help("Number of items to process (must be positive)")
236
.check("Must be positive") { it > 0 }
237
238
private val files by argument()
239
.multiple()
240
.help("List of files to process (at least one required)")
241
.validate { require(it.isNotEmpty()) { "At least one file required" } }
242
}
243
```
244
245
## Argument Value Patterns
246
247
### Single Required Argument
248
249
```kotlin
250
class MyCommand : CliktCommand() {
251
private val filename by argument(name = "FILE", help = "Input file")
252
253
override fun run() {
254
echo("Processing file: $filename")
255
}
256
}
257
```
258
259
### Optional Argument
260
261
```kotlin
262
class MyCommand : CliktCommand() {
263
private val outputFile by argument(name = "OUTPUT", help = "Output file").optional()
264
265
override fun run() {
266
val output = outputFile ?: "default.txt"
267
echo("Output file: $output")
268
}
269
}
270
```
271
272
### Multiple Arguments
273
274
```kotlin
275
class MyCommand : CliktCommand() {
276
private val inputFiles by argument(name = "FILES", help = "Input files").multiple()
277
278
override fun run() {
279
if (inputFiles.isEmpty()) {
280
echo("No files specified")
281
} else {
282
echo("Processing ${inputFiles.size} files:")
283
inputFiles.forEach { echo(" - $it") }
284
}
285
}
286
}
287
```
288
289
### Mixed Argument Types
290
291
```kotlin
292
class MyCommand : CliktCommand() {
293
private val operation by argument(name = "OPERATION", help = "Operation to perform")
294
.choice("copy", "move", "delete")
295
private val source by argument(name = "SOURCE", help = "Source file")
296
private val destination by argument(name = "DEST", help = "Destination file").optional()
297
298
override fun run() {
299
when (operation) {
300
"copy", "move" -> {
301
requireNotNull(destination) { "Destination required for $operation" }
302
echo("$operation $source to $destination")
303
}
304
"delete" -> {
305
echo("Deleting $source")
306
}
307
}
308
}
309
}
310
```
311
312
## Argument Interfaces
313
314
```kotlin { .api }
315
/**
316
* Base argument interface
317
*/
318
interface Argument {
319
/** The metavar for this argument */
320
val name: String
321
322
/** The number of values that this argument takes (negative indicates variable number) */
323
val nvalues: Int
324
325
/** If true, an error will be thrown if this argument is not given */
326
val required: Boolean
327
328
/** The description of this argument */
329
fun getArgumentHelp(context: Context): String
330
331
/** Extra information about this argument to pass to the help formatter */
332
val helpTags: Map<String, String>
333
334
/** Optional set of strings to use when the user invokes shell autocomplete */
335
val completionCandidates: CompletionCandidates
336
337
/** Information about this argument for the help output */
338
fun parameterHelp(context: Context): ParameterHelp.Argument?
339
340
/** Called after this command's argv is parsed to transform and store the argument's value */
341
fun finalize(context: Context, values: List<String>)
342
343
/** Called after all parameters have been finalized to perform validation */
344
fun postValidate(context: Context)
345
}
346
347
/**
348
* Argument property delegate interface
349
*/
350
interface ArgumentDelegate<out T> : Argument, ReadOnlyProperty<CliktCommand, T>, PropertyDelegateProvider<CliktCommand, ReadOnlyProperty<CliktCommand, T>> {
351
/** The value for this argument */
352
val value: T
353
354
override fun getValue(thisRef: CliktCommand, property: KProperty<*>): T = value
355
}
356
357
/**
358
* Raw unprocessed argument
359
*/
360
interface RawArgument : Argument
361
362
/**
363
* Argument with processed values
364
*/
365
interface ProcessedArgument<out AllT, out ValueT> : Argument
366
```
367
368
## Type Aliases
369
370
```kotlin { .api }
371
typealias ArgValueConverter<InT, ValueT> = ArgumentTransformContext.(InT) -> ValueT
372
typealias ArgValueTransformer<T> = ArgValueConverter<String, T>
373
typealias ArgValidator<T> = ArgumentTransformContext.(T) -> Unit
374
```