|
Option-- Documentation
2.2Introduction.This library provides a number of classes to help applications with the tedious choir of parsing command line arguments. I made this library as this is a thing that keeps poping up, so I thought: `Why not put that stuff which I did a thousand times over into a library, and save me the grief of doing over and over again?' If you fell the same way, this library is for you.UsageThe use of this library is really easy. First, include the header file optionmm/command_line.hh:#ifndef OPTIONMM_command_line #include <optionmm/command_line.hh> #endif Then, in the main program, construct an instance of the class optionmm::command_line: int main(int argc, char** argv) { optionmm::basic_command_line<> cl("Demonstration of Option--", "1.0", "Copyright (c) 2002 Christian Holm", "", argc, argv); The first argument of the constructor is a tenative title of the application at hand, and the second is the version number (as a string) of the application.
If the project is using Autoconf, the preprocessor macros The third argument is a short line giving the copyright information of the application. This is shown under the application title when the user requests help.
The fourth and fifth arguments are the command line length and array of arguments. These are usually called One can pass an error handler class as a template parameter to the declaration of the optionmm::basic_command_line object. This class should define the appropriate member functions to deal with unknown arguments, and bad option values. See also optionmm::default_error_handler. The next step is to define some options: optionmm::basic_option<int> i_opt('i', "int", "Integer option", 0);
The class optionmm::basic_option is a templated class. The requirements of the type parameter, is that it is assignable, and that it is possible to convert to from a string (
class foo { ... }; std::istream& operator>>(std::istream& i, foo& f) { ... } The template class optionmm::basic_option takes two more optional parameters, both of which should be booleans.
The optional second template parameter specifies whether or not the option needs an argument. An error will be issued if the application user didn't specify an argument for an option that has this template parameter set to
The optional third template parameter specifies whether or not the option can take multiple values (arguments or set count). If this parameter is
The first argument to the constructor is the letter of the short command line option the object corresponds to. If The second argument to the constructor, is the long command line option corresponding to the argument. If this is left blank (the empty string) the object has no corresponding long option. The third argument, is the help string corresponding to the object. This is shown, along with the applicaion synopsis and option list, when the user requests help from the application. The final fourth argument to the constructor, is the default value for the option object. Note that this must be of the value type of the option object.
The library provides
optionmm::int_option I_opt('I', "Int", "Integer option", 42); After defining an option, the optionmm::basic_command_line object needs to know about it:
After registering all the options the application may need, the application must call optionmm::basic_command_line::process to process the actual command line.
if (!cl.process()) return 1;
The member function optionmm::basic_command_line::process returns
Note, that optionmm::basic_command_line::process changes the arguments of
The optionmm::basic_command_line has two automatic options build in: One for showing the help, and one for showing the version number of the application. These are invoked from the command line by
Both of these member functions return After having processed the command line, and testing for errors or the like, the optionmm::basic_option objects now contain the values passed by the application user. The application can then retrive these values by (possibly repeated) calls to optionmm::basic_option::value. For example, one could print the values on standard out:
Error handlingError handling is taken care of the template argument to optionmm::basic_command_line. It's a policy argument. The type should define four public member function, all returning abool :
bool on_onknown(char c,std::string& progname)
bool on_onknown(const char* c,std::string& progname)
template <typename O> bool on_missing_argument(O&, bool is_short,std::string& progname)
template <typename O> bool on_bad_argument(O&, bool is_short,std::string& progname)
All these methods should return Client code can freely define new error handlers to suite the needs of the application. For example: struct my_error_handler { bool on_unknown(char c, const std::string& progname) { throw std::runtime_error("unknown option"); return true; } bool on_unknown(const std::string& str, const std::string& progname) { throw std::runtime_error("unknown option"); return true; } template <typename Option> bool on_missing_argument(Option& o, bool is_short, const std::string& progname) { throw std::runtime_error("missing argument to an option"); return true; } template <typename Option> bool on_bad_argument(Option& o, bool is_short, const std::string& progname) { throw std::runtime_error("bad argument to an option"); return true; } }; ... int main(int argc, char** argv) { optionmm::basic_command_line<my_error_handler> cl(...); ... try { cl.process(); ... } catch (std::exception& e) { std::cerr << e.what() << std::endl; return 1; } return 0; }
Converting the command line arguments to optionvalues.
When the command line arguments enters the application function ( Hence we need to convert the C strings to what ever type a given option wants and stores. This is done via a trait argument to the optionmm::basic_option structure. This trait type should define two member functions:
bool convert (const char *arg, value_type &val) value_type and store it in the second output argument. It should return true on success, and false otherwise.
bool convert (reference val)
!val to val (possibly via a temporary).
The default trait is optionmm::option_trait. The first member function is implemented using std::stringstream s(str); Type t; s >> t; str is some std::string object, and Type is some type for which the extraction operator std::istream operator>>(std::istream& i, Type& t); Hence, defining the above extraction operator for a user type, allows it to be used seemlessly with the Option-- classes, as well as providing a useful tool in I/O operations, all in one go - pretty neat, eh! For example, one could do
struct foo { foo(int f) : _foo(0) {} int _foo; }; std::istream& operator(std::istream& i, foo& f) { return i >> f._foo; } int main(int argc, char** argv) { optionmm::command_line cl("Trying foo", "1.0", "Copyright (c) 2003 Christian Holm", "", argc, argv); optionmm::basic_option<foo> foo_option('f',"foo", "foo option",foo()); cl.add(foo_option); return cl.process(); } Application UsageRunning an application with lines like the above (demo.cc ) with various command lines will give:prompt> ./demo -h Demonstration of Option-- version 1.0 Copyright (c) 2002 Christian Holm Usage: demo [OPTIONS] -h, --help Show this help --version Show version information -i, --int=VALUE Integer option (*) -I, --Int=VALUE Integer option (*) prompt> ./demo --version Demonstration of Option-- version 1.0 Copyright (c) 2002 Christian Holm 0 prompt> ./demo -i 10 -i 42 10 42 prompt> ./demo --int=42 -i50 -I10 -I 19 42 50 prompt> ./demo -f Option `-f' unknown, try `demo --help' Support FeaturesThe library comes with two extra files: an Autoconf macro fileoptionmm.m4 that defines AM_PATH_OPTIONMM , and a SH script optionmm-config that developers can use to get the relevant information into thier build system.The syntax of the Autoconf macro is AM_PATH_OPTIONMM([MINIMUM-VERSION[,ACTION-IF_FOUND[,ACTION-IF-NOT-FOUND]]) OPTIONMM_CPPFLAGS to the relevant preprocessor flags for including <optionmm/command_line.hh>, and OPTIONMM_CONFIG to point to the optionmm-config shell script.
The shell script Usage: optionmm-config [options] --prefix Gives the installation prefix --includedir Gives path to headers --cppflags Gives preprocessor information --version Gives version information --help Gives this help
Finally, there's a man(1) page for CopyrightCopyright (C) 2002 Christian Holm Christensen <cholm@nbi.dk>This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library; if not, write to the Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA See also Licence of the source code.
|