X-Git-Url: http://g0dil.de/git?a=blobdiff_plain;f=senf%2FUtils%2FConsole%2FMainpage.dox;h=23c86015a5a81f67ced8def5be25ec44420d0074;hb=99c145da3884f5c20a74337927ef2cbc073d80d7;hp=4177e2f4aa51be6d9e69447e05056abbfa9dc72f;hpb=9cb871b939efe93e35dd96808d25089399acfc46;p=senf.git diff --git a/senf/Utils/Console/Mainpage.dox b/senf/Utils/Console/Mainpage.dox index 4177e2f..23c8601 100644 --- a/senf/Utils/Console/Mainpage.dox +++ b/senf/Utils/Console/Mainpage.dox @@ -65,6 +65,7 @@ } namespace kw = senf::console::kw; + namespace fty = senf::console::factory; int main(int argc, char** argv) { @@ -73,11 +74,10 @@ .doc("This is someServer server"); // Add a command - senf::console::root() - .add("mycommand", &mycommand) + senf::console::root().add("mycommand", fty::Command(&mycommand) .doc("If is given, flurgle the , otherwise burgle it") .arg("foo") - .arg(kw::name = "bar", kw::default_value = 0); + .arg(kw::name = "bar", kw::default_value = 0) ); // Parse command line parameters senf::console::parseOptions(argc,argv); @@ -137,7 +137,8 @@ \section intro_commands Implementing console/config commands - \seechapter \ref console_commands + \seechapter \ref console_commands \n + \seechapter \ref senf::console::factory The console/config language does not define, how arguments are passed to the commands, it just tokenizes the input and passes the tokens to the commands which then handle the @@ -276,9 +277,19 @@ Options can be abbreviated at each directory boundary: A command /foo/bar/do can be called as --f-b-d as long as this name is unique. - Everything after the first '=' character is parsed into argument tokens using the normal - config/console parser. If the option has no '=' character, the list of argument tokens will be - empty. + Everything after the first '=' character is passed as arguments to the command. The exact + interpretation depends on the command: + \li If the command only takes a single token as argument (e.g. a single string or numeric + value), everything after the '=' sign is parsed into a single token (e.g. see rows 2 and 3 + of the following table). + \li In all other cases, the string after the '=' sign is parsed into argument tokens using the + config/console parser. In this case, quoted strings need to be quoted twice, once for the + shell and once for the config/console parser (e.g. see rows 4 and 5 of the following table). + \li If the option has no '=' character, the list of argument tokens will be empty (e.g. see row + 1 of the following table) + + Without these rules, multi-word string arguments would \e always have to be quoted twice (for + the shell and the config/console parser). @@ -297,8 +308,8 @@ - - + + @@ -306,10 +317,13 @@ -
CommandFile syntaxOption syntax
void doo(std::string const &)/path/to/doo "some test";--path-to-doo='"some text"'/path/to/doo "some text";--path-to-doo="some text"
/path/to/doo take 1; --path-to-doo="take 1"
- The last column is additionally quoted using standard \c sh quoting: quotes in arguments need to - be additionally quoted for the shell. + + void doo(std::string const &, int) + /path/to/doo "take two" 1; + --path-to-doo='"take two" 1' + + Short options are registered as aliases for long options. They can be registered with or without an implied parameter and can optionally take a parameter. so after @@ -333,7 +347,7 @@ $ program --mycommand="2 3" --mycommand="4 5" - (Beware, that the second argument to \c alias() is \e not shell quoted). + (Beware, that the second argument to \c alias() must \e not be shell quoted). \subsection console_access_root Changing the root node @@ -363,7 +377,8 @@ parsing. \code - // Create a console/config aware object and place it into the node tree + // Create a console/config aware object and place it (that is it's directory node) into the node + // tree FooObject foo; senf::console::root().add("foo", foo.dir); @@ -573,20 +588,19 @@ /** \defgroup console_commands Supported command types The Console/config library supports quite a number of different command types. All these types - of command are registered, by passing them to DirectoryNode::add() + of command are registered by passing an appropriate factory instance to DirectoryNode::add() \autotoc \section console_cmdadd Adding commands and setting attributes - Basically, all commands are added using senf::console::DirectoryNode::add(). What exactly - happens depends on the type of object added. + Basically, all commands are added using senf::console::DirectoryNode::add(). \code - dir.add("name", callback) + namespace fty = senf::console::factory; + dir.add("name", fty::Command(callback)); \endcode - will add a command 'name' which will execute 'callback' when called, where 'callback' can be a - lot of things as documented in the following chapters. + will add the command 'name' which will execute 'callback' when called. The add call always returns (something which can be used as) a reference to the command node added: @@ -597,22 +611,16 @@ Depending on the object added, you can also bind to a more specific node type (e.g. senf::console::SimpleCommand) if you know the type of node returned. - Depending on the type of object added, there are additional attributes which can be set. These - attributes are always set by calling them on the return value before saving that value as a - node reference. It is \e not guaranteed, you can call these members on the node - reference. + Nodes are always added using a factory from the senf::console::factory namespace. The factory + has additional (type specific) attributes. These attributes are set by calling member functions + called 'attributors' on the temporary factory instance. It is \e not guaranteed, you can call + these members on the node reference returned by the \c add() call. \code - dir.add("name", callback) - .doc("The documentation"); - \endcode - sets the \e doc attribute (if that is available, otherwise this will fail to compile). The - attribute members return value is again (something which can be used as) a reference to the - command node - \code - senf::console::CommandNode & node ( - dir.add("name", callback) - .doc("The documentation") ); + namespace fty = senf::console::factory; + dir.add("name", fty::Command(callback) .doc("The documentation") ); \endcode + sets the \e doc attribute (if that is available, otherwise this will fail to compile). + \see senf::console::factory for a list of all node factories. \section console_manualparse Manually parsing command arguments @@ -648,12 +656,12 @@ Registering this callback is done by simply adding it. To provide online help, pass it to 'doc()': \code - senf::console::root() - .add("test1", &fun1) + namespace fty = senf::console::factory; + senf::console::root().add("test1", fty::Command(&fun1) .doc("Usage:\n" " test1 arg\n" "\n" - "Echo 'arg' to the console"); + "Echo 'arg' to the console") ); \endcode The callback may now be called interactively on the console by it's registered name: @@ -675,7 +683,7 @@ \endhtmlonly As you can see above, the arguments and tokens are returned as + href="http://www.boost.org/doc/libs/release/libs/range/doc/html/range/reference/utilities/iterator_range.html"> boost::iterator_range instances. These behave much like containers: They have \c begin() and \c end() and some other useful members. @@ -707,8 +715,8 @@ This extremely simple callback may be registered by adding it to a senf::console::DirectoryNode. \code - senf::console::root() - .add("test2", &fun2); + namespace fty = senf::console::factory; + senf::console::root().add("test2", fty::Command(&fun2)); \endcode The functionality is now identical to \c test1: \htmlonly @@ -734,13 +742,14 @@ passed the current consoles output stream object in this argument. With this, the callback can output arbitrary messages to the network console. \code + namespace fty = senf::console::factory; + void fun3(std::ostream & os, unsigned n, std::string text) { while (n-- > 0) os << text << std::endl; } - senf::console::root() - .add("test3", &fun3); + senf::console::root().add("test3", fty::Command(&fun3)); \endcode This simple command can now be used thus: @@ -766,10 +775,10 @@ Automatically parsed commands can be overloaded: You can register multiple commands under the same name. Each overload is tried in turn until no SyntaxErrorException is raised. \code - senf::console::root() - .add("test4", &fun3); - senf::console::root() - .add("test4", &fun2); + namespace fty = senf::console::factory; + + senf::console::root().add("test4", fty::Command(&fun3)); + senf::console::root().add("test4", fty::Command(&fun2)); \endcode And now, we can call \c test4 with one or two args:
@@ -794,13 +803,13 @@
     Utils/membind.hh to simplify this:
 
     \code
+    namespace fty = senf::console::factory;
+
     void over(int);
     void over(int,int);
 
-    senf::console::root()
-        .add("over", SENF_FNP(void, over, (int)));
-    senf::console::root()
-        .add("over", SENF_FNP(void, over, (int,int));
+    senf::console::root().add("over", fty::Command(SENF_FNP(void, over, (int))));
+    senf::console::root().add("over", fty::Command(SENF_FNP(void, over, (int,int)));
 
     class SomeModule {
       senf::console::ScopedDirectory dir;
@@ -809,10 +818,12 @@
       void overlodedMethod(unsigned int)   {....};
 
       void addConsoleCommands() {
-        dir.node().add("overlodedMethod",
-                       SENF_MEMBINDFNP(unsigned int, SomeModule, overlodedMethod, () const));
-        dir.node().add("overlodedMethod",
-                       SENF_MEMBINDFNP(unsigned int, SomeModule, overlodedMethod, (unsigned int));
+        dir.node()
+            .add("overlodedMethod", fty::Command(
+                     SENF_MEMBINDFNP(unsigned int, SomeModule, overlodedMethod, () const)));
+        dir.node()
+            .add("overlodedMethod", fty::Command(
+                     SENF_MEMBINDFNP(unsigned int, SomeModule, overlodedMethod, (unsigned int))));
       }
     }
     \endcode
@@ -823,13 +834,13 @@
     As have seen so far, some documentation is automatically provided. We can add more info, by
     setting additional attributes.
     \code
-    senf::console::root()
-        .add("test5", &fun3)
+    namespace fty = senf::console::factory;
+
+    senf::console::root().add("test5", fty::Command(&fun3)
         .doc("Echo text to the console")
-        .overloadDoc("Repeat {arg12} for {arg11} lines");
-    senf::console::root()
-        .add("test4", &fun2)
-        .overloadDoc("Echo the {arg21} argument")
+        .overloadDoc("Repeat {arg12} for {arg11} lines") );
+    senf::console::root().add("test4", fty::Command(&fun2)
+        .overloadDoc("Echo the {arg21} argument") );
     \endcode
 
     This additional info is used to provide more documentation:
@@ -859,17 +870,16 @@
 
     \code
     namespace kw = senf::console::kw;
+    namespace fty = senf::console::factory;
 
-    senf::console::root()
-        .add("test6", &fun3)
+    senf::console::root().add("test6", fty::Command(&fun3)
         .doc("Echo text to the console")
         .overloadDoc("Repeat {text} for {n} lines");
         .arg( kw::name = "n", kw::description="Number of repetitions" )
-        .arg( kw::name = "text", kw::description="Text to output" );
-    senf::console::root()
-        .add("test6", &fun2)
+        .arg( kw::name = "text", kw::description="Text to output" ) );
+    senf::console::root().add("test6", fty::Command(&fun2)
         .overloadDoc("Echo the {text} argument")
-        .arg( kw::name = "text" );
+        .arg( kw::name = "text" ) );
     \endcode
 
     (Sadly, there is no way to automatically find out the \e name of an argument, just it's type.)
@@ -909,16 +919,15 @@
     order. So the following will give the exactly same result as above:
     \code
     namespace kw = senf::console::kw;
+    namespace fty = senf::console::factory;
 
-    senf::console::root()
-        .add("test6", &fun3)
+    senf::console::root().add("test6", fty::Command(&fun3)
         .doc("Echo text to the console")
         .overloadDoc("Repeat  for  lines");
         .arg("n",    "Number of repetitions")
-        .arg("text", "Text to output");
-    senf::console::root()
-        .add("test6", &fun2)
-        .overloadDoc("Echo the  argument")
+        .arg("text", "Text to output") );
+    senf::console::root().add("test6", fty::Command(&fun2)
+        .overloadDoc("Echo the  argument") );
         .arg("text");
     \endcode
 
@@ -932,12 +941,12 @@
     values. These have to be declared explicitly:
     \code
     namespace kw = senf::console::kw;
+    namespace fty = senf::console::factory;
 
-    senf::console::root()
-        .add("test7", &fun3)
+    senf::console::root().add("test7", fty::Command(&fun3)
         .doc("Echo {text} to the console, repeating {text} for {n} lines")
         .arg("n",    "Number of repetitions", kw::default_value=1)
-        .arg("text", "Text to output");
+        .arg("text", "Text to output") );
     \endcode
 
     Default values can be used together with overloading. Default (optional) value support is quite
@@ -973,13 +982,13 @@
 
     It is possible to add other callable objects besides function (and member-function)
     pointers. However, since it is not possible to automatically deduce the argument and return
-    types in this case, the callables have to be wrapped in a \c boost::function object:
-
+    types in this case, the signature has to be specified explicitly:
     \code
+    namespace fty = senf::console::factory;
+
     senf::console::root()
-        .add("test8",
-             boost::function(
-                 boost::bind(&fun3, _1, 4u, _2)));
+        .add("test8",fty::Command(
+                         boost::bind(&fun3, _1, 4u, _2)));
     \endcode
 
     This works with any callable object where argument types cannot be deduced automatically:
@@ -1044,14 +1053,16 @@
     identical to non-members). They must however be added through a senf::console::ScopedDirectory
     instance to bind them to their instance.
     \code
+    namespace fty = senf::console::factory;
+
     class Test1
     {
     public:
         senf::console::ScopedDirectory dir;
 
         Test1(std::string label) : dir(this), label_ (label)
-            { dir.add("test", &Test::test1);
-              dir.add("test", &Test::test2); }
+            { dir.add("test", fty::Command(&Test::test1, this));
+              dir.add("test", fty::Command(&Test::test2, this)); }
 
         std::string test1(std::string const & text)
             { return label_ + ": " + text; }
@@ -1081,13 +1092,15 @@
     variable command consists of two overloads, one to query the current value and one to change the
     value.
     \code
+    namespace fty = senf::console::factory;
+
     class Test2
     {
     public:
         senf::console::ScopedDirectory dir;
 
         Test2() : dir(this), var_(0)
-            { dir.add("var", var_); }
+            { dir.add("var", fty::Variable(var_) ); }
 
     private:
         int var_;
@@ -1120,9 +1133,11 @@
     The library also supports read-only variables. To make a variable read-only, just wrap it in \c
     boost::cref() (where \c cref stands for \c const reference)
     \code
+    namespace fty = senf::console::factory;
+
     int var (0);
 
-    senf::console::root().add("var1", boost::cref(var));
+    senf::console::root().add("var1", fty::Variable(boost::cref(var)));
     \endcode
     A read-only variable only has a single overload:
     \htmlonly
@@ -1160,6 +1175,8 @@
     reference to the old value. The handler is called, after the value has been changed
 
     \code
+    namespace fty = senf::console::factory;
+
     int var (0);
 
     // Since this is int, it would make sense to declare the argument pass-by-value (int old)
@@ -1169,8 +1186,8 @@
         // ...
     }
 
-    senf::console::root().add("var2",var)
-        .onChange(&varChanged);
+    senf::console::root().add("var2", fty::Variable(var)
+        .onChange(&varChanged) );
     \endcode
 
     After this setup, \c varChanged will be called, whenever the value has changed.
@@ -1261,13 +1278,14 @@
     Enum types are a special case, since it is not possible, to find a string representation for the
     enumerator values automatically. Therefore, enum types need to be registered manually.
     \code
+    namespace fty = senf::console::factory;
+
     enum MyEnum { Sit, Run, Jump };
     SENF_CONSOLE_REGISTER_ENUM( MyEnum, (Sit)(Run)(Jump) );
 
     MyEnum fun4(MyEnum v) { return v }
 
-    senf::console::root()
-        .add("test9", &fun4);
+    senf::console::root().add("test9", fty::Command(&fun4));
     \endcode
 
     After an enum type is registered, it can be used like any other type for arguments or
@@ -1290,6 +1308,8 @@
     register enums defined within some class, use \ref SENF_CONSOLE_REGISTER_ENUM_MEMBER()
 
     \code
+    namespace fty = senf::console::factory;
+
     class Test3
     {
     public:
@@ -1304,7 +1324,7 @@
     SENF_CONSOLE_REGISTER_ENUM_MEMBER( Test3, Color, (Red)(Green)(Blue) );
 
     Test3::Test3() : dir(this)
-        { dir.add("test", &Test3::mem3); }
+        { dir.add("test", fty::Command(&Test3::mem3, this)); }
 
     Test3 test3ob;
     senf::console::root().add("test3ob", test3ob.dir);
@@ -1327,22 +1347,25 @@
     \subsection console_args_convert Handling argument types by conversion
 
     Sometimes an argument type is best handled by just pretending it to be of some other type. The
-    basic idea is, to us \c boost::function to convert the real argument type to some different type
+    basic idea is, to provide an explicit signature with different (but compatible) types to the
+    factory:
 
     \code
+    namespace fty = senf::console::factory;
+
     int fun4(int value)
     {
         return value;
     }
 
     senf::console::root()
-        .add("test8", boost::function(&fun4));
+        .add("test8", fty::Command(&fun4));
     \endcode
 
-    Here, the type signature specified via \c boost::function is different from the real type
-    signature but is compatible. \c boost::function automatically handles the conversion
-    process. Since the console library now sees the argument and return value of type \c bool,
-    the values will be parsed and formatted as boolean values.
+    Here, the type signature passed to fty::Command is different from the real type signature but it
+    is compatible, the conversion is handled automatically. Since the console library now sees the
+    argument and return value of type \c bool, the values will be parsed and formatted as boolean
+    values.
 
 
     \subsection console_args_special Special Console types
@@ -1390,12 +1413,14 @@
     The formatter writes out the value as a parenthesized pair.
 
     \code
+    namespace fty = senf::console::factory;
+
     Coordinate fun5(Coordinate const & p) { return Coordinate(2*p.x, 2*p.y) }
 
     namespace kw = senf::console::kw;
 
     senf::console::root()
-        .add("test10", &fun5)
+        .add("test10", fty::Command(&fun5))
         .arg("x","coordinate to double",
              kw::default_value = Coordinate())
     \endcode
@@ -1433,4 +1458,3 @@
 // compile-command: "scons -u test"
 // mode: auto-fill
 // End:
-