gtest-filepath_test.cc revision fbaaef999ba563838ebd00874ed8a1c01fbf286d
1// Copyright 2008, Google Inc.
2// All rights reserved.
3//
4// Redistribution and use in source and binary forms, with or without
5// modification, are permitted provided that the following conditions are
6// met:
7//
8//     * Redistributions of source code must retain the above copyright
9// notice, this list of conditions and the following disclaimer.
10//     * Redistributions in binary form must reproduce the above
11// copyright notice, this list of conditions and the following disclaimer
12// in the documentation and/or other materials provided with the
13// distribution.
14//     * Neither the name of Google Inc. nor the names of its
15// contributors may be used to endorse or promote products derived from
16// this software without specific prior written permission.
17//
18// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
19// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
20// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
21// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
22// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
23// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
24// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
25// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
26// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
27// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
28// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
29//
30// Authors: keith.ray@gmail.com (Keith Ray)
31//
32// Google Test filepath utilities
33//
34// This file tests classes and functions used internally by
35// Google Test.  They are subject to change without notice.
36//
37// This file is #included from gtest_unittest.cc, to avoid changing
38// build or make-files for some existing Google Test clients. Do not
39// #include this file anywhere else!
40
41#include <gtest/internal/gtest-filepath.h>
42#include <gtest/gtest.h>
43
44// Indicates that this translation unit is part of Google Test's
45// implementation.  It must come before gtest-internal-inl.h is
46// included, or there will be a compiler error.  This trick is to
47// prevent a user from accidentally including gtest-internal-inl.h in
48// his code.
49#define GTEST_IMPLEMENTATION_ 1
50#include "src/gtest-internal-inl.h"
51#undef GTEST_IMPLEMENTATION_
52
53#ifdef _WIN32_WCE
54#include <windows.h>  // NOLINT
55#elif GTEST_OS_WINDOWS
56#include <direct.h>  // NOLINT
57#endif  // _WIN32_WCE
58
59namespace testing {
60namespace internal {
61namespace {
62
63#ifdef _WIN32_WCE
64// TODO(wan@google.com): Move these to the POSIX adapter section in
65// gtest-port.h.
66
67// Windows CE doesn't have the remove C function.
68int remove(const char* path) {
69  LPCWSTR wpath = String::AnsiToUtf16(path);
70  int ret = DeleteFile(wpath) ? 0 : -1;
71  delete [] wpath;
72  return ret;
73}
74// Windows CE doesn't have the _rmdir C function.
75int _rmdir(const char* path) {
76  FilePath filepath(path);
77  LPCWSTR wpath = String::AnsiToUtf16(
78      filepath.RemoveTrailingPathSeparator().c_str());
79  int ret = RemoveDirectory(wpath) ? 0 : -1;
80  delete [] wpath;
81  return ret;
82}
83
84#endif  // _WIN32_WCE
85
86#ifndef _WIN32_WCE
87
88TEST(GetCurrentDirTest, ReturnsCurrentDir) {
89  const FilePath original_dir = FilePath::GetCurrentDir();
90  EXPECT_FALSE(original_dir.IsEmpty());
91
92  posix::ChDir(GTEST_PATH_SEP_);
93  const FilePath cwd = FilePath::GetCurrentDir();
94  posix::ChDir(original_dir.c_str());
95
96#if GTEST_OS_WINDOWS
97  // Skips the ":".
98  const char* const cwd_without_drive = strchr(cwd.c_str(), ':');
99  ASSERT_TRUE(cwd_without_drive != NULL);
100  EXPECT_STREQ(GTEST_PATH_SEP_, cwd_without_drive + 1);
101#else
102  EXPECT_STREQ(GTEST_PATH_SEP_, cwd.c_str());
103#endif
104}
105
106#endif  // _WIN32_WCE
107
108TEST(IsEmptyTest, ReturnsTrueForEmptyPath) {
109  EXPECT_TRUE(FilePath("").IsEmpty());
110  EXPECT_TRUE(FilePath(NULL).IsEmpty());
111}
112
113TEST(IsEmptyTest, ReturnsFalseForNonEmptyPath) {
114  EXPECT_FALSE(FilePath("a").IsEmpty());
115  EXPECT_FALSE(FilePath(".").IsEmpty());
116  EXPECT_FALSE(FilePath("a/b").IsEmpty());
117  EXPECT_FALSE(FilePath("a\\b\\").IsEmpty());
118}
119
120// RemoveDirectoryName "" -> ""
121TEST(RemoveDirectoryNameTest, WhenEmptyName) {
122  EXPECT_STREQ("", FilePath("").RemoveDirectoryName().c_str());
123}
124
125// RemoveDirectoryName "afile" -> "afile"
126TEST(RemoveDirectoryNameTest, ButNoDirectory) {
127  EXPECT_STREQ("afile",
128      FilePath("afile").RemoveDirectoryName().c_str());
129}
130
131// RemoveDirectoryName "/afile" -> "afile"
132TEST(RemoveDirectoryNameTest, RootFileShouldGiveFileName) {
133  EXPECT_STREQ("afile",
134      FilePath(GTEST_PATH_SEP_ "afile").RemoveDirectoryName().c_str());
135}
136
137// RemoveDirectoryName "adir/" -> ""
138TEST(RemoveDirectoryNameTest, WhereThereIsNoFileName) {
139  EXPECT_STREQ("",
140      FilePath("adir" GTEST_PATH_SEP_).RemoveDirectoryName().c_str());
141}
142
143// RemoveDirectoryName "adir/afile" -> "afile"
144TEST(RemoveDirectoryNameTest, ShouldGiveFileName) {
145  EXPECT_STREQ("afile",
146      FilePath("adir" GTEST_PATH_SEP_ "afile").RemoveDirectoryName().c_str());
147}
148
149// RemoveDirectoryName "adir/subdir/afile" -> "afile"
150TEST(RemoveDirectoryNameTest, ShouldAlsoGiveFileName) {
151  EXPECT_STREQ("afile",
152      FilePath("adir" GTEST_PATH_SEP_ "subdir" GTEST_PATH_SEP_ "afile")
153      .RemoveDirectoryName().c_str());
154}
155
156
157// RemoveFileName "" -> "./"
158TEST(RemoveFileNameTest, EmptyName) {
159#ifdef _WIN32_WCE
160  // On Windows CE, we use the root as the current directory.
161  EXPECT_STREQ(GTEST_PATH_SEP_,
162      FilePath("").RemoveFileName().c_str());
163#else
164  EXPECT_STREQ("." GTEST_PATH_SEP_,
165      FilePath("").RemoveFileName().c_str());
166#endif
167}
168
169// RemoveFileName "adir/" -> "adir/"
170TEST(RemoveFileNameTest, ButNoFile) {
171  EXPECT_STREQ("adir" GTEST_PATH_SEP_,
172      FilePath("adir" GTEST_PATH_SEP_).RemoveFileName().c_str());
173}
174
175// RemoveFileName "adir/afile" -> "adir/"
176TEST(RemoveFileNameTest, GivesDirName) {
177  EXPECT_STREQ("adir" GTEST_PATH_SEP_,
178      FilePath("adir" GTEST_PATH_SEP_ "afile")
179      .RemoveFileName().c_str());
180}
181
182// RemoveFileName "adir/subdir/afile" -> "adir/subdir/"
183TEST(RemoveFileNameTest, GivesDirAndSubDirName) {
184  EXPECT_STREQ("adir" GTEST_PATH_SEP_ "subdir" GTEST_PATH_SEP_,
185      FilePath("adir" GTEST_PATH_SEP_ "subdir" GTEST_PATH_SEP_ "afile")
186      .RemoveFileName().c_str());
187}
188
189// RemoveFileName "/afile" -> "/"
190TEST(RemoveFileNameTest, GivesRootDir) {
191  EXPECT_STREQ(GTEST_PATH_SEP_,
192      FilePath(GTEST_PATH_SEP_ "afile").RemoveFileName().c_str());
193}
194
195
196TEST(MakeFileNameTest, GenerateWhenNumberIsZero) {
197  FilePath actual = FilePath::MakeFileName(FilePath("foo"), FilePath("bar"),
198      0, "xml");
199  EXPECT_STREQ("foo" GTEST_PATH_SEP_ "bar.xml", actual.c_str());
200}
201
202TEST(MakeFileNameTest, GenerateFileNameNumberGtZero) {
203  FilePath actual = FilePath::MakeFileName(FilePath("foo"), FilePath("bar"),
204      12, "xml");
205  EXPECT_STREQ("foo" GTEST_PATH_SEP_ "bar_12.xml", actual.c_str());
206}
207
208TEST(MakeFileNameTest, GenerateFileNameWithSlashNumberIsZero) {
209  FilePath actual = FilePath::MakeFileName(FilePath("foo" GTEST_PATH_SEP_),
210      FilePath("bar"), 0, "xml");
211  EXPECT_STREQ("foo" GTEST_PATH_SEP_ "bar.xml", actual.c_str());
212}
213
214TEST(MakeFileNameTest, GenerateFileNameWithSlashNumberGtZero) {
215  FilePath actual = FilePath::MakeFileName(FilePath("foo" GTEST_PATH_SEP_),
216      FilePath("bar"), 12, "xml");
217  EXPECT_STREQ("foo" GTEST_PATH_SEP_ "bar_12.xml", actual.c_str());
218}
219
220TEST(MakeFileNameTest, GenerateWhenNumberIsZeroAndDirIsEmpty) {
221  FilePath actual = FilePath::MakeFileName(FilePath(""), FilePath("bar"),
222      0, "xml");
223  EXPECT_STREQ("bar.xml", actual.c_str());
224}
225
226TEST(MakeFileNameTest, GenerateWhenNumberIsNotZeroAndDirIsEmpty) {
227  FilePath actual = FilePath::MakeFileName(FilePath(""), FilePath("bar"),
228      14, "xml");
229  EXPECT_STREQ("bar_14.xml", actual.c_str());
230}
231
232TEST(ConcatPathsTest, WorksWhenDirDoesNotEndWithPathSep) {
233  FilePath actual = FilePath::ConcatPaths(FilePath("foo"),
234                                          FilePath("bar.xml"));
235  EXPECT_STREQ("foo" GTEST_PATH_SEP_ "bar.xml", actual.c_str());
236}
237
238TEST(ConcatPathsTest, WorksWhenPath1EndsWithPathSep) {
239  FilePath actual = FilePath::ConcatPaths(FilePath("foo" GTEST_PATH_SEP_),
240                                          FilePath("bar.xml"));
241  EXPECT_STREQ("foo" GTEST_PATH_SEP_ "bar.xml", actual.c_str());
242}
243
244TEST(ConcatPathsTest, Path1BeingEmpty) {
245  FilePath actual = FilePath::ConcatPaths(FilePath(""),
246                                          FilePath("bar.xml"));
247  EXPECT_STREQ("bar.xml", actual.c_str());
248}
249
250TEST(ConcatPathsTest, Path2BeingEmpty) {
251  FilePath actual = FilePath::ConcatPaths(FilePath("foo"),
252                                          FilePath(""));
253  EXPECT_STREQ("foo" GTEST_PATH_SEP_, actual.c_str());
254}
255
256TEST(ConcatPathsTest, BothPathBeingEmpty) {
257  FilePath actual = FilePath::ConcatPaths(FilePath(""),
258                                          FilePath(""));
259  EXPECT_STREQ("", actual.c_str());
260}
261
262TEST(ConcatPathsTest, Path1ContainsPathSep) {
263  FilePath actual = FilePath::ConcatPaths(FilePath("foo" GTEST_PATH_SEP_ "bar"),
264                                          FilePath("foobar.xml"));
265  EXPECT_STREQ("foo" GTEST_PATH_SEP_ "bar" GTEST_PATH_SEP_ "foobar.xml",
266               actual.c_str());
267}
268
269TEST(ConcatPathsTest, Path2ContainsPathSep) {
270  FilePath actual = FilePath::ConcatPaths(
271      FilePath("foo" GTEST_PATH_SEP_),
272      FilePath("bar" GTEST_PATH_SEP_ "bar.xml"));
273  EXPECT_STREQ("foo" GTEST_PATH_SEP_ "bar" GTEST_PATH_SEP_ "bar.xml",
274               actual.c_str());
275}
276
277TEST(ConcatPathsTest, Path2EndsWithPathSep) {
278  FilePath actual = FilePath::ConcatPaths(FilePath("foo"),
279                                          FilePath("bar" GTEST_PATH_SEP_));
280  EXPECT_STREQ("foo" GTEST_PATH_SEP_ "bar" GTEST_PATH_SEP_, actual.c_str());
281}
282
283// RemoveTrailingPathSeparator "" -> ""
284TEST(RemoveTrailingPathSeparatorTest, EmptyString) {
285  EXPECT_STREQ("",
286      FilePath("").RemoveTrailingPathSeparator().c_str());
287}
288
289// RemoveTrailingPathSeparator "foo" -> "foo"
290TEST(RemoveTrailingPathSeparatorTest, FileNoSlashString) {
291  EXPECT_STREQ("foo",
292      FilePath("foo").RemoveTrailingPathSeparator().c_str());
293}
294
295// RemoveTrailingPathSeparator "foo/" -> "foo"
296TEST(RemoveTrailingPathSeparatorTest, ShouldRemoveTrailingSeparator) {
297  EXPECT_STREQ(
298      "foo",
299      FilePath("foo" GTEST_PATH_SEP_).RemoveTrailingPathSeparator().c_str());
300}
301
302// RemoveTrailingPathSeparator "foo/bar/" -> "foo/bar/"
303TEST(RemoveTrailingPathSeparatorTest, ShouldRemoveLastSeparator) {
304  EXPECT_STREQ("foo" GTEST_PATH_SEP_ "bar",
305               FilePath("foo" GTEST_PATH_SEP_ "bar" GTEST_PATH_SEP_)
306               .RemoveTrailingPathSeparator().c_str());
307}
308
309// RemoveTrailingPathSeparator "foo/bar" -> "foo/bar"
310TEST(RemoveTrailingPathSeparatorTest, ShouldReturnUnmodified) {
311  EXPECT_STREQ("foo" GTEST_PATH_SEP_ "bar",
312               FilePath("foo" GTEST_PATH_SEP_ "bar")
313               .RemoveTrailingPathSeparator().c_str());
314}
315
316TEST(DirectoryTest, RootDirectoryExists) {
317#if GTEST_OS_WINDOWS  // We are on Windows.
318  char current_drive[_MAX_PATH];  // NOLINT
319  current_drive[0] = static_cast<char>(_getdrive() + 'A' - 1);
320  current_drive[1] = ':';
321  current_drive[2] = '\\';
322  current_drive[3] = '\0';
323  EXPECT_TRUE(FilePath(current_drive).DirectoryExists());
324#else
325  EXPECT_TRUE(FilePath("/").DirectoryExists());
326#endif  // GTEST_OS_WINDOWS
327}
328
329#if GTEST_OS_WINDOWS
330TEST(DirectoryTest, RootOfWrongDriveDoesNotExists) {
331  const int saved_drive_ = _getdrive();
332  // Find a drive that doesn't exist. Start with 'Z' to avoid common ones.
333  for (char drive = 'Z'; drive >= 'A'; drive--)
334    if (_chdrive(drive - 'A' + 1) == -1) {
335      char non_drive[_MAX_PATH];  // NOLINT
336      non_drive[0] = drive;
337      non_drive[1] = ':';
338      non_drive[2] = '\\';
339      non_drive[3] = '\0';
340      EXPECT_FALSE(FilePath(non_drive).DirectoryExists());
341      break;
342    }
343  _chdrive(saved_drive_);
344}
345#endif  // GTEST_OS_WINDOWS
346
347#ifndef _WIN32_WCE
348// Windows CE _does_ consider an empty directory to exist.
349TEST(DirectoryTest, EmptyPathDirectoryDoesNotExist) {
350  EXPECT_FALSE(FilePath("").DirectoryExists());
351}
352#endif  // ! _WIN32_WCE
353
354TEST(DirectoryTest, CurrentDirectoryExists) {
355#if GTEST_OS_WINDOWS  // We are on Windows.
356#ifndef _WIN32_CE  // Windows CE doesn't have a current directory.
357  EXPECT_TRUE(FilePath(".").DirectoryExists());
358  EXPECT_TRUE(FilePath(".\\").DirectoryExists());
359#endif  // _WIN32_CE
360#else
361  EXPECT_TRUE(FilePath(".").DirectoryExists());
362  EXPECT_TRUE(FilePath("./").DirectoryExists());
363#endif  // GTEST_OS_WINDOWS
364}
365
366TEST(NormalizeTest, NullStringsEqualEmptyDirectory) {
367  EXPECT_STREQ("", FilePath(NULL).c_str());
368  EXPECT_STREQ("", FilePath(String(NULL)).c_str());
369}
370
371// "foo/bar" == foo//bar" == "foo///bar"
372TEST(NormalizeTest, MultipleConsecutiveSepaparatorsInMidstring) {
373  EXPECT_STREQ("foo" GTEST_PATH_SEP_ "bar",
374               FilePath("foo" GTEST_PATH_SEP_ "bar").c_str());
375  EXPECT_STREQ("foo" GTEST_PATH_SEP_ "bar",
376               FilePath("foo" GTEST_PATH_SEP_ GTEST_PATH_SEP_ "bar").c_str());
377  EXPECT_STREQ("foo" GTEST_PATH_SEP_ "bar",
378               FilePath("foo" GTEST_PATH_SEP_ GTEST_PATH_SEP_
379                        GTEST_PATH_SEP_ "bar").c_str());
380}
381
382// "/bar" == //bar" == "///bar"
383TEST(NormalizeTest, MultipleConsecutiveSepaparatorsAtStringStart) {
384  EXPECT_STREQ(GTEST_PATH_SEP_ "bar",
385    FilePath(GTEST_PATH_SEP_ "bar").c_str());
386  EXPECT_STREQ(GTEST_PATH_SEP_ "bar",
387    FilePath(GTEST_PATH_SEP_ GTEST_PATH_SEP_ "bar").c_str());
388  EXPECT_STREQ(GTEST_PATH_SEP_ "bar",
389    FilePath(GTEST_PATH_SEP_ GTEST_PATH_SEP_ GTEST_PATH_SEP_ "bar").c_str());
390}
391
392// "foo/" == foo//" == "foo///"
393TEST(NormalizeTest, MultipleConsecutiveSepaparatorsAtStringEnd) {
394  EXPECT_STREQ("foo" GTEST_PATH_SEP_,
395    FilePath("foo" GTEST_PATH_SEP_).c_str());
396  EXPECT_STREQ("foo" GTEST_PATH_SEP_,
397    FilePath("foo" GTEST_PATH_SEP_ GTEST_PATH_SEP_).c_str());
398  EXPECT_STREQ("foo" GTEST_PATH_SEP_,
399    FilePath("foo" GTEST_PATH_SEP_ GTEST_PATH_SEP_ GTEST_PATH_SEP_).c_str());
400}
401
402TEST(AssignmentOperatorTest, DefaultAssignedToNonDefault) {
403  FilePath default_path;
404  FilePath non_default_path("path");
405  non_default_path = default_path;
406  EXPECT_STREQ("", non_default_path.c_str());
407  EXPECT_STREQ("", default_path.c_str());  // RHS var is unchanged.
408}
409
410TEST(AssignmentOperatorTest, NonDefaultAssignedToDefault) {
411  FilePath non_default_path("path");
412  FilePath default_path;
413  default_path = non_default_path;
414  EXPECT_STREQ("path", default_path.c_str());
415  EXPECT_STREQ("path", non_default_path.c_str());  // RHS var is unchanged.
416}
417
418TEST(AssignmentOperatorTest, ConstAssignedToNonConst) {
419  const FilePath const_default_path("const_path");
420  FilePath non_default_path("path");
421  non_default_path = const_default_path;
422  EXPECT_STREQ("const_path", non_default_path.c_str());
423}
424
425class DirectoryCreationTest : public Test {
426 protected:
427  virtual void SetUp() {
428    testdata_path_.Set(FilePath(String::Format("%s%s%s",
429        TempDir().c_str(), GetCurrentExecutableName().c_str(),
430        "_directory_creation" GTEST_PATH_SEP_ "test" GTEST_PATH_SEP_)));
431    testdata_file_.Set(testdata_path_.RemoveTrailingPathSeparator());
432
433    unique_file0_.Set(FilePath::MakeFileName(testdata_path_, FilePath("unique"),
434        0, "txt"));
435    unique_file1_.Set(FilePath::MakeFileName(testdata_path_, FilePath("unique"),
436        1, "txt"));
437
438    remove(testdata_file_.c_str());
439    remove(unique_file0_.c_str());
440    remove(unique_file1_.c_str());
441    posix::RmDir(testdata_path_.c_str());
442  }
443
444  virtual void TearDown() {
445    remove(testdata_file_.c_str());
446    remove(unique_file0_.c_str());
447    remove(unique_file1_.c_str());
448    posix::RmDir(testdata_path_.c_str());
449  }
450
451  String TempDir() const {
452#ifdef _WIN32_WCE
453    return String("\\temp\\");
454
455#elif GTEST_OS_WINDOWS
456    const char* temp_dir = posix::GetEnv("TEMP");
457    if (temp_dir == NULL || temp_dir[0] == '\0')
458      return String("\\temp\\");
459    else if (String(temp_dir).EndsWith("\\"))
460      return String(temp_dir);
461    else
462      return String::Format("%s\\", temp_dir);
463#else
464    return String("/tmp/");
465#endif
466  }
467
468  void CreateTextFile(const char* filename) {
469    FILE* f = posix::FOpen(filename, "w");
470    fprintf(f, "text\n");
471    fclose(f);
472  }
473
474  // Strings representing a directory and a file, with identical paths
475  // except for the trailing separator character that distinquishes
476  // a directory named 'test' from a file named 'test'. Example names:
477  FilePath testdata_path_;  // "/tmp/directory_creation/test/"
478  FilePath testdata_file_;  // "/tmp/directory_creation/test"
479  FilePath unique_file0_;  // "/tmp/directory_creation/test/unique.txt"
480  FilePath unique_file1_;  // "/tmp/directory_creation/test/unique_1.txt"
481};
482
483TEST_F(DirectoryCreationTest, CreateDirectoriesRecursively) {
484  EXPECT_FALSE(testdata_path_.DirectoryExists()) << testdata_path_.c_str();
485  EXPECT_TRUE(testdata_path_.CreateDirectoriesRecursively());
486  EXPECT_TRUE(testdata_path_.DirectoryExists());
487}
488
489TEST_F(DirectoryCreationTest, CreateDirectoriesForAlreadyExistingPath) {
490  EXPECT_FALSE(testdata_path_.DirectoryExists()) << testdata_path_.c_str();
491  EXPECT_TRUE(testdata_path_.CreateDirectoriesRecursively());
492  // Call 'create' again... should still succeed.
493  EXPECT_TRUE(testdata_path_.CreateDirectoriesRecursively());
494}
495
496TEST_F(DirectoryCreationTest, CreateDirectoriesAndUniqueFilename) {
497  FilePath file_path(FilePath::GenerateUniqueFileName(testdata_path_,
498      FilePath("unique"), "txt"));
499  EXPECT_STREQ(unique_file0_.c_str(), file_path.c_str());
500  EXPECT_FALSE(file_path.FileOrDirectoryExists());  // file not there
501
502  testdata_path_.CreateDirectoriesRecursively();
503  EXPECT_FALSE(file_path.FileOrDirectoryExists());  // file still not there
504  CreateTextFile(file_path.c_str());
505  EXPECT_TRUE(file_path.FileOrDirectoryExists());
506
507  FilePath file_path2(FilePath::GenerateUniqueFileName(testdata_path_,
508      FilePath("unique"), "txt"));
509  EXPECT_STREQ(unique_file1_.c_str(), file_path2.c_str());
510  EXPECT_FALSE(file_path2.FileOrDirectoryExists());  // file not there
511  CreateTextFile(file_path2.c_str());
512  EXPECT_TRUE(file_path2.FileOrDirectoryExists());
513}
514
515TEST_F(DirectoryCreationTest, CreateDirectoriesFail) {
516  // force a failure by putting a file where we will try to create a directory.
517  CreateTextFile(testdata_file_.c_str());
518  EXPECT_TRUE(testdata_file_.FileOrDirectoryExists());
519  EXPECT_FALSE(testdata_file_.DirectoryExists());
520  EXPECT_FALSE(testdata_file_.CreateDirectoriesRecursively());
521}
522
523TEST(NoDirectoryCreationTest, CreateNoDirectoriesForDefaultXmlFile) {
524  const FilePath test_detail_xml("test_detail.xml");
525  EXPECT_FALSE(test_detail_xml.CreateDirectoriesRecursively());
526}
527
528TEST(FilePathTest, DefaultConstructor) {
529  FilePath fp;
530  EXPECT_STREQ("", fp.c_str());
531}
532
533TEST(FilePathTest, CharAndCopyConstructors) {
534  const FilePath fp("spicy");
535  EXPECT_STREQ("spicy", fp.c_str());
536
537  const FilePath fp_copy(fp);
538  EXPECT_STREQ("spicy", fp_copy.c_str());
539}
540
541TEST(FilePathTest, StringConstructor) {
542  const FilePath fp(String("cider"));
543  EXPECT_STREQ("cider", fp.c_str());
544}
545
546TEST(FilePathTest, Set) {
547  const FilePath apple("apple");
548  FilePath mac("mac");
549  mac.Set(apple);  // Implement Set() since overloading operator= is forbidden.
550  EXPECT_STREQ("apple", mac.c_str());
551  EXPECT_STREQ("apple", apple.c_str());
552}
553
554TEST(FilePathTest, ToString) {
555  const FilePath file("drink");
556  String str(file.ToString());
557  EXPECT_STREQ("drink", str.c_str());
558}
559
560TEST(FilePathTest, RemoveExtension) {
561  EXPECT_STREQ("app", FilePath("app.exe").RemoveExtension("exe").c_str());
562  EXPECT_STREQ("APP", FilePath("APP.EXE").RemoveExtension("exe").c_str());
563}
564
565TEST(FilePathTest, RemoveExtensionWhenThereIsNoExtension) {
566  EXPECT_STREQ("app", FilePath("app").RemoveExtension("exe").c_str());
567}
568
569TEST(FilePathTest, IsDirectory) {
570  EXPECT_FALSE(FilePath("cola").IsDirectory());
571  EXPECT_TRUE(FilePath("koala" GTEST_PATH_SEP_).IsDirectory());
572}
573
574TEST(FilePathTest, IsAbsolutePath) {
575  EXPECT_FALSE(FilePath("is" GTEST_PATH_SEP_ "relative").IsAbsolutePath());
576  EXPECT_FALSE(FilePath("").IsAbsolutePath());
577#if GTEST_OS_WINDOWS
578  EXPECT_TRUE(FilePath("c:\\" GTEST_PATH_SEP_ "is_not"
579                       GTEST_PATH_SEP_ "relative").IsAbsolutePath());
580  EXPECT_FALSE(FilePath("c:foo" GTEST_PATH_SEP_ "bar").IsAbsolutePath());
581#else
582  EXPECT_TRUE(FilePath(GTEST_PATH_SEP_ "is_not" GTEST_PATH_SEP_ "relative")
583              .IsAbsolutePath());
584#endif  // GTEST_OS_WINDOWS
585}
586
587}  // namespace
588}  // namespace internal
589}  // namespace testing
590
591#undef GTEST_PATH_SEP_
592