Create command line applications with a config file

June 10, 2016 - Jan Pieter Bruins Slot

In this tutorial we’ll be using engage to create a cli application by only using a json config file. Enage was created because at FuelUp we have several bash scripts placed in different folders in the project. I wanted a way to bundle them so that I didn’t have to remember the location of these scripts. Additionally when developing it isn’t uncommon to have to type several commands after another, and it would be nice to have them easy accessible. And I really wanted to have the command fuel up to start the platform from the commandline. :)

So, the solution was to create a cli application and I wanted to do this in Go. However, adding new commands to the application would require co-workers to know Go, update the code and recreate the binaries. I wanted something simpler, just a json file that was easy to edit and would reference the scripts and commands, that would make up the cli application.

This is where ’engage’ comes in, and in the following sections I’ll explain how to install, configure and use it. So that you’ll be able to create your own cli application.

In short, it’ll make this:

{
    "name": "riker",
    "usage": "our first engage app",
    "authors": [
        {
            "name": "William T. Riker",
            "email": "w.t.riker@starfleet.org"
        }
    ],
    "version": "1.0",
    "commands": [
        {
            "name": "say",
            "action": "echo",
            "usage": "use `say` to relay a message"
        }
    ]
}

Into this:

$ riker

NAME:
   riker - our first enage app

USAGE:
   riker [global options] command [command options] [arguments...]
   
VERSION:
   1.0
   
AUTHOR(S):
   William T. Riker <w.t.riker@starfleet.org> 
   
COMMANDS:
    say use `say` to relay a message

GLOBAL OPTIONS:
   --help, -h           show help
   --version, -v        print the version

Installation

First make sure you have the Go Programming Language installed on your system. Then clone the ’engage’ project on your system.

$ git clone git@github.com:erroneousboat/engage.git

Now think of a name you want to give your new cli application. In this example we’ll use riker. Move to the project folder and execute the following command:

$ make APP_NAME=riker

This will place your new application in the bin/ folder. Now lets create our config file and some commands.

Configuration

Create a engage.json file next to your application and add the following lines to it:

{
    "name": "riker",
    "usage": "our first engage app",
    "authors": [
        {
            "name": "William T. Riker",
            "email": "w.t.riker@starfleet.org"
        }
    ],
    "version": "1.0",
    "commands": [
        {
            "name": "say",
            "action": "echo",
            "usage": "use `say` to relay a message"
        }
    ]
}

Now, let’s test it out. Direct yourself to the bin/ folder, which should now contain the riker binary and the engage.json file.

$ ./riker

NAME:
   riker - our first enage app

USAGE:
   riker [global options] command [command options] [arguments...]
   
VERSION:
   1.0
   
AUTHOR(S):
   William T. Riker <w.t.riker@starfleet.org> 
   
COMMANDS:
    say use `say` to relay a message

GLOBAL OPTIONS:
   --help, -h           show help
   --version, -v        print the version

Now let’s try to use our say command.

$ ./riker say "What's a knock-out like you doing in a computer-generated gin joint like this?"
What's a knock-out like you doing in a computer-generated gin joint like this?

Awesome! Now we’ll create a command that will execute two scripts. We’ll create two simple scripts to show that we’re able to chain commands with the use of a semicolon ;.

Create the following files: script1.sh and script2.sh. And add the following lines:

# script1.sh
#!/bin/bash
echo to boldy go where

# script2.sh
#!/bin/bash
echo no man has gone before

Make them executable:

$ sudo chmod +x script1.sh script2.sh

Now update the engage.json:

{
    "name": "riker",
    "usage": "our first engage app",
    "authors": [
        {
            "name": "William T. Riker",
            "email": "w.t.riker@starfleet.org"
        }
    ],
    "version": "1.0",
    "commands": [
        {
            "name": "say",
            "action": "echo",
            "usage": "use `say` to relay a message"
        },
        {
            "name": "tagline",
            "action": "./script1.sh; ./script2.sh",
            "usage": "space the final frontier"
        }
    ]
}

This should give us the following:

$ ./riker tagline
to boldy go where
no man has gone before

We can also use commandline arguments with our cli app. Create a file script3.sh and the lines:

# script3.sh
ARG="$1"
echo Hello ${ARG}

Now update the engage.json:

{
    "name": "riker",
    "usage": "our first engage app",
    "authors": [
        {
            "name": "William T. Riker",
            "email": "w.t.riker@starfleet.org"
        }
    ],
    "version": "1.0",
    "commands": [
        {
            "name": "say",
            "action": "echo",
            "usage": "use `say` to relay a message"
        },
        {
            "name": "tagline",
            "action": "./script1.sh; ./script2.sh",
            "usage": "space the final frontier"
        },
        {
            "name": "greetings",
            "action": "./script3.sh",
            "usage": "use to greet someone"
        }
    ]
}

And, now you can do the following:

$ riker greetings World
Hello World

$ riker greetings Picard
Hello Picard

Usage

Now, that we have created our cli app it would be nice to have it run directly from the commandline, instead of referencing the location of the binary on the filesystem.

When you want to create a cli app for a project for instance, then you might want to place the cli app in that project together with its engage.json and create a symlink in one of the following locations.

Folder Access
$HOME/bin yourself only
/usr/local/bin you and other local users
/usr/local/sbin root only

And, to create the symlink:

$ ln -s ~/location/of/app $HOME/bin

Now you’ll be able to access your cli app directly from the commandline!

Conclusion

In this post I’ve shown you have you can create your own cli application with a config file. If you like to know more about ’engage’, have feedback/suggestions want to follow its development. Then visit the project page on github