Console: Begin implementation of 'Variable' commands
[senf.git] / Console / Mainpage.dox
1 // $Id$
2 //
3 // Copyright (C) 2008 
4 // Fraunhofer Institute for Open Communication Systems (FOKUS)
5 // Competence Center NETwork research (NET), St. Augustin, GERMANY
6 //     Stefan Bund <g0dil@berlios.de>
7 //
8 // This program is free software; you can redistribute it and/or modify
9 // it under the terms of the GNU General Public License as published by
10 // the Free Software Foundation; either version 2 of the License, or
11 // (at your option) any later version.
12 //
13 // This program is distributed in the hope that it will be useful,
14 // but WITHOUT ANY WARRANTY; without even the implied warranty of
15 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16 // GNU General Public License for more details.
17 //
18 // You should have received a copy of the GNU General Public License
19 // along with this program; if not, write to the
20 // Free Software Foundation, Inc.,
21 // 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
22
23 /** \mainpage The Configuration and Runtime Control Library
24
25     The Console library implements a runtime interactive (network) console which allows to
26     configure, control and manipulate a running application in any way. Additionally this library
27     provides support for configuration files and command line parsing which can be used with or
28     without the network console.
29
30     \autotoc
31
32     \section console_intro Introduction
33
34     There are three parts to the Config/console library:
35
36     \li The console/config library is based on a \link node_tree tree of console/config
37         nodes. \endlink
38     \li Besides directories, the node contains command nodes. Commands are based on \link
39         console_commands variables or callbacks.\endlink
40     \li The console/config library is utilized by writing configuration files or interactive
41         commands in \link console_parser the console/config language.\endlink
42
43     The node tree works like a directory structure. Commands are entered into this directory
44     structure and can be called passing arbitrary arguments. Configuration parameters are just
45     commands which set their respective parameter, however the library allows commands to do much
46     more than just that.
47
48     \section console_example Example
49
50     The following example shows a \e very short summary on how to integrate the config/console
51     library. See above links for more:
52
53     \code
54     // Define callback function.
55     void mycommand(std::ostream & os, int foo, int bar)
56     {
57         // ...
58         os << "!! Important message ...\n";
59     }
60
61     namespace kw = senf::console::kw;
62
63     int main(int, char**)
64     {
65         // Provide global documentation
66         senf::console::root()
67             .doc("This is someServer server");
68
69         // Add a command
70         senf::console::root()
71             .add("mycommand", &mycommand)
72             .doc("If <bar> is given, flurgle the <foo>, otherwise burgle it")
73             .arg("foo")
74             .arg(kw::name = "bar", kw::default_value = 0);
75
76         // Start the interactive console server
77         senf::console::Server::start(senf::INet4SocketAddress(senf::INet4Address::None, 23232u))
78             .name("someServer");
79     }
80     \endcode
81
82     after this registration, the console can be accessed easily via telnet:
83     
84     <pre>
85     $ telnet localhost 23232
86     Trying 127.0.0.1...
87     Connected to localhost.
88     Escape character is '^]'
89     xxxx-xx-xx xx:xx:xx.xxxxxx-0000 [NOTICE][senf::console::Server] Registered new client 0xxxxxxx
90     someServer:/# ls
91     mycommand
92     someServer:/# mycommand
93     !! Important message  ...
94     someServer:/# exit
95     xxxx-xx-xx xx:xx:xx.xxxxxx-0000 [NOTICE][senf::console::Server] Disposing client 0xxxxxxx
96     Connection closed by foreign host.
97     $
98     </pre>
99
100
101     \section intro_nodes The node tree
102
103     The basic idea is, that the console/config library manages a directory structure of parameters
104     and auxiliary commands. Parameters are just commands which set a parameter value so everything
105     is either a directory entry (senf::console::DirectoryNode) or a command
106     (senf::console::CommandNode).
107     
108     \see \ref node_tree
109
110
111     \section intro_commands Console/config commands
112
113     The console/config language does not define, how arguments are passed to the commands, it just
114     tokenizes the input and passes the tokens to the commands which then handle the
115     conversion.
116
117     Since parsing the tokens into something usable is quite tedious and error prone, the library
118     implements automatic argument parsing where the argument tokens are automatically parsed
119     depending on argument types. This enables you to register a command taking an integer argument
120     which will be called with an already parsed integer value (or throw a
121     senf::console::SyntaxErrorException if the conversion fails). This will be the most often used
122     command.
123
124     \see \ref console_commands
125     
126
127     \section intro_language The console/config language
128
129     To call the commands and set parameters, a very simple language is defined. The language is
130     almost declarative (e.g. it does not have any control-flow statements) but is processed
131     imperatively from top to bottom. This is very simple and flexible.
132
133     Commands are referenced by their path in the node tree. To simplify working with deeply nested
134     directory structures, the current directory may be changed persistently or temporarily for some
135     commands.
136     \code
137     /server/port 1234;
138     
139     /logger/targets/console {
140         accept senf::log::Debug IMPORTANT;
141         accept server::ServerLog CRITICAL;
142     }
143     \endcode
144
145     \see \ref console_parser
146  */
147
148 /** \defgroup console_commands Supported command types
149
150     The Console/config library supports quite a number of different command types. All these types
151     of command are registered, by passing them to DirectoryNode::add()
152
153     \autotoc
154
155     \section console_cmdadd Adding commands and setting attributes
156
157     Basically, all commands are added using senf::console::DirectoryNode::add(). What exactly
158     happens depends on the type of object added.
159     \code
160     dir.add("name", callback)
161     \endcode
162     will add a command 'name' which will execute 'callback' when called, where 'callback' can be a
163     lot of things as documented in the following chapters.
164
165     The add call always returns (something which can be used as) a reference to the command node
166     added:
167     \code
168     senf::console::CommandNode & node ( dir.add( ... ) );
169     \endcode
170
171     Depending on the object added, you can also bind to a more specific node type
172     (e.g. senf::console::SimpleCommand) if you know the type of node returned.
173
174     Depending on the type of object added, there are additional attributes which can be set. These
175     attributes are always set by calling them on the return value <b>before saving that value as a
176     node reference</b>. It is \e not guaranteed, you can call these members on the node
177     reference.
178     \code
179     dir.add("name", callback)
180         .doc("The documentation");
181     \endcode
182     sets the \e doc attribute (if that is available, otherwise this will fail to compile). The
183     attribute members return value is again (something which can be used as) a reference to the
184     command node
185     \code
186     senf::console::CommandNode & node (
187         dir.add("name", callback)
188             .doc("The documentation") );
189     \endcode
190
191
192     \section console_manualparse Manually parsing command arguments
193
194     This is the most primitive type of command. It will be called with an output stream and with a
195     senf::console::ParseCommandInfo reference which holds information about the command parsed.
196
197     From this information the command callback gets a list of arguments or tokens which then can be
198     interpreted in an arbitrary way.
199     \code
200     void fun1(std::ostream & os, senf::console::ParseCommandInfo const & command)
201     {
202         // We take exactly one argument
203         if (command.arguments().size() != 1) 
204             raise senf::console::SyntaxErrorException("invalid number of arguments");
205
206         senf::console::ParseCommandInfo::TokenRange & argTokens (
207             command.arguments()[0]);
208
209         // The argument must have exactly one token
210         if (argTokens.size() != 1)
211             raise senf::console::SyntaxErrorException("argument syntax error");
212
213         // Retrieve the token value
214         std::string arg (argTokens[0].value());
215
216         // In this example, we just write the argument to the output stream
217         os << arg << std::endl;
218     }
219     \endcode
220     
221     Registering this callback is done by simply adding it. To provide online help, pass it to
222     'doc()':
223     \code
224     senf::console::root()
225         .add("test1", &fun1)
226         .doc("Usage:\n"
227              "    test1 arg\n"
228              "\n"
229              "Echo 'arg' to the console");
230     \endcode
231
232     The callback may now be called interactively on the console by it's registered name:
233     \htmlonly
234     <pre>
235     server:/$ test1
236     invalid number of arguments
237     server:/$ test1 stefan@j32.de
238     stefan@j32.de
239     server:/$ test1 (echo me)
240     argument syntax error
241     server:/$ help test1
242     Usage:
243         test1 arg
244
245     Echo 'arg' to the console
246     server:/$
247     </pre>
248     \endhtmlonly
249
250     As you can see above, the arguments and tokens are returned as <a
251     href="http://www.boost.org/doc/libs/1_33_1/libs/range/doc/utility_class.html#iter_range">
252     boost::iterator_range</a> instances. These behave much like containers: They have \c begin() and
253     \c end() and some other useful members.
254     
255     The parser will have divided the argument tokens into arguments already. This simplifies further
256     parsing. If however you want to access the list of argument tokens as a single list, you can do
257     so using senf::console::ParseCommandInfo::tokens().
258     
259     Parsing arguments is quite simple but can get very tedious. To simplify this task, the parsing
260     can be delegated to the Console/config library. See the next section.
261
262     This type of command has only a single attribute, \e doc to set the commands documentation.
263
264
265     \section console_autoparse Automatic argument parsing
266     
267     To greatly simplify parsing complex commands, we turn to automatic argument parsing. 
268
269     \subsection console_autoadd Adding
270
271     Automatically parsed commands are registered by just adding a callback which has the correct
272     arguments and return-value defined:
273     \code
274     std::string fun2(std::string const & arg)
275     {
276         return arg;
277     }
278     \endcode
279
280     This extremely simple callback may be registered by adding it to a senf::console::DirectoryNode.
281     \code
282     senf::console::root()
283         .add("test2", &fun2);
284     \endcode
285     The functionality is now identical to \c test1:
286     \htmlonly
287     <pre>
288     server:/$ test2
289     invalid number of arguments
290     server:/$ test2 stefan@j32.de
291     stefan@j32.de
292     server:/$ test2 (echo me)
293     argument syntax error
294     server:/$ help test2
295     Usage:
296         test2 arg11:string
297     server:/$
298     </pre>
299     \endhtmlonly
300
301
302     \subsection command_ostream Accessing the console stream
303
304     Commands may have an optional first argument of type <tt>std::ostream &</tt>. This argument is
305     not considered part of the real interface. When the command is executed, the callback will be
306     passed the current console's output stream object in this argument. With this, the callback can
307     output arbitrary messages to the network console.
308     \code
309     void fun3(std::ostream & os, unsigned n, std::string text)
310     {
311         while (n-- > 0) os << text << std::endl;
312     }
313
314     senf::console::root()
315         .add("test3", &fun3);
316     \endcode
317
318     This simple command can now be used thus:
319     \htmlonly
320     <pre>
321     server:/$ test3
322     invalid number of arguments
323     server:/$ test3 stefan@j32.de
324     invalid number of arguments
325     server:/$ test3 2 ok
326     ok
327     ok
328     server:/$ help test3
329     Usage:
330         test3 arg11:int arg12:string
331     server:/$
332     </pre>
333     \endhtmlonly
334
335     \subsection command_overload Overloading
336
337     Automatically parsed commands can be overloaded: You can register multiple commands under the
338     same name. Each overload is tried in turn until no SyntaxErrorException is raised.
339     \code
340     senf::console::root()
341         .add("test4", &fun3);
342     senf::console::root()
343         .add("test4", &fun2);
344     \endcode
345     And now, we can call \c test4 with one or two args:
346     <pre>
347     server:/$ test4
348     invalid number of arguments
349     server:/$ test4 stefan@j32.de
350     stefan@j32.de
351     server:/$ test4 2 ok
352     ok
353     ok
354     server:/$ help test4
355     Usage:
356         1- test4 arg11:int arg12:string
357         2- test4 arg21:string
358     server:/$
359     </pre>
360
361     \subsection console_attributes Attributes
362
363     As have seen so far, some documentation is automatically provided. We can add more info, by
364     setting additional attributes. 
365     \code
366     senf::console::root()
367         .add("test5", &fun3)
368         .doc("Echo text to the console")
369         .overloadDoc("Repeat {arg12} for {arg11} lines");
370     senf::console::root()
371         .add("test4", &fun2)
372         .overloadDoc("Echo the {arg21} argument")
373     \endcode
374
375     This additional info is used to provide more documentation:
376     \htmlonly
377     <pre>
378     server:/$ help test5
379     Usage:
380         1- test5 arg11:int arg12:string
381         2- test5 arg21:string
382
383     Echo text to the console
384
385     Variant 1:
386     Repeat {arg12} for {arg11} lines
387     
388     Variant 2:
389     Echo the {arg21} argument
390     senf:/$
391     </pre>
392     \endhtmlonly
393
394
395     \subsection console_argattributes Argument attributes
396
397     Additional attributes can be set for each parameter. They are all passed to the
398     senf::console::ParsedArgumentAttributor::arg() attribute.
399
400     \code
401     namespace kw = senf::console::kw;
402
403     senf::console::root()
404         .add("test6", &fun3)
405         .doc("Echo text to the console")
406         .overloadDoc("Repeat {text} for {n} lines");
407         .arg( kw::name = "n", kw::description="Number of repetitions" )
408         .arg( kw::name = "text", kw::description="Text to output" );
409     senf::console::root()
410         .add("test6", &fun2)
411         .overloadDoc("Echo the {text} argument")
412         .arg( kw::name = "text" );
413     \endcode
414
415     (Sadly, there is no way to automatically find out the \e name of an argument, just it's type.)
416     Every callback argument corresponds with a call of the \c arg() attribute. Argument attributes
417     are set using keywords from the \ref senf::console::kw namespace. You will probably either use
418     this namespace via a namespace alias (as above) or via a <tt>using namespace
419     senf::console::kw</tt> declaration (but beware of name collisions).
420
421     You don't need to specify any information for an argument: To skip an argument, just call \c
422     arg() without attributes for this argument.
423
424     After adding this information, the online help is much more readable
425       \htmlonly
426     <pre>
427     server:/$ help test6
428     Usage:
429         1- test6 n:int text:string
430         2- test6 text:string
431
432     With:
433         n         Number of repetitions
434         text      Text to output
435
436     Echo text to the console
437
438     Variant 1:
439     Repeat {text} for {n} lines
440     
441     Variant 2:
442     Echo the {text} argument
443     senf:/$
444     </pre>
445     \endhtmlonly
446
447     Since most of the time, we only need to set the name and possibly a description for arguments,
448     there is a shortcut: name and description can be specified as positional arguments in this
449     order. So the following will give the exactly same result as above:
450     \code
451     namespace kw = senf::console::kw;
452
453     senf::console::root()
454         .add("test6", &fun3)
455         .doc("Echo text to the console")
456         .overloadDoc("Repeat <text> for <n> lines");
457         .arg("n",    "Number of repetitions")
458         .arg("text", "Text to output");
459     senf::console::root()
460         .add("test6", &fun2)
461         .overloadDoc("Echo the <text> argument")
462         .arg("text");
463     \endcode
464     
465     Keyword arguments should always be used if additional attributes are set. You can however mix
466     positional and keyword arguments.
467
468     
469     \subsection console_defaults Default values
470     
471     Another information which can not be automatically gathered from the type system is default
472     values. These have to be declared explicitly:
473     \code
474     namespace kw = senf::console::kw;
475
476     senf::console::root()
477         .add("test7", &fun3)
478         .doc("Echo {text} to the console, repeating {text} for {n} lines")
479         .arg("n",    "Number of repetitions", kw::default_value=1)
480         .arg("text", "Text to output");
481     \endcode
482
483     Default values can be used together with overloading. Default (optional) value support is quite
484     flexible, it is not mandatory, for default values to be specified only for the trailing
485     arguments. For the exact definition, how parsed argument values are assigned to overload
486     arguments in the presence of default values, see \ref senf::console::kw::default_value.
487     
488     \htmlonly
489     <pre>
490     server:/$ test7 echo
491     echo
492     server:/$ test7 4 ok
493     ok
494     ok
495     ok
496     ok
497     server:/$ help test7
498     Usage:
499         test4 [n:unsigned] text:string
500     
501     With:
502         n         Number of repetitions
503             default: 1
504         text      Text to output
505
506     Echo {text} to the console, repeating {text} for {n} lines
507     server:/$
508     </pre>
509     \endhtmlonly
510
511
512     \subsection console_boostfn Non-function-pointer commands
513
514     It is possible to add other callable objects besides function (and member-function)
515     pointers. However, since it is not possible to automatically deduce the argument and return
516     types in this case, the callables have to be wrapped in a \c boost::function object:
517
518     \code
519     senf::console::root()
520         .add("test8", 
521              boost::function<void (std::ostream &, std::string const &)>(
522                  boost::bind(&fun3, _1, 4u, _2)));
523     \endcode
524
525     This works with any callable object where argument types cannot be deduced automatically:
526     Boost.Bind expressions, Boost.Lambda expressions, functors and so on.
527     
528     \htmlonly
529     <pre>
530     server:/$ test8 ok
531     ok
532     ok
533     ok
534     ok
535     server:/$ help test8
536     Usage:
537         test8 arg11:string
538     server:/$
539     </pre>
540     \endhtmlonly
541
542
543     \subsection console_attr_summary Attribute summary
544
545     Here a summary of the most common attributes
546
547     <table class="senf fixedwidth">
548
549     <tr><td style="width:14em">\link senf::console::ParsedArgumentAttributorBase::doc() .doc\endlink
550     ( \e doc )</td><td>Set documentation for all overloads</td></tr>
551     
552     <tr><td>\link senf::console::ParsedArgumentAttributorBase::overloadDoc()
553     .overloadDoc\endlink ( \e doc )</td><td>Set documentation for a specific overload</td></tr>
554
555     <tr><td>\link senf::console::ParsedArgumentAttributor::arg() .arg\endlink ( \e argument \e
556     attributes )</td><td>Set argument attributes (see below)</td></tr>
557
558     </table>
559
560     The most important argument attributes (all defined in the senf::console::kw namespace) are:
561     
562     <table class="senf fixed width">
563
564     <tr><td style="width:14em">\link senf::console::kw::name kw::name\endlink</td><td>Parameter
565     name</td></tr>
566
567     <tr><td>\link senf::console::kw::description kw::description\endlink</td><td>One-line
568     description of the argument</td></tr>
569
570     <tr><td>\link senf::console::kw::default_value kw::default_value\endlink</td><td>Arguments
571     default value</td></tr>
572
573     </table>
574
575     \see <a
576         href="classsenf_1_1console_1_1ParsedArgumentAttributor-members.html">senf::console::ParsedArgumentAttributor
577         / List of all members</a> for the complete attribute interface \n
578         \ref senf::console::kw for a list of all argument attribute keywords
579
580         
581     \section console_memberfn Member functions
582     
583     Member functions are supported like non-member functions. They must however be added through a
584     senf::console::ScopedDirectory instance to bind them to their instance.
585     \code
586     class Test 
587     {
588     public:
589         senf::console::ScopedDirectory<Test> dir;
590
591         Test(std::string label) : dir(this), label_ (label) 
592         {
593             dir.add("test4", &Test::test2);
594             dir.add("test4", &Test::test3);
595         }
596
597         std::string test2(std::string const & text)
598             { return label_ + ": " + text; }
599
600         void test3(std::ostream & os, unsigned n, std::string const & text) 
601             { while (n-- > 0) os << label << ": " << text << std::endl; }
602
603     private:
604         std::string label_;
605     };
606
607     // ...
608
609     Test testOb ("test");
610     senf::console::root().add("testobj", testOb.dir);
611     \endcode
612
613     Binding via senf::console::ScopedDirectory ensures, that the commands are automatically removed
614     from the tree when the object is destroyed.
615  */
616
617 \f
618 // Local Variables:
619 // mode: c++
620 // fill-column: 100
621 // comment-column: 40
622 // c-file-style: "senf"
623 // indent-tabs-mode: nil
624 // ispell-local-dictionary: "american"
625 // compile-command: "scons -u test"
626 // mode: auto-fill
627 // End:
628