merge with master
[platform/framework/web/wrt-commons.git] / tests / utils / path_tests.cpp
1 /*
2  * Copyright (c) 2013 Samsung Electronics Co., Ltd All Rights Reserved
3  *
4  *    Licensed under the Apache License, Version 2.0 (the "License");
5  *    you may not use this file except in compliance with the License.
6  *    You may obtain a copy of the License at
7  *
8  *        http://www.apache.org/licenses/LICENSE-2.0
9  *
10  *    Unless required by applicable law or agreed to in writing, software
11  *    distributed under the License is distributed on an "AS IS" BASIS,
12  *    WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  *    See the License for the specific language governing permissions and
14  *    limitations under the License.
15  */
16 /**
17  * @file    path.h
18  * @author  Tomasz Iwanek (t.iwanek@samsung.com)
19  * @version 1.0
20  */
21
22 #include <set>
23 #include <memory>
24
25 #include <dpl/test/test_runner.h>
26 #include <dpl/scoped_dir.h>
27 #include <dpl/scoped_free.h>
28 #include <dpl/utils/path.h>
29 #include <dpl/foreach.h>
30 #include <dpl/log/log.h>
31
32 #include <sys/stat.h>
33 #include <unistd.h>
34
35 using namespace DPL::Utils;
36
37 namespace {
38 //do not used path here we test it
39 std::string rootTest = "/tmp/wrttest/";
40 }
41
42 RUNNER_TEST_GROUP_INIT(DPL_Path)
43
44 /*
45 Name: path_touch
46 Description: constructs paths in many ways
47 Expected: success full constrution
48 */
49 RUNNER_TEST(path_mkfile)
50 {
51     DPL::ScopedDir sd(rootTest);
52
53     struct stat st;
54     Path path = Path(rootTest) / "touch.txt";
55     RUNNER_ASSERT_MSG(lstat(path.Fullpath().c_str(), &st) != 0, "File should not be created");
56     RUNNER_ASSERT(!path.Exists());
57     MakeEmptyFile(path);
58     RUNNER_ASSERT_MSG(lstat(path.Fullpath().c_str(), &st) == 0, "File should be created");
59     RUNNER_ASSERT(path.Exists());
60     RUNNER_ASSERT(path.IsFile());
61     RUNNER_ASSERT(!path.IsDir());
62     RUNNER_ASSERT(!path.IsSymlink());
63 }
64
65 /*
66 Name: path_touch
67 Description: tries to craete file when it exists
68 Expected: failure
69 */
70 RUNNER_TEST(path_mkfile_exists)
71 {
72     DPL::ScopedDir sd(rootTest);
73
74     Path path = Path(rootTest) / "touch.txt";
75     MakeEmptyFile(path);
76     RUNNER_ASSERT(path.Exists());
77     bool cannotCreate2ndTime = false;
78     Try
79     {
80         MakeEmptyFile(path);
81     }
82     Catch(Path::AlreadyExists)
83     {
84         cannotCreate2ndTime = true;
85     }
86     RUNNER_ASSERT_MSG(cannotCreate2ndTime, "File created should not be able to be created second time");
87 }
88
89 /*
90 Name: path_mkfile_invalid_path
91 Description: tries to create file in not exisitng directory
92 Expected: failure at creation
93 */
94 RUNNER_TEST(path_mkfile_invalid_path)
95 {
96     DPL::ScopedDir sd(rootTest);
97
98     Path path = Path(rootTest) / "not_existing" / "touch.txt";
99     bool cannotCreate = false;
100     Try
101     {
102         MakeEmptyFile(path);
103     }
104     Catch(Path::OperationFailed)
105     {
106         cannotCreate = true;
107     }
108     RUNNER_ASSERT_MSG(cannotCreate, "File created should not be able to be created");
109 }
110
111 /*
112 Name: path_mkdir
113 Description: creates valid directory
114 Expected: success direcotry creation
115 */
116 RUNNER_TEST(path_mkdir)
117 {
118     DPL::ScopedDir sd(rootTest);
119
120     struct stat st;
121     Path path = Path(rootTest) / "touchDir";
122     RUNNER_ASSERT_MSG(lstat(path.Fullpath().c_str(), &st) != 0, "Directory should not be created");
123     RUNNER_ASSERT(!path.Exists());
124     MakeDir(path);
125     RUNNER_ASSERT_MSG(lstat(path.Fullpath().c_str(), &st) == 0, "Directory should be created");
126     RUNNER_ASSERT(path.Exists());
127     RUNNER_ASSERT(!path.IsFile());
128     RUNNER_ASSERT(path.IsDir());
129     RUNNER_ASSERT(!path.IsSymlink());
130 }
131
132 /*
133 Name: path_symlink
134 Description: chekc if symlink is correctly recognized
135 Expected: method isSymlink returns true
136 */
137 RUNNER_TEST(path_symlink)
138 {
139     DPL::ScopedDir sd(rootTest);
140
141     struct stat st;
142     Path path = Path(rootTest) / "symlink";
143     RUNNER_ASSERT_MSG(lstat(path.Fullpath().c_str(), &st) != 0, "Symlink should not be created");
144     RUNNER_ASSERT(!path.Exists());
145     (void)symlink("/nonexistisfile/file/file/file ", path.Fullpath().c_str());
146     RUNNER_ASSERT_MSG(lstat(path.Fullpath().c_str(), &st) == 0, "Symlink should be created");
147     RUNNER_ASSERT(path.Exists());
148     RUNNER_ASSERT(!path.IsFile());
149     RUNNER_ASSERT(!path.IsDir());
150     RUNNER_ASSERT(path.IsSymlink());
151 }
152
153 /*
154 Name: path_construction_empty
155 Description: tries to construct empty path
156 Expected: failure
157 */
158 RUNNER_TEST(path_construction_empty)
159 {
160     bool passed = false;
161     Try
162     {
163         Path path1(std::string(""));
164     }
165     Catch(Path::EmptyPath)
166     {
167         passed = true;
168     }
169     RUNNER_ASSERT_MSG(passed, "Construction with empty path do not fails");
170 }
171
172 /*
173 Name: path_construction_root
174 Description: tries to construct root path
175 Expected: success
176 */
177 RUNNER_TEST(path_construction_root)
178 {
179     Path path1(std::string("/"));
180     RUNNER_ASSERT(path1.Fullpath() == "/");
181     RUNNER_ASSERT(path1.Basename() == "");
182     bool passed = false;
183     Try
184     {
185         RUNNER_ASSERT(path1.DirectoryName() == "/");
186     }
187     Catch(Path::InternalError)
188     {
189         passed = true;
190     }
191     RUNNER_ASSERT_MSG(passed, "Directory name for root should be an error");
192 }
193
194 /*
195 Name: path_construction_1
196 Description: constructs paths in many ways
197 Expected: success full constrution
198 */
199 RUNNER_TEST(path_construction_1)
200 {
201     DPL::ScopedFree<char> sf(getcwd(NULL, 0));
202
203     Path path1(std::string("/test/bin/file"));
204     RUNNER_ASSERT(path1.Fullpath() == "/test/bin/file");
205     RUNNER_ASSERT(path1.Basename() == "file");
206     RUNNER_ASSERT(path1.DirectoryName() == "/test/bin");
207 }
208
209 /*
210 Name: path_construction_2
211 Description: constructs paths in many ways
212 Expected: success full constrution
213 */
214 RUNNER_TEST(path_construction_2)
215 {
216     DPL::ScopedFree<char> sf(getcwd(NULL, 0));
217     std::string cwd(sf.Get());
218
219     Path path2(std::string("test/bin/file.eas"));
220     RUNNER_ASSERT(path2.Fullpath() == cwd + "/test/bin/file.eas");
221     RUNNER_ASSERT(path2.Basename() == "file.eas");
222     RUNNER_ASSERT(path2.DirectoryName() == cwd + "/test/bin");
223 }
224
225 /*
226 Name: path_construction_3
227 Description: constructs paths in many ways
228 Expected: success full constrution
229 */
230 RUNNER_TEST(path_construction_3)
231 {
232     DPL::ScopedFree<char> sf(getcwd(NULL, 0));
233     std::string cwd(sf.Get());
234
235     Path path3("test/23/abc");
236     RUNNER_ASSERT(path3.Fullpath() == cwd + "/test/23/abc");
237     RUNNER_ASSERT(path3.Basename() == "abc");
238     RUNNER_ASSERT(path3.DirectoryName() == cwd + "/test/23");
239 }
240
241 /*
242 Name: path_construction_4
243 Description: constructs paths in many ways
244 Expected: success full constrution
245 */
246 RUNNER_TEST(path_construction_4)
247 {
248     DPL::ScopedFree<char> sf(getcwd(NULL, 0));
249
250     Path path4("/test/bin/abc");
251     RUNNER_ASSERT(path4.Fullpath() == "/test/bin/abc");
252     RUNNER_ASSERT(path4.Basename() == "abc");
253     RUNNER_ASSERT(path4.DirectoryName() == "/test/bin");
254 }
255
256 /*
257 Name: path_construction_5
258 Description: constructs paths in many ways
259 Expected: success full constrution
260 */
261 RUNNER_TEST(path_construction_5)
262 {
263     DPL::ScopedFree<char> sf(getcwd(NULL, 0));
264     std::string cwd(sf.Get());
265
266     Path path5(DPL::String(L"test/bin/file.st.exe"));
267     RUNNER_ASSERT(path5.Fullpath() == cwd + "/test/bin/file.st.exe");
268     RUNNER_ASSERT(path5.Basename() == "file.st.exe");
269     RUNNER_ASSERT(path5.DirectoryName() == cwd + "/test/bin");
270 }
271
272 /*
273 Name: path_construction_6
274 Description: constructs paths in many ways
275 Expected: success full constrution
276 */
277 RUNNER_TEST(path_construction_6)
278 {
279     DPL::ScopedFree<char> sf(getcwd(NULL, 0));
280
281     Path path6(DPL::String(L"/test/bin/file"));
282     RUNNER_ASSERT(path6.Fullpath() == "/test/bin/file");
283     RUNNER_ASSERT(path6.Basename() == "file");
284     RUNNER_ASSERT(path6.DirectoryName() == "/test/bin");
285 }
286
287 /*
288 Name: path_construction_7
289 Description: constructs paths in many ways
290 Expected: success full constrution
291 */
292 RUNNER_TEST(path_construction_7)
293 {
294     DPL::ScopedFree<char> sf(getcwd(NULL, 0));
295     std::string cwd(sf.Get());
296
297     Path path7 = Path("test") / "a///23/lol";
298     RUNNER_ASSERT(path7.Fullpath() == cwd + "/test/a/23/lol");
299     RUNNER_ASSERT(path7.Basename() == "lol");
300     RUNNER_ASSERT(path7.DirectoryName() == cwd + "/test/a/23");
301 }
302
303 /*
304 Name: path_construction_8
305 Description: constructs paths in many ways
306 Expected: success full constrution
307 */
308 RUNNER_TEST(path_construction_8)
309 {
310     DPL::ScopedFree<char> sf(getcwd(NULL, 0));
311
312     Path path8 = Path("/test/bin/") / "123" / "dir1.dll";
313     RUNNER_ASSERT(path8.Fullpath() == "/test/bin/123/dir1.dll");
314     RUNNER_ASSERT(path8.Basename() == "dir1.dll");
315     RUNNER_ASSERT(path8.DirectoryName() ==  "/test/bin/123");
316 }
317
318 /*
319 Name: path_construction_9
320 Description: constructs paths in many ways
321 Expected: success full constrution
322 */
323 RUNNER_TEST(path_construction_9)
324 {
325     DPL::ScopedFree<char> sf(getcwd(NULL, 0));
326
327     Path path9 = Path("/test/bin/file.txt//");
328     RUNNER_ASSERT(path9.Fullpath() == "/test/bin/file.txt");
329     RUNNER_ASSERT(path9.Basename() == "file.txt");
330     RUNNER_ASSERT(path9.DirectoryName() ==  "/test/bin");
331 }
332
333 /*
334 Name: path_construction_10
335 Description: constructs paths by appending
336 Expected: success full constrution
337 */
338 RUNNER_TEST(path_construction_10)
339 {
340     Path path10 = Path("/test/");
341     path10 /= "one";
342     path10 /= std::string("two");
343     path10 /= DPL::String(L"three");
344     RUNNER_ASSERT(path10.Fullpath() == "/test/one/two/three");
345     RUNNER_ASSERT(path10.Basename() == "three");
346     RUNNER_ASSERT(path10.DirectoryName() ==  "/test/one/two");
347 }
348
349 /*
350 Name: path_remove
351 Description: tests removing paths
352 Expected: successfull path remove
353 */
354 RUNNER_TEST(path_remove_valid)
355 {
356     DPL::ScopedDir sd(rootTest);
357
358     struct stat st;
359     Path path = Path(rootTest) / "touchDir";
360     RUNNER_ASSERT(!path.Exists());
361
362     MakeDir(path);
363     RUNNER_ASSERT_MSG(lstat(path.Fullpath().c_str(), &st) == 0, "Directory should be created");
364     RUNNER_ASSERT(path.Exists());
365
366     Remove(path);
367     RUNNER_ASSERT_MSG(lstat(path.Fullpath().c_str(), &st) != 0, "Directory should not be created");
368     RUNNER_ASSERT(!path.Exists());
369
370     MakeEmptyFile(path);
371     RUNNER_ASSERT_MSG(lstat(path.Fullpath().c_str(), &st) == 0, "File should be created");
372     RUNNER_ASSERT(path.Exists());
373
374     Remove(path);
375     RUNNER_ASSERT_MSG(lstat(path.Fullpath().c_str(), &st) != 0, "File should not be created");
376     RUNNER_ASSERT(!path.Exists());
377 }
378
379 /*
380 Name: path_remove_invalid
381 Description: tests removing invalid paths
382 Expected: failure at path remove
383 */
384 RUNNER_TEST(path_remove_invalid)
385 {
386     DPL::ScopedDir sd(rootTest);
387
388     Path path = Path(rootTest) / "touchDir";
389
390     bool removedNotExisting = true;
391     Try
392     {
393         Remove(path);
394     }
395     Catch(Path::OperationFailed)
396     {
397         removedNotExisting = false;
398     }
399     RUNNER_ASSERT_MSG(!removedNotExisting, "Removing not existing file");
400 }
401
402 /*
403 Name: path_rename
404 Description: tests path renaming
405 Expected: path is successfully renamed
406 */
407 RUNNER_TEST(path_rename)
408 {
409     DPL::ScopedDir sd(rootTest);
410
411     struct stat st;
412     Path path = Path(rootTest) / "touchDir";
413     Path dirpath = Path(rootTest) / "directory";
414     Path path2 = dirpath / "touchDir2";
415
416     MakeDir(dirpath);
417
418     MakeEmptyFile(path);
419     RUNNER_ASSERT_MSG(lstat(path.Fullpath().c_str(), &st) == 0, "File should be created");
420     RUNNER_ASSERT(path.Exists());
421     RUNNER_ASSERT(!path2.Exists());
422
423     Rename(path, path2);
424     RUNNER_ASSERT(!path.Exists());
425     RUNNER_ASSERT(path2.Exists());
426
427     Rename(path2, path);
428     RUNNER_ASSERT(path.Exists());
429     RUNNER_ASSERT(!path2.Exists());
430
431     //TODO: test for different devices
432 }
433
434 /*
435 Name: path_rename_same
436 Description: tests if renam does not brokens file if target location is equal to source location
437 Expected: path is avaliable
438 */
439 RUNNER_TEST(path_rename_same)
440 {
441     DPL::ScopedDir sd(rootTest);
442
443     struct stat st;
444     Path path = Path(rootTest) / "touchDir";
445
446     MakeDir(path);
447     Rename(path, path);
448     RUNNER_ASSERT(path.Exists());
449 }
450
451 /*
452 Name: path_iterate_not_directory
453 Description: iterates not a directory
454 Expected: success full constrution
455 */
456 RUNNER_TEST(path_iterate_not_directory)
457 {
458     DPL::ScopedDir sd(rootTest);
459
460     Path fileTest = Path(rootTest) / "file.txt";
461     MakeEmptyFile(fileTest);
462
463     bool passed = false;
464     Try
465     {
466         FOREACH(file, fileTest)
467         {
468
469         }
470     }
471     Catch(Path::NotDirectory)
472     {
473         passed = true;
474     }
475     RUNNER_ASSERT(passed);
476 }
477
478 /*
479 Name: path_construction
480 Description: constructs paths in many ways
481 Expected: success full constrution
482 */
483 RUNNER_TEST(path_iterate_empty_directory)
484 {
485     DPL::ScopedDir sd(rootTest);
486
487     Path dirTest = Path(rootTest) / "directory";
488     MakeDir(dirTest);
489
490     bool passed = true;
491     Try
492     {
493         FOREACH(file, dirTest)
494         {
495             passed = false;
496             LogError("Directory should be empty");
497         }
498     }
499     Catch(Path::NotDirectory)
500     {
501         passed = false;
502         LogError("Directory should exists");
503     }
504     RUNNER_ASSERT(passed);
505 }
506
507 /*
508 Name: path_construction
509 Description: constructs paths in many ways
510 Expected: success full constrution
511 */
512 RUNNER_TEST(path_iterate_notempty_directory)
513 {
514     DPL::ScopedDir sd(rootTest);
515
516     Path dirTest = Path(rootTest) / "directory";
517
518     Path path1 = Path(rootTest) / "directory" / "file1";
519     Path path2 = Path(rootTest) / "directory" / "file2";
520     Path path3 = Path(rootTest) / "directory" / "file3";
521
522     std::set<std::string> resultSet;
523     std::set<std::string> testSet;
524     testSet.insert(path1.Fullpath());
525     testSet.insert(path2.Fullpath());
526     testSet.insert(path3.Fullpath());
527
528     MakeDir(dirTest);
529     MakeEmptyFile(path1);
530     MakeEmptyFile(path2);
531     MakeEmptyFile(path3);
532
533     FOREACH(file, dirTest)
534     {
535         resultSet.insert(file->Fullpath());
536     }
537
538     RUNNER_ASSERT_MSG(testSet == resultSet, "Testing");
539 }
540
541 /*
542 Name: path_construction
543 Description: constructs paths in many ways
544 Expected: success full constrution
545 */
546 RUNNER_TEST(path_iterator_copy_constructor)
547 {
548     DPL::ScopedDir sd(rootTest);
549
550     Path dirTest = Path(rootTest) / "directory";
551
552     Path path1 = Path(rootTest) / "directory" / "file1";
553     Path path2 = Path(rootTest) / "directory" / "file2";
554     Path path3 = Path(rootTest) / "directory" / "file3";
555
556     MakeDir(dirTest);
557     MakeEmptyFile(path1);
558     MakeEmptyFile(path2);
559     MakeEmptyFile(path3);
560
561     std::shared_ptr<Path::Iterator> iter1(new Path::Iterator((Path(rootTest) / "directory").Fullpath().c_str()));
562
563     //as it's input iterator it's guaranteed for one element to be iterate only once
564     (*iter1)++;
565     std::shared_ptr<Path::Iterator> iter2(new Path::Iterator( (*iter1)));
566     iter1.reset();
567     (*iter2)++;
568     ++(*iter2);
569     RUNNER_ASSERT_MSG(*iter2 == dirTest.end(), "Iterator is in broken state");
570     iter2.reset();
571 }