blob: 267322009b83e10b6d6adc29e322b7879b8a9de1 [file] [log] [blame]
mark@chromium.org6380e262008-10-04 03:21:47 +09001// Copyright (c) 2008 The Chromium Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
mark@chromium.org6380e262008-10-04 03:21:47 +09005#include "base/basictypes.h"
aa@chromium.org76e5c632008-12-18 17:38:16 +09006#include "base/file_path.h"
7#include "base/file_util.h"
erikkay@google.comc51bf5f2009-01-22 07:15:57 +09008#include "base/string_util.h"
mark@chromium.orge3e1ce72008-10-04 04:05:46 +09009#include "testing/gtest/include/gtest/gtest.h"
aa@chromium.org76e5c632008-12-18 17:38:16 +090010#include "testing/platform_test.h"
mark@chromium.org6380e262008-10-04 03:21:47 +090011
12// This macro helps avoid wrapped lines in the test structs.
13#define FPL(x) FILE_PATH_LITERAL(x)
14
15struct UnaryTestData {
16 const FilePath::CharType* input;
17 const FilePath::CharType* expected;
18};
19
20struct UnaryBooleanTestData {
21 const FilePath::CharType* input;
22 bool expected;
23};
24
25struct BinaryTestData {
26 const FilePath::CharType* inputs[2];
27 const FilePath::CharType* expected;
28};
29
rafaelw@chromium.org465facc2009-06-25 06:28:30 +090030struct BinaryBooleanTestData {
31 const FilePath::CharType* inputs[2];
32 bool expected;
33};
34
rolandsteiner@chromium.org7cde0312009-10-28 14:40:09 +090035struct BinaryIntTestData {
36 const FilePath::CharType* inputs[2];
37 int expected;
38};
39
aa@chromium.org76e5c632008-12-18 17:38:16 +090040// file_util winds up using autoreleased objects on the Mac, so this needs
41// to be a PlatformTest
42class FilePathTest : public PlatformTest {
43 protected:
44 virtual void SetUp() {
45 PlatformTest::SetUp();
46 }
47 virtual void TearDown() {
48 PlatformTest::TearDown();
49 }
50};
51
52TEST_F(FilePathTest, DirName) {
mark@chromium.org6380e262008-10-04 03:21:47 +090053 const struct UnaryTestData cases[] = {
54 { FPL(""), FPL(".") },
55 { FPL("aa"), FPL(".") },
56 { FPL("/aa/bb"), FPL("/aa") },
57 { FPL("/aa/bb/"), FPL("/aa") },
58 { FPL("/aa/bb//"), FPL("/aa") },
59 { FPL("/aa/bb/ccc"), FPL("/aa/bb") },
60 { FPL("/aa"), FPL("/") },
61 { FPL("/aa/"), FPL("/") },
62 { FPL("/"), FPL("/") },
63 { FPL("//"), FPL("//") },
64 { FPL("///"), FPL("/") },
65 { FPL("aa/"), FPL(".") },
66 { FPL("aa/bb"), FPL("aa") },
67 { FPL("aa/bb/"), FPL("aa") },
68 { FPL("aa/bb//"), FPL("aa") },
69 { FPL("aa//bb//"), FPL("aa") },
70 { FPL("aa//bb/"), FPL("aa") },
71 { FPL("aa//bb"), FPL("aa") },
72 { FPL("//aa/bb"), FPL("//aa") },
73 { FPL("//aa/"), FPL("//") },
74 { FPL("//aa"), FPL("//") },
75 { FPL("0:"), FPL(".") },
76 { FPL("@:"), FPL(".") },
77 { FPL("[:"), FPL(".") },
78 { FPL("`:"), FPL(".") },
79 { FPL("{:"), FPL(".") },
80 { FPL("\xB3:"), FPL(".") },
81 { FPL("\xC5:"), FPL(".") },
82#if defined(OS_WIN)
83 { FPL("\x0143:"), FPL(".") },
84#endif // OS_WIN
85#if defined(FILE_PATH_USES_DRIVE_LETTERS)
86 { FPL("c:"), FPL("c:") },
87 { FPL("C:"), FPL("C:") },
88 { FPL("A:"), FPL("A:") },
89 { FPL("Z:"), FPL("Z:") },
90 { FPL("a:"), FPL("a:") },
91 { FPL("z:"), FPL("z:") },
92 { FPL("c:aa"), FPL("c:") },
93 { FPL("c:/"), FPL("c:/") },
94 { FPL("c://"), FPL("c://") },
95 { FPL("c:///"), FPL("c:/") },
96 { FPL("c:/aa"), FPL("c:/") },
97 { FPL("c:/aa/"), FPL("c:/") },
98 { FPL("c:/aa/bb"), FPL("c:/aa") },
99 { FPL("c:aa/bb"), FPL("c:aa") },
100#endif // FILE_PATH_USES_DRIVE_LETTERS
101#if defined(FILE_PATH_USES_WIN_SEPARATORS)
102 { FPL("\\aa\\bb"), FPL("\\aa") },
103 { FPL("\\aa\\bb\\"), FPL("\\aa") },
104 { FPL("\\aa\\bb\\\\"), FPL("\\aa") },
105 { FPL("\\aa\\bb\\ccc"), FPL("\\aa\\bb") },
106 { FPL("\\aa"), FPL("\\") },
107 { FPL("\\aa\\"), FPL("\\") },
108 { FPL("\\"), FPL("\\") },
109 { FPL("\\\\"), FPL("\\\\") },
110 { FPL("\\\\\\"), FPL("\\") },
111 { FPL("aa\\"), FPL(".") },
112 { FPL("aa\\bb"), FPL("aa") },
113 { FPL("aa\\bb\\"), FPL("aa") },
114 { FPL("aa\\bb\\\\"), FPL("aa") },
115 { FPL("aa\\\\bb\\\\"), FPL("aa") },
116 { FPL("aa\\\\bb\\"), FPL("aa") },
117 { FPL("aa\\\\bb"), FPL("aa") },
118 { FPL("\\\\aa\\bb"), FPL("\\\\aa") },
119 { FPL("\\\\aa\\"), FPL("\\\\") },
120 { FPL("\\\\aa"), FPL("\\\\") },
121#if defined(FILE_PATH_USES_DRIVE_LETTERS)
122 { FPL("c:\\"), FPL("c:\\") },
123 { FPL("c:\\\\"), FPL("c:\\\\") },
124 { FPL("c:\\\\\\"), FPL("c:\\") },
125 { FPL("c:\\aa"), FPL("c:\\") },
126 { FPL("c:\\aa\\"), FPL("c:\\") },
127 { FPL("c:\\aa\\bb"), FPL("c:\\aa") },
128 { FPL("c:aa\\bb"), FPL("c:aa") },
129#endif // FILE_PATH_USES_DRIVE_LETTERS
130#endif // FILE_PATH_USES_WIN_SEPARATORS
131 };
132
133 for (size_t i = 0; i < arraysize(cases); ++i) {
134 FilePath input(cases[i].input);
135 FilePath observed = input.DirName();
136 EXPECT_EQ(FilePath::StringType(cases[i].expected), observed.value()) <<
137 "i: " << i << ", input: " << input.value();
138 }
139}
140
aa@chromium.org76e5c632008-12-18 17:38:16 +0900141TEST_F(FilePathTest, BaseName) {
mark@chromium.org6380e262008-10-04 03:21:47 +0900142 const struct UnaryTestData cases[] = {
143 { FPL(""), FPL("") },
144 { FPL("aa"), FPL("aa") },
145 { FPL("/aa/bb"), FPL("bb") },
146 { FPL("/aa/bb/"), FPL("bb") },
147 { FPL("/aa/bb//"), FPL("bb") },
148 { FPL("/aa/bb/ccc"), FPL("ccc") },
149 { FPL("/aa"), FPL("aa") },
150 { FPL("/"), FPL("/") },
151 { FPL("//"), FPL("//") },
152 { FPL("///"), FPL("/") },
153 { FPL("aa/"), FPL("aa") },
154 { FPL("aa/bb"), FPL("bb") },
155 { FPL("aa/bb/"), FPL("bb") },
156 { FPL("aa/bb//"), FPL("bb") },
157 { FPL("aa//bb//"), FPL("bb") },
158 { FPL("aa//bb/"), FPL("bb") },
159 { FPL("aa//bb"), FPL("bb") },
160 { FPL("//aa/bb"), FPL("bb") },
161 { FPL("//aa/"), FPL("aa") },
162 { FPL("//aa"), FPL("aa") },
163 { FPL("0:"), FPL("0:") },
164 { FPL("@:"), FPL("@:") },
165 { FPL("[:"), FPL("[:") },
166 { FPL("`:"), FPL("`:") },
167 { FPL("{:"), FPL("{:") },
168 { FPL("\xB3:"), FPL("\xB3:") },
169 { FPL("\xC5:"), FPL("\xC5:") },
170#if defined(OS_WIN)
171 { FPL("\x0143:"), FPL("\x0143:") },
172#endif // OS_WIN
173#if defined(FILE_PATH_USES_DRIVE_LETTERS)
174 { FPL("c:"), FPL("") },
175 { FPL("C:"), FPL("") },
176 { FPL("A:"), FPL("") },
177 { FPL("Z:"), FPL("") },
178 { FPL("a:"), FPL("") },
179 { FPL("z:"), FPL("") },
180 { FPL("c:aa"), FPL("aa") },
181 { FPL("c:/"), FPL("/") },
182 { FPL("c://"), FPL("//") },
183 { FPL("c:///"), FPL("/") },
184 { FPL("c:/aa"), FPL("aa") },
185 { FPL("c:/aa/"), FPL("aa") },
186 { FPL("c:/aa/bb"), FPL("bb") },
187 { FPL("c:aa/bb"), FPL("bb") },
188#endif // FILE_PATH_USES_DRIVE_LETTERS
189#if defined(FILE_PATH_USES_WIN_SEPARATORS)
190 { FPL("\\aa\\bb"), FPL("bb") },
191 { FPL("\\aa\\bb\\"), FPL("bb") },
192 { FPL("\\aa\\bb\\\\"), FPL("bb") },
193 { FPL("\\aa\\bb\\ccc"), FPL("ccc") },
194 { FPL("\\aa"), FPL("aa") },
195 { FPL("\\"), FPL("\\") },
196 { FPL("\\\\"), FPL("\\\\") },
197 { FPL("\\\\\\"), FPL("\\") },
198 { FPL("aa\\"), FPL("aa") },
199 { FPL("aa\\bb"), FPL("bb") },
200 { FPL("aa\\bb\\"), FPL("bb") },
201 { FPL("aa\\bb\\\\"), FPL("bb") },
202 { FPL("aa\\\\bb\\\\"), FPL("bb") },
203 { FPL("aa\\\\bb\\"), FPL("bb") },
204 { FPL("aa\\\\bb"), FPL("bb") },
205 { FPL("\\\\aa\\bb"), FPL("bb") },
206 { FPL("\\\\aa\\"), FPL("aa") },
207 { FPL("\\\\aa"), FPL("aa") },
208#if defined(FILE_PATH_USES_DRIVE_LETTERS)
209 { FPL("c:\\"), FPL("\\") },
210 { FPL("c:\\\\"), FPL("\\\\") },
211 { FPL("c:\\\\\\"), FPL("\\") },
212 { FPL("c:\\aa"), FPL("aa") },
213 { FPL("c:\\aa\\"), FPL("aa") },
214 { FPL("c:\\aa\\bb"), FPL("bb") },
215 { FPL("c:aa\\bb"), FPL("bb") },
216#endif // FILE_PATH_USES_DRIVE_LETTERS
217#endif // FILE_PATH_USES_WIN_SEPARATORS
218 };
219
220 for (size_t i = 0; i < arraysize(cases); ++i) {
221 FilePath input(cases[i].input);
estade@chromium.orgd872d682009-01-06 08:59:36 +0900222 FilePath observed = input.BaseName();
223 EXPECT_EQ(FilePath::StringType(cases[i].expected), observed.value()) <<
mark@chromium.org6380e262008-10-04 03:21:47 +0900224 "i: " << i << ", input: " << input.value();
225 }
226}
227
aa@chromium.org76e5c632008-12-18 17:38:16 +0900228TEST_F(FilePathTest, Append) {
mark@chromium.org6380e262008-10-04 03:21:47 +0900229 const struct BinaryTestData cases[] = {
230 { { FPL(""), FPL("cc") }, FPL("cc") },
231 { { FPL("."), FPL("ff") }, FPL("ff") },
232 { { FPL("/"), FPL("cc") }, FPL("/cc") },
233 { { FPL("/aa"), FPL("") }, FPL("/aa") },
234 { { FPL("/aa/"), FPL("") }, FPL("/aa") },
235 { { FPL("//aa"), FPL("") }, FPL("//aa") },
236 { { FPL("//aa/"), FPL("") }, FPL("//aa") },
237 { { FPL("//"), FPL("aa") }, FPL("//aa") },
238#if defined(FILE_PATH_USES_DRIVE_LETTERS)
239 { { FPL("c:"), FPL("a") }, FPL("c:a") },
240 { { FPL("c:"), FPL("") }, FPL("c:") },
241 { { FPL("c:/"), FPL("a") }, FPL("c:/a") },
242 { { FPL("c://"), FPL("a") }, FPL("c://a") },
243 { { FPL("c:///"), FPL("a") }, FPL("c:/a") },
244#endif // FILE_PATH_USES_DRIVE_LETTERS
245#if defined(FILE_PATH_USES_WIN_SEPARATORS)
246 // Append introduces the default separator character, so these test cases
247 // need to be defined with different expected results on platforms that use
248 // different default separator characters.
249 { { FPL("\\"), FPL("cc") }, FPL("\\cc") },
250 { { FPL("\\aa"), FPL("") }, FPL("\\aa") },
251 { { FPL("\\aa\\"), FPL("") }, FPL("\\aa") },
252 { { FPL("\\\\aa"), FPL("") }, FPL("\\\\aa") },
253 { { FPL("\\\\aa\\"), FPL("") }, FPL("\\\\aa") },
254 { { FPL("\\\\"), FPL("aa") }, FPL("\\\\aa") },
255 { { FPL("/aa/bb"), FPL("cc") }, FPL("/aa/bb\\cc") },
256 { { FPL("/aa/bb/"), FPL("cc") }, FPL("/aa/bb\\cc") },
257 { { FPL("aa/bb/"), FPL("cc") }, FPL("aa/bb\\cc") },
258 { { FPL("aa/bb"), FPL("cc") }, FPL("aa/bb\\cc") },
259 { { FPL("a/b"), FPL("c") }, FPL("a/b\\c") },
260 { { FPL("a/b/"), FPL("c") }, FPL("a/b\\c") },
261 { { FPL("//aa"), FPL("bb") }, FPL("//aa\\bb") },
262 { { FPL("//aa/"), FPL("bb") }, FPL("//aa\\bb") },
263 { { FPL("\\aa\\bb"), FPL("cc") }, FPL("\\aa\\bb\\cc") },
264 { { FPL("\\aa\\bb\\"), FPL("cc") }, FPL("\\aa\\bb\\cc") },
265 { { FPL("aa\\bb\\"), FPL("cc") }, FPL("aa\\bb\\cc") },
266 { { FPL("aa\\bb"), FPL("cc") }, FPL("aa\\bb\\cc") },
267 { { FPL("a\\b"), FPL("c") }, FPL("a\\b\\c") },
268 { { FPL("a\\b\\"), FPL("c") }, FPL("a\\b\\c") },
269 { { FPL("\\\\aa"), FPL("bb") }, FPL("\\\\aa\\bb") },
270 { { FPL("\\\\aa\\"), FPL("bb") }, FPL("\\\\aa\\bb") },
271#if defined(FILE_PATH_USES_DRIVE_LETTERS)
272 { { FPL("c:\\"), FPL("a") }, FPL("c:\\a") },
273 { { FPL("c:\\\\"), FPL("a") }, FPL("c:\\\\a") },
274 { { FPL("c:\\\\\\"), FPL("a") }, FPL("c:\\a") },
275 { { FPL("c:\\"), FPL("") }, FPL("c:\\") },
276 { { FPL("c:\\a"), FPL("b") }, FPL("c:\\a\\b") },
277 { { FPL("c:\\a\\"), FPL("b") }, FPL("c:\\a\\b") },
278#endif // FILE_PATH_USES_DRIVE_LETTERS
279#else // FILE_PATH_USES_WIN_SEPARATORS
280 { { FPL("/aa/bb"), FPL("cc") }, FPL("/aa/bb/cc") },
281 { { FPL("/aa/bb/"), FPL("cc") }, FPL("/aa/bb/cc") },
282 { { FPL("aa/bb/"), FPL("cc") }, FPL("aa/bb/cc") },
283 { { FPL("aa/bb"), FPL("cc") }, FPL("aa/bb/cc") },
284 { { FPL("a/b"), FPL("c") }, FPL("a/b/c") },
285 { { FPL("a/b/"), FPL("c") }, FPL("a/b/c") },
286 { { FPL("//aa"), FPL("bb") }, FPL("//aa/bb") },
287 { { FPL("//aa/"), FPL("bb") }, FPL("//aa/bb") },
288#if defined(FILE_PATH_USES_DRIVE_LETTERS)
289 { { FPL("c:/"), FPL("a") }, FPL("c:/a") },
290 { { FPL("c:/"), FPL("") }, FPL("c:/") },
291 { { FPL("c:/a"), FPL("b") }, FPL("c:/a/b") },
292 { { FPL("c:/a/"), FPL("b") }, FPL("c:/a/b") },
293#endif // FILE_PATH_USES_DRIVE_LETTERS
294#endif // FILE_PATH_USES_WIN_SEPARATORS
295 };
296
297 for (size_t i = 0; i < arraysize(cases); ++i) {
298 FilePath root(cases[i].inputs[0]);
299 FilePath::StringType leaf(cases[i].inputs[1]);
mark@chromium.orgfac7b262008-12-09 01:49:08 +0900300 FilePath observed_str = root.Append(leaf);
301 EXPECT_EQ(FilePath::StringType(cases[i].expected), observed_str.value()) <<
302 "i: " << i << ", root: " << root.value() << ", leaf: " << leaf;
303 FilePath observed_path = root.Append(FilePath(leaf));
304 EXPECT_EQ(FilePath::StringType(cases[i].expected), observed_path.value()) <<
mark@chromium.org6380e262008-10-04 03:21:47 +0900305 "i: " << i << ", root: " << root.value() << ", leaf: " << leaf;
erikkay@google.comc51bf5f2009-01-22 07:15:57 +0900306
307 // TODO(erikkay): It would be nice to have a unicode test append value to
308 // handle the case when AppendASCII is passed UTF8
309#if defined(OS_WIN)
310 std::string ascii = WideToASCII(leaf);
311#elif defined(OS_POSIX)
312 std::string ascii = leaf;
313#endif
314 observed_str = root.AppendASCII(ascii);
315 EXPECT_EQ(FilePath::StringType(cases[i].expected), observed_str.value()) <<
316 "i: " << i << ", root: " << root.value() << ", leaf: " << leaf;
mark@chromium.org6380e262008-10-04 03:21:47 +0900317 }
318}
319
mark@chromium.org778d9cf2009-10-14 02:31:39 +0900320TEST_F(FilePathTest, StripTrailingSeparators) {
321 const struct UnaryTestData cases[] = {
322 { FPL(""), FPL("") },
323 { FPL("/"), FPL("/") },
324 { FPL("//"), FPL("//") },
325 { FPL("///"), FPL("/") },
326 { FPL("////"), FPL("/") },
327 { FPL("a/"), FPL("a") },
328 { FPL("a//"), FPL("a") },
329 { FPL("a///"), FPL("a") },
330 { FPL("a////"), FPL("a") },
331 { FPL("/a"), FPL("/a") },
332 { FPL("/a/"), FPL("/a") },
333 { FPL("/a//"), FPL("/a") },
334 { FPL("/a///"), FPL("/a") },
335 { FPL("/a////"), FPL("/a") },
336#if defined(FILE_PATH_USES_DRIVE_LETTERS)
337 { FPL("c:"), FPL("c:") },
338 { FPL("c:/"), FPL("c:/") },
339 { FPL("c://"), FPL("c://") },
340 { FPL("c:///"), FPL("c:/") },
341 { FPL("c:////"), FPL("c:/") },
342 { FPL("c:/a"), FPL("c:/a") },
343 { FPL("c:/a/"), FPL("c:/a") },
344 { FPL("c:/a//"), FPL("c:/a") },
345 { FPL("c:/a///"), FPL("c:/a") },
346 { FPL("c:/a////"), FPL("c:/a") },
347#endif // FILE_PATH_USES_DRIVE_LETTERS
348#if defined(FILE_PATH_USES_WIN_SEPARATORS)
349 { FPL("\\"), FPL("\\") },
350 { FPL("\\\\"), FPL("\\\\") },
351 { FPL("\\\\\\"), FPL("\\") },
352 { FPL("\\\\\\\\"), FPL("\\") },
353 { FPL("a\\"), FPL("a") },
354 { FPL("a\\\\"), FPL("a") },
355 { FPL("a\\\\\\"), FPL("a") },
356 { FPL("a\\\\\\\\"), FPL("a") },
357 { FPL("\\a"), FPL("\\a") },
358 { FPL("\\a\\"), FPL("\\a") },
359 { FPL("\\a\\\\"), FPL("\\a") },
360 { FPL("\\a\\\\\\"), FPL("\\a") },
361 { FPL("\\a\\\\\\\\"), FPL("\\a") },
362#if defined(FILE_PATH_USES_DRIVE_LETTERS)
363 { FPL("c:\\"), FPL("c:\\") },
364 { FPL("c:\\\\"), FPL("c:\\\\") },
365 { FPL("c:\\\\\\"), FPL("c:\\") },
366 { FPL("c:\\\\\\\\"), FPL("c:\\") },
367 { FPL("c:\\a"), FPL("c:\\a") },
368 { FPL("c:\\a\\"), FPL("c:\\a") },
369 { FPL("c:\\a\\\\"), FPL("c:\\a") },
370 { FPL("c:\\a\\\\\\"), FPL("c:\\a") },
371 { FPL("c:\\a\\\\\\\\"), FPL("c:\\a") },
372#endif // FILE_PATH_USES_DRIVE_LETTERS
373#endif // FILE_PATH_USES_WIN_SEPARATORS
374 };
375
376 for (size_t i = 0; i < arraysize(cases); ++i) {
377 FilePath input(cases[i].input);
378 FilePath observed = input.StripTrailingSeparators();
379 EXPECT_EQ(FilePath::StringType(cases[i].expected), observed.value()) <<
380 "i: " << i << ", input: " << input.value();
381 }
382}
383
aa@chromium.org76e5c632008-12-18 17:38:16 +0900384TEST_F(FilePathTest, IsAbsolute) {
mark@chromium.org6380e262008-10-04 03:21:47 +0900385 const struct UnaryBooleanTestData cases[] = {
386 { FPL(""), false },
387 { FPL("a"), false },
388 { FPL("c:"), false },
389 { FPL("c:a"), false },
390 { FPL("a/b"), false },
391 { FPL("//"), true },
392 { FPL("//a"), true },
393 { FPL("c:a/b"), false },
394 { FPL("?:/a"), false },
395#if defined(FILE_PATH_USES_DRIVE_LETTERS)
396 { FPL("/"), false },
397 { FPL("/a"), false },
398 { FPL("/."), false },
399 { FPL("/.."), false },
400 { FPL("c:/"), true },
401 { FPL("c:/a"), true },
402 { FPL("c:/."), true },
403 { FPL("c:/.."), true },
404 { FPL("C:/a"), true },
405 { FPL("d:/a"), true },
406#else // FILE_PATH_USES_DRIVE_LETTERS
407 { FPL("/"), true },
408 { FPL("/a"), true },
409 { FPL("/."), true },
410 { FPL("/.."), true },
411 { FPL("c:/"), false },
412#endif // FILE_PATH_USES_DRIVE_LETTERS
413#if defined(FILE_PATH_USES_WIN_SEPARATORS)
414 { FPL("a\\b"), false },
415 { FPL("\\\\"), true },
416 { FPL("\\\\a"), true },
417 { FPL("a\\b"), false },
418 { FPL("\\\\"), true },
419 { FPL("//a"), true },
420 { FPL("c:a\\b"), false },
421 { FPL("?:\\a"), false },
422#if defined(FILE_PATH_USES_DRIVE_LETTERS)
423 { FPL("\\"), false },
424 { FPL("\\a"), false },
425 { FPL("\\."), false },
426 { FPL("\\.."), false },
427 { FPL("c:\\"), true },
428 { FPL("c:\\"), true },
429 { FPL("c:\\a"), true },
430 { FPL("c:\\."), true },
431 { FPL("c:\\.."), true },
432 { FPL("C:\\a"), true },
433 { FPL("d:\\a"), true },
434#else // FILE_PATH_USES_DRIVE_LETTERS
435 { FPL("\\"), true },
436 { FPL("\\a"), true },
437 { FPL("\\."), true },
438 { FPL("\\.."), true },
439 { FPL("c:\\"), false },
440#endif // FILE_PATH_USES_DRIVE_LETTERS
441#endif // FILE_PATH_USES_WIN_SEPARATORS
442 };
443
444 for (size_t i = 0; i < arraysize(cases); ++i) {
445 FilePath input(cases[i].input);
446 bool observed = input.IsAbsolute();
447 EXPECT_EQ(cases[i].expected, observed) <<
448 "i: " << i << ", input: " << input.value();
449 }
450}
aa@chromium.org76e5c632008-12-18 17:38:16 +0900451
rafaelw@chromium.org465facc2009-06-25 06:28:30 +0900452TEST_F(FilePathTest, PathComponentsTest) {
453 const struct UnaryTestData cases[] = {
454 { FPL("//foo/bar/baz/"), FPL("|//|foo|bar|baz")},
455 { FPL("///"), FPL("|/")},
456 { FPL("/foo//bar//baz/"), FPL("|/|foo|bar|baz")},
457 { FPL("/foo/bar/baz/"), FPL("|/|foo|bar|baz")},
458 { FPL("/foo/bar/baz//"), FPL("|/|foo|bar|baz")},
459 { FPL("/foo/bar/baz///"), FPL("|/|foo|bar|baz")},
460 { FPL("/foo/bar/baz"), FPL("|/|foo|bar|baz")},
461 { FPL("/foo/bar.bot/baz.txt"), FPL("|/|foo|bar.bot|baz.txt")},
462 { FPL("//foo//bar/baz"), FPL("|//|foo|bar|baz")},
463 { FPL("/"), FPL("|/")},
464 { FPL("foo"), FPL("|foo")},
465 { FPL(""), FPL("")},
466#if defined(FILE_PATH_USES_DRIVE_LETTERS)
467 { FPL("e:/foo"), FPL("|e:|/|foo")},
468 { FPL("e:/"), FPL("|e:|/")},
469 { FPL("e:"), FPL("|e:")},
470#endif // FILE_PATH_USES_DRIVE_LETTERS
471#if defined(FILE_PATH_USES_WIN_SEPARATORS)
472 { FPL("../foo"), FPL("|..|foo")},
473 { FPL("./foo"), FPL("|foo")},
474 { FPL("../foo/bar/"), FPL("|..|foo|bar") },
475 { FPL("\\\\foo\\bar\\baz\\"), FPL("|\\\\|foo|bar|baz")},
476 { FPL("\\\\\\"), FPL("|\\")},
477 { FPL("\\foo\\\\bar\\\\baz\\"), FPL("|\\|foo|bar|baz")},
478 { FPL("\\foo\\bar\\baz\\"), FPL("|\\|foo|bar|baz")},
479 { FPL("\\foo\\bar\\baz\\\\"), FPL("|\\|foo|bar|baz")},
480 { FPL("\\foo\\bar\\baz\\\\\\"), FPL("|\\|foo|bar|baz")},
481 { FPL("\\foo\\bar\\baz"), FPL("|\\|foo|bar|baz")},
482 { FPL("\\foo\\bar/baz\\\\\\"), FPL("|\\|foo|bar|baz")},
483 { FPL("/foo\\bar\\baz"), FPL("|/|foo|bar|baz")},
484 { FPL("\\foo\\bar.bot\\baz.txt"), FPL("|\\|foo|bar.bot|baz.txt")},
485 { FPL("\\\\foo\\\\bar\\baz"), FPL("|\\\\|foo|bar|baz")},
486 { FPL("\\"), FPL("|\\")},
487#endif // FILE_PATH_USES_WIN_SEPARATORS
488 };
489
490 for (size_t i = 0; i < arraysize(cases); ++i) {
491 FilePath input(cases[i].input);
492 std::vector<FilePath::StringType> comps;
493 input.GetComponents(&comps);
494
495 FilePath::StringType observed;
496 for (size_t j = 0; j < comps.size(); ++j) {
497 observed.append(FILE_PATH_LITERAL("|"), 1);
498 observed.append(comps[j]);
499 }
500 EXPECT_EQ(FilePath::StringType(cases[i].expected), observed) <<
501 "i: " << i << ", input: " << input.value();
502 }
503}
504
tim@chromium.org72835072009-10-27 11:17:53 +0900505TEST_F(FilePathTest, AppendAndResolveRelativeTest) {
506 const struct BinaryTestData cases[] = {
507#if defined(FILE_PATH_USES_DRIVE_LETTERS)
508 { { FPL("c:/"), FPL("foo") }, FPL("c:/foo") },
509 { { FPL("f:/foo/bar"), FPL("..") }, FPL("f:/foo") },
510 { { FPL("f:/foo.bar"), FPL("..") }, FPL("f:/") },
511 { { FPL("F:/foo/.."), FPL("./bar/.") }, FPL("F:/bar") },
512 { { FPL("E:/Foo/bar"), FPL("../..") }, FPL("E:/") },
513 { { FPL("E:/Foo/bar/."), FPL("../..") }, FPL("E:/") },
514 { { FPL("e:/foo/.."), FPL("bar/..") }, FPL("e:/") },
515 { { FPL("c:/foo/./bar/.."), FPL("../baz") }, FPL("c:/baz") },
516 { { FPL("E:/./foo/bar/.."), FPL("../baz/..") }, FPL("E:/") },
517 { { FPL("x:/foo/../bar/.."), FPL("baz/../boo") }, FPL("x:/boo") },
518 { { FPL("E:/foo.bar/.."), FPL("../baz/..") }, FPL("") },
519 { { FPL("Z:/foo"), FPL("../..") }, FPL("") },
520 { { FPL("y:/"), FPL("..") }, FPL("") },
521 { { FPL("B:/.."), FPL("bar/.") }, FPL("") },
522 { { FPL("a:/foo/.."), FPL("..") }, FPL("") },
523 { { FPL("r:/.."), FPL("..") }, FPL("") },
524 { { FPL("F:/foo/.."), FPL("../..") }, FPL("") },
525 { { FPL("O:/foo/bar/.."), FPL("../..") }, FPL("") },
526#endif // FILE_PATH_USES_DRIVE_LETTERS
527#if defined(FILE_PATH_USES_WIN_SEPARATORS)
528 { { FPL("\\\\"), FPL("foo") }, FPL("\\\\foo") },
529 { { FPL("\\\\foo"), FPL("bar") }, FPL("\\\\foo\\bar") },
530 { { FPL("\\\\foo\\bar"), FPL("..") }, FPL("\\\\foo") },
531 { { FPL("\\\\foo.bar"), FPL("..") }, FPL("\\\\") },
532 { { FPL("\\\\Foo\\bar"), FPL("..\\..") }, FPL("\\\\") },
533 { { FPL("\\\\Foo\\bar\\."), FPL("..\\..") }, FPL("\\\\") },
534 { { FPL("\\\\foo\\bar"), FPL("foo\\..\\baz") }, FPL("\\\\foo\\bar\\baz") },
535 { { FPL("\\\\foo\\.\\bar"), FPL("..\\baz\\.") }, FPL("\\\\foo\\baz") },
536 { { FPL("\\\\.\\foo\\.."), FPL("bar") }, FPL("\\\\bar") },
537 { { FPL("\\\\foo\\.."), FPL(".\\bar\\..") }, FPL("\\\\") },
538 { { FPL("\\\\foo\\bar\\.."), FPL("..\\baz") }, FPL("\\\\baz") },
539 { { FPL("\\\\foo\\bar\\.."), FPL("..\\baz\\..") }, FPL("\\\\") },
540 { { FPL("\\\\foo\\..\\bar\\.."), FPL("baz\\..\\boo") }, FPL("\\\\boo"), },
541 { { FPL("\\\\foo.bar\\.."), FPL("..\\baz\\..") }, FPL("") },
542 { { FPL("\\\\foo"), FPL("..\\..") }, FPL("") },
543 { { FPL("\\\\"), FPL("..") }, FPL("") },
544 { { FPL("\\\\.."), FPL("bar\\.") }, FPL("") },
545 { { FPL("\\\\foo\\.."), FPL("..") }, FPL("") },
546 { { FPL("\\\\.."), FPL("..") }, FPL("") },
547 { { FPL("\\\\foo\\.."), FPL("..\\..") }, FPL("") },
548 { { FPL("\\\\foo\\bar\\.."), FPL("..\\..") }, FPL("") },
549#if defined(FILE_PATH_USES_DRIVE_LETTERS)
550 { { FPL("E:/foo"), FPL("bar") }, FPL("E:/foo\\bar") },
551 { { FPL("C:/foo/bar"), FPL("foo/../baz") }, FPL("C:/foo\\bar\\baz") },
552 { { FPL("e:/foo/bar"), FPL("../baz") }, FPL("e:/foo\\baz") },
553#endif
554#else // FILE_PATH_USES_WIN_SEPARAORS
555 { { FPL("/"), FPL("foo") }, FPL("/foo") },
556 { { FPL("/foo"), FPL("bar") }, FPL("/foo/bar") },
557 { { FPL("/foo/bar/"), FPL("..") }, FPL("/foo") },
558 { { FPL("/foo.bar"), FPL("..") }, FPL("/") },
559 { { FPL("//foo"), FPL("..") }, FPL("//") },
560 { { FPL("/foo/./bar"), FPL("../..") }, FPL("/") },
561 { { FPL("/foo/bar/."), FPL("foo/../baz") }, FPL("/foo/bar/baz") },
562 { { FPL("/./foo/bar"), FPL("../baz/.") }, FPL("/foo/baz") },
563 { { FPL("/foo/.."), FPL("./bar") }, FPL("/bar") },
564 { { FPL("/foo/.."), FPL("bar/..") }, FPL("/") },
565 { { FPL("//foo/bar/.."), FPL("../baz") }, FPL("//baz") },
566 { { FPL("/foo/bar/.."), FPL("../baz/..") }, FPL("/") },
567 { { FPL("/foo/../bar/.."), FPL("baz/../boo") }, FPL("/boo") },
568 { { FPL("//foo.bar/.."), FPL("../baz") }, FPL("") },
569 { { FPL("/foo"), FPL("../..") }, FPL("") },
570 { { FPL("//"), FPL("..") }, FPL("") },
571 { { FPL("/.."), FPL("./bar") }, FPL("") },
572 { { FPL("/foo/.."), FPL("..") }, FPL("") },
573 { { FPL("/.."), FPL("..") }, FPL("") },
574 { { FPL("/foo/.."), FPL("../..") }, FPL("") },
575 { { FPL("/foo/bar/.."), FPL("../..") }, FPL("") },
576#if defined(FILE_PATH_USES_DRIVE_LETTERS)
577 { { FPL("E:/foo"), FPL("bar") }, FPL("E:/foo/bar") },
578 { { FPL("C:/foo/bar"), FPL("foo/../baz") }, FPL("C:/foo/bar/baz") },
579 { { FPL("e:/foo/bar"), FPL("../baz") }, FPL("e:/foo/baz") },
580#endif
581#endif // FILE_PATH_USES_WIN_SEPARAORS
582 };
583
584 for (size_t i = 0; i < arraysize(cases); ++i) {
585 FilePath parent(cases[i].inputs[0]);
586 FilePath child(cases[i].inputs[1]);
587
588 FilePath result;
589 EXPECT_EQ(cases[i].expected[0] != '\0',
590 parent.AppendAndResolveRelative(child, &result)) <<
591 "i: " << i << ", parent: " << parent.value() << ", child: " <<
592 child.value();
593 EXPECT_STREQ(cases[i].expected, result.value().c_str());
594 }
595}
596
rafaelw@chromium.org465facc2009-06-25 06:28:30 +0900597TEST_F(FilePathTest, IsParentTest) {
598 const struct BinaryBooleanTestData cases[] = {
avi@chromium.org8c3a9b32009-06-30 05:31:29 +0900599 { { FPL("/"), FPL("/foo/bar/baz") }, true},
600 { { FPL("/foo/bar"), FPL("/foo/bar/baz") }, true},
601 { { FPL("/foo/bar/"), FPL("/foo/bar/baz") }, true},
602 { { FPL("//foo/bar/"), FPL("//foo/bar/baz") }, true},
603 { { FPL("/foo/bar"), FPL("/foo2/bar/baz") }, false},
604 { { FPL("/foo/bar.txt"), FPL("/foo/bar/baz") }, false},
605 { { FPL("/foo/bar"), FPL("/foo/bar2/baz") }, false},
606 { { FPL("/foo/bar"), FPL("/foo/bar") }, false},
607 { { FPL("/foo/bar/baz"), FPL("/foo/bar") }, false},
608 { { FPL("foo/bar"), FPL("foo/bar/baz") }, true},
609 { { FPL("foo/bar"), FPL("foo2/bar/baz") }, false},
610 { { FPL("foo/bar"), FPL("foo/bar2/baz") }, false},
611 { { FPL(""), FPL("foo") }, false},
rafaelw@chromium.org465facc2009-06-25 06:28:30 +0900612#if defined(FILE_PATH_USES_DRIVE_LETTERS)
avi@chromium.org8c3a9b32009-06-30 05:31:29 +0900613 { { FPL("c:/foo/bar"), FPL("c:/foo/bar/baz") }, true},
rafaelw@chromium.org724cf542009-07-01 10:03:34 +0900614 { { FPL("E:/foo/bar"), FPL("e:/foo/bar/baz") }, true},
615 { { FPL("f:/foo/bar"), FPL("F:/foo/bar/baz") }, true},
616 { { FPL("E:/Foo/bar"), FPL("e:/foo/bar/baz") }, false},
617 { { FPL("f:/foo/bar"), FPL("F:/foo/Bar/baz") }, false},
avi@chromium.org8c3a9b32009-06-30 05:31:29 +0900618 { { FPL("c:/"), FPL("c:/foo/bar/baz") }, true},
619 { { FPL("c:"), FPL("c:/foo/bar/baz") }, true},
620 { { FPL("c:/foo/bar"), FPL("d:/foo/bar/baz") }, false},
rafaelw@chromium.org724cf542009-07-01 10:03:34 +0900621 { { FPL("c:/foo/bar"), FPL("D:/foo/bar/baz") }, false},
622 { { FPL("C:/foo/bar"), FPL("d:/foo/bar/baz") }, false},
avi@chromium.org8c3a9b32009-06-30 05:31:29 +0900623 { { FPL("c:/foo/bar"), FPL("c:/foo2/bar/baz") }, false},
rafaelw@chromium.org724cf542009-07-01 10:03:34 +0900624 { { FPL("e:/foo/bar"), FPL("E:/foo2/bar/baz") }, false},
625 { { FPL("F:/foo/bar"), FPL("f:/foo2/bar/baz") }, false},
avi@chromium.org8c3a9b32009-06-30 05:31:29 +0900626 { { FPL("c:/foo/bar"), FPL("c:/foo/bar2/baz") }, false},
rafaelw@chromium.org465facc2009-06-25 06:28:30 +0900627#endif // FILE_PATH_USES_DRIVE_LETTERS
628#if defined(FILE_PATH_USES_WIN_SEPARATORS)
avi@chromium.org8c3a9b32009-06-30 05:31:29 +0900629 { { FPL("\\foo\\bar"), FPL("\\foo\\bar\\baz") }, true},
630 { { FPL("\\foo/bar"), FPL("\\foo\\bar\\baz") }, true},
631 { { FPL("\\foo/bar"), FPL("\\foo/bar/baz") }, true},
632 { { FPL("\\"), FPL("\\foo\\bar\\baz") }, true},
633 { { FPL(""), FPL("\\foo\\bar\\baz") }, false},
634 { { FPL("\\foo\\bar"), FPL("\\foo2\\bar\\baz") }, false},
635 { { FPL("\\foo\\bar"), FPL("\\foo\\bar2\\baz") }, false},
rafaelw@chromium.org724cf542009-07-01 10:03:34 +0900636#endif // FILE_PATH_USES_WIN_SEPARATORS
rafaelw@chromium.org465facc2009-06-25 06:28:30 +0900637 };
638
639 for (size_t i = 0; i < arraysize(cases); ++i) {
640 FilePath parent(cases[i].inputs[0]);
641 FilePath child(cases[i].inputs[1]);
642
643 EXPECT_EQ(parent.IsParent(child), cases[i].expected) <<
mad@chromium.orgcc4f7b32009-10-21 00:27:21 +0900644 "i: " << i << ", parent: " << parent.value() << ", child: " <<
645 child.value();
rafaelw@chromium.org465facc2009-06-25 06:28:30 +0900646 }
647}
648
mark@chromium.org752010c2009-09-24 05:32:41 +0900649TEST_F(FilePathTest, AppendRelativePathTest) {
mark@chromium.orgaf9f62a2009-09-17 06:03:44 +0900650 const struct BinaryTestData cases[] = {
mark@chromium.org752010c2009-09-24 05:32:41 +0900651#if defined(FILE_PATH_USES_WIN_SEPARATORS)
652 { { FPL("/"), FPL("/foo/bar/baz") }, FPL("foo\\bar\\baz")},
653#else // FILE_PATH_USES_WIN_SEPARATORS
mark@chromium.orgaf9f62a2009-09-17 06:03:44 +0900654 { { FPL("/"), FPL("/foo/bar/baz") }, FPL("foo/bar/baz")},
mark@chromium.org752010c2009-09-24 05:32:41 +0900655#endif // FILE_PATH_USES_WIN_SEPARATORS
mark@chromium.orgaf9f62a2009-09-17 06:03:44 +0900656 { { FPL("/foo/bar"), FPL("/foo/bar/baz") }, FPL("baz")},
657 { { FPL("/foo/bar/"), FPL("/foo/bar/baz") }, FPL("baz")},
658 { { FPL("//foo/bar/"), FPL("//foo/bar/baz") }, FPL("baz")},
659 { { FPL("/foo/bar"), FPL("/foo2/bar/baz") }, FPL("")},
660 { { FPL("/foo/bar.txt"), FPL("/foo/bar/baz") }, FPL("")},
661 { { FPL("/foo/bar"), FPL("/foo/bar2/baz") }, FPL("")},
662 { { FPL("/foo/bar"), FPL("/foo/bar") }, FPL("")},
663 { { FPL("/foo/bar/baz"), FPL("/foo/bar") }, FPL("")},
664 { { FPL("foo/bar"), FPL("foo/bar/baz") }, FPL("baz")},
665 { { FPL("foo/bar"), FPL("foo2/bar/baz") }, FPL("")},
666 { { FPL("foo/bar"), FPL("foo/bar2/baz") }, FPL("")},
667 { { FPL(""), FPL("foo") }, FPL("")},
668#if defined(FILE_PATH_USES_DRIVE_LETTERS)
669 { { FPL("c:/foo/bar"), FPL("c:/foo/bar/baz") }, FPL("baz")},
670 { { FPL("E:/foo/bar"), FPL("e:/foo/bar/baz") }, FPL("baz")},
671 { { FPL("f:/foo/bar"), FPL("F:/foo/bar/baz") }, FPL("baz")},
672 { { FPL("E:/Foo/bar"), FPL("e:/foo/bar/baz") }, FPL("")},
673 { { FPL("f:/foo/bar"), FPL("F:/foo/Bar/baz") }, FPL("")},
mark@chromium.org752010c2009-09-24 05:32:41 +0900674#if defined(FILE_PATH_USES_WIN_SEPARATORS)
675 { { FPL("c:/"), FPL("c:/foo/bar/baz") }, FPL("foo\\bar\\baz")},
676 // TODO(akalin): Figure out how to handle the corner case in the
677 // commented-out test case below. Appending to an empty path gives
678 // /foo\bar\baz but appending to a nonempty path "blah" gives
679 // blah\foo\bar\baz.
680 // { { FPL("c:"), FPL("c:/foo/bar/baz") }, FPL("foo\\bar\\baz")},
681#endif // FILE_PATH_USES_WIN_SEPARATORS
mark@chromium.orgaf9f62a2009-09-17 06:03:44 +0900682 { { FPL("c:/foo/bar"), FPL("d:/foo/bar/baz") }, FPL("")},
683 { { FPL("c:/foo/bar"), FPL("D:/foo/bar/baz") }, FPL("")},
684 { { FPL("C:/foo/bar"), FPL("d:/foo/bar/baz") }, FPL("")},
685 { { FPL("c:/foo/bar"), FPL("c:/foo2/bar/baz") }, FPL("")},
686 { { FPL("e:/foo/bar"), FPL("E:/foo2/bar/baz") }, FPL("")},
687 { { FPL("F:/foo/bar"), FPL("f:/foo2/bar/baz") }, FPL("")},
688 { { FPL("c:/foo/bar"), FPL("c:/foo/bar2/baz") }, FPL("")},
689#endif // FILE_PATH_USES_DRIVE_LETTERS
690#if defined(FILE_PATH_USES_WIN_SEPARATORS)
691 { { FPL("\\foo\\bar"), FPL("\\foo\\bar\\baz") }, FPL("baz")},
692 { { FPL("\\foo/bar"), FPL("\\foo\\bar\\baz") }, FPL("baz")},
693 { { FPL("\\foo/bar"), FPL("\\foo/bar/baz") }, FPL("baz")},
694 { { FPL("\\"), FPL("\\foo\\bar\\baz") }, FPL("foo\\bar\\baz")},
695 { { FPL(""), FPL("\\foo\\bar\\baz") }, FPL("")},
696 { { FPL("\\foo\\bar"), FPL("\\foo2\\bar\\baz") }, FPL("")},
697 { { FPL("\\foo\\bar"), FPL("\\foo\\bar2\\baz") }, FPL("")},
698#endif // FILE_PATH_USES_WIN_SEPARATORS
699 };
700
701 const FilePath base(FPL("blah"));
702
703 for (size_t i = 0; i < arraysize(cases); ++i) {
704 FilePath parent(cases[i].inputs[0]);
705 FilePath child(cases[i].inputs[1]);
706 {
707 FilePath result;
708 bool success = parent.AppendRelativePath(child, &result);
709 EXPECT_EQ(cases[i].expected[0] != '\0', success) <<
710 "i: " << i << ", parent: " << parent.value() << ", child: " <<
711 child.value();
712 EXPECT_STREQ(cases[i].expected, result.value().c_str()) <<
713 "i: " << i << ", parent: " << parent.value() << ", child: " <<
714 child.value();
715 }
716 {
717 FilePath result(base);
718 bool success = parent.AppendRelativePath(child, &result);
719 EXPECT_EQ(cases[i].expected[0] != '\0', success) <<
720 "i: " << i << ", parent: " << parent.value() << ", child: " <<
721 child.value();
722 EXPECT_EQ(base.Append(cases[i].expected).value(), result.value()) <<
723 "i: " << i << ", parent: " << parent.value() << ", child: " <<
724 child.value();
725 }
726 }
727}
728
rafaelw@chromium.org724cf542009-07-01 10:03:34 +0900729TEST_F(FilePathTest, EqualityTest) {
730 const struct BinaryBooleanTestData cases[] = {
731 { { FPL("/foo/bar/baz"), FPL("/foo/bar/baz") }, true},
732 { { FPL("/foo/bar"), FPL("/foo/bar/baz") }, false},
733 { { FPL("/foo/bar/baz"), FPL("/foo/bar") }, false},
734 { { FPL("//foo/bar/"), FPL("//foo/bar/") }, true},
735 { { FPL("/foo/bar"), FPL("/foo2/bar") }, false},
736 { { FPL("/foo/bar.txt"), FPL("/foo/bar") }, false},
737 { { FPL("foo/bar"), FPL("foo/bar") }, true},
738 { { FPL("foo/bar"), FPL("foo/bar/baz") }, false},
739 { { FPL(""), FPL("foo") }, false},
740#if defined(FILE_PATH_USES_DRIVE_LETTERS)
741 { { FPL("c:/foo/bar"), FPL("c:/foo/bar") }, true},
742 { { FPL("E:/foo/bar"), FPL("e:/foo/bar") }, true},
743 { { FPL("f:/foo/bar"), FPL("F:/foo/bar") }, true},
744 { { FPL("E:/Foo/bar"), FPL("e:/foo/bar") }, false},
745 { { FPL("f:/foo/bar"), FPL("F:/foo/Bar") }, false},
746 { { FPL("c:/"), FPL("c:/") }, true},
747 { { FPL("c:"), FPL("c:") }, true},
748 { { FPL("c:/foo/bar"), FPL("d:/foo/bar") }, false},
749 { { FPL("c:/foo/bar"), FPL("D:/foo/bar") }, false},
750 { { FPL("C:/foo/bar"), FPL("d:/foo/bar") }, false},
751 { { FPL("c:/foo/bar"), FPL("c:/foo2/bar") }, false},
752#endif // FILE_PATH_USES_DRIVE_LETTERS
753#if defined(FILE_PATH_USES_WIN_SEPARATORS)
754 { { FPL("\\foo\\bar"), FPL("\\foo\\bar") }, true},
755 { { FPL("\\foo/bar"), FPL("\\foo/bar") }, true},
756 { { FPL("\\foo/bar"), FPL("\\foo\bar") }, false},
757 { { FPL("\\"), FPL("\\") }, true},
758 { { FPL("\\"), FPL("/") }, false},
759 { { FPL(""), FPL("\\") }, false},
760 { { FPL("\\foo\\bar"), FPL("\\foo2\\bar") }, false},
761 { { FPL("\\foo\\bar"), FPL("\\foo\\bar2") }, false},
762#if defined(FILE_PATH_USES_DRIVE_LETTERS)
763 { { FPL("c:\\foo\\bar"), FPL("c:\\foo\\bar") }, true},
764 { { FPL("E:\\foo\\bar"), FPL("e:\\foo\\bar") }, true},
765 { { FPL("f:\\foo\\bar"), FPL("F:\\foo/bar") }, false},
766#endif // FILE_PATH_USES_DRIVE_LETTERS
767#endif // FILE_PATH_USES_WIN_SEPARATORS
768 };
769
770 for (size_t i = 0; i < arraysize(cases); ++i) {
771 FilePath a(cases[i].inputs[0]);
772 FilePath b(cases[i].inputs[1]);
773
774 EXPECT_EQ(a == b, cases[i].expected) <<
775 "equality i: " << i << ", a: " << a.value() << ", b: " <<
776 b.value();
777 }
778
rafaelw@chromium.org724cf542009-07-01 10:03:34 +0900779 for (size_t i = 0; i < arraysize(cases); ++i) {
780 FilePath a(cases[i].inputs[0]);
781 FilePath b(cases[i].inputs[1]);
782
783 EXPECT_EQ(a != b, !cases[i].expected) <<
784 "inequality i: " << i << ", a: " << a.value() << ", b: " <<
785 b.value();
786 }
787}
788
erikkay@google.com985d4202009-01-10 03:26:19 +0900789TEST_F(FilePathTest, Extension) {
790 FilePath base_dir(FILE_PATH_LITERAL("base_dir"));
791
792 FilePath jpg = base_dir.Append(FILE_PATH_LITERAL("foo.jpg"));
793 EXPECT_EQ(jpg.Extension(), FILE_PATH_LITERAL(".jpg"));
794
795 FilePath base = jpg.BaseName().RemoveExtension();
796 EXPECT_EQ(base.value(), FILE_PATH_LITERAL("foo"));
797
798 FilePath path_no_ext = base_dir.Append(base);
799 EXPECT_EQ(jpg.RemoveExtension().value(), path_no_ext.value());
800
801 EXPECT_EQ(path_no_ext.value(), path_no_ext.RemoveExtension().value());
802 EXPECT_EQ(path_no_ext.Extension(), FILE_PATH_LITERAL(""));
803}
804
805TEST_F(FilePathTest, Extension2) {
806 const struct UnaryTestData cases[] = {
807#if defined(FILE_PATH_USES_WIN_SEPARATORS)
808 { FPL("C:\\a\\b\\c.ext"), FPL(".ext") },
809 { FPL("C:\\a\\b\\c."), FPL(".") },
810 { FPL("C:\\a\\b\\c"), FPL("") },
811 { FPL("C:\\a\\b\\"), FPL("") },
812 { FPL("C:\\a\\b.\\"), FPL(".") },
813 { FPL("C:\\a\\b\\c.ext1.ext2"), FPL(".ext2") },
814 { FPL("C:\\foo.bar\\\\\\"), FPL(".bar") },
815 { FPL("C:\\foo.bar\\.."), FPL("") },
816 { FPL("C:\\foo.bar\\..\\\\"), FPL("") },
817#endif
818 { FPL("/foo/bar/baz.ext"), FPL(".ext") },
819 { FPL("/foo/bar/baz."), FPL(".") },
820 { FPL("/foo/bar/baz.."), FPL(".") },
821 { FPL("/foo/bar/baz"), FPL("") },
822 { FPL("/foo/bar/"), FPL("") },
823 { FPL("/foo/bar./"), FPL(".") },
824 { FPL("/foo/bar/baz.ext1.ext2"), FPL(".ext2") },
825 { FPL("."), FPL("") },
826 { FPL(".."), FPL("") },
827 { FPL("./foo"), FPL("") },
828 { FPL("./foo.ext"), FPL(".ext") },
829 { FPL("/foo.ext1/bar.ext2"), FPL(".ext2") },
830 { FPL("/foo.bar////"), FPL(".bar") },
831 { FPL("/foo.bar/.."), FPL("") },
832 { FPL("/foo.bar/..////"), FPL("") },
833 };
834 for (unsigned int i = 0; i < arraysize(cases); ++i) {
835 FilePath path(cases[i].input);
836 FilePath::StringType extension = path.Extension();
837 EXPECT_STREQ(cases[i].expected, extension.c_str()) << "i: " << i <<
838 ", path: " << path.value();
839 }
840}
841
842TEST_F(FilePathTest, InsertBeforeExtension) {
843 const struct BinaryTestData cases[] = {
844 { { FPL(""), FPL("") }, FPL("") },
845 { { FPL(""), FPL("txt") }, FPL("") },
846 { { FPL("."), FPL("txt") }, FPL("") },
847 { { FPL(".."), FPL("txt") }, FPL("") },
848 { { FPL("foo.dll"), FPL("txt") }, FPL("footxt.dll") },
849 { { FPL("."), FPL("") }, FPL(".") },
850 { { FPL("foo.dll"), FPL(".txt") }, FPL("foo.txt.dll") },
851 { { FPL("foo"), FPL("txt") }, FPL("footxt") },
852 { { FPL("foo"), FPL(".txt") }, FPL("foo.txt") },
853 { { FPL("foo.baz.dll"), FPL("txt") }, FPL("foo.baztxt.dll") },
854 { { FPL("foo.baz.dll"), FPL(".txt") }, FPL("foo.baz.txt.dll") },
855 { { FPL("foo.dll"), FPL("") }, FPL("foo.dll") },
856 { { FPL("foo.dll"), FPL(".") }, FPL("foo..dll") },
857 { { FPL("foo"), FPL("") }, FPL("foo") },
858 { { FPL("foo"), FPL(".") }, FPL("foo.") },
859 { { FPL("foo.baz.dll"), FPL("") }, FPL("foo.baz.dll") },
860 { { FPL("foo.baz.dll"), FPL(".") }, FPL("foo.baz..dll") },
861#if defined(FILE_PATH_USES_WIN_SEPARATORS)
862 { { FPL("\\"), FPL("") }, FPL("\\") },
863 { { FPL("\\"), FPL("txt") }, FPL("\\txt") },
864 { { FPL("\\."), FPL("txt") }, FPL("") },
865 { { FPL("\\.."), FPL("txt") }, FPL("") },
866 { { FPL("\\."), FPL("") }, FPL("\\.") },
867 { { FPL("C:\\bar\\foo.dll"), FPL("txt") },
868 FPL("C:\\bar\\footxt.dll") },
869 { { FPL("C:\\bar.baz\\foodll"), FPL("txt") },
870 FPL("C:\\bar.baz\\foodlltxt") },
871 { { FPL("C:\\bar.baz\\foo.dll"), FPL("txt") },
872 FPL("C:\\bar.baz\\footxt.dll") },
873 { { FPL("C:\\bar.baz\\foo.dll.exe"), FPL("txt") },
874 FPL("C:\\bar.baz\\foo.dlltxt.exe") },
875 { { FPL("C:\\bar.baz\\foo"), FPL("") },
876 FPL("C:\\bar.baz\\foo") },
877 { { FPL("C:\\bar.baz\\foo.exe"), FPL("") },
878 FPL("C:\\bar.baz\\foo.exe") },
879 { { FPL("C:\\bar.baz\\foo.dll.exe"), FPL("") },
880 FPL("C:\\bar.baz\\foo.dll.exe") },
881 { { FPL("C:\\bar\\baz\\foo.exe"), FPL(" (1)") },
882 FPL("C:\\bar\\baz\\foo (1).exe") },
883 { { FPL("C:\\foo.baz\\\\"), FPL(" (1)") }, FPL("C:\\foo (1).baz") },
884 { { FPL("C:\\foo.baz\\..\\"), FPL(" (1)") }, FPL("") },
885#endif
886 { { FPL("/"), FPL("") }, FPL("/") },
887 { { FPL("/"), FPL("txt") }, FPL("/txt") },
888 { { FPL("/."), FPL("txt") }, FPL("") },
889 { { FPL("/.."), FPL("txt") }, FPL("") },
890 { { FPL("/."), FPL("") }, FPL("/.") },
891 { { FPL("/bar/foo.dll"), FPL("txt") }, FPL("/bar/footxt.dll") },
892 { { FPL("/bar.baz/foodll"), FPL("txt") }, FPL("/bar.baz/foodlltxt") },
893 { { FPL("/bar.baz/foo.dll"), FPL("txt") }, FPL("/bar.baz/footxt.dll") },
894 { { FPL("/bar.baz/foo.dll.exe"), FPL("txt") },
895 FPL("/bar.baz/foo.dlltxt.exe") },
896 { { FPL("/bar.baz/foo"), FPL("") }, FPL("/bar.baz/foo") },
897 { { FPL("/bar.baz/foo.exe"), FPL("") }, FPL("/bar.baz/foo.exe") },
898 { { FPL("/bar.baz/foo.dll.exe"), FPL("") }, FPL("/bar.baz/foo.dll.exe") },
899 { { FPL("/bar/baz/foo.exe"), FPL(" (1)") }, FPL("/bar/baz/foo (1).exe") },
900 { { FPL("/bar/baz/..////"), FPL(" (1)") }, FPL("") },
901 };
902 for (unsigned int i = 0; i < arraysize(cases); ++i) {
903 FilePath path(cases[i].inputs[0]);
904 FilePath result = path.InsertBeforeExtension(cases[i].inputs[1]);
905 EXPECT_EQ(cases[i].expected, result.value()) << "i: " << i <<
906 ", path: " << path.value() << ", insert: " << cases[i].inputs[1];
907 }
908}
909
910TEST_F(FilePathTest, ReplaceExtension) {
911 const struct BinaryTestData cases[] = {
912 { { FPL(""), FPL("") }, FPL("") },
913 { { FPL(""), FPL("txt") }, FPL("") },
914 { { FPL("."), FPL("txt") }, FPL("") },
915 { { FPL(".."), FPL("txt") }, FPL("") },
916 { { FPL("."), FPL("") }, FPL("") },
917 { { FPL("foo.dll"), FPL("txt") }, FPL("foo.txt") },
918 { { FPL("foo..dll"), FPL("txt") }, FPL("foo..txt") },
919 { { FPL("foo.dll"), FPL(".txt") }, FPL("foo.txt") },
920 { { FPL("foo"), FPL("txt") }, FPL("foo.txt") },
921 { { FPL("foo."), FPL("txt") }, FPL("foo.txt") },
922 { { FPL("foo.."), FPL("txt") }, FPL("foo..txt") },
923 { { FPL("foo"), FPL(".txt") }, FPL("foo.txt") },
924 { { FPL("foo.baz.dll"), FPL("txt") }, FPL("foo.baz.txt") },
925 { { FPL("foo.baz.dll"), FPL(".txt") }, FPL("foo.baz.txt") },
926 { { FPL("foo.dll"), FPL("") }, FPL("foo") },
927 { { FPL("foo.dll"), FPL(".") }, FPL("foo") },
928 { { FPL("foo"), FPL("") }, FPL("foo") },
929 { { FPL("foo"), FPL(".") }, FPL("foo") },
930 { { FPL("foo.baz.dll"), FPL("") }, FPL("foo.baz") },
931 { { FPL("foo.baz.dll"), FPL(".") }, FPL("foo.baz") },
932#if defined(FILE_PATH_USES_WIN_SEPARATORS)
933 { { FPL("C:\\foo.bar\\foo"), FPL("baz") }, FPL("C:\\foo.bar\\foo.baz") },
934 { { FPL("C:\\foo.bar\\..\\\\"), FPL("baz") }, FPL("") },
935#endif
936 { { FPL("/foo.bar/foo"), FPL("baz") }, FPL("/foo.bar/foo.baz") },
937 { { FPL("/foo.bar/..////"), FPL("baz") }, FPL("") },
938 };
939 for (unsigned int i = 0; i < arraysize(cases); ++i) {
940 FilePath path(cases[i].inputs[0]);
941 FilePath replaced = path.ReplaceExtension(cases[i].inputs[1]);
942 EXPECT_EQ(cases[i].expected, replaced.value()) << "i: " << i <<
943 ", path: " << path.value() << ", replace: " << cases[i].inputs[1];
944 }
945}
avi@chromium.org8c3a9b32009-06-30 05:31:29 +0900946
947TEST_F(FilePathTest, MatchesExtension) {
948 const struct BinaryBooleanTestData cases[] = {
rolandsteiner@chromium.org7cde0312009-10-28 14:40:09 +0900949 { { FPL("foo"), FPL("") }, true},
950 { { FPL("foo"), FPL(".") }, false},
951 { { FPL("foo."), FPL("") }, false},
952 { { FPL("foo."), FPL(".") }, true},
953 { { FPL("foo.txt"), FPL(".dll") }, false},
954 { { FPL("foo.txt"), FPL(".txt") }, true},
955 { { FPL("foo.txt.dll"), FPL(".txt") }, false},
956 { { FPL("foo.txt.dll"), FPL(".dll") }, true},
957 { { FPL("foo.TXT"), FPL(".txt") }, true},
958 { { FPL("foo.txt"), FPL(".TXT") }, true},
959 { { FPL("foo.tXt"), FPL(".txt") }, true},
960 { { FPL("foo.txt"), FPL(".tXt") }, true},
961 { { FPL("foo.tXt"), FPL(".TXT") }, true},
962 { { FPL("foo.tXt"), FPL(".tXt") }, true},
avi@chromium.org8c3a9b32009-06-30 05:31:29 +0900963#if defined(FILE_PATH_USES_DRIVE_LETTERS)
rolandsteiner@chromium.org7cde0312009-10-28 14:40:09 +0900964 { { FPL("c:/foo.txt.dll"), FPL(".txt") }, false},
965 { { FPL("c:/foo.txt"), FPL(".txt") }, true},
avi@chromium.org8c3a9b32009-06-30 05:31:29 +0900966#endif // FILE_PATH_USES_DRIVE_LETTERS
967#if defined(FILE_PATH_USES_WIN_SEPARATORS)
rolandsteiner@chromium.org7cde0312009-10-28 14:40:09 +0900968 { { FPL("c:\\bar\\foo.txt.dll"), FPL(".txt") }, false},
969 { { FPL("c:\\bar\\foo.txt"), FPL(".txt") }, true},
avi@chromium.org8c3a9b32009-06-30 05:31:29 +0900970#endif // FILE_PATH_USES_DRIVE_LETTERS
rolandsteiner@chromium.org7cde0312009-10-28 14:40:09 +0900971 { { FPL("/bar/foo.txt.dll"), FPL(".txt") }, false},
972 { { FPL("/bar/foo.txt"), FPL(".txt") }, true},
973#if defined(OS_WIN) || defined(OS_MACOSX)
974 // Umlauts A, O, U: direct comparison, and upper case vs. lower case
975 { { FPL("foo.\u00E4\u00F6\u00FC"), FPL(".\u00E4\u00F6\u00FC") }, true},
976 { { FPL("foo.\u00C4\u00D6\u00DC"), FPL(".\u00E4\u00F6\u00FC") }, true},
977 // C with circumflex: direct comparison, and upper case vs. lower case
978 { { FPL("foo.\u0109"), FPL(".\u0109") }, true},
979 { { FPL("foo.\u0108"), FPL(".\u0109") }, true},
980#endif
avi@chromium.org8c3a9b32009-06-30 05:31:29 +0900981 };
982
983 for (size_t i = 0; i < arraysize(cases); ++i) {
984 FilePath path(cases[i].inputs[0]);
985 FilePath::StringType ext(cases[i].inputs[1]);
986
987 EXPECT_EQ(cases[i].expected, path.MatchesExtension(ext)) <<
988 "i: " << i << ", path: " << path.value() << ", ext: " << ext;
989 }
990}
cevans@chromium.org48dc54c2009-08-16 06:44:31 +0900991
rolandsteiner@chromium.org7cde0312009-10-28 14:40:09 +0900992TEST_F(FilePathTest, CompareIgnoreCase) {
993 const struct BinaryIntTestData cases[] = {
994 { { FPL("foo"), FPL("foo") }, 0},
995 { { FPL("FOO"), FPL("foo") }, 0},
996 { { FPL("foo.ext"), FPL("foo.ext") }, 0},
997 { { FPL("FOO.EXT"), FPL("foo.ext") }, 0},
998 { { FPL("Foo.Ext"), FPL("foo.ext") }, 0},
999 { { FPL("foO"), FPL("foo") }, 0},
1000 { { FPL("foo"), FPL("foO") }, 0},
1001 { { FPL("fOo"), FPL("foo") }, 0},
1002 { { FPL("foo"), FPL("fOo") }, 0},
1003 { { FPL("bar"), FPL("foo") }, -1},
1004 { { FPL("foo"), FPL("bar") }, 1},
1005 { { FPL("BAR"), FPL("foo") }, -1},
1006 { { FPL("FOO"), FPL("bar") }, 1},
1007 { { FPL("bar"), FPL("FOO") }, -1},
1008 { { FPL("foo"), FPL("BAR") }, 1},
1009 { { FPL("BAR"), FPL("FOO") }, -1},
1010 { { FPL("FOO"), FPL("BAR") }, 1},
1011 // German "Eszett" (lower case and the new-fangled upper case)
1012 // Note that uc(<lowercase eszett>) => "SS", NOT <uppercase eszett>!
1013 // However, neither Windows nor Mac OSX converts these.
1014 // (or even have glyphs for <uppercase eszett>)
1015 { { FPL("\u00DF"), FPL("\u00DF") }, 0},
1016 { { FPL("\u1E9E"), FPL("\u1E9E") }, 0},
1017 { { FPL("\u00DF"), FPL("\u1E9E") }, -1},
1018 { { FPL("SS"), FPL("\u00DF") }, -1},
1019 { { FPL("SS"), FPL("\u1E9E") }, -1},
1020#if defined(OS_WIN) || defined(OS_MACOSX)
1021 // Umlauts A, O, U: direct comparison, and upper case vs. lower case
1022 { { FPL("\u00E4\u00F6\u00FC"), FPL("\u00E4\u00F6\u00FC") }, 0},
1023 { { FPL("\u00C4\u00D6\u00DC"), FPL("\u00E4\u00F6\u00FC") }, 0},
1024 // C with circumflex: direct comparison, and upper case vs. lower case
1025 { { FPL("\u0109"), FPL("\u0109") }, 0},
1026 { { FPL("\u0108"), FPL("\u0109") }, 0},
1027 // Cyrillic letter SHA: direct comparison, and upper case vs. lower case
1028 { { FPL("\u0428"), FPL("\u0428") }, 0},
1029 { { FPL("\u0428"), FPL("\u0448") }, 0},
1030 // Greek letter DELTA: direct comparison, and upper case vs. lower case
1031 { { FPL("\u0394"), FPL("\u0394") }, 0},
1032 { { FPL("\u0394"), FPL("\u03B4") }, 0},
1033 // Japanese full-width A: direct comparison, and upper case vs. lower case
1034 // Note that full-width and standard characters are considered different.
1035 { { FPL("\uFF21"), FPL("\uFF21") }, 0},
1036 { { FPL("\uFF21"), FPL("\uFF41") }, 0},
1037 { { FPL("A"), FPL("\uFF21") }, -1},
1038 { { FPL("A"), FPL("\uFF41") }, -1},
1039 { { FPL("a"), FPL("\uFF21") }, -1},
1040 { { FPL("a"), FPL("\uFF41") }, -1},
1041#endif
1042#if defined(OS_MACOSX)
1043 // Codepoints > 0x1000
1044 // Georgian letter DON: direct comparison, and upper case vs. lower case
1045 { { FPL("\u10A3"), FPL("\u10A3") }, 0},
1046 { { FPL("\u10A3"), FPL("\u10D3") }, 0},
1047 // Combining characters vs. pre-composed characters, upper and lower case
1048 { { FPL("k\u0301u\u032Do\u0304\u0301n"), FPL("\u1E31\u1E77\u1E53n") }, 0},
1049 { { FPL("k\u0301u\u032Do\u0304\u0301n"), FPL("kuon") }, 1},
1050 { { FPL("kuon"), FPL("k\u0301u\u032Do\u0304\u0301n") }, -1},
1051 { { FPL("K\u0301U\u032DO\u0304\u0301N"), FPL("KUON") }, 1},
1052 { { FPL("KUON"), FPL("K\u0301U\u032DO\u0304\u0301N") }, -1},
1053 { { FPL("k\u0301u\u032Do\u0304\u0301n"), FPL("KUON") }, 1},
1054 { { FPL("K\u0301U\u032DO\u0304\u0301N"), FPL("\u1E31\u1E77\u1E53n") }, 0},
1055 { { FPL("k\u0301u\u032Do\u0304\u0301n"), FPL("\u1E30\u1E76\u1E52n") }, 0},
1056 { { FPL("k\u0301u\u032Do\u0304\u0302n"), FPL("\u1E30\u1E76\u1E52n") }, 1},
1057#endif
1058 };
1059
1060 for (size_t i = 0; i < arraysize(cases); ++i) {
1061 FilePath::StringType s1(cases[i].inputs[0]);
1062 FilePath::StringType s2(cases[i].inputs[1]);
1063 int result = FilePath::CompareIgnoreCase(s1, s2);
1064 EXPECT_EQ(cases[i].expected, result) <<
1065 "i: " << i << ", s1: " << s1 << ", s2: " << s2;
1066 }
1067}
1068
cevans@chromium.org48dc54c2009-08-16 06:44:31 +09001069TEST_F(FilePathTest, ReferencesParent) {
1070 const struct UnaryBooleanTestData cases[] = {
1071 { FPL("."), false },
1072 { FPL(".."), true },
1073 { FPL("a.."), false },
1074 { FPL("..a"), false },
1075 { FPL("../"), true },
1076 { FPL("/.."), true },
1077 { FPL("/../"), true },
1078 { FPL("/a../"), false },
1079 { FPL("/..a/"), false },
1080 { FPL("//.."), true },
1081 { FPL("..//"), true },
1082 { FPL("//..//"), true },
1083 { FPL("a//..//c"), true },
1084 { FPL("../b/c"), true },
1085 { FPL("/../b/c"), true },
1086 { FPL("a/b/.."), true },
1087 { FPL("a/b/../"), true },
1088 { FPL("a/../c"), true },
1089 { FPL("a/b/c"), false },
1090 };
1091
1092 for (size_t i = 0; i < arraysize(cases); ++i) {
1093 FilePath input(cases[i].input);
1094 bool observed = input.ReferencesParent();
1095 EXPECT_EQ(cases[i].expected, observed) <<
1096 "i: " << i << ", input: " << input.value();
1097 }
1098}