Alpas Console
As you may have already noticed, Alpas comes with a bunch of console commands—make:controller
, make:job
,
and route:list
, to name a few, that assist you in performing some tasks from a command-line. You can run an
Alpas command by prepending it with alpas
.
To see a list of all the Alpas commands as well as a short description for each, you can use alpas list
command.
Custom Commands
If the core Alpas commands are not enough for you, it is easy to create your own. Alpas actually wraps clikt command library in its own thin wrapper. Clikt is very powerful library that makes writing command line interfaces simple and intuitive. It has pretty much everything you would ever need to create powerful command-line interfaces.
Simple Commands
When writing a simple custom command, all you have to do is extend dev.alpas.console.Command
class and
override the run()
method. The Command
constructor receives a number of optional parameters allowing
you to configure your commands the way you want it. This includes help text, summary text etc.
The easiest way to create a command is by using make:command
Alpas command, which will
generate a new command under console/commands
folder.
$ alpas make:command GreetCommand
class GreetCommand : Command(name = "greet", help = "Say hello.") {
private val name by argument()
override fun run() {
success("Hello, $name!")
}
}
After registering this new command, you can call it like so:
$ alpas greet you
> Hello, you!
Generator Commands
Generator commands create some files and folders when invoked. make:command
is actually an example of a
generator command and so is make:controller
.
While you can use a simple command like GreetCommand
above to write a generator
command, you have to wire a few things to get it right.
Instead of extending dev.alpas.console.Command
class, you can extend dev.alpas.console.GeneratorCommand
class to make your life much easier while writing generator commands. While it may not always satisfy
all your needs, most of the time it will. Even if it doesn't, it's a good place to start.
You can pass --generator
or -g
to make:command
command to create a generator type command
for you. Then all you have to do is override one abstract method—populateOutputFile()
.
Let's see an example of how we can write a make:sandwich
generator command that creates a NameOfSandwich.kt
file under sandwiches
folder, creating this folder if it doesn't already exist.
- Create the command itself:
$ alpas make:command MakeSandwich -g
- Modify
console/commands/MakeSandwich.kt
file to:
class MakeSandwich(srcPackage: String) :
GeneratorCommand(srcPackage, name = "make:sandwich", help = "Make a sandwich.") {
override fun populateOutputFile(
filename: String,
actualname: String,
vararg parentDirs: String
): OutputFile {
val dir = "sandwiches"
val file = File(sourceOutputPath(dir, *parentDirs), "${filename.toPascalCase()}.kt")
return OutputFile()
.target(file)
.packageName(makePackageName(dir, *parentDirs))
.stub(
"""
package StubPackageName
class StubClazzName {
fun whoAreYou() {
println("I am a StubClazzName sandwich")
}
}
""".trimIndent()
)
}
override fun onCompleted(outputFile: OutputFile) {
withColors {
echo(green("MakeSandwich CREATED 🙌"))
echo("${brightGreen(outputFile.target.name)}: ${dim(outputFile.target.path)}")
}
}
}
Notice that we have a couple of placeholders in the code—StubPackageName
and StubClazzName
, both
of which will be replaced with proper text automatically when we actually run the command.
- Register this command in
ConsoleKernel
class:
// ...
override fun commands(app: Application): List<Command> {
return listOf(MakeSandwich(app.srcPackage))
}
// ...
- Now we are ready to make ourselves a sandwich or two:
$ alpas make:sandwich club
This command will generate a sandwiches/Club.kt
file.
You can actually create multiple sandwiches in one go:
$ alpas make:sandwich club blt
Registering Custom Commands
After you have created your own commands, you must register them with the app. Otherwise, they won't be available
to you. You can register a command in a number of ways—the easiest one is by overriding commands()
method
in ConsoleKernel
class and returning a list of all your commands.
// ...
override fun commands(app: Application): List<Command> {
return listOf(GreetCommand())
}
// ...
An alternative way is by creating and registering a new Service Provider.
/tip/ Clikt comes with many other powerful features such as
parameters
,flags
,choice options
,input prompts
,password masking
and much more. The best part of it is that the features are properly documented with lots of real-world examples. We highly recommend consulting its documentation when creating your own commands.
Writing Output
When you need to write some output to the console, you can use info
, success
, warning
, and error
methods. Most of these methods respect --quiet
flag and also use proper ANSI colors for their purpose.
// ...
// prints the message in red; does NOT respect --quiet flag
error("Oops! We have a problem.")
// prints the message in green; respects --quiet flag
success("Yay! This is working.")
// ...
If you need more control over coloring the output, you can use withColors()
method. Alpas uses the full-featured
text styling Mordant library for coloring console outputs. This allows you to color the output
anyway you want. Keep in mind that withColors()
won't print anything if --quiet
flag is set.
/power/ Alpas Console is proudly powered by Clikt and Mordant.