package cmdlang
Module Cmdlang.CommandSource
Declarative Command-line Parsing for OCaml.
Cmdlang is a library for creating command-line parsers in OCaml. Implemented as an OCaml EDSL, its declarative specification language lives at the intersection of other well-established similar libraries.
Cmdlang exposes a single module named Command, which contains the entire API to declare command line parsers.
Assuming Cmdlang.Command to be available in your scope as Command, the following is a minimalist command that does nothing:
let cmd : unit Command.t =
Command.make
~summary:"A command that does nothing."
(let open Command.Std in
let+ () = Arg.return () in
())
;;To get started with this API refers to this tutorial from cmdlang's documentation.
Terminology
The terminology used by cmdlang is inspired by climate.
Arguments
An Argument is a distinct piece of information passed to the program on the command line. For example, in the command make -td --jobs 4 all, there are 4 arguments: -t, -d, --jobs 4, and all. Arguments are declared using the module Arg.
Arguments can be either positional or named:
Positional arguments
Positional arguments are identified by their position (0-based) in the argument list rather than by name.
Named arguments
Named arguments can be either short or long:
- Short named arguments begin with a single
-followed by a single non-character, such as-l. - Long named arguments begin with
--followed by several non-characters, such as--jobs.
Parameters
A Parameter is a single value that is attached to a named argument on the command line. For example, in make --jobs 4, "jobs" is the argument name and 4 is its parameter. Parameters are declared using the module Param.
docv
The term docv is a convention in the API to denote the string that will be printed in the help messages in place of the value that is actually expected. This applies to both positional arguments and parameters of named arguments. For example, in the help message for a named argument, you might see --flag VALUE, where "VALUE" is the docv representing the expected parameter. Similarly, for positional arguments, you might see usage like ./main.exe VAL VAL, where "VAL" is the docv representing the expected positional argument. The name docv stands for "documentation value" and was inspired by cmdliner.
Supported Command Line Syntax
Not all syntaxes are supported by all backends, so you should check the documentation of the targeted backend for more information, and choose your execution engine according to your preferences.
For example, some backends may support combining a collection of short named arguments together with a single leading - followed by each short argument name (in which case ls -la is an alternative way of writing ls -l -a).
As another example, we list here the different ways supported by climate of passing a parameter to a named argument on the command line:
make --jobs=4 (* long name with equals sign *) make --jobs 4 (* long name space delimited *) make -j 4 (* short name space delimited *) make -j4 (* short name without space *)
Utils
A type to represent lists that are statically known to be non-empty.
Interfaces
These interfaces are convenient to use with the Param module, so you can apply its helpers to custom modules. For example, if your module My_enum implements the Enumerated_stringable interface, then you can build a parser for it with:
Param.enumerated (module My_enum)An interface for types that have a finite number of inhabitants that all have a canonical string representation.
An interface for types that can be parsed from strings, when parsing never results in failures.
An interface for types that can be parsed from strings, with the possibility of parsing failures.
Building Parameters
Refer to the Parameters terminology.
Building Arguments
Building Commands
Create a command with the given argument specification and summary.
readmeis an optional function that returns a detailed description of the command.summaryis a short description of what the command does.- The argument specification is provided by an
'a Arg.t.
Example:
let hello_cmd =
Command.make
~summary:"Prints [\"Hello, world!\"]."
~readme:(fun () ->
"This would usually be a longer description of the command.\n\
It can be written on multiple lines.")
(let open Command.Std in
let+ () = Arg.return () in
print_endline "Hello, world!")
;;val group :
?default:'a Arg.t ->
?readme:(unit -> string) ->
summary:string ->
(string * 'a t) list ->
'a tCreate a group of subcommands with a common summary.
defaultis an optional default command to run if no subcommand is specified.readmeis an optional function that returns a detailed description of the command group.summaryis a short description of what the command group does.- The subcommands are provided as a list of (name, command) pairs.
Example of a group with no default command:
let cmd_group =
Command.group
~summary:"A group of related commands."
[ "hello", hello_cmd; "goodbye", goodbye_cmd ]
;;Each command in the group may itself be a group, allowing for hierarchical trees of commands.
Applicative operations
These operations are used to build command-line parsers in a declarative style.
For use with the ( let+ ) style.
Let operators
For use with the ( let+ ) style:
let cmd : unit Command.t =
Command.make
~summary:"A command that does nothing."
(let open Command.Std in
let+ () = Arg.return () in
())
;;Ppx_let
For use with the ( let%map_open.Command ) style:
let cmd : unit Command.t =
Command.make
~summary:"A command that does nothing."
(let%map_open.Command () = Arg.return () in
())
;;Private
This module is exported to be used by libraries with strong ties to cmdlang. Its signature may change in breaking ways at any time without prior notice, and outside of the guidelines set by semver.