- add sources.
[platform/framework/web/crosswalk.git] / src / chrome / installer / util / move_tree_work_item_unittest.cc
1 // Copyright (c) 2011 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
5 #include <windows.h>
6
7 #include <fstream>
8
9 #include "base/base_paths.h"
10 #include "base/file_util.h"
11 #include "base/files/memory_mapped_file.h"
12 #include "base/memory/scoped_ptr.h"
13 #include "base/path_service.h"
14 #include "base/strings/string_util.h"
15 #include "chrome/installer/util/installer_util_test_common.h"
16 #include "chrome/installer/util/move_tree_work_item.h"
17 #include "chrome/installer/util/work_item.h"
18 #include "testing/gtest/include/gtest/gtest.h"
19
20 namespace {
21 class MoveTreeWorkItemTest : public testing::Test {
22  protected:
23   virtual void SetUp() {
24     ASSERT_TRUE(temp_from_dir_.CreateUniqueTempDir());
25     ASSERT_TRUE(temp_to_dir_.CreateUniqueTempDir());
26   }
27
28   base::ScopedTempDir temp_from_dir_;
29   base::ScopedTempDir temp_to_dir_;
30 };
31
32 // Simple function to dump some text into a new file.
33 void CreateTextFile(const std::wstring& filename,
34                     const std::wstring& contents) {
35   std::wofstream file;
36   file.open(WideToASCII(filename).c_str());
37   ASSERT_TRUE(file.is_open());
38   file << contents;
39   file.close();
40 }
41
42 // Simple function to read text from a file.
43 std::wstring ReadTextFile(const base::FilePath& path) {
44   WCHAR contents[64];
45   std::wifstream file;
46   file.open(WideToASCII(path.value()).c_str());
47   EXPECT_TRUE(file.is_open());
48   file.getline(contents, arraysize(contents));
49   file.close();
50   return std::wstring(contents);
51 }
52
53 const wchar_t kTextContent1[] = L"Gooooooooooooooooooooogle";
54 const wchar_t kTextContent2[] = L"Overwrite Me";
55 };  // namespace
56
57 // Move one directory from source to destination when destination does not
58 // exist.
59 TEST_F(MoveTreeWorkItemTest, MoveDirectory) {
60   // Create two level deep source dir
61   base::FilePath from_dir1(temp_from_dir_.path());
62   from_dir1 = from_dir1.AppendASCII("From_Dir1");
63   file_util::CreateDirectory(from_dir1);
64   ASSERT_TRUE(base::PathExists(from_dir1));
65
66   base::FilePath from_dir2(from_dir1);
67   from_dir2 = from_dir2.AppendASCII("From_Dir2");
68   file_util::CreateDirectory(from_dir2);
69   ASSERT_TRUE(base::PathExists(from_dir2));
70
71   base::FilePath from_file(from_dir2);
72   from_file = from_file.AppendASCII("From_File");
73   CreateTextFile(from_file.value(), kTextContent1);
74   ASSERT_TRUE(base::PathExists(from_file));
75
76   // Generate destination path
77   base::FilePath to_dir(temp_from_dir_.path());
78   to_dir = to_dir.AppendASCII("To_Dir");
79   ASSERT_FALSE(base::PathExists(to_dir));
80
81   base::FilePath to_file(to_dir);
82   to_file = to_file.AppendASCII("From_Dir2");
83   to_file = to_file.AppendASCII("From_File");
84   ASSERT_FALSE(base::PathExists(to_file));
85
86   // test Do()
87   scoped_ptr<MoveTreeWorkItem> work_item(
88       WorkItem::CreateMoveTreeWorkItem(from_dir1,
89                                        to_dir,
90                                        temp_to_dir_.path(),
91                                        WorkItem::ALWAYS_MOVE));
92   EXPECT_TRUE(work_item->Do());
93
94   EXPECT_FALSE(base::PathExists(from_dir1));
95   EXPECT_TRUE(base::PathExists(to_dir));
96   EXPECT_TRUE(base::PathExists(to_file));
97
98   // test rollback()
99   work_item->Rollback();
100
101   EXPECT_TRUE(base::PathExists(from_dir1));
102   EXPECT_TRUE(base::PathExists(from_file));
103   EXPECT_FALSE(base::PathExists(to_dir));
104 }
105
106 // Move one directory from source to destination when destination already
107 // exists.
108 TEST_F(MoveTreeWorkItemTest, MoveDirectoryDestExists) {
109   // Create two level deep source dir
110   base::FilePath from_dir1(temp_from_dir_.path());
111   from_dir1 = from_dir1.AppendASCII("From_Dir1");
112   file_util::CreateDirectory(from_dir1);
113   ASSERT_TRUE(base::PathExists(from_dir1));
114
115   base::FilePath from_dir2(from_dir1);
116   from_dir2 = from_dir2.AppendASCII("From_Dir2");
117   file_util::CreateDirectory(from_dir2);
118   ASSERT_TRUE(base::PathExists(from_dir2));
119
120   base::FilePath from_file(from_dir2);
121   from_file = from_file.AppendASCII("From_File");
122   CreateTextFile(from_file.value(), kTextContent1);
123   ASSERT_TRUE(base::PathExists(from_file));
124
125   // Create destination path
126   base::FilePath to_dir(temp_from_dir_.path());
127   to_dir = to_dir.AppendASCII("To_Dir");
128   file_util::CreateDirectory(to_dir);
129   ASSERT_TRUE(base::PathExists(to_dir));
130
131   base::FilePath orig_to_file(to_dir);
132   orig_to_file = orig_to_file.AppendASCII("To_File");
133   CreateTextFile(orig_to_file.value(), kTextContent2);
134   ASSERT_TRUE(base::PathExists(orig_to_file));
135
136   base::FilePath new_to_file(to_dir);
137   new_to_file = new_to_file.AppendASCII("From_Dir2");
138   new_to_file = new_to_file.AppendASCII("From_File");
139   ASSERT_FALSE(base::PathExists(new_to_file));
140
141   // test Do(), don't check for duplicates.
142   scoped_ptr<MoveTreeWorkItem> work_item(
143       WorkItem::CreateMoveTreeWorkItem(from_dir1,
144                                        to_dir,
145                                        temp_to_dir_.path(),
146                                        WorkItem::ALWAYS_MOVE));
147   EXPECT_TRUE(work_item->Do());
148
149   EXPECT_FALSE(base::PathExists(from_dir1));
150   EXPECT_TRUE(base::PathExists(to_dir));
151   EXPECT_TRUE(base::PathExists(new_to_file));
152   EXPECT_FALSE(base::PathExists(orig_to_file));
153
154   // test rollback()
155   work_item->Rollback();
156
157   EXPECT_TRUE(base::PathExists(from_dir1));
158   EXPECT_TRUE(base::PathExists(to_dir));
159   EXPECT_FALSE(base::PathExists(new_to_file));
160   EXPECT_TRUE(base::PathExists(orig_to_file));
161   EXPECT_EQ(0, ReadTextFile(orig_to_file).compare(kTextContent2));
162   EXPECT_EQ(0, ReadTextFile(from_file).compare(kTextContent1));
163 }
164
165 // Move one file from source to destination when destination does not
166 // exist.
167 TEST_F(MoveTreeWorkItemTest, MoveAFile) {
168   // Create a file inside source dir
169   base::FilePath from_dir(temp_from_dir_.path());
170   from_dir = from_dir.AppendASCII("From_Dir");
171   file_util::CreateDirectory(from_dir);
172   ASSERT_TRUE(base::PathExists(from_dir));
173
174   base::FilePath from_file(from_dir);
175   from_file = from_file.AppendASCII("From_File");
176   CreateTextFile(from_file.value(), kTextContent1);
177   ASSERT_TRUE(base::PathExists(from_file));
178
179   // Generate destination file name
180   base::FilePath to_file(temp_from_dir_.path());
181   to_file = to_file.AppendASCII("To_File");
182   ASSERT_FALSE(base::PathExists(to_file));
183
184   // test Do()
185   scoped_ptr<MoveTreeWorkItem> work_item(
186       WorkItem::CreateMoveTreeWorkItem(from_file,
187                                        to_file,
188                                        temp_to_dir_.path(),
189                                        WorkItem::ALWAYS_MOVE));
190   EXPECT_TRUE(work_item->Do());
191
192   EXPECT_TRUE(base::PathExists(from_dir));
193   EXPECT_FALSE(base::PathExists(from_file));
194   EXPECT_TRUE(base::PathExists(to_file));
195   EXPECT_EQ(0, ReadTextFile(to_file).compare(kTextContent1));
196
197   // test rollback()
198   work_item->Rollback();
199
200   EXPECT_TRUE(base::PathExists(from_dir));
201   EXPECT_TRUE(base::PathExists(from_file));
202   EXPECT_FALSE(base::PathExists(to_file));
203   EXPECT_EQ(0, ReadTextFile(from_file).compare(kTextContent1));
204 }
205
206 // Move one file from source to destination when destination already
207 // exists.
208 TEST_F(MoveTreeWorkItemTest, MoveFileDestExists) {
209   // Create a file inside source dir
210   base::FilePath from_dir(temp_from_dir_.path());
211   from_dir = from_dir.AppendASCII("From_Dir");
212   file_util::CreateDirectory(from_dir);
213   ASSERT_TRUE(base::PathExists(from_dir));
214
215   base::FilePath from_file(from_dir);
216   from_file = from_file.AppendASCII("From_File");
217   CreateTextFile(from_file.value(), kTextContent1);
218   ASSERT_TRUE(base::PathExists(from_file));
219
220   // Create destination path
221   base::FilePath to_dir(temp_from_dir_.path());
222   to_dir = to_dir.AppendASCII("To_Dir");
223   file_util::CreateDirectory(to_dir);
224   ASSERT_TRUE(base::PathExists(to_dir));
225
226   base::FilePath to_file(to_dir);
227   to_file = to_file.AppendASCII("To_File");
228   CreateTextFile(to_file.value(), kTextContent2);
229   ASSERT_TRUE(base::PathExists(to_file));
230
231   // test Do()
232   scoped_ptr<MoveTreeWorkItem> work_item(
233       WorkItem::CreateMoveTreeWorkItem(from_file,
234                                        to_dir,
235                                        temp_to_dir_.path(),
236                                        WorkItem::ALWAYS_MOVE));
237   EXPECT_TRUE(work_item->Do());
238
239   EXPECT_TRUE(base::PathExists(from_dir));
240   EXPECT_FALSE(base::PathExists(from_file));
241   EXPECT_TRUE(base::PathExists(to_dir));
242   EXPECT_FALSE(base::PathExists(to_file));
243   EXPECT_EQ(0, ReadTextFile(to_dir).compare(kTextContent1));
244
245   // test rollback()
246   work_item->Rollback();
247
248   EXPECT_TRUE(base::PathExists(from_dir));
249   EXPECT_EQ(0, ReadTextFile(from_file).compare(kTextContent1));
250   EXPECT_TRUE(base::PathExists(to_dir));
251   EXPECT_EQ(0, ReadTextFile(to_file).compare(kTextContent2));
252 }
253
254 // Move one file from source to destination when destination already
255 // exists and is in use.
256 TEST_F(MoveTreeWorkItemTest, MoveFileDestInUse) {
257   // Create a file inside source dir
258   base::FilePath from_dir(temp_from_dir_.path());
259   from_dir = from_dir.AppendASCII("From_Dir");
260   file_util::CreateDirectory(from_dir);
261   ASSERT_TRUE(base::PathExists(from_dir));
262
263   base::FilePath from_file(from_dir);
264   from_file = from_file.AppendASCII("From_File");
265   CreateTextFile(from_file.value(), kTextContent1);
266   ASSERT_TRUE(base::PathExists(from_file));
267
268   // Create an executable in destination path by copying ourself to it.
269   base::FilePath to_dir(temp_from_dir_.path());
270   to_dir = to_dir.AppendASCII("To_Dir");
271   file_util::CreateDirectory(to_dir);
272   ASSERT_TRUE(base::PathExists(to_dir));
273
274   wchar_t exe_full_path_str[MAX_PATH];
275   ::GetModuleFileName(NULL, exe_full_path_str, MAX_PATH);
276   base::FilePath exe_full_path(exe_full_path_str);
277   base::FilePath to_file(to_dir);
278   to_file = to_file.AppendASCII("To_File");
279   base::CopyFile(exe_full_path, to_file);
280   ASSERT_TRUE(base::PathExists(to_file));
281
282   // Run the executable in destination path
283   STARTUPINFOW si = {sizeof(si)};
284   PROCESS_INFORMATION pi = {0};
285   ASSERT_TRUE(::CreateProcess(NULL,
286                               const_cast<wchar_t*>(to_file.value().c_str()),
287                               NULL, NULL, FALSE,
288                               CREATE_NO_WINDOW | CREATE_SUSPENDED,
289                               NULL, NULL, &si, &pi));
290
291   // test Do()
292   scoped_ptr<MoveTreeWorkItem> work_item(
293       WorkItem::CreateMoveTreeWorkItem(from_file,
294                                        to_file,
295                                        temp_to_dir_.path(),
296                                        WorkItem::ALWAYS_MOVE));
297   EXPECT_TRUE(work_item->Do());
298
299   EXPECT_TRUE(base::PathExists(from_dir));
300   EXPECT_FALSE(base::PathExists(from_file));
301   EXPECT_TRUE(base::PathExists(to_dir));
302   EXPECT_EQ(0, ReadTextFile(to_file).compare(kTextContent1));
303
304   // test rollback()
305   work_item->Rollback();
306
307   EXPECT_TRUE(base::PathExists(from_dir));
308   EXPECT_EQ(0, ReadTextFile(from_file).compare(kTextContent1));
309   EXPECT_TRUE(base::PathExists(to_dir));
310   EXPECT_TRUE(base::ContentsEqual(exe_full_path, to_file));
311
312   TerminateProcess(pi.hProcess, 0);
313   EXPECT_TRUE(WaitForSingleObject(pi.hProcess, 10000) == WAIT_OBJECT_0);
314   CloseHandle(pi.hProcess);
315   CloseHandle(pi.hThread);
316 }
317
318 // Move one file that is in use to destination.
319 TEST_F(MoveTreeWorkItemTest, MoveFileInUse) {
320   // Create an executable for source by copying ourself to a new source dir.
321   base::FilePath from_dir(temp_from_dir_.path());
322   from_dir = from_dir.AppendASCII("From_Dir");
323   file_util::CreateDirectory(from_dir);
324   ASSERT_TRUE(base::PathExists(from_dir));
325
326   wchar_t exe_full_path_str[MAX_PATH];
327   ::GetModuleFileName(NULL, exe_full_path_str, MAX_PATH);
328   base::FilePath exe_full_path(exe_full_path_str);
329   base::FilePath from_file(from_dir);
330   from_file = from_file.AppendASCII("From_File");
331   base::CopyFile(exe_full_path, from_file);
332   ASSERT_TRUE(base::PathExists(from_file));
333
334   // Create a destination source dir and generate destination file name.
335   base::FilePath to_dir(temp_from_dir_.path());
336   to_dir = to_dir.AppendASCII("To_Dir");
337   file_util::CreateDirectory(to_dir);
338   ASSERT_TRUE(base::PathExists(to_dir));
339
340   base::FilePath to_file(to_dir);
341   to_file = to_file.AppendASCII("To_File");
342   CreateTextFile(to_file.value(), kTextContent1);
343   ASSERT_TRUE(base::PathExists(to_file));
344
345   // Run the executable in source path
346   STARTUPINFOW si = {sizeof(si)};
347   PROCESS_INFORMATION pi = {0};
348   ASSERT_TRUE(::CreateProcess(NULL,
349                               const_cast<wchar_t*>(from_file.value().c_str()),
350                               NULL, NULL, FALSE,
351                               CREATE_NO_WINDOW | CREATE_SUSPENDED,
352                               NULL, NULL, &si, &pi));
353
354   // test Do()
355   scoped_ptr<MoveTreeWorkItem> work_item(
356       WorkItem::CreateMoveTreeWorkItem(from_file,
357                                        to_file,
358                                        temp_to_dir_.path(),
359                                        WorkItem::ALWAYS_MOVE));
360   EXPECT_TRUE(work_item->Do());
361
362   EXPECT_TRUE(base::PathExists(from_dir));
363   EXPECT_FALSE(base::PathExists(from_file));
364   EXPECT_TRUE(base::PathExists(to_dir));
365   EXPECT_TRUE(base::ContentsEqual(exe_full_path, to_file));
366
367   // Close the process and make sure all the conditions after Do() are
368   // still true.
369   TerminateProcess(pi.hProcess, 0);
370   EXPECT_TRUE(WaitForSingleObject(pi.hProcess, 10000) == WAIT_OBJECT_0);
371   CloseHandle(pi.hProcess);
372   CloseHandle(pi.hThread);
373
374   EXPECT_TRUE(base::PathExists(from_dir));
375   EXPECT_FALSE(base::PathExists(from_file));
376   EXPECT_TRUE(base::PathExists(to_dir));
377   EXPECT_TRUE(base::ContentsEqual(exe_full_path, to_file));
378
379   // test rollback()
380   work_item->Rollback();
381
382   EXPECT_TRUE(base::PathExists(from_dir));
383   EXPECT_TRUE(base::ContentsEqual(exe_full_path, from_file));
384   EXPECT_TRUE(base::PathExists(to_dir));
385   EXPECT_EQ(0, ReadTextFile(to_file).compare(kTextContent1));
386 }
387
388 // Move one directory from source to destination when destination already
389 // exists.
390 TEST_F(MoveTreeWorkItemTest, MoveDirectoryDestExistsCheckForDuplicatesFull) {
391   // Create two level deep source dir
392   base::FilePath from_dir1(temp_from_dir_.path());
393   from_dir1 = from_dir1.AppendASCII("From_Dir1");
394   file_util::CreateDirectory(from_dir1);
395   ASSERT_TRUE(base::PathExists(from_dir1));
396
397   base::FilePath from_dir2(from_dir1);
398   from_dir2 = from_dir2.AppendASCII("From_Dir2");
399   file_util::CreateDirectory(from_dir2);
400   ASSERT_TRUE(base::PathExists(from_dir2));
401
402   base::FilePath from_file(from_dir2);
403   from_file = from_file.AppendASCII("From_File");
404   CreateTextFile(from_file.value(), kTextContent1);
405   ASSERT_TRUE(base::PathExists(from_file));
406
407   // // Create a file hierarchy identical to the one in the source directory.
408   base::FilePath to_dir(temp_from_dir_.path());
409   to_dir = to_dir.AppendASCII("To_Dir");
410   ASSERT_TRUE(installer::test::CopyFileHierarchy(from_dir1, to_dir));
411
412   // Lock one of the files in the to destination directory to prevent moves.
413   base::FilePath orig_to_file(
414       to_dir.AppendASCII("From_Dir2").AppendASCII("From_File"));
415   base::MemoryMappedFile mapped_file;
416   EXPECT_TRUE(mapped_file.Initialize(orig_to_file));
417
418   // First check that we can't do the regular Move().
419   scoped_ptr<MoveTreeWorkItem> work_item(
420       WorkItem::CreateMoveTreeWorkItem(from_dir1,
421                                        to_dir,
422                                        temp_to_dir_.path(),
423                                        WorkItem::ALWAYS_MOVE));
424   EXPECT_FALSE(work_item->Do());
425   work_item->Rollback();
426
427   // Now test Do() with the check for duplicates. This should pass.
428   work_item.reset(
429       WorkItem::CreateMoveTreeWorkItem(from_dir1,
430                                        to_dir,
431                                        temp_to_dir_.path(),
432                                        WorkItem::CHECK_DUPLICATES));
433   EXPECT_TRUE(work_item->Do());
434
435   // Make sure that we "moved" the files, i.e. that the source directory isn't
436   // there anymore,
437   EXPECT_FALSE(base::PathExists(from_dir1));
438   // Make sure that the original directory structure and file are still present.
439   EXPECT_TRUE(base::PathExists(to_dir));
440   EXPECT_TRUE(base::PathExists(orig_to_file));
441   // Make sure that the backup path is not empty.
442   EXPECT_FALSE(file_util::IsDirectoryEmpty(temp_to_dir_.path()));
443
444   // Check that the work item believes the source to have been moved.
445   EXPECT_TRUE(work_item->source_moved_to_backup_);
446   EXPECT_FALSE(work_item->moved_to_dest_path_);
447   EXPECT_FALSE(work_item->moved_to_backup_);
448
449   // test rollback()
450   work_item->Rollback();
451
452   // Once we rollback all the original files should still be there, as should
453   // the source files.
454   EXPECT_TRUE(base::PathExists(from_dir1));
455   EXPECT_TRUE(base::PathExists(to_dir));
456   EXPECT_TRUE(base::PathExists(orig_to_file));
457   EXPECT_EQ(0, ReadTextFile(orig_to_file).compare(kTextContent1));
458   EXPECT_EQ(0, ReadTextFile(from_file).compare(kTextContent1));
459 }
460
461 // Move one directory from source to destination when destination already
462 // exists but contains only a subset of the files in source.
463 TEST_F(MoveTreeWorkItemTest, MoveDirectoryDestExistsCheckForDuplicatesPartial) {
464   // Create two level deep source dir
465   base::FilePath from_dir1(temp_from_dir_.path());
466   from_dir1 = from_dir1.AppendASCII("From_Dir1");
467   file_util::CreateDirectory(from_dir1);
468   ASSERT_TRUE(base::PathExists(from_dir1));
469
470   base::FilePath from_dir2(from_dir1);
471   from_dir2 = from_dir2.AppendASCII("From_Dir2");
472   file_util::CreateDirectory(from_dir2);
473   ASSERT_TRUE(base::PathExists(from_dir2));
474
475   base::FilePath from_file(from_dir2);
476   from_file = from_file.AppendASCII("From_File");
477   CreateTextFile(from_file.value(), kTextContent1);
478   ASSERT_TRUE(base::PathExists(from_file));
479
480   base::FilePath from_file2(from_dir2);
481   from_file2 = from_file2.AppendASCII("From_File2");
482   CreateTextFile(from_file2.value(), kTextContent2);
483   ASSERT_TRUE(base::PathExists(from_file2));
484
485   // Create destination path
486   base::FilePath to_dir(temp_from_dir_.path());
487   to_dir = to_dir.AppendASCII("To_Dir");
488   file_util::CreateDirectory(to_dir);
489   ASSERT_TRUE(base::PathExists(to_dir));
490
491   // Create a sub-directory of the same name as in the source directory.
492   base::FilePath to_dir2(to_dir);
493   to_dir2 = to_dir2.AppendASCII("From_Dir2");
494   file_util::CreateDirectory(to_dir2);
495   ASSERT_TRUE(base::PathExists(to_dir2));
496
497   // Create one of the files in the to sub-directory, but not the other.
498   base::FilePath orig_to_file(to_dir2);
499   orig_to_file = orig_to_file.AppendASCII("From_File");
500   CreateTextFile(orig_to_file.value(), kTextContent1);
501   ASSERT_TRUE(base::PathExists(orig_to_file));
502
503   // test Do(), check for duplicates.
504   scoped_ptr<MoveTreeWorkItem> work_item(
505       WorkItem::CreateMoveTreeWorkItem(from_dir1,
506                                        to_dir,
507                                        temp_to_dir_.path(),
508                                        WorkItem::CHECK_DUPLICATES));
509   EXPECT_TRUE(work_item->Do());
510
511   // Make sure that we "moved" the files, i.e. that the source directory isn't
512   // there anymore,
513   EXPECT_FALSE(base::PathExists(from_dir1));
514   // Make sure that the original directory structure and file are still present.
515   EXPECT_TRUE(base::PathExists(to_dir));
516   EXPECT_TRUE(base::PathExists(orig_to_file));
517   // Make sure that the backup path is not empty.
518   EXPECT_FALSE(file_util::IsDirectoryEmpty(temp_to_dir_.path()));
519   // Make sure that the "new" file is also present.
520   base::FilePath new_to_file2(to_dir2);
521   new_to_file2 = new_to_file2.AppendASCII("From_File2");
522   EXPECT_TRUE(base::PathExists(new_to_file2));
523
524   // Check that the work item believes that this was a regular move.
525   EXPECT_FALSE(work_item->source_moved_to_backup_);
526   EXPECT_TRUE(work_item->moved_to_dest_path_);
527   EXPECT_TRUE(work_item->moved_to_backup_);
528
529   // test rollback()
530   work_item->Rollback();
531
532   // Once we rollback all the original files should still be there, as should
533   // the source files.
534   EXPECT_TRUE(base::PathExists(from_dir1));
535   EXPECT_TRUE(base::PathExists(to_dir));
536   EXPECT_TRUE(base::PathExists(orig_to_file));
537   EXPECT_EQ(0, ReadTextFile(orig_to_file).compare(kTextContent1));
538   EXPECT_EQ(0, ReadTextFile(from_file).compare(kTextContent1));
539
540   // Also, after rollback the new "to" file should be gone.
541   EXPECT_FALSE(base::PathExists(new_to_file2));
542 }