1 // Copyright (c) 2012 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.
6 #include "base/bind_helpers.h"
7 #include "base/command_line.h"
8 #include "base/file_util.h"
9 #include "base/files/file_path.h"
10 #include "base/files/scoped_temp_dir.h"
11 #include "base/path_service.h"
12 #include "base/prefs/pref_member.h"
13 #include "base/prefs/pref_service.h"
14 #include "base/test/test_file_util.h"
15 #include "chrome/app/chrome_command_ids.h"
16 #include "chrome/browser/download/chrome_download_manager_delegate.h"
17 #include "chrome/browser/download/download_history.h"
18 #include "chrome/browser/download/download_prefs.h"
19 #include "chrome/browser/download/download_service.h"
20 #include "chrome/browser/download/download_service_factory.h"
21 #include "chrome/browser/download/save_package_file_picker.h"
22 #include "chrome/browser/history/download_row.h"
23 #include "chrome/browser/net/url_request_mock_util.h"
24 #include "chrome/browser/profiles/profile.h"
25 #include "chrome/browser/ui/browser.h"
26 #include "chrome/browser/ui/browser_commands.h"
27 #include "chrome/browser/ui/browser_window.h"
28 #include "chrome/browser/ui/tabs/tab_strip_model.h"
29 #include "chrome/common/chrome_paths.h"
30 #include "chrome/common/chrome_switches.h"
31 #include "chrome/common/pref_names.h"
32 #include "chrome/common/url_constants.h"
33 #include "chrome/test/base/in_process_browser_test.h"
34 #include "chrome/test/base/ui_test_utils.h"
35 #include "content/public/browser/download_item.h"
36 #include "content/public/browser/download_manager.h"
37 #include "content/public/browser/notification_service.h"
38 #include "content/public/browser/notification_types.h"
39 #include "content/public/browser/web_contents.h"
40 #include "content/public/test/test_utils.h"
41 #include "content/test/net/url_request_mock_http_job.h"
42 #include "testing/gtest/include/gtest/gtest.h"
44 using content::BrowserContext;
45 using content::BrowserThread;
46 using content::DownloadItem;
47 using content::DownloadManager;
48 using content::URLRequestMockHTTPJob;
49 using content::WebContents;
53 // Waits for an item record in the downloads database to match |filter|. See
54 // DownloadStoredProperly() below for an example filter.
55 class DownloadPersistedObserver : public DownloadHistory::Observer {
57 typedef base::Callback<bool(
59 const history::DownloadRow&)> PersistedFilter;
61 DownloadPersistedObserver(Profile* profile, const PersistedFilter& filter)
66 DownloadServiceFactory::GetForBrowserContext(profile_)->
67 GetDownloadHistory()->AddObserver(this);
70 virtual ~DownloadPersistedObserver() {
71 DownloadService* service = DownloadServiceFactory::GetForBrowserContext(
73 if (service && service->GetDownloadHistory())
74 service->GetDownloadHistory()->RemoveObserver(this);
77 bool WaitForPersisted() {
81 content::RunMessageLoop();
86 virtual void OnDownloadStored(DownloadItem* item,
87 const history::DownloadRow& info) OVERRIDE {
88 persisted_ = persisted_ || filter_.Run(item, info);
89 if (persisted_ && waiting_)
90 base::MessageLoopForUI::current()->Quit();
96 PersistedFilter filter_;
100 DISALLOW_COPY_AND_ASSIGN(DownloadPersistedObserver);
103 // Waits for an item record to be removed from the downloads database.
104 class DownloadRemovedObserver : public DownloadPersistedObserver {
106 DownloadRemovedObserver(Profile* profile, int32 download_id)
107 : DownloadPersistedObserver(profile, PersistedFilter()),
110 download_id_(download_id) {
112 virtual ~DownloadRemovedObserver() {}
114 bool WaitForRemoved() {
118 content::RunMessageLoop();
123 virtual void OnDownloadStored(DownloadItem* item,
124 const history::DownloadRow& info) OVERRIDE {
127 virtual void OnDownloadsRemoved(const DownloadHistory::IdSet& ids) OVERRIDE {
128 removed_ = ids.find(download_id_) != ids.end();
129 if (removed_ && waiting_)
130 base::MessageLoopForUI::current()->Quit();
138 DISALLOW_COPY_AND_ASSIGN(DownloadRemovedObserver);
141 bool DownloadStoredProperly(
142 const GURL& expected_url,
143 const base::FilePath& expected_path,
145 DownloadItem::DownloadState expected_state,
147 const history::DownloadRow& info) {
148 // This function may be called multiple times for a given test. Returning
149 // false doesn't necessarily mean that the test has failed or will fail, it
150 // might just mean that the test hasn't passed yet.
151 if (info.target_path != expected_path) {
152 VLOG(20) << __FUNCTION__ << " " << info.target_path.value()
153 << " != " << expected_path.value();
156 if (info.url_chain.size() != 1u) {
157 VLOG(20) << __FUNCTION__ << " " << info.url_chain.size()
161 if (info.url_chain[0] != expected_url) {
162 VLOG(20) << __FUNCTION__ << " " << info.url_chain[0].spec()
163 << " != " << expected_url.spec();
166 if ((num_files >= 0) && (info.received_bytes != num_files)) {
167 VLOG(20) << __FUNCTION__ << " " << num_files
168 << " != " << info.received_bytes;
171 if (info.state != expected_state) {
172 VLOG(20) << __FUNCTION__ << " " << info.state
173 << " != " << expected_state;
179 const base::FilePath::CharType kTestDir[] = FILE_PATH_LITERAL("save_page");
181 static const char kAppendedExtension[] =
188 // Loosely based on logic in DownloadTestObserver.
189 class DownloadItemCreatedObserver : public DownloadManager::Observer {
191 explicit DownloadItemCreatedObserver(DownloadManager* manager)
192 : waiting_(false), manager_(manager) {
193 manager->AddObserver(this);
196 virtual ~DownloadItemCreatedObserver() {
198 manager_->RemoveObserver(this);
201 // Wait for the first download item created after object creation.
202 // Note that this class provides no protection against the download
203 // being destroyed between creation and return of WaitForNewDownloadItem();
204 // the caller must guarantee that in some other fashion.
205 void WaitForDownloadItem(std::vector<DownloadItem*>* items_seen) {
207 // The manager went away before we were asked to wait; return
208 // what we have, even if it's null.
209 *items_seen = items_seen_;
213 if (items_seen_.empty()) {
215 content::RunMessageLoop();
219 *items_seen = items_seen_;
224 // DownloadManager::Observer
225 virtual void OnDownloadCreated(
226 DownloadManager* manager, DownloadItem* item) OVERRIDE {
227 DCHECK_EQ(manager, manager_);
228 items_seen_.push_back(item);
231 base::MessageLoopForUI::current()->Quit();
234 virtual void ManagerGoingDown(DownloadManager* manager) OVERRIDE {
235 manager_->RemoveObserver(this);
238 base::MessageLoopForUI::current()->Quit();
242 DownloadManager* manager_;
243 std::vector<DownloadItem*> items_seen_;
245 DISALLOW_COPY_AND_ASSIGN(DownloadItemCreatedObserver);
248 class SavePackageFinishedObserver : public content::DownloadManager::Observer {
250 SavePackageFinishedObserver(content::DownloadManager* manager,
251 const base::Closure& callback)
252 : download_manager_(manager),
253 callback_(callback) {
254 download_manager_->AddObserver(this);
257 virtual ~SavePackageFinishedObserver() {
258 if (download_manager_)
259 download_manager_->RemoveObserver(this);
262 // DownloadManager::Observer:
263 virtual void OnSavePackageSuccessfullyFinished(
264 content::DownloadManager* manager, content::DownloadItem* item) OVERRIDE {
267 virtual void ManagerGoingDown(content::DownloadManager* manager) OVERRIDE {
268 download_manager_->RemoveObserver(this);
269 download_manager_ = NULL;
273 content::DownloadManager* download_manager_;
274 base::Closure callback_;
276 DISALLOW_COPY_AND_ASSIGN(SavePackageFinishedObserver);
279 class SavePageBrowserTest : public InProcessBrowserTest {
281 SavePageBrowserTest() {}
282 virtual ~SavePageBrowserTest();
285 virtual void SetUp() OVERRIDE {
286 ASSERT_TRUE(PathService::Get(chrome::DIR_TEST_DATA, &test_dir_));
287 ASSERT_TRUE(save_dir_.CreateUniqueTempDir());
288 InProcessBrowserTest::SetUp();
291 virtual void SetUpOnMainThread() OVERRIDE {
292 browser()->profile()->GetPrefs()->SetFilePath(
293 prefs::kDownloadDefaultDirectory, save_dir_.path());
294 browser()->profile()->GetPrefs()->SetFilePath(
295 prefs::kSaveFileDefaultDirectory, save_dir_.path());
296 BrowserThread::PostTask(
297 BrowserThread::IO, FROM_HERE,
298 base::Bind(&chrome_browser_net::SetUrlRequestMocksEnabled, true));
301 GURL NavigateToMockURL(const std::string& prefix) {
302 GURL url = URLRequestMockHTTPJob::GetMockUrl(
303 base::FilePath(kTestDir).AppendASCII(prefix + ".htm"));
304 ui_test_utils::NavigateToURL(browser(), url);
308 // Returns full paths of destination file and directory.
309 void GetDestinationPaths(const std::string& prefix,
310 base::FilePath* full_file_name,
311 base::FilePath* dir) {
312 *full_file_name = save_dir_.path().AppendASCII(prefix + ".htm");
313 *dir = save_dir_.path().AppendASCII(prefix + "_files");
316 WebContents* GetCurrentTab(Browser* browser) const {
317 WebContents* current_tab =
318 browser->tab_strip_model()->GetActiveWebContents();
319 EXPECT_TRUE(current_tab);
323 // Returns true if and when there was a single download created, and its url
324 // is |expected_url|.
325 bool VerifySavePackageExpectations(
327 const GURL& expected_url) const {
328 // Generally, there should only be one download item created
329 // in all of these tests. If it's already here, grab it; if not,
330 // wait for it to show up.
331 std::vector<DownloadItem*> items;
332 DownloadManager* manager(
333 BrowserContext::GetDownloadManager(browser->profile()));
334 manager->GetAllDownloads(&items);
335 if (items.size() == 0u) {
336 DownloadItemCreatedObserver(manager).WaitForDownloadItem(&items);
339 EXPECT_EQ(1u, items.size());
340 if (1u != items.size())
342 DownloadItem* download_item(items[0]);
344 return (expected_url == download_item->GetOriginalUrl());
347 // Note on synchronization:
349 // For each Save Page As operation, we create a corresponding shell
350 // DownloadItem to display progress to the user. That DownloadItem goes
351 // through its own state transitions, including being persisted out to the
352 // history database, and the download shelf is not shown until after the
353 // persistence occurs. Save Package completion (and marking the DownloadItem
354 // as completed) occurs asynchronously from persistence. Thus if we want to
355 // examine either UI state or DB state, we need to wait until both the save
356 // package operation is complete and the relevant download item has been
359 DownloadManager* GetDownloadManager() const {
360 DownloadManager* download_manager =
361 BrowserContext::GetDownloadManager(browser()->profile());
362 EXPECT_TRUE(download_manager);
363 return download_manager;
366 // Path to directory containing test data.
367 base::FilePath test_dir_;
369 // Temporary directory we will save pages to.
370 base::ScopedTempDir save_dir_;
373 DISALLOW_COPY_AND_ASSIGN(SavePageBrowserTest);
376 SavePageBrowserTest::~SavePageBrowserTest() {
379 // Disabled on Windows due to flakiness. http://crbug.com/162323
380 // TODO(linux_aura) http://crbug.com/163931
381 #if defined(OS_WIN) || (defined(OS_LINUX) && !defined(OS_CHROMEOS) && defined(USE_AURA))
382 #define MAYBE_SaveHTMLOnly DISABLED_SaveHTMLOnly
384 #define MAYBE_SaveHTMLOnly SaveHTMLOnly
386 IN_PROC_BROWSER_TEST_F(SavePageBrowserTest, MAYBE_SaveHTMLOnly) {
387 GURL url = NavigateToMockURL("a");
389 base::FilePath full_file_name, dir;
390 GetDestinationPaths("a", &full_file_name, &dir);
391 DownloadPersistedObserver persisted(browser()->profile(), base::Bind(
392 &DownloadStoredProperly, url, full_file_name, 1,
393 DownloadItem::COMPLETE));
394 scoped_refptr<content::MessageLoopRunner> loop_runner(
395 new content::MessageLoopRunner);
396 SavePackageFinishedObserver observer(
397 content::BrowserContext::GetDownloadManager(browser()->profile()),
398 loop_runner->QuitClosure());
399 ASSERT_TRUE(GetCurrentTab(browser())->SavePage(full_file_name, dir,
400 content::SAVE_PAGE_TYPE_AS_ONLY_HTML));
402 ASSERT_TRUE(VerifySavePackageExpectations(browser(), url));
403 persisted.WaitForPersisted();
404 EXPECT_TRUE(browser()->window()->IsDownloadShelfVisible());
405 EXPECT_TRUE(base::PathExists(full_file_name));
406 EXPECT_FALSE(base::PathExists(dir));
407 EXPECT_TRUE(base::ContentsEqual(test_dir_.Append(base::FilePath(
408 kTestDir)).Append(FILE_PATH_LITERAL("a.htm")), full_file_name));
411 // http://crbug.com/162323
412 // http://crbug.com/163931
413 IN_PROC_BROWSER_TEST_F(SavePageBrowserTest, DISABLED_SaveHTMLOnlyCancel) {
414 GURL url = NavigateToMockURL("a");
415 DownloadManager* manager(GetDownloadManager());
416 std::vector<DownloadItem*> downloads;
417 manager->GetAllDownloads(&downloads);
418 ASSERT_EQ(0u, downloads.size());
420 base::FilePath full_file_name, dir;
421 GetDestinationPaths("a", &full_file_name, &dir);
422 DownloadItemCreatedObserver creation_observer(manager);
423 DownloadPersistedObserver persisted(browser()->profile(), base::Bind(
424 &DownloadStoredProperly, url, full_file_name, -1,
425 DownloadItem::CANCELLED));
426 // -1 to disable number of files check; we don't update after cancel, and
427 // we don't know when the single file completed in relationship to
430 ASSERT_TRUE(GetCurrentTab(browser())->SavePage(full_file_name, dir,
431 content::SAVE_PAGE_TYPE_AS_ONLY_HTML));
432 std::vector<DownloadItem*> items;
433 creation_observer.WaitForDownloadItem(&items);
434 ASSERT_EQ(1UL, items.size());
435 ASSERT_EQ(url.spec(), items[0]->GetOriginalUrl().spec());
436 items[0]->Cancel(true);
437 // TODO(rdsmith): Fix DII::Cancel() to actually cancel the save package.
438 // Currently it's ignored.
440 persisted.WaitForPersisted();
442 EXPECT_TRUE(browser()->window()->IsDownloadShelfVisible());
444 // TODO(benjhayden): Figure out how to safely wait for SavePackage's finished
445 // notification, then expect the contents of the downloaded file.
448 class DelayingDownloadManagerDelegate : public ChromeDownloadManagerDelegate {
450 explicit DelayingDownloadManagerDelegate(Profile* profile)
451 : ChromeDownloadManagerDelegate(profile) {
453 virtual bool ShouldCompleteDownload(
454 content::DownloadItem* item,
455 const base::Closure& user_complete_callback) OVERRIDE {
460 virtual ~DelayingDownloadManagerDelegate() {}
463 DISALLOW_COPY_AND_ASSIGN(DelayingDownloadManagerDelegate);
466 IN_PROC_BROWSER_TEST_F(SavePageBrowserTest, SaveHTMLOnlyTabDestroy) {
467 GURL url = NavigateToMockURL("a");
468 DownloadManager* manager(GetDownloadManager());
469 scoped_refptr<DelayingDownloadManagerDelegate> delaying_delegate(
470 new DelayingDownloadManagerDelegate(browser()->profile()));
471 delaying_delegate->SetNextId(content::DownloadItem::kInvalidId + 1);
472 manager->SetDelegate(delaying_delegate.get());
473 std::vector<DownloadItem*> downloads;
474 manager->GetAllDownloads(&downloads);
475 ASSERT_EQ(0u, downloads.size());
477 base::FilePath full_file_name, dir;
478 GetDestinationPaths("a", &full_file_name, &dir);
479 DownloadItemCreatedObserver creation_observer(manager);
480 ASSERT_TRUE(GetCurrentTab(browser())->SavePage(full_file_name, dir,
481 content::SAVE_PAGE_TYPE_AS_ONLY_HTML));
482 std::vector<DownloadItem*> items;
483 creation_observer.WaitForDownloadItem(&items);
484 ASSERT_TRUE(items.size() == 1);
486 // Close the tab; does this cancel the download?
487 GetCurrentTab(browser())->Close();
488 EXPECT_EQ(DownloadItem::CANCELLED, items[0]->GetState());
490 EXPECT_FALSE(base::PathExists(full_file_name));
491 EXPECT_FALSE(base::PathExists(dir));
493 manager->SetDelegate(NULL);
496 // Disabled on Windows due to flakiness. http://crbug.com/162323
497 // TODO(linux_aura) http://crbug.com/163931
498 #if defined(OS_WIN) || (defined(OS_LINUX) && !defined(OS_CHROMEOS) && defined(USE_AURA))
499 #define MAYBE_SaveViewSourceHTMLOnly DISABLED_SaveViewSourceHTMLOnly
501 #define MAYBE_SaveViewSourceHTMLOnly SaveViewSourceHTMLOnly
503 IN_PROC_BROWSER_TEST_F(SavePageBrowserTest, MAYBE_SaveViewSourceHTMLOnly) {
504 base::FilePath file_name(FILE_PATH_LITERAL("a.htm"));
505 GURL view_source_url = URLRequestMockHTTPJob::GetMockViewSourceUrl(
506 base::FilePath(kTestDir).Append(file_name));
507 GURL actual_page_url = URLRequestMockHTTPJob::GetMockUrl(
508 base::FilePath(kTestDir).Append(file_name));
509 ui_test_utils::NavigateToURL(browser(), view_source_url);
511 base::FilePath full_file_name, dir;
512 GetDestinationPaths("a", &full_file_name, &dir);
513 DownloadPersistedObserver persisted(browser()->profile(), base::Bind(
514 &DownloadStoredProperly, actual_page_url, full_file_name, 1,
515 DownloadItem::COMPLETE));
516 scoped_refptr<content::MessageLoopRunner> loop_runner(
517 new content::MessageLoopRunner);
518 SavePackageFinishedObserver observer(
519 content::BrowserContext::GetDownloadManager(browser()->profile()),
520 loop_runner->QuitClosure());
521 ASSERT_TRUE(GetCurrentTab(browser())->SavePage(full_file_name, dir,
522 content::SAVE_PAGE_TYPE_AS_ONLY_HTML));
524 ASSERT_TRUE(VerifySavePackageExpectations(browser(), actual_page_url));
525 persisted.WaitForPersisted();
527 EXPECT_TRUE(browser()->window()->IsDownloadShelfVisible());
529 EXPECT_TRUE(base::PathExists(full_file_name));
530 EXPECT_FALSE(base::PathExists(dir));
531 EXPECT_TRUE(base::ContentsEqual(
532 test_dir_.Append(base::FilePath(kTestDir)).Append(file_name),
536 // Disabled on Windows due to flakiness. http://crbug.com/162323
537 // TODO(linux_aura) http://crbug.com/163931
538 #if defined(OS_WIN) || (defined(OS_LINUX) && !defined(OS_CHROMEOS) && defined(USE_AURA))
539 #define MAYBE_SaveCompleteHTML DISABLED_SaveCompleteHTML
541 #define MAYBE_SaveCompleteHTML SaveCompleteHTML
543 IN_PROC_BROWSER_TEST_F(SavePageBrowserTest, MAYBE_SaveCompleteHTML) {
544 GURL url = NavigateToMockURL("b");
546 base::FilePath full_file_name, dir;
547 GetDestinationPaths("b", &full_file_name, &dir);
548 DownloadPersistedObserver persisted(browser()->profile(), base::Bind(
549 &DownloadStoredProperly, url, full_file_name, 3,
550 DownloadItem::COMPLETE));
551 scoped_refptr<content::MessageLoopRunner> loop_runner(
552 new content::MessageLoopRunner);
553 SavePackageFinishedObserver observer(
554 content::BrowserContext::GetDownloadManager(browser()->profile()),
555 loop_runner->QuitClosure());
556 ASSERT_TRUE(GetCurrentTab(browser())->SavePage(
557 full_file_name, dir, content::SAVE_PAGE_TYPE_AS_COMPLETE_HTML));
559 ASSERT_TRUE(VerifySavePackageExpectations(browser(), url));
560 persisted.WaitForPersisted();
562 EXPECT_TRUE(browser()->window()->IsDownloadShelfVisible());
564 EXPECT_TRUE(base::PathExists(full_file_name));
565 EXPECT_TRUE(base::PathExists(dir));
566 EXPECT_TRUE(base::TextContentsEqual(
567 test_dir_.Append(base::FilePath(kTestDir)).AppendASCII("b.saved1.htm"),
569 EXPECT_TRUE(base::ContentsEqual(
570 test_dir_.Append(base::FilePath(kTestDir)).AppendASCII("1.png"),
571 dir.AppendASCII("1.png")));
572 EXPECT_TRUE(base::ContentsEqual(
573 test_dir_.Append(base::FilePath(kTestDir)).AppendASCII("1.css"),
574 dir.AppendASCII("1.css")));
577 // Invoke a save page during the initial navigation.
578 // (Regression test for http://crbug.com/156538).
579 // Disabled on Windows due to flakiness. http://crbug.com/162323
580 // TODO(linux_aura) http://crbug.com/163931
581 #if defined(OS_WIN) || (defined(OS_LINUX) && !defined(OS_CHROMEOS) && defined(USE_AURA))
582 #define MAYBE_SaveDuringInitialNavigationIncognito DISABLED_SaveDuringInitialNavigationIncognito
584 #define MAYBE_SaveDuringInitialNavigationIncognito SaveDuringInitialNavigationIncognito
586 IN_PROC_BROWSER_TEST_F(SavePageBrowserTest,
587 MAYBE_SaveDuringInitialNavigationIncognito) {
588 // Open an Incognito window.
589 Browser* incognito = CreateIncognitoBrowser(); // Waits.
590 ASSERT_TRUE(incognito);
592 // Create a download item creation waiter on that window.
593 DownloadItemCreatedObserver creation_observer(
594 BrowserContext::GetDownloadManager(incognito->profile()));
596 // Navigate, unblocking with new tab.
597 GURL url = URLRequestMockHTTPJob::GetMockUrl(
598 base::FilePath(kTestDir).AppendASCII("b.htm"));
599 NavigateToURLWithDisposition(incognito, url, NEW_FOREGROUND_TAB,
600 ui_test_utils::BROWSER_TEST_WAIT_FOR_TAB);
602 // Save the page before completion.
603 base::FilePath full_file_name, dir;
604 GetDestinationPaths("b", &full_file_name, &dir);
605 scoped_refptr<content::MessageLoopRunner> loop_runner(
606 new content::MessageLoopRunner);
607 SavePackageFinishedObserver observer(
608 content::BrowserContext::GetDownloadManager(incognito->profile()),
609 loop_runner->QuitClosure());
610 ASSERT_TRUE(GetCurrentTab(incognito)->SavePage(
611 full_file_name, dir, content::SAVE_PAGE_TYPE_AS_COMPLETE_HTML));
614 ASSERT_TRUE(VerifySavePackageExpectations(incognito, url));
616 // Confirm download shelf is visible.
617 EXPECT_TRUE(incognito->window()->IsDownloadShelfVisible());
619 // We can't check more than this because SavePackage is racing with
620 // the page load. If the page load won the race, then SavePackage
621 // might have completed. If the page load lost the race, then
622 // SavePackage will cancel because there aren't any resources to
626 IN_PROC_BROWSER_TEST_F(SavePageBrowserTest, NoSave) {
627 ui_test_utils::NavigateToURL(browser(), GURL(content::kAboutBlankURL));
628 EXPECT_FALSE(chrome::CanSavePage(browser()));
631 // Disabled on Windows due to flakiness. http://crbug.com/162323
632 // TODO(linux_aura) http://crbug.com/163931
633 #if defined(OS_WIN) || (defined(OS_LINUX) && !defined(OS_CHROMEOS) && defined(USE_AURA))
634 #define MAYBE_FileNameFromPageTitle DISABLED_FileNameFromPageTitle
636 #define MAYBE_FileNameFromPageTitle FileNameFromPageTitle
638 IN_PROC_BROWSER_TEST_F(SavePageBrowserTest, MAYBE_FileNameFromPageTitle) {
639 GURL url = NavigateToMockURL("b");
641 base::FilePath full_file_name = save_dir_.path().AppendASCII(
642 std::string("Test page for saving page feature") + kAppendedExtension);
643 base::FilePath dir = save_dir_.path().AppendASCII(
644 "Test page for saving page feature_files");
645 DownloadPersistedObserver persisted(browser()->profile(), base::Bind(
646 &DownloadStoredProperly, url, full_file_name, 3,
647 DownloadItem::COMPLETE));
648 scoped_refptr<content::MessageLoopRunner> loop_runner(
649 new content::MessageLoopRunner);
650 SavePackageFinishedObserver observer(
651 content::BrowserContext::GetDownloadManager(browser()->profile()),
652 loop_runner->QuitClosure());
653 ASSERT_TRUE(GetCurrentTab(browser())->SavePage(
654 full_file_name, dir, content::SAVE_PAGE_TYPE_AS_COMPLETE_HTML));
657 ASSERT_TRUE(VerifySavePackageExpectations(browser(), url));
658 persisted.WaitForPersisted();
660 EXPECT_TRUE(browser()->window()->IsDownloadShelfVisible());
662 EXPECT_TRUE(base::PathExists(full_file_name));
663 EXPECT_TRUE(base::PathExists(dir));
664 EXPECT_TRUE(base::TextContentsEqual(
665 test_dir_.Append(base::FilePath(kTestDir)).AppendASCII("b.saved2.htm"),
667 EXPECT_TRUE(base::ContentsEqual(
668 test_dir_.Append(base::FilePath(kTestDir)).AppendASCII("1.png"),
669 dir.AppendASCII("1.png")));
670 EXPECT_TRUE(base::ContentsEqual(
671 test_dir_.Append(base::FilePath(kTestDir)).AppendASCII("1.css"),
672 dir.AppendASCII("1.css")));
675 // Disabled on Windows due to flakiness. http://crbug.com/162323
676 // TODO(linux_aura) http://crbug.com/163931
677 #if defined(OS_WIN) || (defined(OS_LINUX) && !defined(OS_CHROMEOS) && defined(USE_AURA))
678 #define MAYBE_RemoveFromList DISABLED_RemoveFromList
680 #define MAYBE_RemoveFromList RemoveFromList
682 IN_PROC_BROWSER_TEST_F(SavePageBrowserTest, MAYBE_RemoveFromList) {
683 GURL url = NavigateToMockURL("a");
685 base::FilePath full_file_name, dir;
686 GetDestinationPaths("a", &full_file_name, &dir);
687 DownloadPersistedObserver persisted(browser()->profile(), base::Bind(
688 &DownloadStoredProperly, url, full_file_name, 1,
689 DownloadItem::COMPLETE));
690 scoped_refptr<content::MessageLoopRunner> loop_runner(
691 new content::MessageLoopRunner);
692 SavePackageFinishedObserver observer(
693 content::BrowserContext::GetDownloadManager(browser()->profile()),
694 loop_runner->QuitClosure());
695 ASSERT_TRUE(GetCurrentTab(browser())->SavePage(full_file_name, dir,
696 content::SAVE_PAGE_TYPE_AS_ONLY_HTML));
699 ASSERT_TRUE(VerifySavePackageExpectations(browser(), url));
700 persisted.WaitForPersisted();
702 EXPECT_TRUE(browser()->window()->IsDownloadShelfVisible());
704 DownloadManager* manager(GetDownloadManager());
705 std::vector<DownloadItem*> downloads;
706 manager->GetAllDownloads(&downloads);
707 ASSERT_EQ(1UL, downloads.size());
708 DownloadRemovedObserver removed(browser()->profile(), downloads[0]->GetId());
710 EXPECT_EQ(manager->RemoveAllDownloads(), 1);
712 removed.WaitForRemoved();
714 EXPECT_TRUE(base::PathExists(full_file_name));
715 EXPECT_FALSE(base::PathExists(dir));
716 EXPECT_TRUE(base::ContentsEqual(test_dir_.Append(base::FilePath(
717 kTestDir)).Append(FILE_PATH_LITERAL("a.htm")), full_file_name));
720 // This tests that a webpage with the title "test.exe" is saved as
722 // We probably don't care to handle this on Linux or Mac.
724 IN_PROC_BROWSER_TEST_F(SavePageBrowserTest, CleanFilenameFromPageTitle) {
725 const base::FilePath file_name(FILE_PATH_LITERAL("c.htm"));
726 base::FilePath download_dir =
727 DownloadPrefs::FromDownloadManager(GetDownloadManager())->
729 base::FilePath full_file_name =
730 download_dir.AppendASCII(std::string("test.exe") + kAppendedExtension);
731 base::FilePath dir = download_dir.AppendASCII("test.exe_files");
733 EXPECT_FALSE(base::PathExists(full_file_name));
734 GURL url = URLRequestMockHTTPJob::GetMockUrl(
735 base::FilePath(kTestDir).Append(file_name));
736 ui_test_utils::NavigateToURL(browser(), url);
738 SavePackageFilePicker::SetShouldPromptUser(false);
739 scoped_refptr<content::MessageLoopRunner> loop_runner(
740 new content::MessageLoopRunner);
741 SavePackageFinishedObserver observer(
742 content::BrowserContext::GetDownloadManager(browser()->profile()),
743 loop_runner->QuitClosure());
744 chrome::SavePage(browser());
747 EXPECT_TRUE(base::PathExists(full_file_name));
749 EXPECT_TRUE(file_util::DieFileDie(full_file_name, false));
750 EXPECT_TRUE(file_util::DieFileDie(dir, true));
754 class SavePageAsMHTMLBrowserTest : public SavePageBrowserTest {
756 SavePageAsMHTMLBrowserTest() {}
757 virtual ~SavePageAsMHTMLBrowserTest();
758 virtual void SetUpCommandLine(CommandLine* command_line) OVERRIDE {
759 command_line->AppendSwitch(switches::kSavePageAsMHTML);
763 DISALLOW_COPY_AND_ASSIGN(SavePageAsMHTMLBrowserTest);
766 SavePageAsMHTMLBrowserTest::~SavePageAsMHTMLBrowserTest() {
769 IN_PROC_BROWSER_TEST_F(SavePageAsMHTMLBrowserTest, SavePageAsMHTML) {
770 static const int64 kFileSizeMin = 2758;
771 GURL url = NavigateToMockURL("b");
772 base::FilePath download_dir = DownloadPrefs::FromDownloadManager(
773 GetDownloadManager())->DownloadPath();
774 base::FilePath full_file_name = download_dir.AppendASCII(std::string(
775 "Test page for saving page feature.mhtml"));
776 SavePackageFilePicker::SetShouldPromptUser(false);
777 DownloadPersistedObserver persisted(browser()->profile(), base::Bind(
778 &DownloadStoredProperly, url, full_file_name, -1,
779 DownloadItem::COMPLETE));
780 scoped_refptr<content::MessageLoopRunner> loop_runner(
781 new content::MessageLoopRunner);
782 SavePackageFinishedObserver observer(
783 content::BrowserContext::GetDownloadManager(browser()->profile()),
784 loop_runner->QuitClosure());
785 chrome::SavePage(browser());
787 ASSERT_TRUE(VerifySavePackageExpectations(browser(), url));
788 persisted.WaitForPersisted();
790 ASSERT_TRUE(base::PathExists(full_file_name));
791 int64 actual_file_size = -1;
792 EXPECT_TRUE(file_util::GetFileSize(full_file_name, &actual_file_size));
793 EXPECT_LE(kFileSizeMin, actual_file_size);
796 IN_PROC_BROWSER_TEST_F(SavePageBrowserTest, SavePageBrowserTest_NonMHTML) {
797 SavePackageFilePicker::SetShouldPromptUser(false);
798 GURL url("data:text/plain,foo");
799 ui_test_utils::NavigateToURL(browser(), url);
800 scoped_refptr<content::MessageLoopRunner> loop_runner(
801 new content::MessageLoopRunner);
802 SavePackageFinishedObserver observer(
803 content::BrowserContext::GetDownloadManager(browser()->profile()),
804 loop_runner->QuitClosure());
805 chrome::SavePage(browser());
807 base::FilePath download_dir = DownloadPrefs::FromDownloadManager(
808 GetDownloadManager())->DownloadPath();
809 base::FilePath filename = download_dir.AppendASCII("dataurl.txt");
810 ASSERT_TRUE(base::PathExists(filename));
811 std::string contents;
812 EXPECT_TRUE(base::ReadFileToString(filename, &contents));
813 EXPECT_EQ("foo", contents);