1 // operations_unit_test.cpp ----------------------------------------------------------//
3 // Copyright Beman Dawes 2008, 2009, 2015
5 // Distributed under the Boost Software License, Version 1.0.
6 // See http://www.boost.org/LICENSE_1_0.txt
8 // Library home page: http://www.boost.org/libs/filesystem
10 // ------------------------------------------------------------------------------------//
12 // This program is misnamed - it is really a smoke test rather than a unit test
14 // ------------------------------------------------------------------------------------//
17 #include <boost/config/warning_disable.hpp>
19 // See deprecated_test for tests of deprecated features
20 #ifndef BOOST_FILESYSTEM_NO_DEPRECATED
21 # define BOOST_FILESYSTEM_NO_DEPRECATED
23 #ifndef BOOST_SYSTEM_NO_DEPRECATED
24 # define BOOST_SYSTEM_NO_DEPRECATED
27 #include <boost/filesystem.hpp> // make sure filesystem.hpp works
29 #include <boost/config.hpp>
30 # if defined( BOOST_NO_STD_WSTRING )
31 # error Configuration not supported: Boost.Filesystem V3 and later requires std::wstring support
34 #include <boost/system/error_code.hpp>
35 #include <boost/detail/lightweight_test.hpp>
36 #include <boost/detail/lightweight_main.hpp>
39 using namespace boost::filesystem
;
40 using namespace boost::system
;
45 #define CHECK(x) check(x, __FILE__, __LINE__)
49 const path
temp_dir(initial_path() / unique_path("op-unit_test-%%%%-%%%%-%%%%"));
53 void check(bool ok
, const char* file
, int line
)
57 ++::boost::detail::test_errors();
59 cout
<< file
<< '(' << line
<< "): test failed\n";
62 // file_status_test ----------------------------------------------------------------//
64 void file_status_test()
66 cout
<< "file_status test..." << endl
;
68 file_status s
= status(".");
69 int v
= s
.permissions();
70 cout
<< " status(\".\") permissions are "
71 << std::oct
<< (v
& 0777) << std::dec
<< endl
;
72 CHECK((v
& 0400) == 0400);
74 s
= symlink_status(".");
76 cout
<< " symlink_status(\".\") permissions are "
77 << std::oct
<< (v
& 0777) << std::dec
<< endl
;
78 CHECK((v
& 0400) == 0400);
81 // query_test ----------------------------------------------------------------------//
85 cout
<< "query test..." << endl
;
89 CHECK(file_size("no-such-file", ec
) == static_cast<boost::uintmax_t>(-1));
90 CHECK(ec
== errc::no_such_file_or_directory
);
92 CHECK(status("no-such-file") == file_status(file_not_found
, no_perms
));
95 CHECK(is_directory("/"));
96 CHECK(!exists("no-such-file"));
101 cout
<< "exists(\"/\", ec) resulted in non-zero ec.value()" << endl
;
102 cout
<< "ec value: " << ec
.value() << ", message: "<< ec
.message() << endl
;
107 CHECK(is_directory("/"));
108 CHECK(!is_regular_file("/"));
109 CHECK(!boost::filesystem::is_empty("/"));
110 CHECK(!is_other("/"));
113 // directory_iterator_test -----------------------------------------------//
115 void directory_iterator_test()
117 cout
<< "directory_iterator_test..." << endl
;
119 directory_iterator end
;
121 directory_iterator
it(".");
123 CHECK(!it
->path().empty());
125 if (is_regular_file(it
->status()))
127 CHECK(is_regular_file(it
->symlink_status()));
128 CHECK(!is_directory(it
->status()));
129 CHECK(!is_symlink(it
->status()));
130 CHECK(!is_directory(it
->symlink_status()));
131 CHECK(!is_symlink(it
->symlink_status()));
135 CHECK(is_directory(it
->status()));
136 CHECK(is_directory(it
->symlink_status()));
137 CHECK(!is_regular_file(it
->status()));
138 CHECK(!is_regular_file(it
->symlink_status()));
139 CHECK(!is_symlink(it
->status()));
140 CHECK(!is_symlink(it
->symlink_status()));
143 for (; it
!= end
; ++it
)
145 //cout << " " << it->path() << "\n";
148 CHECK(directory_iterator(".") != directory_iterator());
149 CHECK(directory_iterator() == end
);
151 #ifndef BOOST_NO_CXX11_RANGE_BASED_FOR
152 for (directory_entry
& x
: directory_iterator("."))
154 CHECK(!x
.path().empty());
155 //cout << " " << x.path() << "\n";
157 const directory_iterator
dir_itr(".");
158 for (directory_entry
& x
: dir_itr
)
160 CHECK(!x
.path().empty());
161 //cout << " " << x.path() << "\n";
165 for (directory_iterator
itr("."); itr
!= directory_iterator(); ++itr
)
167 CHECK(!itr
->path().empty());
168 //cout << " " << itr->path() << "\n";
171 cout
<< "directory_iterator_test complete" << endl
;
174 // recursive_directory_iterator_test -----------------------------------------------//
176 void recursive_directory_iterator_test()
178 cout
<< "recursive_directory_iterator_test..." << endl
;
180 recursive_directory_iterator end
;
182 recursive_directory_iterator
it("..");
184 CHECK(!it
->path().empty());
186 if (is_regular_file(it
->status()))
188 CHECK(is_regular_file(it
->symlink_status()));
189 CHECK(!is_directory(it
->status()));
190 CHECK(!is_symlink(it
->status()));
191 CHECK(!is_directory(it
->symlink_status()));
192 CHECK(!is_symlink(it
->symlink_status()));
196 CHECK(is_directory(it
->status()));
197 CHECK(is_directory(it
->symlink_status()));
198 CHECK(!is_regular_file(it
->status()));
199 CHECK(!is_regular_file(it
->symlink_status()));
200 CHECK(!is_symlink(it
->status()));
201 CHECK(!is_symlink(it
->symlink_status()));
204 for (; it
!= end
; ++it
)
206 //cout << " " << it->path() << "\n";
209 CHECK(recursive_directory_iterator("..") != recursive_directory_iterator());
210 CHECK(recursive_directory_iterator() == end
);
212 #ifndef BOOST_NO_CXX11_RANGE_BASED_FOR
213 for (directory_entry
& x
: recursive_directory_iterator(".."))
215 CHECK(!x
.path().empty());
216 //cout << " " << x.path() << "\n";
218 const recursive_directory_iterator
dir_itr("..");
219 for (directory_entry
& x
: dir_itr
)
221 CHECK(!x
.path().empty());
222 //cout << " " << x.path() << "\n";
226 for (recursive_directory_iterator
itr("..");
227 itr
!= recursive_directory_iterator(); ++itr
)
229 CHECK(!itr
->path().empty());
230 //cout << " " << itr->path() << "\n";
233 cout
<< "recursive_directory_iterator_test complete" << endl
;
236 // operations_test -------------------------------------------------------//
238 void operations_test()
240 cout
<< "operations test..." << endl
;
244 CHECK(!create_directory("/", ec
));
246 CHECK(!boost::filesystem::remove("no-such-file-or-directory"));
247 CHECK(!remove_all("no-such-file-or-directory"));
249 space_info info
= space("/");
251 CHECK(info
.available
<= info
.capacity
);
253 CHECK(equivalent("/", "/"));
254 CHECK(!equivalent("/", "."));
256 std::time_t ft
= last_write_time(".");
258 last_write_time(".", ft
, ec
);
261 // directory_entry_test ------------------------------------------------------------//
263 void directory_entry_test()
265 cout
<< "directory_entry test..." << endl
;
267 directory_entry
de("foo.bar",
268 file_status(regular_file
, owner_all
), file_status(directory_file
, group_all
));
270 CHECK(de
.path() == "foo.bar");
271 CHECK(de
.status() == file_status(regular_file
, owner_all
));
272 CHECK(de
.symlink_status() == file_status(directory_file
, group_all
));
273 CHECK(de
< directory_entry("goo.bar"));
274 CHECK(de
== directory_entry("foo.bar"));
275 CHECK(de
!= directory_entry("goo.bar"));
276 de
.replace_filename("bar.foo");
277 CHECK(de
.path() == "bar.foo");
280 // directory_entry_overload_test ---------------------------------------------------//
282 void directory_entry_overload_test()
284 cout
<< "directory_entry overload test..." << endl
;
286 directory_iterator
it(".");
290 // error_handling_test -------------------------------------------------------------//
292 void error_handling_test()
294 cout
<< "error handling test..." << endl
;
299 file_size("no-such-file");
301 catch (const boost::filesystem::filesystem_error
& ex
)
304 cout
<< "\nas expected, attempt to get size of non-existent file threw a filesystem_error\n"
305 "what() returns " << ex
.what() << "\n";
309 cout
<< "\nunexpected exception type caught" << endl
;
315 CHECK(!create_directory("/", ec
));
318 // string_file_tests ---------------------------------------------------------------//
320 void string_file_tests()
322 cout
<< "string_file_tests..." << endl
;
323 std::string
contents("0123456789");
324 path
p(temp_dir
/ "string_file");
325 save_string_file(p
, contents
);
326 save_string_file(p
, contents
);
327 BOOST_TEST_EQ(file_size(p
), 10u);
328 std::string round_trip
;
329 load_string_file(p
, round_trip
);
330 BOOST_TEST_EQ(contents
, round_trip
);
333 } // unnamed namespace
335 //--------------------------------------------------------------------------------------//
339 //--------------------------------------------------------------------------------------//
341 int cpp_main(int, char*[])
343 // document state of critical macros
344 #ifdef BOOST_POSIX_API
345 cout
<< "BOOST_POSIX_API is defined\n";
347 #ifdef BOOST_WINDOWS_API
348 cout
<< "BOOST_WINDOWS_API is defined\n";
350 cout
<< "BOOST_FILESYSTEM_DECL" << BOOST_STRINGIZE(=BOOST_FILESYSTEM_DECL
) << "\n";
351 cout
<< "BOOST_SYMBOL_VISIBLE" << BOOST_STRINGIZE(=BOOST_SYMBOL_VISIBLE
) << "\n";
353 cout
<< "current_path() is " << current_path().string() << endl
;
355 create_directory(temp_dir
);
359 directory_iterator_test();
360 recursive_directory_iterator_test();
362 directory_entry_test();
363 directory_entry_overload_test();
364 error_handling_test();
367 cout
<< unique_path() << endl
;
368 cout
<< unique_path("foo-%%%%%-%%%%%-bar") << endl
;
369 cout
<< unique_path("foo-%%%%%-%%%%%-%%%%%-%%%%%-%%%%%-%%%%%-%%%%%-%%%%-bar") << endl
;
370 cout
<< unique_path("foo-%%%%%-%%%%%-%%%%%-%%%%%-%%%%%-%%%%%-%%%%%-%%%%%-bar") << endl
;
372 cout
<< "testing complete" << endl
;
377 cout
<< "post-test removal of " << temp_dir
<< endl
;
378 BOOST_TEST(remove_all(temp_dir
) != 0);
379 // above was added just to simplify testing, but it ended up detecting
380 // a bug (failure to close an internal search handle).
381 cout
<< "post-test removal complete" << endl
;
382 // BOOST_TEST(!fs::exists(dir)); // nice test, but doesn't play well with TortoiseGit cache
385 return ::boost::report_errors();