switch to new MPL based Fraunhofer FOKUS Public License
[senf.git] / senf / Utils / Console / Executor.test.cc
1 // $Id$
2 //
3 // Copyright (C) 2008
4 // Fraunhofer Institute for Open Communication Systems (FOKUS)
5 //
6 // The contents of this file are subject to the Fraunhofer FOKUS Public License
7 // Version 1.0 (the "License"); you may not use this file except in compliance
8 // with the License. You may obtain a copy of the License at 
9 // http://senf.berlios.de/license.html
10 //
11 // The Fraunhofer FOKUS Public License Version 1.0 is based on, 
12 // but modifies the Mozilla Public License Version 1.1.
13 // See the full license text for the amendments.
14 //
15 // Software distributed under the License is distributed on an "AS IS" basis, 
16 // WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License 
17 // for the specific language governing rights and limitations under the License.
18 //
19 // The Original Code is Fraunhofer FOKUS code.
20 //
21 // The Initial Developer of the Original Code is Fraunhofer-Gesellschaft e.V. 
22 // (registered association), Hansastraße 27 c, 80686 Munich, Germany.
23 // All Rights Reserved.
24 //
25 // Contributor(s):
26 //   Stefan Bund <g0dil@berlios.de>
27
28 /** \file
29     \brief Executor unit tests */
30
31 //#include "Executor.test.hh"
32 //#include "Executor.test.ih"
33
34 // Custom includes
35 #include <sstream>
36 #include <vector>
37 #include "Console.hh"
38
39 #include <senf/Utils/auto_unit_test.hh>
40 #include <boost/test/test_tools.hpp>
41
42 #define prefix_
43 //-/////////////////////////////////////////////////////////////////////////////////////////////////
44
45 namespace {
46     std::vector<senf::console::ParseCommandInfo> commands;
47     void setCommand(senf::console::ParseCommandInfo const & cmd) {
48         commands.push_back(cmd);
49     }
50     void testCommand(std::ostream & os, senf::console::ParseCommandInfo const & command) {
51         os << "testCommand\n";
52     }
53 }
54
55 SENF_AUTO_UNIT_TEST(executor)
56 {
57     namespace fty = senf::console::factory;
58
59     senf::console::root().add("dir 1",fty::Directory()).add("dir3",fty::Directory());
60     senf::console::root().add("dir2",fty::Directory()).doc("Helptext").add("test",fty::Command(&testCommand));
61
62     senf::console::Executor executor;
63     senf::console::CommandParser parser;
64
65     BOOST_CHECK( &executor.cwd() == &senf::console::root() );
66
67     {
68         std::stringstream os;
69         parser.parse("cd \"dir 1\"", &setCommand);
70         executor(os, commands.back());
71         BOOST_CHECK_EQUAL( commands.back().builtin(), senf::console::ParseCommandInfo::BuiltinCD );
72         BOOST_CHECK( executor.cwd() == senf::console::root()["dir 1"] );
73         BOOST_CHECK_EQUAL( executor.cwdPath(), "/dir 1" );
74         BOOST_CHECK_EQUAL( os.str(), "" );
75     }
76
77     {
78         std::stringstream os;
79         parser.parse("cd /dir2", &setCommand);
80         executor(os, commands.back());
81         BOOST_CHECK_EQUAL( commands.back().builtin(), senf::console::ParseCommandInfo::BuiltinCD );
82         BOOST_CHECK( &executor.cwd() == &senf::console::root()["dir2"] );
83         BOOST_CHECK_EQUAL( os.str(), "" );
84     }
85
86     {
87         std::stringstream os;
88         parser.parse("cd \"dir 1\"", &setCommand);
89         BOOST_CHECK_THROW( executor(os, commands.back()), senf::console::SyntaxErrorException );
90         BOOST_CHECK_EQUAL( commands.back().builtin(), senf::console::ParseCommandInfo::BuiltinCD );
91         BOOST_CHECK( &executor.cwd() == &senf::console::root()["dir2"] );
92         BOOST_CHECK_EQUAL( os.str(), "" );
93     }
94
95     {
96         std::stringstream os;
97         parser.parse("cd /", &setCommand);
98         executor(os, commands.back());
99         BOOST_CHECK_EQUAL( commands.back().builtin(), senf::console::ParseCommandInfo::BuiltinCD );
100         BOOST_CHECK( &executor.cwd() == &senf::console::root() );
101         BOOST_CHECK_EQUAL( os.str(), "" );
102     }
103
104     {
105         std::stringstream os;
106         parser.parse("ll", &setCommand);
107         executor(os, commands.back());
108         BOOST_CHECK_EQUAL( commands.back().builtin(), senf::console::ParseCommandInfo::BuiltinLL );
109         BOOST_CHECK_EQUAL( os.str(),
110                            "dir 1/                      \n"
111                            "dir2/                       Helptext\n"
112                            "sys/                        \n" );
113     }
114
115     {
116         std::stringstream os;
117         parser.parse("ll \"dir 1\"", &setCommand);
118         executor(os, commands.back());
119         BOOST_CHECK_EQUAL( commands.back().builtin(), senf::console::ParseCommandInfo::BuiltinLL );
120         BOOST_CHECK_EQUAL( os.str(), "dir3/                       \n" );
121     }
122
123     {
124         std::stringstream os;
125         parser.parse("ls dir3", &setCommand);
126         BOOST_CHECK_THROW( executor(os, commands.back()), senf::console::SyntaxErrorException );
127         BOOST_CHECK_EQUAL( commands.back().builtin(), senf::console::ParseCommandInfo::BuiltinLS );
128         BOOST_CHECK_EQUAL( os.str(), "" );
129     }
130
131     {
132         std::stringstream os;
133         parser.parse("lr", &setCommand);
134         executor(os, commands.back());
135         BOOST_CHECK_EQUAL( commands.back().builtin(), senf::console::ParseCommandInfo::BuiltinLR );
136         BOOST_CHECK_EQUAL( os.str().substr(0,213),
137                            "dir 1/                                  \n"
138                            "  dir3/                                 \n"
139                            "dir2/                                   Helptext\n"
140                            "  test                                  \n"
141                            "sys/                                    \n" );
142     }
143
144     {
145         std::stringstream os;
146         parser.parse("\"dir 1\"/dir3 { }", &setCommand);
147         executor(os, commands.rbegin()[1]);
148         BOOST_CHECK_EQUAL( commands.rbegin()[1].builtin(), senf::console::ParseCommandInfo::BuiltinPUSHD );
149         BOOST_CHECK( &executor.cwd() == &senf::console::root()["dir 1"]["dir3"] );
150         BOOST_CHECK_EQUAL( os.str(), "" );
151     }
152
153     {
154         std::stringstream os;
155         executor(os, commands.back());
156         BOOST_CHECK_EQUAL( commands.back().builtin(), senf::console::ParseCommandInfo::BuiltinPOPD );
157         BOOST_CHECK( &executor.cwd() == &senf::console::root() );
158         BOOST_CHECK_EQUAL( os.str(), "" );
159     }
160
161     {
162         std::stringstream os;
163         parser.parse("exit", &setCommand);
164         BOOST_CHECK_EQUAL( commands.back().builtin(), senf::console::ParseCommandInfo::BuiltinEXIT );
165         BOOST_CHECK_THROW( executor(os, commands.back()), senf::console::Executor::ExitException );
166         BOOST_CHECK_EQUAL( os.str(), "" );
167     }
168
169     {
170         std::stringstream os;
171         parser.parse("help /dir2", &setCommand);
172         executor(os, commands.back());
173         BOOST_CHECK_EQUAL( commands.back().builtin(), senf::console::ParseCommandInfo::BuiltinHELP );
174         BOOST_CHECK_EQUAL( os.str(), "Helptext\n" );
175     }
176
177     {
178         std::stringstream os;
179         parser.parse("dir2/test", &setCommand);
180         executor(os, commands.back());
181         BOOST_CHECK_EQUAL( commands.back().builtin(), senf::console::ParseCommandInfo::NoBuiltin );
182         BOOST_CHECK_EQUAL( os.str(), "testCommand\n" );
183     }
184
185     commands.clear();
186     senf::console::root().remove("dir 1");
187     senf::console::root().remove("dir2");
188 }
189
190 SENF_AUTO_UNIT_TEST(executorChroot)
191 {
192     namespace fty = senf::console::factory;
193
194     senf::console::root().add("dir1",fty::Directory()).add("dir3",fty::Directory());
195     senf::console::root().add("dir2",fty::Directory().doc("Helptext"))
196         .add("test", fty::Command(&testCommand));
197
198     senf::console::Executor executor;
199     senf::console::CommandParser parser;
200
201     executor.chroot( senf::console::root()["dir2"] );
202
203     BOOST_CHECK( & executor.chroot() == & senf::console::root()["dir2"] );
204
205     {
206         std::stringstream os;
207         parser.parse("../test", &setCommand);
208         executor(os, commands.back());
209         BOOST_CHECK_EQUAL( commands.back().builtin(), senf::console::ParseCommandInfo::NoBuiltin );
210         BOOST_CHECK_EQUAL( os.str(), "testCommand\n" );
211     }
212
213     commands.clear();
214     senf::console::root().remove("dir1");
215     senf::console::root().remove("dir2");
216 }
217
218 namespace {
219
220     void testPolicy(senf::console::DirectoryNode & dir, std::string const & entry)
221     {
222         if (dir == senf::console::root() && entry == "dir2")
223             throw senf::console::Executor::IgnoreCommandException();
224     }
225 }
226
227 SENF_AUTO_UNIT_TEST(executorPolicy)
228 {
229     namespace fty = senf::console::factory;
230
231     senf::console::root().add("dir1",fty::Directory()).add("dir3",fty::Directory());
232     senf::console::root().add("dir2",fty::Directory().doc("Helptext"))
233         .add("test",fty::Command(&testCommand));
234
235     senf::console::Executor executor;
236     senf::console::CommandParser parser;
237
238     executor.policy(&testPolicy);
239
240     {
241         std::stringstream os;
242         parser.parse("ll dir1", &setCommand);
243         executor(os, commands.back());
244         BOOST_CHECK_EQUAL( commands.back().builtin(), senf::console::ParseCommandInfo::BuiltinLL );
245         BOOST_CHECK_EQUAL( os.str(), "dir3/                       \n" );
246     }
247
248     {
249         std::stringstream os;
250         parser.parse("dir2/test", &setCommand);
251         executor(os, commands.back());
252         BOOST_CHECK_EQUAL( commands.back().builtin(), senf::console::ParseCommandInfo::NoBuiltin );
253         BOOST_CHECK_EQUAL( os.str(), "" );
254     }
255
256     commands.clear();
257     senf::console::root().remove("dir1");
258     senf::console::root().remove("dir2");
259 }
260
261 SENF_AUTO_UNIT_TEST(executorAuto)
262 {
263     namespace fty = senf::console::factory;
264
265     senf::console::root().add("tdir1",fty::Directory()).add("dir3",fty::Directory());
266     senf::console::root().add("dir2",fty::Directory().doc("Helptext"))
267         .add("test",fty::Command(&testCommand));
268
269     senf::console::Executor executor;
270     executor
271         .autocomplete(true)
272         .autocd(true);
273     senf::console::CommandParser parser;
274
275     {
276         std::stringstream os;
277         parser.parse("dir2", &setCommand);
278         executor(os, commands.back());
279         BOOST_CHECK_EQUAL( executor.cwdPath(), "/dir2" );
280         BOOST_CHECK_EQUAL( os.str(), "" );
281     }
282
283     {
284         std::stringstream os;
285         parser.parse("..", &setCommand);
286         executor(os, commands.back());
287         BOOST_CHECK_EQUAL( executor.cwdPath(), "/" );
288         BOOST_CHECK_EQUAL( os.str(), "" );
289     }
290
291     {
292         std::stringstream os;
293         parser.parse("d", &setCommand);
294         executor(os, commands.back());
295         BOOST_CHECK_EQUAL( executor.cwdPath(), "/dir2" );
296         BOOST_CHECK_EQUAL( os.str(), "" );
297     }
298
299     {
300         std::stringstream os;
301         parser.parse("t", &setCommand);
302         executor(os, commands.back());
303         BOOST_CHECK_EQUAL( os.str(), "testCommand\n" );
304     }
305
306     commands.clear();
307     senf::console::root().remove("tdir1");
308     senf::console::root().remove("dir2");
309 }
310
311 //-/////////////////////////////////////////////////////////////////////////////////////////////////
312 #undef prefix_
313
314 \f
315 // Local Variables:
316 // mode: c++
317 // fill-column: 100
318 // comment-column: 40
319 // c-file-style: "senf"
320 // indent-tabs-mode: nil
321 // ispell-local-dictionary: "american"
322 // compile-command: "scons -u test"
323 // End: