Command creation & execution - kvnxiao/kommandant GitHub Wiki
This page will explain how command and subcommand creation and execution works.
Registering and activating commands requires an instance of the Kommandant
class:
val kommandant = Kommandant()
A simple command in Kotlin which returns a string value can be defined and added to the command bank immediately like so (using a builder):
kommandant.addCommand(CommandBuilder<String>("kotlintest").withPrefix("-").withAliases("printargs").build(execute {
context, opt ->
if (context.hasArgs()) {
context.args!!
} else {
"No arguments provided."
}
}))
All commands require a uniqueName
identifier string when registering in the bank, and no two commands may have the same unique name. Additionally, a command will fail to add if its prefix and aliases clashes with that of another command's.
This command has a uniqueName
of "kotlintest"
and uses the prefix -
with the alias printargs
. This command can be executed by providing a single string input to Kommandant#process
:
val result1 = kommandant.process<String>("-printargs")
// result1.success == true, meaning the command was successfully found in the command bank and activated.
println(result1.result!!) // will print "No arguments provided."
val result2 = kommandant.process<String>("-printargs abc123 hello world!")
// result2.success == true, meaning the command was successfully found in the command bank and activated.
println(result2.result!!) // will print "abc123 hello world!"
Subcommands are specific arguments of parent command with its own execution logic. Rather than using conditional logic on a command's arguments, subcommands may be added instead to perform a specific task.
For example, a command -printargs
may have a subcommand countspaces
which counts the number of spaces in the following arguments provided after the subcommand. Additionally, subcommands may have their own subcommands; the hierarchy can run as deep as you need it to be!
NOTE: By default, if a subcommand is called, all of its parent command functions are suppressed, but this can be changed to enable both the parent and subcommand executing at once by setting the command property execWithSubCommands
to true
.
kommandant.addCommand(CommandBuilder<String>("kotlintest").withPrefix("-").withAliases("printargs").build(execute {
context, opt ->
if (context.hasArgs()) {
context.args!!
} else {
"No arguments provided."
}
}).addSubcommand(CommandBuilder<Int>("kotlintest_countspaces").withAliases("countspaces").build(execute {
context, opt ->
if (context.hasArgs()) {
context.args!!.count({ it == ' ' }) // count number of spaces in the provided arguments
} else {
0
}
}))
val mainResult = kommandant.process<String>("-printargs abc123 hello world!")
println(mainResult.result!!) // will print "abc123 hello world!"
val subResult = kommandant.process<Int>("-printargs countspaces abc123 hello world!")
println(subResult.result!!) // will print 2
As stated in the wiki home page, there are three ways of creating commands:
-
ICommand
constructor CommandBuilder
-
CommandAnn
annotation processing