save_page_handler.cc 2.3 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071
  1. // Copyright (c) 2015 GitHub, Inc.
  2. // Use of this source code is governed by the MIT license that can be
  3. // found in the LICENSE file.
  4. #include "atom/browser/api/save_page_handler.h"
  5. #include <string>
  6. #include <utility>
  7. #include "atom/browser/atom_browser_context.h"
  8. #include "base/callback.h"
  9. #include "base/files/file_path.h"
  10. #include "content/public/browser/web_contents.h"
  11. namespace atom {
  12. namespace api {
  13. SavePageHandler::SavePageHandler(content::WebContents* web_contents,
  14. util::Promise promise)
  15. : web_contents_(web_contents), promise_(std::move(promise)) {}
  16. SavePageHandler::~SavePageHandler() {}
  17. void SavePageHandler::OnDownloadCreated(content::DownloadManager* manager,
  18. download::DownloadItem* item) {
  19. // OnDownloadCreated is invoked during WebContents::SavePage, so the |item|
  20. // here is the one stated by WebContents::SavePage.
  21. item->AddObserver(this);
  22. }
  23. bool SavePageHandler::Handle(const base::FilePath& full_path,
  24. const content::SavePageType& save_type) {
  25. auto* download_manager = content::BrowserContext::GetDownloadManager(
  26. web_contents_->GetBrowserContext());
  27. download_manager->AddObserver(this);
  28. // Chromium will create a 'foo_files' directory under the directory of saving
  29. // page 'foo.html' for holding other resource files of 'foo.html'.
  30. base::FilePath saved_main_directory_path = full_path.DirName().Append(
  31. full_path.RemoveExtension().BaseName().value() +
  32. FILE_PATH_LITERAL("_files"));
  33. bool result =
  34. web_contents_->SavePage(full_path, saved_main_directory_path, save_type);
  35. download_manager->RemoveObserver(this);
  36. // If initialization fails which means fail to create |DownloadItem|, we need
  37. // to delete the |SavePageHandler| instance to avoid memory-leak.
  38. if (!result) {
  39. promise_.RejectWithErrorMessage("Failed to save the page");
  40. delete this;
  41. }
  42. return result;
  43. }
  44. void SavePageHandler::OnDownloadUpdated(download::DownloadItem* item) {
  45. if (item->IsDone()) {
  46. if (item->GetState() == download::DownloadItem::COMPLETE)
  47. promise_.Resolve();
  48. else
  49. promise_.RejectWithErrorMessage("Failed to save the page.");
  50. Destroy(item);
  51. }
  52. }
  53. void SavePageHandler::Destroy(download::DownloadItem* item) {
  54. item->RemoveObserver(this);
  55. delete this;
  56. }
  57. } // namespace api
  58. } // namespace atom