Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(338)

Side by Side Diff: chrome/browser/download/chrome_download_manager_delegate.cc

Issue 10704052: Download filename determination refactor (3/3) (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Created 8 years, 5 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 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 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "chrome/browser/download/chrome_download_manager_delegate.h" 5 #include "chrome/browser/download/chrome_download_manager_delegate.h"
6 6
7 #include <string> 7 #include <string>
8 8
9 #include "base/bind.h" 9 #include "base/bind.h"
10 #include "base/bind_helpers.h" 10 #include "base/bind_helpers.h"
(...skipping 117 matching lines...) Expand 10 before | Expand all | Expand 10 after
128 } 128 }
129 129
130 DownloadId ChromeDownloadManagerDelegate::GetNextId() { 130 DownloadId ChromeDownloadManagerDelegate::GetNextId() {
131 if (!profile_->IsOffTheRecord()) 131 if (!profile_->IsOffTheRecord())
132 return DownloadId(this, next_download_id_++); 132 return DownloadId(this, next_download_id_++);
133 133
134 return BrowserContext::GetDownloadManager(profile_->GetOriginalProfile())-> 134 return BrowserContext::GetDownloadManager(profile_->GetOriginalProfile())->
135 GetDelegate()->GetNextId(); 135 GetDelegate()->GetNextId();
136 } 136 }
137 137
138 bool ChromeDownloadManagerDelegate::ShouldStartDownload(int32 download_id) { 138 bool ChromeDownloadManagerDelegate::DetermineDownloadTarget(
139 DownloadItem* download) {
139 // We create a download item and store it in our download map, and inform the 140 // We create a download item and store it in our download map, and inform the
140 // history system of a new download. Since this method can be called while the 141 // history system of a new download. Since this method can be called while the
141 // history service thread is still reading the persistent state, we do not 142 // history service thread is still reading the persistent state, we do not
142 // insert the new DownloadItem into 'history_downloads_' or inform our 143 // insert the new DownloadItem into 'history_downloads_' or inform our
143 // observers at this point. OnCreateDownloadEntryComplete() handles that 144 // observers at this point. OnCreateDownloadEntryComplete() handles that
144 // finalization of the the download creation as a callback from the history 145 // finalization of the the download creation as a callback from the history
145 // thread. 146 // thread.
146 DownloadItem* download =
147 download_manager_->GetActiveDownloadItem(download_id);
148 if (!download)
149 return false;
150
151 #if defined(ENABLE_SAFE_BROWSING) 147 #if defined(ENABLE_SAFE_BROWSING)
152 DownloadProtectionService* service = GetDownloadProtectionService(); 148 DownloadProtectionService* service = GetDownloadProtectionService();
153 if (service) { 149 if (service) {
154 VLOG(2) << __FUNCTION__ << "() Start SB URL check for download = " 150 VLOG(2) << __FUNCTION__ << "() Start SB URL check for download = "
155 << download->DebugString(false); 151 << download->DebugString(false);
156 service->CheckDownloadUrl( 152 service->CheckDownloadUrl(
157 DownloadProtectionService::DownloadInfo::FromDownloadItem(*download), 153 DownloadProtectionService::DownloadInfo::FromDownloadItem(*download),
158 base::Bind( 154 base::Bind(
159 &ChromeDownloadManagerDelegate::CheckDownloadUrlDone, 155 &ChromeDownloadManagerDelegate::CheckDownloadUrlDone,
160 this, 156 this,
161 download->GetId())); 157 download->GetId()));
162 return false; 158 return true;
163 } 159 }
164 #endif 160 #endif
165 CheckDownloadUrlDone(download_id, DownloadProtectionService::SAFE); 161 CheckDownloadUrlDone(download->GetId(), DownloadProtectionService::SAFE);
166 return false; 162 return true;
167 } 163 }
168 164
169 void ChromeDownloadManagerDelegate::ChooseDownloadPath(DownloadItem* item) { 165 void ChromeDownloadManagerDelegate::ChooseDownloadPath(
166 DownloadItem* item,
167 const FilePath& suggested_path,
168 const base::Callback<void(const FilePath&)>& file_selected_callback) {
170 // Deletes itself. 169 // Deletes itself.
171 DownloadFilePicker* file_picker = 170 DownloadFilePicker* file_picker =
172 #if defined(OS_CHROMEOS) 171 #if defined(OS_CHROMEOS)
173 new DownloadFilePickerChromeOS(); 172 new DownloadFilePickerChromeOS();
174 #else 173 #else
175 new DownloadFilePicker(); 174 new DownloadFilePicker();
176 #endif 175 #endif
177 file_picker->Init(download_manager_, item); 176 file_picker->Init(download_manager_, item, suggested_path,
177 file_selected_callback);
178 } 178 }
179 179
180 FilePath ChromeDownloadManagerDelegate::GetIntermediatePath( 180 FilePath ChromeDownloadManagerDelegate::GetIntermediatePath(
181 const DownloadItem& download) { 181 const FilePath& target_path,
182 content::DownloadDangerType danger_type) {
182 // If the download is not dangerous, just append .crdownload to the target 183 // If the download is not dangerous, just append .crdownload to the target
183 // path. 184 // path.
184 if (download.GetDangerType() == content::DOWNLOAD_DANGER_TYPE_NOT_DANGEROUS) 185 if (danger_type == content::DOWNLOAD_DANGER_TYPE_NOT_DANGEROUS)
185 return download_util::GetCrDownloadPath(download.GetTargetFilePath()); 186 return download_util::GetCrDownloadPath(target_path);
186 187
187 // If the download is potentially dangerous we create a filename of the form 188 // If the download is potentially dangerous we create a filename of the form
188 // 'Unconfirmed <random>.crdownload'. 189 // 'Unconfirmed <random>.crdownload'.
189 FilePath::StringType file_name; 190 FilePath::StringType file_name;
190 FilePath dir = download.GetTargetFilePath().DirName(); 191 FilePath dir = target_path.DirName();
191 #if defined(OS_WIN) 192 #if defined(OS_WIN)
192 string16 unconfirmed_prefix = 193 string16 unconfirmed_prefix =
193 l10n_util::GetStringUTF16(IDS_DOWNLOAD_UNCONFIRMED_PREFIX); 194 l10n_util::GetStringUTF16(IDS_DOWNLOAD_UNCONFIRMED_PREFIX);
194 #else 195 #else
195 std::string unconfirmed_prefix = 196 std::string unconfirmed_prefix =
196 l10n_util::GetStringUTF8(IDS_DOWNLOAD_UNCONFIRMED_PREFIX); 197 l10n_util::GetStringUTF8(IDS_DOWNLOAD_UNCONFIRMED_PREFIX);
197 #endif 198 #endif
198 base::SStringPrintf( 199 base::SStringPrintf(
199 &file_name, 200 &file_name,
200 unconfirmed_prefix.append( 201 unconfirmed_prefix.append(
(...skipping 447 matching lines...) Expand 10 before | Expand all | Expand 10 after
648 !ShouldOpenFileBasedOnExtension(generated_name)) 649 !ShouldOpenFileBasedOnExtension(generated_name))
649 should_prompt = true; 650 should_prompt = true;
650 } 651 }
651 if (download_prefs_->IsDownloadPathManaged()) 652 if (download_prefs_->IsDownloadPathManaged())
652 should_prompt = false; 653 should_prompt = false;
653 654
654 // Determine the proper path for a download, by either one of the following: 655 // Determine the proper path for a download, by either one of the following:
655 // 1) using the default download directory. 656 // 1) using the default download directory.
656 // 2) prompting the user. 657 // 2) prompting the user.
657 FilePath target_directory; 658 FilePath target_directory;
658 if (should_prompt && !download_manager_->LastDownloadPath().empty()) 659 if (should_prompt && !last_download_path_.empty())
659 target_directory = download_manager_->LastDownloadPath(); 660 target_directory = last_download_path_;
660 else 661 else
661 target_directory = download_prefs_->download_path(); 662 target_directory = download_prefs_->download_path();
662 suggested_path = target_directory.Append(generated_name); 663 suggested_path = target_directory.Append(generated_name);
663 } else { 664 } else {
664 DCHECK(!should_prompt); 665 DCHECK(!should_prompt);
665 suggested_path = download->GetForcedFilePath(); 666 suggested_path = download->GetForcedFilePath();
666 } 667 }
667 668
668 // If the download hasn't already been marked dangerous (could be 669 // If the download hasn't already been marked dangerous (could be
669 // DANGEROUS_URL), check if it is a dangerous file. 670 // DANGEROUS_URL), check if it is a dangerous file.
(...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after
703 #else 704 #else
704 GetReservedPath( 705 GetReservedPath(
705 *download, suggested_path, download_prefs_->download_path(), 706 *download, suggested_path, download_prefs_->download_path(),
706 !is_forced_path, 707 !is_forced_path,
707 base::Bind(&ChromeDownloadManagerDelegate::OnPathReservationAvailable, 708 base::Bind(&ChromeDownloadManagerDelegate::OnPathReservationAvailable,
708 this, download->GetId(), should_prompt, danger_type)); 709 this, download->GetId(), should_prompt, danger_type));
709 #endif 710 #endif
710 } 711 }
711 712
712 #if defined (OS_CHROMEOS) 713 #if defined (OS_CHROMEOS)
714 // TODO(asanka): Merge this logic with the logic in DownloadFilePickerChromeOS.
713 void ChromeDownloadManagerDelegate::SubstituteGDataDownloadPathCallback( 715 void ChromeDownloadManagerDelegate::SubstituteGDataDownloadPathCallback(
714 int32 download_id, 716 int32 download_id,
715 bool should_prompt, 717 bool should_prompt,
716 bool is_forced_path, 718 bool is_forced_path,
717 content::DownloadDangerType danger_type, 719 content::DownloadDangerType danger_type,
718 const FilePath& suggested_path) { 720 const FilePath& suggested_path) {
719 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); 721 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
720 DownloadItem* download = 722 DownloadItem* download =
721 download_manager_->GetActiveDownloadItem(download_id); 723 download_manager_->GetActiveDownloadItem(download_id);
722 if (!download) 724 if (!download)
723 return; 725 return;
724 726
725 GetReservedPath( 727 GetReservedPath(
726 *download, suggested_path, download_prefs_->download_path(), 728 *download, suggested_path, download_prefs_->download_path(),
727 !is_forced_path, 729 !is_forced_path,
728 base::Bind(&ChromeDownloadManagerDelegate::OnPathReservationAvailable, 730 base::Bind(&ChromeDownloadManagerDelegate::OnPathReservationAvailable,
729 this, download->GetId(), should_prompt, danger_type)); 731 this, download->GetId(), should_prompt, danger_type));
730 } 732 }
731 #endif 733 #endif
732 734
733 void ChromeDownloadManagerDelegate::OnPathReservationAvailable( 735 void ChromeDownloadManagerDelegate::OnPathReservationAvailable(
734 int32 download_id, 736 int32 download_id,
735 bool should_prompt, 737 bool should_prompt,
736 content::DownloadDangerType danger_type, 738 content::DownloadDangerType danger_type,
737 const FilePath& target_path, 739 const FilePath& reserved_path,
738 bool target_path_verified) { 740 bool reserved_path_verified) {
739 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); 741 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
740 DownloadItem* download = 742 DownloadItem* download =
741 download_manager_->GetActiveDownloadItem(download_id); 743 download_manager_->GetActiveDownloadItem(download_id);
742 if (!download) 744 if (!download)
743 return; 745 return;
744 DownloadItem::TargetDisposition disposition; 746 if (should_prompt || !reserved_path_verified) {
745 // If the target path could not be verified then the path was non-existant, 747 // If the target path could not be verified then the path was non-existant,
746 // non writeable or could not be uniquified. Prompt the user. 748 // non writeable or could not be uniquified. Prompt the user.
747 if (should_prompt || !target_path_verified) 749 ChooseDownloadPath(
748 disposition = DownloadItem::TARGET_DISPOSITION_PROMPT; 750 download, reserved_path,
749 else 751 base::Bind(&ChromeDownloadManagerDelegate::OnTargetPathAvailable,
750 disposition = DownloadItem::TARGET_DISPOSITION_OVERWRITE; 752 this, download_id, DownloadItem::TARGET_DISPOSITION_PROMPT,
751 download->OnTargetPathDetermined(target_path, disposition, danger_type); 753 danger_type));
752 download_manager_->RestartDownload(download_id); 754 } else {
755 OnTargetPathAvailable(download_id,
756 DownloadItem::TARGET_DISPOSITION_OVERWRITE,
757 danger_type, reserved_path);
758 }
759 }
760
761 void ChromeDownloadManagerDelegate::OnTargetPathAvailable(
762 int32 download_id,
763 DownloadItem::TargetDisposition disposition,
764 content::DownloadDangerType danger_type,
765 const FilePath& target_path) {
766 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
767 DownloadItem* download =
768 download_manager_->GetActiveDownloadItem(download_id);
769 if (!download)
770 return;
771
772 // If |target_path| is empty, then that means that the user wants to cancel
773 // the download.
774 if (target_path.empty()) {
775 DCHECK_EQ(DownloadItem::TARGET_DISPOSITION_PROMPT, disposition);
776 download->Cancel(true);
777 return;
778 }
779
780 // Retain the last directory. Exclude temporary downloads since the path
781 // likely points at the location of a temporary file.
782 if (disposition == DownloadItem::TARGET_DISPOSITION_PROMPT &&
783 !download->IsTemporary())
784 last_download_path_ = target_path.DirName();
785
786 FilePath intermediate_path = GetIntermediatePath(target_path, danger_type);
787 download->OnDownloadTargetDetermined(target_path, disposition, danger_type,
788 intermediate_path);
753 } 789 }
754 790
755 void ChromeDownloadManagerDelegate::OnItemAddedToPersistentStore( 791 void ChromeDownloadManagerDelegate::OnItemAddedToPersistentStore(
756 int32 download_id, int64 db_handle) { 792 int32 download_id, int64 db_handle) {
757 // It's not immediately obvious, but HistoryBackend::CreateDownload() can 793 // It's not immediately obvious, but HistoryBackend::CreateDownload() can
758 // call this function with an invalid |db_handle|. For instance, this can 794 // call this function with an invalid |db_handle|. For instance, this can
759 // happen when the history database is offline. We cannot have multiple 795 // happen when the history database is offline. We cannot have multiple
760 // DownloadItems with the same invalid db_handle, so we need to assign a 796 // DownloadItems with the same invalid db_handle, so we need to assign a
761 // unique |db_handle| here. 797 // unique |db_handle| here.
762 if (db_handle == DownloadItem::kUninitializedHandle) 798 if (db_handle == DownloadItem::kUninitializedHandle)
763 db_handle = download_history_->GetNextFakeDbHandle(); 799 db_handle = download_history_->GetNextFakeDbHandle();
764 download_manager_->OnItemAddedToPersistentStore(download_id, db_handle); 800 download_manager_->OnItemAddedToPersistentStore(download_id, db_handle);
765 } 801 }
802
803 void ChromeDownloadManagerDelegate::ClearTransientState() {
804 last_download_path_.clear();
805 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698