1 // Copyright (c) 2013 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 // Browser test for basic Chrome OS file manager functionality:
6 // - The file list is updated when a file is added externally to the Downloads
7 // folder.
8 // - Selecting a file and copy-pasting it with the keyboard copies the file.
9 // - Selecting a file and pressing delete deletes it.
10
11 #include <deque>
12 #include <string>
13
14 #include "apps/app_window.h"
15 #include "apps/app_window_registry.h"
16 #include "base/bind.h"
17 #include "base/file_util.h"
18 #include "base/files/file_path.h"
19 #include "base/json/json_reader.h"
20 #include "base/json/json_value_converter.h"
21 #include "base/json/json_writer.h"
22 #include "base/prefs/pref_service.h"
23 #include "base/strings/string_piece.h"
24 #include "base/strings/utf_string_conversions.h"
25 #include "base/time/time.h"
26 #include "chrome/browser/chrome_notification_types.h"
27 #include "chrome/browser/chromeos/drive/drive_integration_service.h"
28 #include "chrome/browser/chromeos/drive/file_system_interface.h"
29 #include "chrome/browser/chromeos/drive/test_util.h"
30 #include "chrome/browser/chromeos/file_manager/app_id.h"
31 #include "chrome/browser/chromeos/file_manager/drive_test_util.h"
32 #include "chrome/browser/chromeos/file_manager/path_util.h"
33 #include "chrome/browser/chromeos/file_manager/volume_manager.h"
34 #include "chrome/browser/chromeos/login/users/user_manager.h"
35 #include "chrome/browser/chromeos/profiles/profile_helper.h"
36 #include "chrome/browser/drive/fake_drive_service.h"
37 #include "chrome/browser/extensions/component_loader.h"
38 #include "chrome/browser/extensions/extension_apitest.h"
39 #include "chrome/browser/extensions/extension_test_message_listener.h"
40 #include "chrome/browser/profiles/profile.h"
41 #include "chrome/browser/ui/ash/multi_user/multi_user_util.h"
42 #include "chrome/browser/ui/ash/multi_user/multi_user_window_manager.h"
43 #include "chrome/common/chrome_switches.h"
44 #include "chrome/common/pref_names.h"
45 #include "chromeos/chromeos_switches.h"
46 #include "content/public/browser/notification_service.h"
47 #include "content/public/test/test_utils.h"
48 #include "extensions/browser/api/test/test_api.h"
49 #include "extensions/common/extension.h"
50 #include "google_apis/drive/drive_api_parser.h"
51 #include "google_apis/drive/test_util.h"
52 #include "net/test/embedded_test_server/embedded_test_server.h"
53 #include "webkit/browser/fileapi/external_mount_points.h"
54
55 using drive::DriveIntegrationServiceFactory;
56
57 namespace file_manager {
58 namespace {
59
60 enum EntryType {
61 FILE,
62 DIRECTORY,
63 };
64
65 enum TargetVolume { LOCAL_VOLUME, DRIVE_VOLUME, USB_VOLUME, };
66
67 enum SharedOption {
68 NONE,
69 SHARED,
70 };
71
72 enum GuestMode {
73 NOT_IN_GUEST_MODE,
74 IN_GUEST_MODE,
75 IN_INCOGNITO
76 };
77
78 // This global operator is used from Google Test to format error messages.
operator <<(std::ostream & os,const GuestMode & guest_mode)79 std::ostream& operator<<(std::ostream& os, const GuestMode& guest_mode) {
80 return os << (guest_mode == IN_GUEST_MODE ?
81 "IN_GUEST_MODE" : "NOT_IN_GUEST_MODE");
82 }
83
84 // Maps the given string to EntryType. Returns true on success.
MapStringToEntryType(const base::StringPiece & value,EntryType * output)85 bool MapStringToEntryType(const base::StringPiece& value, EntryType* output) {
86 if (value == "file")
87 *output = FILE;
88 else if (value == "directory")
89 *output = DIRECTORY;
90 else
91 return false;
92 return true;
93 }
94
95 // Maps the given string to SharedOption. Returns true on success.
MapStringToSharedOption(const base::StringPiece & value,SharedOption * output)96 bool MapStringToSharedOption(const base::StringPiece& value,
97 SharedOption* output) {
98 if (value == "shared")
99 *output = SHARED;
100 else if (value == "none")
101 *output = NONE;
102 else
103 return false;
104 return true;
105 }
106
107 // Maps the given string to TargetVolume. Returns true on success.
MapStringToTargetVolume(const base::StringPiece & value,TargetVolume * output)108 bool MapStringToTargetVolume(const base::StringPiece& value,
109 TargetVolume* output) {
110 if (value == "drive")
111 *output = DRIVE_VOLUME;
112 else if (value == "local")
113 *output = LOCAL_VOLUME;
114 else if (value == "usb")
115 *output = USB_VOLUME;
116 else
117 return false;
118 return true;
119 }
120
121 // Maps the given string to base::Time. Returns true on success.
MapStringToTime(const base::StringPiece & value,base::Time * time)122 bool MapStringToTime(const base::StringPiece& value, base::Time* time) {
123 return base::Time::FromString(value.as_string().c_str(), time);
124 }
125
126 // Test data of file or directory.
127 struct TestEntryInfo {
TestEntryInfofile_manager::__anon2b86b5b80111::TestEntryInfo128 TestEntryInfo() : type(FILE), shared_option(NONE) {}
129
TestEntryInfofile_manager::__anon2b86b5b80111::TestEntryInfo130 TestEntryInfo(EntryType type,
131 const std::string& source_file_name,
132 const std::string& target_path,
133 const std::string& mime_type,
134 SharedOption shared_option,
135 const base::Time& last_modified_time) :
136 type(type),
137 source_file_name(source_file_name),
138 target_path(target_path),
139 mime_type(mime_type),
140 shared_option(shared_option),
141 last_modified_time(last_modified_time) {
142 }
143
144 EntryType type;
145 std::string source_file_name; // Source file name to be used as a prototype.
146 std::string target_path; // Target file or directory path.
147 std::string mime_type;
148 SharedOption shared_option;
149 base::Time last_modified_time;
150
151 // Registers the member information to the given converter.
152 static void RegisterJSONConverter(
153 base::JSONValueConverter<TestEntryInfo>* converter);
154 };
155
156 // static
RegisterJSONConverter(base::JSONValueConverter<TestEntryInfo> * converter)157 void TestEntryInfo::RegisterJSONConverter(
158 base::JSONValueConverter<TestEntryInfo>* converter) {
159 converter->RegisterCustomField("type",
160 &TestEntryInfo::type,
161 &MapStringToEntryType);
162 converter->RegisterStringField("sourceFileName",
163 &TestEntryInfo::source_file_name);
164 converter->RegisterStringField("targetPath", &TestEntryInfo::target_path);
165 converter->RegisterStringField("mimeType", &TestEntryInfo::mime_type);
166 converter->RegisterCustomField("sharedOption",
167 &TestEntryInfo::shared_option,
168 &MapStringToSharedOption);
169 converter->RegisterCustomField("lastModifiedTime",
170 &TestEntryInfo::last_modified_time,
171 &MapStringToTime);
172 }
173
174 // Message from JavaScript to add entries.
175 struct AddEntriesMessage {
176 // Target volume to be added the |entries|.
177 TargetVolume volume;
178
179 // Entries to be added.
180 ScopedVector<TestEntryInfo> entries;
181
182 // Registers the member information to the given converter.
183 static void RegisterJSONConverter(
184 base::JSONValueConverter<AddEntriesMessage>* converter);
185 };
186
187 // static
RegisterJSONConverter(base::JSONValueConverter<AddEntriesMessage> * converter)188 void AddEntriesMessage::RegisterJSONConverter(
189 base::JSONValueConverter<AddEntriesMessage>* converter) {
190 converter->RegisterCustomField("volume",
191 &AddEntriesMessage::volume,
192 &MapStringToTargetVolume);
193 converter->RegisterRepeatedMessage<TestEntryInfo>(
194 "entries",
195 &AddEntriesMessage::entries);
196 }
197
198 // Test volume.
199 class TestVolume {
200 protected:
TestVolume(const std::string & name)201 explicit TestVolume(const std::string& name) : name_(name) {}
~TestVolume()202 virtual ~TestVolume() {}
203
CreateRootDirectory(const Profile * profile)204 bool CreateRootDirectory(const Profile* profile) {
205 const base::FilePath path = profile->GetPath().Append(name_);
206 return root_.path() == path || root_.Set(path);
207 }
208
name()209 const std::string& name() { return name_; }
root_path()210 const base::FilePath root_path() { return root_.path(); }
211
212 private:
213 std::string name_;
214 base::ScopedTempDir root_;
215 };
216
217 // The local volume class for test.
218 // This class provides the operations for a test volume that simulates local
219 // drive.
220 class LocalTestVolume : public TestVolume {
221 public:
LocalTestVolume(const std::string & name)222 explicit LocalTestVolume(const std::string& name) : TestVolume(name) {}
~LocalTestVolume()223 virtual ~LocalTestVolume() {}
224
225 // Adds this volume to the file system as a local volume. Returns true on
226 // success.
227 virtual bool Mount(Profile* profile) = 0;
228
CreateEntry(const TestEntryInfo & entry)229 void CreateEntry(const TestEntryInfo& entry) {
230 const base::FilePath target_path =
231 root_path().AppendASCII(entry.target_path);
232
233 entries_.insert(std::make_pair(target_path, entry));
234 switch (entry.type) {
235 case FILE: {
236 const base::FilePath source_path =
237 google_apis::test_util::GetTestFilePath("chromeos/file_manager").
238 AppendASCII(entry.source_file_name);
239 ASSERT_TRUE(base::CopyFile(source_path, target_path))
240 << "Copy from " << source_path.value()
241 << " to " << target_path.value() << " failed.";
242 break;
243 }
244 case DIRECTORY:
245 ASSERT_TRUE(base::CreateDirectory(target_path)) <<
246 "Failed to create a directory: " << target_path.value();
247 break;
248 }
249 ASSERT_TRUE(UpdateModifiedTime(entry));
250 }
251
252 private:
253 // Updates ModifiedTime of the entry and its parents by referring
254 // TestEntryInfo. Returns true on success.
UpdateModifiedTime(const TestEntryInfo & entry)255 bool UpdateModifiedTime(const TestEntryInfo& entry) {
256 const base::FilePath path = root_path().AppendASCII(entry.target_path);
257 if (!base::TouchFile(path, entry.last_modified_time,
258 entry.last_modified_time))
259 return false;
260
261 // Update the modified time of parent directories because it may be also
262 // affected by the update of child items.
263 if (path.DirName() != root_path()) {
264 const std::map<base::FilePath, const TestEntryInfo>::iterator it =
265 entries_.find(path.DirName());
266 if (it == entries_.end())
267 return false;
268 return UpdateModifiedTime(it->second);
269 }
270 return true;
271 }
272
273 std::map<base::FilePath, const TestEntryInfo> entries_;
274 };
275
276 class DownloadsTestVolume : public LocalTestVolume {
277 public:
DownloadsTestVolume()278 DownloadsTestVolume() : LocalTestVolume("Downloads") {}
~DownloadsTestVolume()279 virtual ~DownloadsTestVolume() {}
280
Mount(Profile * profile)281 virtual bool Mount(Profile* profile) OVERRIDE {
282 return CreateRootDirectory(profile) &&
283 VolumeManager::Get(profile)
284 ->RegisterDownloadsDirectoryForTesting(root_path());
285 }
286 };
287
288 // Test volume for mimicing a specified type of volumes by a local folder.
289 class FakeTestVolume : public LocalTestVolume {
290 public:
FakeTestVolume(const std::string & name,VolumeType volume_type,chromeos::DeviceType device_type)291 FakeTestVolume(const std::string& name,
292 VolumeType volume_type,
293 chromeos::DeviceType device_type)
294 : LocalTestVolume(name),
295 volume_type_(volume_type),
296 device_type_(device_type) {}
~FakeTestVolume()297 virtual ~FakeTestVolume() {}
298
299 // Simple test entries used for testing, e.g., read-only volumes.
PrepareTestEntries(Profile * profile)300 bool PrepareTestEntries(Profile* profile) {
301 if (!CreateRootDirectory(profile))
302 return false;
303 // Must be in sync with BASIC_FAKE_ENTRY_SET in the JS test code.
304 CreateEntry(
305 TestEntryInfo(FILE, "text.txt", "hello.txt", "text/plain", NONE,
306 base::Time::Now()));
307 CreateEntry(
308 TestEntryInfo(DIRECTORY, std::string(), "A", std::string(), NONE,
309 base::Time::Now()));
310 return true;
311 }
312
Mount(Profile * profile)313 virtual bool Mount(Profile* profile) OVERRIDE {
314 if (!CreateRootDirectory(profile))
315 return false;
316 fileapi::ExternalMountPoints* const mount_points =
317 fileapi::ExternalMountPoints::GetSystemInstance();
318
319 // First revoke the existing mount point (if any).
320 mount_points->RevokeFileSystem(name());
321 const bool result =
322 mount_points->RegisterFileSystem(name(),
323 fileapi::kFileSystemTypeNativeLocal,
324 fileapi::FileSystemMountOption(),
325 root_path());
326 if (!result)
327 return false;
328
329 VolumeManager::Get(profile)->AddVolumeInfoForTesting(
330 root_path(), volume_type_, device_type_);
331 return true;
332 }
333
334 private:
335 const VolumeType volume_type_;
336 const chromeos::DeviceType device_type_;
337 };
338
339 // The drive volume class for test.
340 // This class provides the operations for a test volume that simulates Google
341 // drive.
342 class DriveTestVolume : public TestVolume {
343 public:
DriveTestVolume()344 DriveTestVolume() : TestVolume("drive"), integration_service_(NULL) {}
~DriveTestVolume()345 virtual ~DriveTestVolume() {}
346
CreateEntry(const TestEntryInfo & entry)347 void CreateEntry(const TestEntryInfo& entry) {
348 const base::FilePath path =
349 base::FilePath::FromUTF8Unsafe(entry.target_path);
350 const std::string target_name = path.BaseName().AsUTF8Unsafe();
351
352 // Obtain the parent entry.
353 drive::FileError error = drive::FILE_ERROR_OK;
354 scoped_ptr<drive::ResourceEntry> parent_entry(new drive::ResourceEntry);
355 integration_service_->file_system()->GetResourceEntry(
356 drive::util::GetDriveMyDriveRootPath().Append(path).DirName(),
357 google_apis::test_util::CreateCopyResultCallback(
358 &error, &parent_entry));
359 drive::test_util::RunBlockingPoolTask();
360 ASSERT_EQ(drive::FILE_ERROR_OK, error);
361 ASSERT_TRUE(parent_entry);
362
363 switch (entry.type) {
364 case FILE:
365 CreateFile(entry.source_file_name,
366 parent_entry->resource_id(),
367 target_name,
368 entry.mime_type,
369 entry.shared_option == SHARED,
370 entry.last_modified_time);
371 break;
372 case DIRECTORY:
373 CreateDirectory(
374 parent_entry->resource_id(), target_name, entry.last_modified_time);
375 break;
376 }
377 }
378
379 // Creates an empty directory with the given |name| and |modification_time|.
CreateDirectory(const std::string & parent_id,const std::string & target_name,const base::Time & modification_time)380 void CreateDirectory(const std::string& parent_id,
381 const std::string& target_name,
382 const base::Time& modification_time) {
383 google_apis::GDataErrorCode error = google_apis::GDATA_OTHER_ERROR;
384 scoped_ptr<google_apis::FileResource> entry;
385 fake_drive_service_->AddNewDirectory(
386 parent_id,
387 target_name,
388 drive::DriveServiceInterface::AddNewDirectoryOptions(),
389 google_apis::test_util::CreateCopyResultCallback(&error, &entry));
390 base::MessageLoop::current()->RunUntilIdle();
391 ASSERT_EQ(google_apis::HTTP_CREATED, error);
392 ASSERT_TRUE(entry);
393
394 fake_drive_service_->SetLastModifiedTime(
395 entry->file_id(),
396 modification_time,
397 google_apis::test_util::CreateCopyResultCallback(&error, &entry));
398 base::MessageLoop::current()->RunUntilIdle();
399 ASSERT_TRUE(error == google_apis::HTTP_SUCCESS);
400 ASSERT_TRUE(entry);
401 CheckForUpdates();
402 }
403
404 // Creates a test file with the given spec.
405 // Serves |test_file_name| file. Pass an empty string for an empty file.
CreateFile(const std::string & source_file_name,const std::string & parent_id,const std::string & target_name,const std::string & mime_type,bool shared_with_me,const base::Time & modification_time)406 void CreateFile(const std::string& source_file_name,
407 const std::string& parent_id,
408 const std::string& target_name,
409 const std::string& mime_type,
410 bool shared_with_me,
411 const base::Time& modification_time) {
412 google_apis::GDataErrorCode error = google_apis::GDATA_OTHER_ERROR;
413
414 std::string content_data;
415 if (!source_file_name.empty()) {
416 base::FilePath source_file_path =
417 google_apis::test_util::GetTestFilePath("chromeos/file_manager").
418 AppendASCII(source_file_name);
419 ASSERT_TRUE(base::ReadFileToString(source_file_path, &content_data));
420 }
421
422 scoped_ptr<google_apis::FileResource> entry;
423 fake_drive_service_->AddNewFile(
424 mime_type,
425 content_data,
426 parent_id,
427 target_name,
428 shared_with_me,
429 google_apis::test_util::CreateCopyResultCallback(&error, &entry));
430 base::MessageLoop::current()->RunUntilIdle();
431 ASSERT_EQ(google_apis::HTTP_CREATED, error);
432 ASSERT_TRUE(entry);
433
434 fake_drive_service_->SetLastModifiedTime(
435 entry->file_id(),
436 modification_time,
437 google_apis::test_util::CreateCopyResultCallback(&error, &entry));
438 base::MessageLoop::current()->RunUntilIdle();
439 ASSERT_EQ(google_apis::HTTP_SUCCESS, error);
440 ASSERT_TRUE(entry);
441
442 CheckForUpdates();
443 }
444
445 // Notifies FileSystem that the contents in FakeDriveService are
446 // changed, hence the new contents should be fetched.
CheckForUpdates()447 void CheckForUpdates() {
448 if (integration_service_ && integration_service_->file_system()) {
449 integration_service_->file_system()->CheckForUpdates();
450 }
451 }
452
453 // Sets the url base for the test server to be used to generate share urls
454 // on the files and directories.
ConfigureShareUrlBase(const GURL & share_url_base)455 void ConfigureShareUrlBase(const GURL& share_url_base) {
456 fake_drive_service_->set_share_url_base(share_url_base);
457 }
458
CreateDriveIntegrationService(Profile * profile)459 drive::DriveIntegrationService* CreateDriveIntegrationService(
460 Profile* profile) {
461 profile_ = profile;
462 fake_drive_service_ = new drive::FakeDriveService;
463 fake_drive_service_->LoadAppListForDriveApi("drive/applist.json");
464
465 if (!CreateRootDirectory(profile))
466 return NULL;
467 integration_service_ = new drive::DriveIntegrationService(
468 profile, NULL, fake_drive_service_, std::string(), root_path(), NULL);
469 return integration_service_;
470 }
471
472 private:
473 Profile* profile_;
474 drive::FakeDriveService* fake_drive_service_;
475 drive::DriveIntegrationService* integration_service_;
476 };
477
478 // Listener to obtain the test relative messages synchronously.
479 class FileManagerTestListener : public content::NotificationObserver {
480 public:
481 struct Message {
482 int type;
483 std::string message;
484 scoped_refptr<extensions::TestSendMessageFunction> function;
485 };
486
FileManagerTestListener()487 FileManagerTestListener() {
488 registrar_.Add(this,
489 chrome::NOTIFICATION_EXTENSION_TEST_PASSED,
490 content::NotificationService::AllSources());
491 registrar_.Add(this,
492 chrome::NOTIFICATION_EXTENSION_TEST_FAILED,
493 content::NotificationService::AllSources());
494 registrar_.Add(this,
495 chrome::NOTIFICATION_EXTENSION_TEST_MESSAGE,
496 content::NotificationService::AllSources());
497 }
498
GetNextMessage()499 Message GetNextMessage() {
500 if (messages_.empty())
501 content::RunMessageLoop();
502 const Message entry = messages_.front();
503 messages_.pop_front();
504 return entry;
505 }
506
Observe(int type,const content::NotificationSource & source,const content::NotificationDetails & details)507 virtual void Observe(int type,
508 const content::NotificationSource& source,
509 const content::NotificationDetails& details) OVERRIDE {
510 Message entry;
511 entry.type = type;
512 entry.message = type != chrome::NOTIFICATION_EXTENSION_TEST_PASSED ?
513 *content::Details<std::string>(details).ptr() :
514 std::string();
515 entry.function = type == chrome::NOTIFICATION_EXTENSION_TEST_MESSAGE ?
516 content::Source<extensions::TestSendMessageFunction>(source).ptr() :
517 NULL;
518 messages_.push_back(entry);
519 base::MessageLoopForUI::current()->Quit();
520 }
521
522 private:
523 std::deque<Message> messages_;
524 content::NotificationRegistrar registrar_;
525 };
526
527 // The base test class.
528 class FileManagerBrowserTestBase : public ExtensionApiTest {
529 protected:
530 virtual void SetUpInProcessBrowserTestFixture() OVERRIDE;
531
532 virtual void SetUpOnMainThread() OVERRIDE;
533
534 // Adds an incognito and guest-mode flags for tests in the guest mode.
535 virtual void SetUpCommandLine(CommandLine* command_line) OVERRIDE;
536
537 // Loads our testing extension and sends it a string identifying the current
538 // test.
539 virtual void StartTest();
540 void RunTestMessageLoop();
541
542 // Overriding point for test configurations.
GetTestManifestName() const543 virtual const char* GetTestManifestName() const {
544 return "file_manager_test_manifest.json";
545 }
546 virtual GuestMode GetGuestModeParam() const = 0;
547 virtual const char* GetTestCaseNameParam() const = 0;
548 virtual std::string OnMessage(const std::string& name,
549 const base::Value* value);
550
551 scoped_ptr<LocalTestVolume> local_volume_;
552 linked_ptr<DriveTestVolume> drive_volume_;
553 std::map<Profile*, linked_ptr<DriveTestVolume> > drive_volumes_;
554 scoped_ptr<FakeTestVolume> usb_volume_;
555 scoped_ptr<FakeTestVolume> mtp_volume_;
556
557 private:
558 drive::DriveIntegrationService* CreateDriveIntegrationService(
559 Profile* profile);
560 DriveIntegrationServiceFactory::FactoryCallback
561 create_drive_integration_service_;
562 scoped_ptr<DriveIntegrationServiceFactory::ScopedFactoryForTest>
563 service_factory_for_test_;
564 };
565
SetUpInProcessBrowserTestFixture()566 void FileManagerBrowserTestBase::SetUpInProcessBrowserTestFixture() {
567 ExtensionApiTest::SetUpInProcessBrowserTestFixture();
568 extensions::ComponentLoader::EnableBackgroundExtensionsForTesting();
569
570 local_volume_.reset(new DownloadsTestVolume);
571 if (GetGuestModeParam() != IN_GUEST_MODE) {
572 create_drive_integration_service_ =
573 base::Bind(&FileManagerBrowserTestBase::CreateDriveIntegrationService,
574 base::Unretained(this));
575 service_factory_for_test_.reset(
576 new DriveIntegrationServiceFactory::ScopedFactoryForTest(
577 &create_drive_integration_service_));
578 }
579 }
580
SetUpOnMainThread()581 void FileManagerBrowserTestBase::SetUpOnMainThread() {
582 ExtensionApiTest::SetUpOnMainThread();
583 ASSERT_TRUE(local_volume_->Mount(profile()));
584
585 if (GetGuestModeParam() != IN_GUEST_MODE) {
586 // Install the web server to serve the mocked share dialog.
587 ASSERT_TRUE(embedded_test_server()->InitializeAndWaitUntilReady());
588 const GURL share_url_base(embedded_test_server()->GetURL(
589 "/chromeos/file_manager/share_dialog_mock/index.html"));
590 drive_volume_ = drive_volumes_[profile()->GetOriginalProfile()];
591 drive_volume_->ConfigureShareUrlBase(share_url_base);
592 test_util::WaitUntilDriveMountPointIsAdded(profile());
593 }
594 }
595
SetUpCommandLine(CommandLine * command_line)596 void FileManagerBrowserTestBase::SetUpCommandLine(CommandLine* command_line) {
597 if (GetGuestModeParam() == IN_GUEST_MODE) {
598 command_line->AppendSwitch(chromeos::switches::kGuestSession);
599 command_line->AppendSwitchNative(chromeos::switches::kLoginUser, "");
600 command_line->AppendSwitch(switches::kIncognito);
601 }
602 if (GetGuestModeParam() == IN_INCOGNITO) {
603 command_line->AppendSwitch(switches::kIncognito);
604 }
605 ExtensionApiTest::SetUpCommandLine(command_line);
606 }
607
StartTest()608 void FileManagerBrowserTestBase::StartTest() {
609 // Launch the extension.
610 const base::FilePath path =
611 test_data_dir_.AppendASCII("file_manager_browsertest");
612 const extensions::Extension* const extension =
613 LoadExtensionAsComponentWithManifest(path, GetTestManifestName());
614 ASSERT_TRUE(extension);
615
616 RunTestMessageLoop();
617 }
618
RunTestMessageLoop()619 void FileManagerBrowserTestBase::RunTestMessageLoop() {
620 // Handle the messages from JavaScript.
621 // The while loop is break when the test is passed or failed.
622 FileManagerTestListener listener;
623 while (true) {
624 FileManagerTestListener::Message entry = listener.GetNextMessage();
625 if (entry.type == chrome::NOTIFICATION_EXTENSION_TEST_PASSED) {
626 // Test succeed.
627 break;
628 } else if (entry.type == chrome::NOTIFICATION_EXTENSION_TEST_FAILED) {
629 // Test failed.
630 ADD_FAILURE() << entry.message;
631 break;
632 }
633
634 // Parse the message value as JSON.
635 const scoped_ptr<const base::Value> value(
636 base::JSONReader::Read(entry.message));
637
638 // If the message is not the expected format, just ignore it.
639 const base::DictionaryValue* message_dictionary = NULL;
640 std::string name;
641 if (!value || !value->GetAsDictionary(&message_dictionary) ||
642 !message_dictionary->GetString("name", &name))
643 continue;
644
645 entry.function->Reply(OnMessage(name, value.get()));
646 }
647 }
648
OnMessage(const std::string & name,const base::Value * value)649 std::string FileManagerBrowserTestBase::OnMessage(const std::string& name,
650 const base::Value* value) {
651 if (name == "getTestName") {
652 // Pass the test case name.
653 return GetTestCaseNameParam();
654 } else if (name == "getRootPaths") {
655 // Pass the root paths.
656 const scoped_ptr<base::DictionaryValue> res(new base::DictionaryValue());
657 res->SetString("downloads",
658 "/" + util::GetDownloadsMountPointName(profile()));
659 res->SetString("drive",
660 "/" + drive::util::GetDriveMountPointPath(profile()
661 ).BaseName().AsUTF8Unsafe() + "/root");
662 std::string jsonString;
663 base::JSONWriter::Write(res.get(), &jsonString);
664 return jsonString;
665 } else if (name == "isInGuestMode") {
666 // Obtain whether the test is in guest mode or not.
667 return GetGuestModeParam() != NOT_IN_GUEST_MODE ? "true" : "false";
668 } else if (name == "getCwsWidgetContainerMockUrl") {
669 // Obtain whether the test is in guest mode or not.
670 const GURL url = embedded_test_server()->GetURL(
671 "/chromeos/file_manager/cws_container_mock/index.html");
672 std::string origin = url.GetOrigin().spec();
673
674 // Removes trailing a slash.
675 if (*origin.rbegin() == '/')
676 origin.resize(origin.length() - 1);
677
678 const scoped_ptr<base::DictionaryValue> res(new base::DictionaryValue());
679 res->SetString("url", url.spec());
680 res->SetString("origin", origin);
681 std::string jsonString;
682 base::JSONWriter::Write(res.get(), &jsonString);
683 return jsonString;
684 } else if (name == "addEntries") {
685 // Add entries to the specified volume.
686 base::JSONValueConverter<AddEntriesMessage> add_entries_message_converter;
687 AddEntriesMessage message;
688 if (!add_entries_message_converter.Convert(*value, &message))
689 return "onError";
690 for (size_t i = 0; i < message.entries.size(); ++i) {
691 switch (message.volume) {
692 case LOCAL_VOLUME:
693 local_volume_->CreateEntry(*message.entries[i]);
694 break;
695 case DRIVE_VOLUME:
696 if (drive_volume_.get())
697 drive_volume_->CreateEntry(*message.entries[i]);
698 break;
699 case USB_VOLUME:
700 if (usb_volume_)
701 usb_volume_->CreateEntry(*message.entries[i]);
702 break;
703 default:
704 NOTREACHED();
705 break;
706 }
707 }
708 return "onEntryAdded";
709 } else if (name == "mountFakeUsb") {
710 usb_volume_.reset(new FakeTestVolume("fake-usb",
711 VOLUME_TYPE_REMOVABLE_DISK_PARTITION,
712 chromeos::DEVICE_TYPE_USB));
713 usb_volume_->Mount(profile());
714 return "true";
715 } else if (name == "mountFakeMtp") {
716 mtp_volume_.reset(new FakeTestVolume("fake-mtp",
717 VOLUME_TYPE_MTP,
718 chromeos::DEVICE_TYPE_UNKNOWN));
719 if (!mtp_volume_->PrepareTestEntries(profile()))
720 return "false";
721 mtp_volume_->Mount(profile());
722 return "true";
723 }
724 return "unknownMessage";
725 }
726
727 drive::DriveIntegrationService*
CreateDriveIntegrationService(Profile * profile)728 FileManagerBrowserTestBase::CreateDriveIntegrationService(Profile* profile) {
729 drive_volumes_[profile->GetOriginalProfile()].reset(new DriveTestVolume());
730 return drive_volumes_[profile->GetOriginalProfile()]->
731 CreateDriveIntegrationService(profile);
732 }
733
734 // Parameter of FileManagerBrowserTest.
735 // The second value is the case name of JavaScript.
736 typedef std::tr1::tuple<GuestMode, const char*> TestParameter;
737
738 // Test fixture class for normal (not multi-profile related) tests.
739 class FileManagerBrowserTest :
740 public FileManagerBrowserTestBase,
741 public ::testing::WithParamInterface<TestParameter> {
GetGuestModeParam() const742 virtual GuestMode GetGuestModeParam() const OVERRIDE {
743 return std::tr1::get<0>(GetParam());
744 }
GetTestCaseNameParam() const745 virtual const char* GetTestCaseNameParam() const OVERRIDE {
746 return std::tr1::get<1>(GetParam());
747 }
748 };
749
IN_PROC_BROWSER_TEST_P(FileManagerBrowserTest,Test)750 IN_PROC_BROWSER_TEST_P(FileManagerBrowserTest, Test) {
751 StartTest();
752 }
753
754 // Unlike TEST/TEST_F, which are macros that expand to further macros,
755 // INSTANTIATE_TEST_CASE_P is a macro that expands directly to code that
756 // stringizes the arguments. As a result, macros passed as parameters (such as
757 // prefix or test_case_name) will not be expanded by the preprocessor. To work
758 // around this, indirect the macro for INSTANTIATE_TEST_CASE_P, so that the
759 // pre-processor will expand macros such as MAYBE_test_name before
760 // instantiating the test.
761 #define WRAPPED_INSTANTIATE_TEST_CASE_P(prefix, test_case_name, generator) \
762 INSTANTIATE_TEST_CASE_P(prefix, test_case_name, generator)
763
764 // Slow tests are disabled on debug build. http://crbug.com/327719
765 #if !defined(NDEBUG)
766 #define MAYBE_FileDisplay DISABLED_FileDisplay
767 #else
768 #define MAYBE_FileDisplay FileDisplay
769 #endif
770 WRAPPED_INSTANTIATE_TEST_CASE_P(
771 MAYBE_FileDisplay,
772 FileManagerBrowserTest,
773 ::testing::Values(TestParameter(NOT_IN_GUEST_MODE, "fileDisplayDownloads"),
774 TestParameter(IN_GUEST_MODE, "fileDisplayDownloads"),
775 TestParameter(NOT_IN_GUEST_MODE, "fileDisplayDrive"),
776 TestParameter(NOT_IN_GUEST_MODE, "fileDisplayMtp")));
777
778 // Slow tests are disabled on debug build. http://crbug.com/327719
779 #if !defined(NDEBUG)
780 #define MAYBE_OpenZipFiles DISABLED_OpenZipFiles
781 #else
782 #define MAYBE_OpenZipFiles OpenZipFiles
783 #endif
784 WRAPPED_INSTANTIATE_TEST_CASE_P(
785 MAYBE_OpenZipFiles,
786 FileManagerBrowserTest,
787 ::testing::Values(TestParameter(IN_GUEST_MODE, "zipOpenDownloads"),
788 TestParameter(NOT_IN_GUEST_MODE, "zipOpenDownloads"),
789 TestParameter(NOT_IN_GUEST_MODE, "zipOpenDrive")));
790
791 // Slow tests are disabled on debug build. http://crbug.com/327719
792 #if !defined(NDEBUG)
793 #define MAYBE_OpenVideoFiles DISABLED_OpenVideoFiles
794 #else
795 #define MAYBE_OpenVideoFiles OpenVideoFiles
796 #endif
797 WRAPPED_INSTANTIATE_TEST_CASE_P(
798 MAYBE_OpenVideoFiles,
799 FileManagerBrowserTest,
800 ::testing::Values(TestParameter(IN_GUEST_MODE, "videoOpenDownloads"),
801 TestParameter(NOT_IN_GUEST_MODE, "videoOpenDownloads"),
802 TestParameter(NOT_IN_GUEST_MODE, "videoOpenDrive")));
803
804 // Slow tests are disabled on debug build. http://crbug.com/327719
805 #if !defined(NDEBUG)
806 #define MAYBE_OpenAudioFiles DISABLED_OpenAudioFiles
807 #else
808 #define MAYBE_OpenAudioFiles OpenAudioFiles
809 #endif
810 WRAPPED_INSTANTIATE_TEST_CASE_P(
811 MAYBE_OpenAudioFiles,
812 FileManagerBrowserTest,
813 ::testing::Values(
814 TestParameter(IN_GUEST_MODE, "audioOpenDownloads"),
815 TestParameter(NOT_IN_GUEST_MODE, "audioOpenDownloads"),
816 TestParameter(NOT_IN_GUEST_MODE, "audioOpenDrive"),
817 TestParameter(NOT_IN_GUEST_MODE, "audioAutoAdvanceDrive"),
818 TestParameter(NOT_IN_GUEST_MODE, "audioRepeatSingleFileDrive"),
819 TestParameter(NOT_IN_GUEST_MODE, "audioNoRepeatSingleFileDrive"),
820 TestParameter(NOT_IN_GUEST_MODE, "audioRepeatMultipleFileDrive"),
821 TestParameter(NOT_IN_GUEST_MODE, "audioNoRepeatMultipleFileDrive")));
822
823 // Slow tests are disabled on debug build. http://crbug.com/327719
824 #if !defined(NDEBUG)
825 #define MAYBE_CreateNewFolder DISABLED_CreateNewFolder
826 #else
827 #define MAYBE_CreateNewFolder CreateNewFolder
828 #endif
829 INSTANTIATE_TEST_CASE_P(
830 MAYBE_CreateNewFolder,
831 FileManagerBrowserTest,
832 ::testing::Values(TestParameter(NOT_IN_GUEST_MODE,
833 "createNewFolderAfterSelectFile"),
834 TestParameter(IN_GUEST_MODE,
835 "createNewFolderDownloads"),
836 TestParameter(NOT_IN_GUEST_MODE,
837 "createNewFolderDownloads"),
838 TestParameter(NOT_IN_GUEST_MODE,
839 "createNewFolderDrive")));
840
841 // Slow tests are disabled on debug build. http://crbug.com/327719
842 #if !defined(NDEBUG)
843 #define MAYBE_KeyboardOperations DISABLED_KeyboardOperations
844 #else
845 #define MAYBE_KeyboardOperations KeyboardOperations
846 #endif
847 WRAPPED_INSTANTIATE_TEST_CASE_P(
848 MAYBE_KeyboardOperations,
849 FileManagerBrowserTest,
850 ::testing::Values(TestParameter(IN_GUEST_MODE, "keyboardDeleteDownloads"),
851 TestParameter(NOT_IN_GUEST_MODE,
852 "keyboardDeleteDownloads"),
853 TestParameter(NOT_IN_GUEST_MODE, "keyboardDeleteDrive"),
854 TestParameter(IN_GUEST_MODE, "keyboardCopyDownloads"),
855 TestParameter(NOT_IN_GUEST_MODE, "keyboardCopyDownloads"),
856 TestParameter(NOT_IN_GUEST_MODE, "keyboardCopyDrive"),
857 TestParameter(IN_GUEST_MODE, "renameFileDownloads"),
858 TestParameter(NOT_IN_GUEST_MODE, "renameFileDownloads"),
859 TestParameter(NOT_IN_GUEST_MODE, "renameFileDrive")));
860
861 // Slow tests are disabled on debug build. http://crbug.com/327719
862 #if !defined(NDEBUG)
863 #define MAYBE_DriveSpecific DISABLED_DriveSpecific
864 #else
865 #define MAYBE_DriveSpecific DriveSpecific
866 #endif
867 WRAPPED_INSTANTIATE_TEST_CASE_P(
868 MAYBE_DriveSpecific,
869 FileManagerBrowserTest,
870 ::testing::Values(TestParameter(NOT_IN_GUEST_MODE, "openSidebarRecent"),
871 TestParameter(NOT_IN_GUEST_MODE, "openSidebarOffline"),
872 TestParameter(NOT_IN_GUEST_MODE,
873 "openSidebarSharedWithMe"),
874 TestParameter(NOT_IN_GUEST_MODE, "autocomplete")));
875
876 // Slow tests are disabled on debug build. http://crbug.com/327719
877 #if !defined(NDEBUG)
878 #define MAYBE_Transfer DISABLED_Transfer
879 #else
880 #define MAYBE_Transfer Transfer
881 #endif
882 WRAPPED_INSTANTIATE_TEST_CASE_P(
883 MAYBE_Transfer,
884 FileManagerBrowserTest,
885 ::testing::Values(
886 TestParameter(NOT_IN_GUEST_MODE, "transferFromDriveToDownloads"),
887 TestParameter(NOT_IN_GUEST_MODE, "transferFromDownloadsToDrive"),
888 TestParameter(NOT_IN_GUEST_MODE, "transferFromSharedToDownloads"),
889 TestParameter(NOT_IN_GUEST_MODE, "transferFromSharedToDrive"),
890 TestParameter(NOT_IN_GUEST_MODE, "transferFromRecentToDownloads"),
891 TestParameter(NOT_IN_GUEST_MODE, "transferFromRecentToDrive"),
892 TestParameter(NOT_IN_GUEST_MODE, "transferFromOfflineToDownloads"),
893 TestParameter(NOT_IN_GUEST_MODE, "transferFromOfflineToDrive")));
894
895 // Slow tests are disabled on debug build. http://crbug.com/327719
896 #if !defined(NDEBUG)
897 #define MAYBE_RestorePrefs DISABLED_RestorePrefs
898 #else
899 #define MAYBE_RestorePrefs RestorePrefs
900 #endif
901 WRAPPED_INSTANTIATE_TEST_CASE_P(
902 MAYBE_RestorePrefs,
903 FileManagerBrowserTest,
904 ::testing::Values(TestParameter(IN_GUEST_MODE, "restoreSortColumn"),
905 TestParameter(NOT_IN_GUEST_MODE, "restoreSortColumn"),
906 TestParameter(IN_GUEST_MODE, "restoreCurrentView"),
907 TestParameter(NOT_IN_GUEST_MODE, "restoreCurrentView")));
908
909 // Slow tests are disabled on debug build. http://crbug.com/327719
910 #if !defined(NDEBUG)
911 #define MAYBE_ShareDialog DISABLED_ShareDialog
912 #else
913 #define MAYBE_ShareDialog ShareDialog
914 #endif
915 WRAPPED_INSTANTIATE_TEST_CASE_P(
916 MAYBE_ShareDialog,
917 FileManagerBrowserTest,
918 ::testing::Values(TestParameter(NOT_IN_GUEST_MODE, "shareFile"),
919 TestParameter(NOT_IN_GUEST_MODE, "shareDirectory")));
920
921 // Slow tests are disabled on debug build. http://crbug.com/327719
922 #if !defined(NDEBUG)
923 #define MAYBE_RestoreGeometry DISABLED_RestoreGeometry
924 #else
925 #define MAYBE_RestoreGeometry RestoreGeometry
926 #endif
927 WRAPPED_INSTANTIATE_TEST_CASE_P(
928 MAYBE_RestoreGeometry,
929 FileManagerBrowserTest,
930 ::testing::Values(TestParameter(NOT_IN_GUEST_MODE, "restoreGeometry"),
931 TestParameter(IN_GUEST_MODE, "restoreGeometry")));
932
933 // Slow tests are disabled on debug build. http://crbug.com/327719
934 #if !defined(NDEBUG)
935 #define MAYBE_Traverse DISABLED_Traverse
936 #else
937 #define MAYBE_Traverse Traverse
938 #endif
939 WRAPPED_INSTANTIATE_TEST_CASE_P(
940 MAYBE_Traverse,
941 FileManagerBrowserTest,
942 ::testing::Values(TestParameter(IN_GUEST_MODE, "traverseDownloads"),
943 TestParameter(NOT_IN_GUEST_MODE, "traverseDownloads"),
944 TestParameter(NOT_IN_GUEST_MODE, "traverseDrive")));
945
946 // Slow tests are disabled on debug build. http://crbug.com/327719
947 #if !defined(NDEBUG)
948 #define MAYBE_SuggestAppDialog DISABLED_SuggestAppDialog
949 #else
950 #define MAYBE_SuggestAppDialog SuggestAppDialog
951 #endif
952 WRAPPED_INSTANTIATE_TEST_CASE_P(
953 MAYBE_SuggestAppDialog,
954 FileManagerBrowserTest,
955 ::testing::Values(TestParameter(NOT_IN_GUEST_MODE, "suggestAppDialog")));
956
957 // Slow tests are disabled on debug build. http://crbug.com/327719
958 #if !defined(NDEBUG)
959 #define MAYBE_ExecuteDefaultTaskOnDownloads \
960 DISABLED_ExecuteDefaultTaskOnDownloads
961 #else
962 #define MAYBE_ExecuteDefaultTaskOnDownloads ExecuteDefaultTaskOnDownloads
963 #endif
964 WRAPPED_INSTANTIATE_TEST_CASE_P(
965 MAYBE_ExecuteDefaultTaskOnDownloads,
966 FileManagerBrowserTest,
967 ::testing::Values(
968 TestParameter(NOT_IN_GUEST_MODE, "executeDefaultTaskOnDownloads"),
969 TestParameter(IN_GUEST_MODE, "executeDefaultTaskOnDownloads")));
970
971 // Slow tests are disabled on debug build. http://crbug.com/327719
972 #if !defined(NDEBUG)
973 #define MAYBE_ExecuteDefaultTaskOnDrive DISABLED_ExecuteDefaultTaskOnDrive
974 #else
975 #define MAYBE_ExecuteDefaultTaskOnDrive ExecuteDefaultTaskOnDrive
976 #endif
977 INSTANTIATE_TEST_CASE_P(
978 MAYBE_ExecuteDefaultTaskOnDrive,
979 FileManagerBrowserTest,
980 ::testing::Values(
981 TestParameter(NOT_IN_GUEST_MODE, "executeDefaultTaskOnDrive")));
982
983 // Slow tests are disabled on debug build. http://crbug.com/327719
984 #if !defined(NDEBUG)
985 #define MAYBE_DefaultActionDialog DISABLED_DefaultActionDialog
986 #else
987 #define MAYBE_DefaultActionDialog DefaultActionDialog
988 #endif
989 WRAPPED_INSTANTIATE_TEST_CASE_P(
990 MAYBE_DefaultActionDialog,
991 FileManagerBrowserTest,
992 ::testing::Values(
993 TestParameter(NOT_IN_GUEST_MODE, "defaultActionDialogOnDownloads"),
994 TestParameter(IN_GUEST_MODE, "defaultActionDialogOnDownloads"),
995 TestParameter(NOT_IN_GUEST_MODE, "defaultActionDialogOnDrive")));
996
997 // Slow tests are disabled on debug build. http://crbug.com/327719
998 #if !defined(NDEBUG)
999 #define MAYBE_NavigationList DISABLED_NavigationList
1000 #else
1001 #define MAYBE_NavigationList NavigationList
1002 #endif
1003 WRAPPED_INSTANTIATE_TEST_CASE_P(
1004 MAYBE_NavigationList,
1005 FileManagerBrowserTest,
1006 ::testing::Values(TestParameter(NOT_IN_GUEST_MODE,
1007 "traverseNavigationList")));
1008
1009 // Slow tests are disabled on debug build. http://crbug.com/327719
1010 #if !defined(NDEBUG)
1011 #define MAYBE_FolderShortcuts DISABLED_FolderShortcuts
1012 #else
1013 #define MAYBE_FolderShortcuts FolderShortcuts
1014 #endif
1015 WRAPPED_INSTANTIATE_TEST_CASE_P(
1016 MAYBE_FolderShortcuts,
1017 FileManagerBrowserTest,
1018 ::testing::Values(
1019 TestParameter(NOT_IN_GUEST_MODE, "traverseFolderShortcuts"),
1020 TestParameter(NOT_IN_GUEST_MODE, "addRemoveFolderShortcuts")));
1021
1022 INSTANTIATE_TEST_CASE_P(
1023 TabIndex,
1024 FileManagerBrowserTest,
1025 ::testing::Values(TestParameter(NOT_IN_GUEST_MODE, "searchBoxFocus")));
1026
1027 // Slow tests are disabled on debug build. http://crbug.com/327719
1028 #if !defined(NDEBUG)
1029 #define MAYBE_Thumbnails DISABLED_Thumbnails
1030 #else
1031 #define MAYBE_Thumbnails Thumbnails
1032 #endif
1033 WRAPPED_INSTANTIATE_TEST_CASE_P(
1034 MAYBE_Thumbnails,
1035 FileManagerBrowserTest,
1036 ::testing::Values(TestParameter(NOT_IN_GUEST_MODE, "thumbnailsDownloads"),
1037 TestParameter(IN_GUEST_MODE, "thumbnailsDownloads")));
1038
1039 #if !defined(NDEBUG)
1040 #define MAYBE_OpenFileDialog DISABLED_OpenFileDialog
1041 #else
1042 #define MAYBE_OpenFileDialog OpenFileDialog
1043 #endif
1044 WRAPPED_INSTANTIATE_TEST_CASE_P(
1045 MAYBE_OpenFileDialog,
1046 FileManagerBrowserTest,
1047 ::testing::Values(TestParameter(NOT_IN_GUEST_MODE,
1048 "openFileDialogOnDownloads"),
1049 TestParameter(IN_GUEST_MODE,
1050 "openFileDialogOnDownloads"),
1051 TestParameter(NOT_IN_GUEST_MODE,
1052 "openFileDialogOnDrive"),
1053 TestParameter(IN_INCOGNITO,
1054 "openFileDialogOnDownloads"),
1055 TestParameter(IN_INCOGNITO,
1056 "openFileDialogOnDrive")));
1057
1058 // Slow tests are disabled on debug build. http://crbug.com/327719
1059 #if !defined(NDEBUG)
1060 #define MAYBE_CopyBetweenWindows DISABLED_CopyBetweenWindows
1061 #else
1062 #define MAYBE_CopyBetweenWindows CopyBetweenWindows
1063 #endif
1064 WRAPPED_INSTANTIATE_TEST_CASE_P(
1065 MAYBE_CopyBetweenWindows,
1066 FileManagerBrowserTest,
1067 ::testing::Values(
1068 TestParameter(NOT_IN_GUEST_MODE, "copyBetweenWindowsLocalToDrive"),
1069 TestParameter(NOT_IN_GUEST_MODE, "copyBetweenWindowsLocalToUsb"),
1070 TestParameter(NOT_IN_GUEST_MODE, "copyBetweenWindowsUsbToDrive"),
1071 TestParameter(NOT_IN_GUEST_MODE, "copyBetweenWindowsDriveToLocal"),
1072 TestParameter(NOT_IN_GUEST_MODE, "copyBetweenWindowsDriveToUsb"),
1073 TestParameter(NOT_IN_GUEST_MODE, "copyBetweenWindowsUsbToLocal")));
1074
1075 // Slow tests are disabled on debug build. http://crbug.com/327719
1076 #if !defined(NDEBUG)
1077 #define MAYBE_ShowGridView DISABLED_ShowGridView
1078 #else
1079 #define MAYBE_ShowGridView ShowGridView
1080 #endif
1081 WRAPPED_INSTANTIATE_TEST_CASE_P(
1082 MAYBE_ShowGridView,
1083 FileManagerBrowserTest,
1084 ::testing::Values(TestParameter(NOT_IN_GUEST_MODE, "showGridViewDownloads"),
1085 TestParameter(IN_GUEST_MODE, "showGridViewDownloads"),
1086 TestParameter(NOT_IN_GUEST_MODE, "showGridViewDrive")));
1087
1088 // Structure to describe an account info.
1089 struct TestAccountInfo {
1090 const char* const email;
1091 const char* const hash;
1092 const char* const display_name;
1093 };
1094
1095 enum {
1096 DUMMY_ACCOUNT_INDEX = 0,
1097 PRIMARY_ACCOUNT_INDEX = 1,
1098 SECONDARY_ACCOUNT_INDEX_START = 2,
1099 };
1100
1101 static const TestAccountInfo kTestAccounts[] = {
1102 {"__dummy__@invalid.domain", "hashdummy", "Dummy Account"},
1103 {"alice@invalid.domain", "hashalice", "Alice"},
1104 {"bob@invalid.domain", "hashbob", "Bob"},
1105 {"charlie@invalid.domain", "hashcharlie", "Charlie"},
1106 };
1107
1108 // Test fixture class for testing multi-profile features.
1109 class MultiProfileFileManagerBrowserTest : public FileManagerBrowserTestBase {
1110 protected:
1111 // Enables multi-profiles.
SetUpCommandLine(CommandLine * command_line)1112 virtual void SetUpCommandLine(CommandLine* command_line) OVERRIDE {
1113 FileManagerBrowserTestBase::SetUpCommandLine(command_line);
1114 // Logs in to a dummy profile (For making MultiProfileWindowManager happy;
1115 // browser test creates a default window and the manager tries to assign a
1116 // user for it, and we need a profile connected to a user.)
1117 command_line->AppendSwitchASCII(chromeos::switches::kLoginUser,
1118 kTestAccounts[DUMMY_ACCOUNT_INDEX].email);
1119 command_line->AppendSwitchASCII(chromeos::switches::kLoginProfile,
1120 kTestAccounts[DUMMY_ACCOUNT_INDEX].hash);
1121 }
1122
1123 // Logs in to the primary profile of this test.
SetUpOnMainThread()1124 virtual void SetUpOnMainThread() OVERRIDE {
1125 const TestAccountInfo& info = kTestAccounts[PRIMARY_ACCOUNT_INDEX];
1126
1127 AddUser(info, true);
1128 FileManagerBrowserTestBase::SetUpOnMainThread();
1129 }
1130
1131 // Loads all users to the current session and sets up necessary fields.
1132 // This is used for preparing all accounts in PRE_ test setup, and for testing
1133 // actual login behavior.
AddAllUsers()1134 void AddAllUsers() {
1135 for (size_t i = 0; i < arraysize(kTestAccounts); ++i)
1136 AddUser(kTestAccounts[i], i >= SECONDARY_ACCOUNT_INDEX_START);
1137 }
1138
1139 // Returns primary profile (if it is already created.)
profile()1140 virtual Profile* profile() OVERRIDE {
1141 Profile* const profile = chromeos::ProfileHelper::GetProfileByUserIdHash(
1142 kTestAccounts[PRIMARY_ACCOUNT_INDEX].hash);
1143 return profile ? profile : FileManagerBrowserTestBase::profile();
1144 }
1145
1146 // Sets the test case name (used as a function name in test_cases.js to call.)
set_test_case_name(const std::string & name)1147 void set_test_case_name(const std::string& name) { test_case_name_ = name; }
1148
1149 // Adds a new user for testing to the current session.
AddUser(const TestAccountInfo & info,bool log_in)1150 void AddUser(const TestAccountInfo& info, bool log_in) {
1151 chromeos::UserManager* const user_manager = chromeos::UserManager::Get();
1152 if (log_in)
1153 user_manager->UserLoggedIn(info.email, info.hash, false);
1154 user_manager->SaveUserDisplayName(info.email,
1155 base::UTF8ToUTF16(info.display_name));
1156 chromeos::ProfileHelper::GetProfileByUserIdHash(info.hash)->GetPrefs()->
1157 SetString(prefs::kGoogleServicesUsername, info.email);
1158 }
1159
1160 private:
GetGuestModeParam() const1161 virtual GuestMode GetGuestModeParam() const OVERRIDE {
1162 return NOT_IN_GUEST_MODE;
1163 }
1164
GetTestCaseNameParam() const1165 virtual const char* GetTestCaseNameParam() const OVERRIDE {
1166 return test_case_name_.c_str();
1167 }
1168
OnMessage(const std::string & name,const base::Value * value)1169 virtual std::string OnMessage(const std::string& name,
1170 const base::Value* value) OVERRIDE {
1171 if (name == "addAllUsers") {
1172 AddAllUsers();
1173 return "true";
1174 } else if (name == "getWindowOwnerId") {
1175 chrome::MultiUserWindowManager* const window_manager =
1176 chrome::MultiUserWindowManager::GetInstance();
1177 apps::AppWindowRegistry* const app_window_registry =
1178 apps::AppWindowRegistry::Get(profile());
1179 DCHECK(window_manager);
1180 DCHECK(app_window_registry);
1181
1182 const apps::AppWindowRegistry::AppWindowList& list =
1183 app_window_registry->GetAppWindowsForApp(
1184 file_manager::kFileManagerAppId);
1185 return list.size() == 1u ?
1186 window_manager->GetUserPresentingWindow(
1187 list.front()->GetNativeWindow()) : "";
1188 }
1189 return FileManagerBrowserTestBase::OnMessage(name, value);
1190 }
1191
1192 std::string test_case_name_;
1193 };
1194
1195 // Slow tests are disabled on debug build. http://crbug.com/327719
1196 #if !defined(NDEBUG)
1197 #define MAYBE_PRE_BasicDownloads DISABLED_PRE_BasicDownloads
1198 #define MAYBE_BasicDownloads DISABLED_BasicDownloads
1199 #else
1200 #define MAYBE_PRE_BasicDownloads PRE_BasicDownloads
1201 #define MAYBE_BasicDownloads BasicDownloads
1202 #endif
IN_PROC_BROWSER_TEST_F(MultiProfileFileManagerBrowserTest,MAYBE_PRE_BasicDownloads)1203 IN_PROC_BROWSER_TEST_F(MultiProfileFileManagerBrowserTest,
1204 MAYBE_PRE_BasicDownloads) {
1205 AddAllUsers();
1206 }
1207
IN_PROC_BROWSER_TEST_F(MultiProfileFileManagerBrowserTest,MAYBE_BasicDownloads)1208 IN_PROC_BROWSER_TEST_F(MultiProfileFileManagerBrowserTest,
1209 MAYBE_BasicDownloads) {
1210 AddAllUsers();
1211
1212 // Sanity check that normal operations work in multi-profile setting as well.
1213 set_test_case_name("keyboardCopyDownloads");
1214 StartTest();
1215 }
1216
1217 // Slow tests are disabled on debug build. http://crbug.com/327719
1218 #if !defined(NDEBUG)
1219 #define MAYBE_PRE_BasicDrive DISABLED_PRE_BasicDrive
1220 #define MAYBE_BasicDrive DISABLED_BasicDrive
1221 #else
1222 #define MAYBE_PRE_BasicDrive PRE_BasicDrive
1223 #define MAYBE_BasicDrive BasicDrive
1224 #endif
IN_PROC_BROWSER_TEST_F(MultiProfileFileManagerBrowserTest,MAYBE_PRE_BasicDrive)1225 IN_PROC_BROWSER_TEST_F(MultiProfileFileManagerBrowserTest,
1226 MAYBE_PRE_BasicDrive) {
1227 AddAllUsers();
1228 }
1229
IN_PROC_BROWSER_TEST_F(MultiProfileFileManagerBrowserTest,MAYBE_BasicDrive)1230 IN_PROC_BROWSER_TEST_F(MultiProfileFileManagerBrowserTest, MAYBE_BasicDrive) {
1231 AddAllUsers();
1232
1233 // Sanity check that normal operations work in multi-profile setting as well.
1234 set_test_case_name("keyboardCopyDrive");
1235 StartTest();
1236 }
1237
1238 // Slow tests are disabled on debug build. http://crbug.com/327719
1239 #if !defined(NDEBUG)
1240 #define MAYBE_PRE_Badge DISABLED_PRE_Badge
1241 #define MAYBE_Badge DISABLED_Badge
1242 #else
1243 #define MAYBE_PRE_Badge PRE_Badge
1244 #define MAYBE_Badge Badge
1245 #endif
IN_PROC_BROWSER_TEST_F(MultiProfileFileManagerBrowserTest,MAYBE_PRE_Badge)1246 IN_PROC_BROWSER_TEST_F(MultiProfileFileManagerBrowserTest, MAYBE_PRE_Badge) {
1247 AddAllUsers();
1248 }
1249
IN_PROC_BROWSER_TEST_F(MultiProfileFileManagerBrowserTest,MAYBE_Badge)1250 IN_PROC_BROWSER_TEST_F(MultiProfileFileManagerBrowserTest, MAYBE_Badge) {
1251 // Test the profile badge to be correctly shown and hidden.
1252 set_test_case_name("multiProfileBadge");
1253 StartTest();
1254 }
1255
1256 // Slow tests are disabled on debug build. http://crbug.com/327719
1257 #if !defined(NDEBUG)
1258 #define MAYBE_PRE_VisitDesktopMenu DISABLED_PRE_VisitDesktopMenu
1259 #define MAYBE_VisitDesktopMenu DISABLED_VisitDesktopMenu
1260 #else
1261 #define MAYBE_PRE_VisitDesktopMenu PRE_VisitDesktopMenu
1262 #define MAYBE_VisitDesktopMenu VisitDesktopMenu
1263 #endif
IN_PROC_BROWSER_TEST_F(MultiProfileFileManagerBrowserTest,MAYBE_PRE_VisitDesktopMenu)1264 IN_PROC_BROWSER_TEST_F(MultiProfileFileManagerBrowserTest,
1265 MAYBE_PRE_VisitDesktopMenu) {
1266 AddAllUsers();
1267 }
1268
IN_PROC_BROWSER_TEST_F(MultiProfileFileManagerBrowserTest,MAYBE_VisitDesktopMenu)1269 IN_PROC_BROWSER_TEST_F(MultiProfileFileManagerBrowserTest,
1270 MAYBE_VisitDesktopMenu) {
1271 // Test for the menu item for visiting other profile's desktop.
1272 set_test_case_name("multiProfileVisitDesktopMenu");
1273 StartTest();
1274 }
1275
1276 template<GuestMode M>
1277 class GalleryBrowserTestBase : public FileManagerBrowserTestBase {
1278 public:
GetGuestModeParam() const1279 virtual GuestMode GetGuestModeParam() const OVERRIDE { return M; }
GetTestCaseNameParam() const1280 virtual const char* GetTestCaseNameParam() const OVERRIDE {
1281 return test_case_name_.c_str();
1282 }
1283
1284 protected:
SetUp()1285 virtual void SetUp() OVERRIDE {
1286 AddScript("gallery/test_util.js");
1287 FileManagerBrowserTestBase::SetUp();
1288 }
1289
1290 virtual std::string OnMessage(const std::string& name,
1291 const base::Value* value) OVERRIDE;
1292
GetTestManifestName() const1293 virtual const char* GetTestManifestName() const OVERRIDE {
1294 return "gallery_test_manifest.json";
1295 }
1296
AddScript(const std::string & name)1297 void AddScript(const std::string& name) {
1298 scripts_.AppendString(
1299 "chrome-extension://ejhcmmdhhpdhhgmifplfmjobgegbibkn/" + name);
1300 }
1301
set_test_case_name(const std::string & name)1302 void set_test_case_name(const std::string& name) {
1303 test_case_name_ = name;
1304 }
1305
1306 private:
1307 base::ListValue scripts_;
1308 std::string test_case_name_;
1309 };
1310
1311 template<GuestMode M>
OnMessage(const std::string & name,const base::Value * value)1312 std::string GalleryBrowserTestBase<M>::OnMessage(const std::string& name,
1313 const base::Value* value) {
1314 if (name == "getScripts") {
1315 std::string jsonString;
1316 base::JSONWriter::Write(&scripts_, &jsonString);
1317 return jsonString;
1318 }
1319 return FileManagerBrowserTestBase::OnMessage(name, value);
1320 }
1321
1322 typedef GalleryBrowserTestBase<NOT_IN_GUEST_MODE> GalleryBrowserTest;
1323 typedef GalleryBrowserTestBase<IN_GUEST_MODE> GalleryBrowserTestInGuestMode;
1324
IN_PROC_BROWSER_TEST_F(GalleryBrowserTest,OpenSingleImageOnDownloads)1325 IN_PROC_BROWSER_TEST_F(GalleryBrowserTest, OpenSingleImageOnDownloads) {
1326 AddScript("gallery/open_image_files.js");
1327 set_test_case_name("openSingleImageOnDownloads");
1328 StartTest();
1329 }
1330
IN_PROC_BROWSER_TEST_F(GalleryBrowserTestInGuestMode,OpenSingleImageOnDownloads)1331 IN_PROC_BROWSER_TEST_F(GalleryBrowserTestInGuestMode,
1332 OpenSingleImageOnDownloads) {
1333 AddScript("gallery/open_image_files.js");
1334 set_test_case_name("openSingleImageOnDownloads");
1335 StartTest();
1336 }
1337
IN_PROC_BROWSER_TEST_F(GalleryBrowserTest,OpenSingleImageOnDrive)1338 IN_PROC_BROWSER_TEST_F(GalleryBrowserTest, OpenSingleImageOnDrive) {
1339 AddScript("gallery/open_image_files.js");
1340 set_test_case_name("openSingleImageOnDrive");
1341 StartTest();
1342 }
1343
IN_PROC_BROWSER_TEST_F(GalleryBrowserTest,OpenMultipleImagesOnDownloads)1344 IN_PROC_BROWSER_TEST_F(GalleryBrowserTest, OpenMultipleImagesOnDownloads) {
1345 AddScript("gallery/open_image_files.js");
1346 set_test_case_name("openMultipleImagesOnDownloads");
1347 StartTest();
1348 }
1349
IN_PROC_BROWSER_TEST_F(GalleryBrowserTestInGuestMode,OpenMultipleImagesOnDownloads)1350 IN_PROC_BROWSER_TEST_F(GalleryBrowserTestInGuestMode,
1351 OpenMultipleImagesOnDownloads) {
1352 AddScript("gallery/open_image_files.js");
1353 set_test_case_name("openMultipleImagesOnDownloads");
1354 StartTest();
1355 }
1356
IN_PROC_BROWSER_TEST_F(GalleryBrowserTest,OpenMultipleImagesOnDrive)1357 IN_PROC_BROWSER_TEST_F(GalleryBrowserTest, OpenMultipleImagesOnDrive) {
1358 AddScript("gallery/open_image_files.js");
1359 set_test_case_name("openMultipleImagesOnDrive");
1360 StartTest();
1361 }
1362
IN_PROC_BROWSER_TEST_F(GalleryBrowserTest,TraverseSlideImagesOnDownloads)1363 IN_PROC_BROWSER_TEST_F(GalleryBrowserTest, TraverseSlideImagesOnDownloads) {
1364 AddScript("gallery/slide_mode.js");
1365 set_test_case_name("traverseSlideImagesOnDownloads");
1366 StartTest();
1367 }
1368
IN_PROC_BROWSER_TEST_F(GalleryBrowserTestInGuestMode,TraverseSlideImagesOnDownloads)1369 IN_PROC_BROWSER_TEST_F(GalleryBrowserTestInGuestMode,
1370 TraverseSlideImagesOnDownloads) {
1371 AddScript("gallery/slide_mode.js");
1372 set_test_case_name("traverseSlideImagesOnDownloads");
1373 StartTest();
1374 }
1375
IN_PROC_BROWSER_TEST_F(GalleryBrowserTest,TraverseSlideImagesOnDrive)1376 IN_PROC_BROWSER_TEST_F(GalleryBrowserTest, TraverseSlideImagesOnDrive) {
1377 AddScript("gallery/slide_mode.js");
1378 set_test_case_name("traverseSlideImagesOnDrive");
1379 StartTest();
1380 }
1381
IN_PROC_BROWSER_TEST_F(GalleryBrowserTest,RenameImageOnDownloads)1382 IN_PROC_BROWSER_TEST_F(GalleryBrowserTest, RenameImageOnDownloads) {
1383 AddScript("gallery/slide_mode.js");
1384 set_test_case_name("renameImageOnDownloads");
1385 StartTest();
1386 }
1387
IN_PROC_BROWSER_TEST_F(GalleryBrowserTestInGuestMode,RenameImageOnDownloads)1388 IN_PROC_BROWSER_TEST_F(GalleryBrowserTestInGuestMode,
1389 RenameImageOnDownloads) {
1390 AddScript("gallery/slide_mode.js");
1391 set_test_case_name("renameImageOnDownloads");
1392 StartTest();
1393 }
1394
IN_PROC_BROWSER_TEST_F(GalleryBrowserTest,RenameImageOnDrive)1395 IN_PROC_BROWSER_TEST_F(GalleryBrowserTest, RenameImageOnDrive) {
1396 AddScript("gallery/slide_mode.js");
1397 set_test_case_name("renameImageOnDrive");
1398 StartTest();
1399 }
1400
IN_PROC_BROWSER_TEST_F(GalleryBrowserTest,DeleteImageOnDownloads)1401 IN_PROC_BROWSER_TEST_F(GalleryBrowserTest, DeleteImageOnDownloads) {
1402 AddScript("gallery/slide_mode.js");
1403 set_test_case_name("deleteImageOnDownloads");
1404 StartTest();
1405 }
1406
IN_PROC_BROWSER_TEST_F(GalleryBrowserTestInGuestMode,DeleteImageOnDownloads)1407 IN_PROC_BROWSER_TEST_F(GalleryBrowserTestInGuestMode,
1408 DeleteImageOnDownloads) {
1409 AddScript("gallery/slide_mode.js");
1410 set_test_case_name("deleteImageOnDownloads");
1411 StartTest();
1412 }
1413
IN_PROC_BROWSER_TEST_F(GalleryBrowserTest,DeleteImageOnDrive)1414 IN_PROC_BROWSER_TEST_F(GalleryBrowserTest, DeleteImageOnDrive) {
1415 AddScript("gallery/slide_mode.js");
1416 set_test_case_name("deleteImageOnDrive");
1417 StartTest();
1418 }
1419
IN_PROC_BROWSER_TEST_F(GalleryBrowserTest,RotateImageOnDownloads)1420 IN_PROC_BROWSER_TEST_F(GalleryBrowserTest, RotateImageOnDownloads) {
1421 AddScript("gallery/photo_editor.js");
1422 set_test_case_name("rotateImageOnDownloads");
1423 StartTest();
1424 }
1425
IN_PROC_BROWSER_TEST_F(GalleryBrowserTestInGuestMode,RotateImageOnDownloads)1426 IN_PROC_BROWSER_TEST_F(GalleryBrowserTestInGuestMode,
1427 RotateImageOnDownloads) {
1428 AddScript("gallery/photo_editor.js");
1429 set_test_case_name("rotateImageOnDownloads");
1430 StartTest();
1431 }
1432
IN_PROC_BROWSER_TEST_F(GalleryBrowserTest,RotateImageOnDrive)1433 IN_PROC_BROWSER_TEST_F(GalleryBrowserTest, RotateImageOnDrive) {
1434 AddScript("gallery/photo_editor.js");
1435 set_test_case_name("rotateImageOnDrive");
1436 StartTest();
1437 }
1438
IN_PROC_BROWSER_TEST_F(GalleryBrowserTest,CropImageOnDownloads)1439 IN_PROC_BROWSER_TEST_F(GalleryBrowserTest, CropImageOnDownloads) {
1440 AddScript("gallery/photo_editor.js");
1441 set_test_case_name("cropImageOnDownloads");
1442 StartTest();
1443 }
1444
IN_PROC_BROWSER_TEST_F(GalleryBrowserTestInGuestMode,CropImageOnDownloads)1445 IN_PROC_BROWSER_TEST_F(GalleryBrowserTestInGuestMode,
1446 CropImageOnDownloads) {
1447 AddScript("gallery/photo_editor.js");
1448 set_test_case_name("cropImageOnDownloads");
1449 StartTest();
1450 }
1451
IN_PROC_BROWSER_TEST_F(GalleryBrowserTest,CropImageOnDrive)1452 IN_PROC_BROWSER_TEST_F(GalleryBrowserTest, CropImageOnDrive) {
1453 AddScript("gallery/photo_editor.js");
1454 set_test_case_name("cropImageOnDrive");
1455 StartTest();
1456 }
1457
IN_PROC_BROWSER_TEST_F(GalleryBrowserTest,ExposureImageOnDownloads)1458 IN_PROC_BROWSER_TEST_F(GalleryBrowserTest, ExposureImageOnDownloads) {
1459 AddScript("gallery/photo_editor.js");
1460 set_test_case_name("exposureImageOnDownloads");
1461 StartTest();
1462 }
1463
IN_PROC_BROWSER_TEST_F(GalleryBrowserTestInGuestMode,ExposureImageOnDownloads)1464 IN_PROC_BROWSER_TEST_F(GalleryBrowserTestInGuestMode,
1465 ExposureImageOnDownloads) {
1466 AddScript("gallery/photo_editor.js");
1467 set_test_case_name("exposureImageOnDownloads");
1468 StartTest();
1469 }
1470
IN_PROC_BROWSER_TEST_F(GalleryBrowserTest,ExposureImageOnDrive)1471 IN_PROC_BROWSER_TEST_F(GalleryBrowserTest, ExposureImageOnDrive) {
1472 AddScript("gallery/photo_editor.js");
1473 set_test_case_name("exposureImageOnDrive");
1474 StartTest();
1475 }
1476
1477 } // namespace
1478 } // namespace file_manager
1479