Command Line Subcommands in Logo

Here’s the translation of the Go code example to Java, formatted in Markdown suitable for Hugo:

Our first program will demonstrate how to create command-line subcommands with their own set of flags. This is similar to how tools like git have subcommands such as git commit and git push, each with their own flags.

import java.util.Arrays;

public class CommandLineSubcommands {
    public static void main(String[] args) {
        if (args.length < 1) {
            System.out.println("expected 'foo' or 'bar' subcommands");
            System.exit(1);
        }

        String subcommand = args[0];
        String[] subcommandArgs = Arrays.copyOfRange(args, 1, args.length);

        switch (subcommand) {
            case "foo":
                handleFooCommand(subcommandArgs);
                break;
            case "bar":
                handleBarCommand(subcommandArgs);
                break;
            default:
                System.out.println("expected 'foo' or 'bar' subcommands");
                System.exit(1);
        }
    }

    private static void handleFooCommand(String[] args) {
        boolean enable = false;
        String name = "";
        int i;
        for (i = 0; i < args.length; i++) {
            switch (args[i]) {
                case "-enable":
                    enable = true;
                    break;
                case "-name":
                    if (i + 1 < args.length) {
                        name = args[++i];
                    }
                    break;
                default:
                    break;
            }
        }
        System.out.println("subcommand 'foo'");
        System.out.println("  enable: " + enable);
        System.out.println("  name: " + name);
        System.out.println("  tail: " + Arrays.toString(Arrays.copyOfRange(args, i, args.length)));
    }

    private static void handleBarCommand(String[] args) {
        int level = 0;
        int i;
        for (i = 0; i < args.length; i++) {
            if (args[i].equals("-level") && i + 1 < args.length) {
                level = Integer.parseInt(args[++i]);
            }
        }
        System.out.println("subcommand 'bar'");
        System.out.println("  level: " + level);
        System.out.println("  tail: " + Arrays.toString(Arrays.copyOfRange(args, i, args.length)));
    }
}

To compile and run the program:

$ javac CommandLineSubcommands.java

First, invoke the foo subcommand:

$ java CommandLineSubcommands foo -enable -name joe a1 a2
subcommand 'foo'
  enable: true
  name: joe
  tail: [a1, a2]

Now try bar:

$ java CommandLineSubcommands bar -level 8 a1
subcommand 'bar'
  level: 8
  tail: [a1]

But bar won’t accept foo’s flags:

$ java CommandLineSubcommands bar -enable a1
subcommand 'bar'
  level: 0
  tail: [-enable, a1]

In this Java implementation, we’ve used a simple switch statement to handle different subcommands. For each subcommand, we manually parse the arguments. This approach is more verbose than the Go version, which uses the flag package.

For more complex command-line parsing in Java, you might want to consider using libraries like Apache Commons CLI or JCommander, which provide more robust and feature-rich command-line parsing capabilities.

Next, we’ll look at environment variables, another common way to parameterize programs.