[java] How do I parse command line arguments in Java?

What is a good way of parsing command line arguments in Java?

This question is related to java command-line command-line-arguments picocli

The answer is


Someone pointed me to args4j lately which is annotation based. I really like it!


I've used JOpt and found it quite handy: http://jopt-simple.sourceforge.net/

The front page also provides a list of about 8 alternative libraries, check them out and pick the one that most suits your needs.


Argparse4j is best I have found. It mimics Python's argparse libary which is very convenient and powerful.


As one of the comments mentioned earlier (https://github.com/pcj/google-options) would be a good choice to start with.

One thing I want to add-on is:

1) If you run into some parser reflection error, please try use a newer version of the guava. in my case:

maven_jar(
    name = "com_google_guava_guava",
    artifact = "com.google.guava:guava:19.0",
    server = "maven2_server",
)

maven_jar(
    name = "com_github_pcj_google_options",
    artifact = "com.github.pcj:google-options:jar:1.0.0",
    server = "maven2_server",
)

maven_server(
    name = "maven2_server",
    url = "http://central.maven.org/maven2/",
)

2) When running the commandline:

bazel run path/to/your:project -- --var1 something --var2 something -v something

3) When you need the usage help, just type:

bazel run path/to/your:project -- --help

I've used JOpt and found it quite handy: http://jopt-simple.sourceforge.net/

The front page also provides a list of about 8 alternative libraries, check them out and pick the one that most suits your needs.


Yeap.

I think you're looking for something like this: http://commons.apache.org/cli

The Apache Commons CLI library provides an API for processing command line interfaces.


Take a look at the Commons CLI project, lots of good stuff in there.


If you want something lightweight (jar size ~ 20 kb) and simple to use, you can try argument-parser. It can be used in most of the use cases, supports specifying arrays in the argument and has no dependency on any other library. It works for Java 1.5 or above. Below excerpt shows an example on how to use it:

public static void main(String[] args) {
    String usage = "--day|-d day --mon|-m month [--year|-y year][--dir|-ds directoriesToSearch]";
    ArgumentParser argParser = new ArgumentParser(usage, InputData.class);
    InputData inputData = (InputData) argParser.parse(args);
    showData(inputData);

    new StatsGenerator().generateStats(inputData);
}

More examples can be found here


Maybe these

  • JArgs command line option parsing suite for Java - this tiny project provides a convenient, compact, pre-packaged and comprehensively documented suite of command line option parsers for the use of Java programmers. Initially, parsing compatible with GNU-style 'getopt' is provided.

  • ritopt, The Ultimate Options Parser for Java - Although, several command line option standards have been preposed, ritopt follows the conventions prescribed in the opt package.


I know most people here are going to find 10 million reasons why they dislike my way, but nevermind. I like to keep things simple, so I just separate the key from the value using a '=' and store them in a HashMap like this:

Map<String, String> argsMap = new HashMap<>();
for (String arg: args) {
    String[] parts = arg.split("=");
    argsMap.put(parts[0], parts[1]);
} 

You could always maintain a list with the arguments you are expecting, to help the user in case he forgot an argument or used a wrong one... However, if you want too many features this solution is not for you anyway.


This is Google's command line parsing library open-sourced as part of the Bazel project. Personally I think it's the best one out there, and far easier than Apache CLI.

https://github.com/pcj/google-options

Installation

Bazel

maven_jar(
    name = "com_github_pcj_google_options",
    artifact = "com.github.pcj:google-options:jar:1.0.0",
    sha1 = "85d54fe6771e5ff0d54827b0a3315c3e12fdd0c7",
)

Gradle

dependencies {
  compile 'com.github.pcj:google-options:1.0.0'
}

Maven

<dependency>
  <groupId>com.github.pcj</groupId>
  <artifactId>google-options</artifactId>
  <version>1.0.0</version>
</dependency>

Usage

Create a class that extends OptionsBase and defines your @Option(s).

package example;

import com.google.devtools.common.options.Option;
import com.google.devtools.common.options.OptionsBase;

import java.util.List;

/**
 * Command-line options definition for example server.
 */
public class ServerOptions extends OptionsBase {

  @Option(
      name = "help",
      abbrev = 'h',
      help = "Prints usage info.",
      defaultValue = "true"
    )
  public boolean help;

  @Option(
      name = "host",
      abbrev = 'o',
      help = "The server host.",
      category = "startup",
      defaultValue = ""
  )
  public String host;

  @Option(
    name = "port",
    abbrev = 'p',
    help = "The server port.",
    category = "startup",
    defaultValue = "8080"
    )
    public int port;

  @Option(
    name = "dir",
    abbrev = 'd',
    help = "Name of directory to serve static files.",
    category = "startup",
    allowMultiple = true,
    defaultValue = ""
    )
    public List<String> dirs;

}

Parse the arguments and use them.

package example;

import com.google.devtools.common.options.OptionsParser;
import java.util.Collections;

public class Server {

  public static void main(String[] args) {
    OptionsParser parser = OptionsParser.newOptionsParser(ServerOptions.class);
    parser.parseAndExitUponError(args);
    ServerOptions options = parser.getOptions(ServerOptions.class);
    if (options.host.isEmpty() || options.port < 0 || options.dirs.isEmpty()) {
      printUsage(parser);
      return;
    }

    System.out.format("Starting server at %s:%d...\n", options.host, options.port);
    for (String dirname : options.dirs) {
      System.out.format("\\--> Serving static files at <%s>\n", dirname);
    }
  }

  private static void printUsage(OptionsParser parser) {
    System.out.println("Usage: java -jar server.jar OPTIONS");
    System.out.println(parser.describeOptions(Collections.<String, String>emptyMap(),
                                              OptionsParser.HelpVerbosity.LONG));
  }

}

https://github.com/pcj/google-options


Maybe these

  • JArgs command line option parsing suite for Java - this tiny project provides a convenient, compact, pre-packaged and comprehensively documented suite of command line option parsers for the use of Java programmers. Initially, parsing compatible with GNU-style 'getopt' is provided.

  • ritopt, The Ultimate Options Parser for Java - Although, several command line option standards have been preposed, ritopt follows the conventions prescribed in the opt package.


I wrote another one: http://argparse4j.sourceforge.net/

Argparse4j is a command line argument parser library for Java, based on Python's argparse.


If you want something lightweight (jar size ~ 20 kb) and simple to use, you can try argument-parser. It can be used in most of the use cases, supports specifying arrays in the argument and has no dependency on any other library. It works for Java 1.5 or above. Below excerpt shows an example on how to use it:

public static void main(String[] args) {
    String usage = "--day|-d day --mon|-m month [--year|-y year][--dir|-ds directoriesToSearch]";
    ArgumentParser argParser = new ArgumentParser(usage, InputData.class);
    InputData inputData = (InputData) argParser.parse(args);
    showData(inputData);

    new StatsGenerator().generateStats(inputData);
}

More examples can be found here


Take a look at the Commons CLI project, lots of good stuff in there.


I want to show you my implementation: ReadyCLI

Advantages:

  • for lazy programmers: a very small number of classes to learn, just see the two small examples on the README in the repository and you are already at 90% of learning; just start coding your CLI/Parser without any other knowledge; ReadyCLI allows coding CLIs in the most natural way;
  • it is designed with Developer Experience in mind; it largely uses the Builder design pattern and functional interfaces for Lambda Expressions, to allow a very quick coding;
  • it supports Options, Flags and Sub-Commands;
  • it allows to parse arguments from command-line and to build more complex and interactive CLIs;
  • a CLI can be started on Standard I/O just as easily as on any other I/O interface, such as sockets;
  • it gives great support for documentation of commands.

I developed this project as I needed new features (options, flag, sub-commands) and that could be used in the simplest possible way in my projects.


I've used JOpt and found it quite handy: http://jopt-simple.sourceforge.net/

The front page also provides a list of about 8 alternative libraries, check them out and pick the one that most suits your needs.



I've used JOpt and found it quite handy: http://jopt-simple.sourceforge.net/

The front page also provides a list of about 8 alternative libraries, check them out and pick the one that most suits your needs.



Take a look at the Commons CLI project, lots of good stuff in there.


If you are already using Spring Boot, argument parsing comes out of the box.

If you want to run something after startup, implement the ApplicationRunner interface:

@SpringBootApplication
public class Application implements ApplicationRunner {

  public static void main(String[] args) {
    SpringApplication.run(Application.class, args);
  }

  @Override
  public void run(ApplicationArguments args) {
    args.containsOption("my-flag-option"); // test if --my-flag-option was set
    args.getOptionValues("my-option");     // returns values of --my-option=value1 --my-option=value2 
    args.getOptionNames();                 // returns a list of all available options
    // do something with your args
  }
}

Your run method will be invoked after the context has started up successfully.

If you need access to the arguments before you fire up your application context, you can just simply parse the application arguments manually:

@SpringBootApplication
public class Application implements ApplicationRunner {

  public static void main(String[] args) {
    ApplicationArguments arguments = new DefaultApplicationArguments(args);
    // do whatever you like with your arguments
    // see above ...
    SpringApplication.run(Application.class, args);
  }

}

And finally, if you need access to your arguments in a bean, just inject the ApplicationArguments:

@Component
public class MyBean {

   @Autowired
   private ApplicationArguments arguments;

   // ...
}

Take a look at the more recent JCommander.

I created it. I’m happy to receive questions or feature requests.


For Spring users, we should mention also https://docs.spring.io/spring/docs/current/javadoc-api/org/springframework/core/env/SimpleCommandLinePropertySource.html and his twin brother https://docs.spring.io/spring/docs/current/javadoc-api/org/springframework/core/env/JOptCommandLinePropertySource.html (JOpt implementation of the same functionality). The advantage in Spring is that you can directly bind the command line arguments to attributes, there is an example here https://docs.spring.io/spring/docs/current/javadoc-api/org/springframework/core/env/CommandLinePropertySource.html


Maybe these

  • JArgs command line option parsing suite for Java - this tiny project provides a convenient, compact, pre-packaged and comprehensively documented suite of command line option parsers for the use of Java programmers. Initially, parsing compatible with GNU-style 'getopt' is provided.

  • ritopt, The Ultimate Options Parser for Java - Although, several command line option standards have been preposed, ritopt follows the conventions prescribed in the opt package.


As one of the comments mentioned earlier (https://github.com/pcj/google-options) would be a good choice to start with.

One thing I want to add-on is:

1) If you run into some parser reflection error, please try use a newer version of the guava. in my case:

maven_jar(
    name = "com_google_guava_guava",
    artifact = "com.google.guava:guava:19.0",
    server = "maven2_server",
)

maven_jar(
    name = "com_github_pcj_google_options",
    artifact = "com.github.pcj:google-options:jar:1.0.0",
    server = "maven2_server",
)

maven_server(
    name = "maven2_server",
    url = "http://central.maven.org/maven2/",
)

2) When running the commandline:

bazel run path/to/your:project -- --var1 something --var2 something -v something

3) When you need the usage help, just type:

bazel run path/to/your:project -- --help

Yeap.

I think you're looking for something like this: http://commons.apache.org/cli

The Apache Commons CLI library provides an API for processing command line interfaces.


It is 2021, time to do better than Commons CLI... :-)

Should you build your own Java command line parser, or use a library?

Many small utility-like applications probably roll their own command line parsing to avoid the additional external dependency. picocli may be an interesting alternative.

Picocli is a modern library and framework for building powerful, user-friendly, GraalVM-enabled command line apps with ease. It lives in 1 source file so apps can include it as source to avoid adding a dependency.

It supports colors, autocompletion, subcommands, and more. Written in Java, usable from Groovy, Kotlin, Scala, etc.

Minimal usage help with ANSI colors

Features:

  • Annotation based: declarative, avoids duplication and expresses programmer intent
  • Convenient: parse user input and run your business logic with one line of code
  • Strongly typed everything - command line options as well as positional parameters
  • POSIX clustered short options (<command> -xvfInputFile as well as <command> -x -v -f InputFile)
  • Fine-grained control: an arity model that allows a minimum, maximum and variable number of parameters, e.g, "1..*", "3..5"
  • Subcommands (can be nested to arbitrary depth)
  • Feature-rich: composable arg groups, splitting quoted args, repeatable subcommands, and many more
  • User-friendly: usage help message uses colors to contrast important elements like option names from the rest of the usage help to reduce the cognitive load on the user
  • Distribute your app as a GraalVM native image
  • Works with Java 5 and higher
  • Extensive and meticulous documentation

The usage help message is easy to customize with annotations (without programming). For example:

Extended usage help message (source)

I couldn't resist adding one more screenshot to show what usage help messages are possible. Usage help is the face of your application, so be creative and have fun!

picocli demo

Disclaimer: I created picocli. Feedback or questions very welcome.


Maybe these

  • JArgs command line option parsing suite for Java - this tiny project provides a convenient, compact, pre-packaged and comprehensively documented suite of command line option parsers for the use of Java programmers. Initially, parsing compatible with GNU-style 'getopt' is provided.

  • ritopt, The Ultimate Options Parser for Java - Although, several command line option standards have been preposed, ritopt follows the conventions prescribed in the opt package.


I want to show you my implementation: ReadyCLI

Advantages:

  • for lazy programmers: a very small number of classes to learn, just see the two small examples on the README in the repository and you are already at 90% of learning; just start coding your CLI/Parser without any other knowledge; ReadyCLI allows coding CLIs in the most natural way;
  • it is designed with Developer Experience in mind; it largely uses the Builder design pattern and functional interfaces for Lambda Expressions, to allow a very quick coding;
  • it supports Options, Flags and Sub-Commands;
  • it allows to parse arguments from command-line and to build more complex and interactive CLIs;
  • a CLI can be started on Standard I/O just as easily as on any other I/O interface, such as sockets;
  • it gives great support for documentation of commands.

I developed this project as I needed new features (options, flag, sub-commands) and that could be used in the simplest possible way in my projects.


Argparse4j is best I have found. It mimics Python's argparse libary which is very convenient and powerful.


Yeap.

I think you're looking for something like this: http://commons.apache.org/cli

The Apache Commons CLI library provides an API for processing command line interfaces.



It is 2021, time to do better than Commons CLI... :-)

Should you build your own Java command line parser, or use a library?

Many small utility-like applications probably roll their own command line parsing to avoid the additional external dependency. picocli may be an interesting alternative.

Picocli is a modern library and framework for building powerful, user-friendly, GraalVM-enabled command line apps with ease. It lives in 1 source file so apps can include it as source to avoid adding a dependency.

It supports colors, autocompletion, subcommands, and more. Written in Java, usable from Groovy, Kotlin, Scala, etc.

Minimal usage help with ANSI colors

Features:

  • Annotation based: declarative, avoids duplication and expresses programmer intent
  • Convenient: parse user input and run your business logic with one line of code
  • Strongly typed everything - command line options as well as positional parameters
  • POSIX clustered short options (<command> -xvfInputFile as well as <command> -x -v -f InputFile)
  • Fine-grained control: an arity model that allows a minimum, maximum and variable number of parameters, e.g, "1..*", "3..5"
  • Subcommands (can be nested to arbitrary depth)
  • Feature-rich: composable arg groups, splitting quoted args, repeatable subcommands, and many more
  • User-friendly: usage help message uses colors to contrast important elements like option names from the rest of the usage help to reduce the cognitive load on the user
  • Distribute your app as a GraalVM native image
  • Works with Java 5 and higher
  • Extensive and meticulous documentation

The usage help message is easy to customize with annotations (without programming). For example:

Extended usage help message (source)

I couldn't resist adding one more screenshot to show what usage help messages are possible. Usage help is the face of your application, so be creative and have fun!

picocli demo

Disclaimer: I created picocli. Feedback or questions very welcome.


Take a look at the Commons CLI project, lots of good stuff in there.


This is Google's command line parsing library open-sourced as part of the Bazel project. Personally I think it's the best one out there, and far easier than Apache CLI.

https://github.com/pcj/google-options

Installation

Bazel

maven_jar(
    name = "com_github_pcj_google_options",
    artifact = "com.github.pcj:google-options:jar:1.0.0",
    sha1 = "85d54fe6771e5ff0d54827b0a3315c3e12fdd0c7",
)

Gradle

dependencies {
  compile 'com.github.pcj:google-options:1.0.0'
}

Maven

<dependency>
  <groupId>com.github.pcj</groupId>
  <artifactId>google-options</artifactId>
  <version>1.0.0</version>
</dependency>

Usage

Create a class that extends OptionsBase and defines your @Option(s).

package example;

import com.google.devtools.common.options.Option;
import com.google.devtools.common.options.OptionsBase;

import java.util.List;

/**
 * Command-line options definition for example server.
 */
public class ServerOptions extends OptionsBase {

  @Option(
      name = "help",
      abbrev = 'h',
      help = "Prints usage info.",
      defaultValue = "true"
    )
  public boolean help;

  @Option(
      name = "host",
      abbrev = 'o',
      help = "The server host.",
      category = "startup",
      defaultValue = ""
  )
  public String host;

  @Option(
    name = "port",
    abbrev = 'p',
    help = "The server port.",
    category = "startup",
    defaultValue = "8080"
    )
    public int port;

  @Option(
    name = "dir",
    abbrev = 'd',
    help = "Name of directory to serve static files.",
    category = "startup",
    allowMultiple = true,
    defaultValue = ""
    )
    public List<String> dirs;

}

Parse the arguments and use them.

package example;

import com.google.devtools.common.options.OptionsParser;
import java.util.Collections;

public class Server {

  public static void main(String[] args) {
    OptionsParser parser = OptionsParser.newOptionsParser(ServerOptions.class);
    parser.parseAndExitUponError(args);
    ServerOptions options = parser.getOptions(ServerOptions.class);
    if (options.host.isEmpty() || options.port < 0 || options.dirs.isEmpty()) {
      printUsage(parser);
      return;
    }

    System.out.format("Starting server at %s:%d...\n", options.host, options.port);
    for (String dirname : options.dirs) {
      System.out.format("\\--> Serving static files at <%s>\n", dirname);
    }
  }

  private static void printUsage(OptionsParser parser) {
    System.out.println("Usage: java -jar server.jar OPTIONS");
    System.out.println(parser.describeOptions(Collections.<String, String>emptyMap(),
                                              OptionsParser.HelpVerbosity.LONG));
  }

}

https://github.com/pcj/google-options


airline @ Github looks good. It is based on annotation and is trying to emulate Git command line structures.



Someone pointed me to args4j lately which is annotation based. I really like it!


Take a look at the more recent JCommander.

I created it. I’m happy to receive questions or feature requests.


For Spring users, we should mention also https://docs.spring.io/spring/docs/current/javadoc-api/org/springframework/core/env/SimpleCommandLinePropertySource.html and his twin brother https://docs.spring.io/spring/docs/current/javadoc-api/org/springframework/core/env/JOptCommandLinePropertySource.html (JOpt implementation of the same functionality). The advantage in Spring is that you can directly bind the command line arguments to attributes, there is an example here https://docs.spring.io/spring/docs/current/javadoc-api/org/springframework/core/env/CommandLinePropertySource.html


If you are already using Spring Boot, argument parsing comes out of the box.

If you want to run something after startup, implement the ApplicationRunner interface:

@SpringBootApplication
public class Application implements ApplicationRunner {

  public static void main(String[] args) {
    SpringApplication.run(Application.class, args);
  }

  @Override
  public void run(ApplicationArguments args) {
    args.containsOption("my-flag-option"); // test if --my-flag-option was set
    args.getOptionValues("my-option");     // returns values of --my-option=value1 --my-option=value2 
    args.getOptionNames();                 // returns a list of all available options
    // do something with your args
  }
}

Your run method will be invoked after the context has started up successfully.

If you need access to the arguments before you fire up your application context, you can just simply parse the application arguments manually:

@SpringBootApplication
public class Application implements ApplicationRunner {

  public static void main(String[] args) {
    ApplicationArguments arguments = new DefaultApplicationArguments(args);
    // do whatever you like with your arguments
    // see above ...
    SpringApplication.run(Application.class, args);
  }

}

And finally, if you need access to your arguments in a bean, just inject the ApplicationArguments:

@Component
public class MyBean {

   @Autowired
   private ApplicationArguments arguments;

   // ...
}

I wrote another one: http://argparse4j.sourceforge.net/

Argparse4j is a command line argument parser library for Java, based on Python's argparse.


Someone pointed me to args4j lately which is annotation based. I really like it!


Someone pointed me to args4j lately which is annotation based. I really like it!



I know most people here are going to find 10 million reasons why they dislike my way, but nevermind. I like to keep things simple, so I just separate the key from the value using a '=' and store them in a HashMap like this:

Map<String, String> argsMap = new HashMap<>();
for (String arg: args) {
    String[] parts = arg.split("=");
    argsMap.put(parts[0], parts[1]);
} 

You could always maintain a list with the arguments you are expecting, to help the user in case he forgot an argument or used a wrong one... However, if you want too many features this solution is not for you anyway.


airline @ Github looks good. It is based on annotation and is trying to emulate Git command line structures.



Examples related to java

Under what circumstances can I call findViewById with an Options Menu / Action Bar item? How much should a function trust another function How to implement a simple scenario the OO way Two constructors How do I get some variable from another class in Java? this in equals method How to split a string in two and store it in a field How to do perspective fixing? String index out of range: 4 My eclipse won't open, i download the bundle pack it keeps saying error log

Examples related to command-line

Git is not working after macOS Update (xcrun: error: invalid active developer path (/Library/Developer/CommandLineTools) Flutter command not found Angular - ng: command not found how to run python files in windows command prompt? How to run .NET Core console app from the command line Copy Paste in Bash on Ubuntu on Windows How to find which version of TensorFlow is installed in my system? How to install JQ on Mac by command-line? Python not working in the command line of git bash Run function in script from command line (Node JS)

Examples related to command-line-arguments

How to pass arguments to Shell Script through docker run How can I pass variable to ansible playbook in the command line? Use Robocopy to copy only changed files? mkdir's "-p" option What is Robocopy's "restartable" option? How do you run a .exe with parameters using vba's shell()? Bash command line and input limit Check number of arguments passed to a Bash script Parsing boolean values with argparse Import SQL file by command line in Windows 7

Examples related to picocli

How do I parse command line arguments in Java?