Chromium Code Reviews| Index: chrome/browser/download/chrome_download_manager_delegate.cc |
| diff --git a/chrome/browser/download/chrome_download_manager_delegate.cc b/chrome/browser/download/chrome_download_manager_delegate.cc |
| index 9a7f18ee80c9b598105018017b320f4f160acfd5..cbb14e9a3d13a455a90cc6bd944b819a355de663 100644 |
| --- a/chrome/browser/download/chrome_download_manager_delegate.cc |
| +++ b/chrome/browser/download/chrome_download_manager_delegate.cc |
| @@ -135,7 +135,9 @@ DownloadId ChromeDownloadManagerDelegate::GetNextId() { |
| GetDelegate()->GetNextId(); |
| } |
| -bool ChromeDownloadManagerDelegate::ShouldStartDownload(int32 download_id) { |
| +bool ChromeDownloadManagerDelegate::DetermineDownloadTarget( |
| + DownloadItem* download, |
| + const content::DownloadTargetCallback& callback) { |
| // We create a download item and store it in our download map, and inform the |
| // history system of a new download. Since this method can be called while the |
| // history service thread is still reading the persistent state, we do not |
| @@ -143,11 +145,6 @@ bool ChromeDownloadManagerDelegate::ShouldStartDownload(int32 download_id) { |
| // observers at this point. OnCreateDownloadEntryComplete() handles that |
| // finalization of the the download creation as a callback from the history |
| // thread. |
|
Randy Smith (Not in Mondays)
2012/07/10 18:33:09
This comment seems very strange; can you clean it
asanka
2012/07/11 20:03:32
Removed.
|
| - DownloadItem* download = |
| - download_manager_->GetActiveDownloadItem(download_id); |
| - if (!download) |
| - return false; |
| - |
| #if defined(ENABLE_SAFE_BROWSING) |
| DownloadProtectionService* service = GetDownloadProtectionService(); |
| if (service) { |
| @@ -158,15 +155,20 @@ bool ChromeDownloadManagerDelegate::ShouldStartDownload(int32 download_id) { |
| base::Bind( |
| &ChromeDownloadManagerDelegate::CheckDownloadUrlDone, |
| this, |
| - download->GetId())); |
| - return false; |
| + download->GetId(), |
| + callback)); |
| + return true; |
| } |
| #endif |
| - CheckDownloadUrlDone(download_id, DownloadProtectionService::SAFE); |
| - return false; |
| + CheckDownloadUrlDone(download->GetId(), callback, |
| + DownloadProtectionService::SAFE); |
| + return true; |
| } |
| -void ChromeDownloadManagerDelegate::ChooseDownloadPath(DownloadItem* item) { |
| +void ChromeDownloadManagerDelegate::ChooseDownloadPath( |
| + DownloadItem* item, |
| + const FilePath& suggested_path, |
| + const base::Callback<void(const FilePath&)>& file_selected_callback) { |
| // Deletes itself. |
| DownloadFilePicker* file_picker = |
| #if defined(OS_CHROMEOS) |
| @@ -174,20 +176,22 @@ void ChromeDownloadManagerDelegate::ChooseDownloadPath(DownloadItem* item) { |
| #else |
| new DownloadFilePicker(); |
| #endif |
| - file_picker->Init(download_manager_, item); |
| + file_picker->Init(download_manager_, item, suggested_path, |
| + file_selected_callback); |
| } |
| FilePath ChromeDownloadManagerDelegate::GetIntermediatePath( |
| - const DownloadItem& download) { |
| + const FilePath& target_path, |
| + content::DownloadDangerType danger_type) { |
| // If the download is not dangerous, just append .crdownload to the target |
| // path. |
| - if (download.GetDangerType() == content::DOWNLOAD_DANGER_TYPE_NOT_DANGEROUS) |
| - return download_util::GetCrDownloadPath(download.GetTargetFilePath()); |
| + if (danger_type == content::DOWNLOAD_DANGER_TYPE_NOT_DANGEROUS) |
| + return download_util::GetCrDownloadPath(target_path); |
| // If the download is potentially dangerous we create a filename of the form |
| // 'Unconfirmed <random>.crdownload'. |
| FilePath::StringType file_name; |
| - FilePath dir = download.GetTargetFilePath().DirName(); |
| + FilePath dir = target_path.DirName(); |
| #if defined(OS_WIN) |
| string16 unconfirmed_prefix = |
| l10n_util::GetStringUTF16(IDS_DOWNLOAD_UNCONFIRMED_PREFIX); |
| @@ -532,7 +536,7 @@ void ChromeDownloadManagerDelegate::GetReservedPath( |
| const FilePath& target_path, |
| const FilePath& default_download_path, |
| bool should_uniquify_path, |
| - const DownloadPathReservationTracker::ReservedPathCallback callback) { |
| + const DownloadPathReservationTracker::ReservedPathCallback& callback) { |
| DownloadPathReservationTracker::GetReservedPath( |
| download, target_path, default_download_path, should_uniquify_path, |
| callback); |
| @@ -540,6 +544,7 @@ void ChromeDownloadManagerDelegate::GetReservedPath( |
| void ChromeDownloadManagerDelegate::CheckDownloadUrlDone( |
| int32 download_id, |
| + const content::DownloadTargetCallback& callback, |
| DownloadProtectionService::DownloadCheckResult result) { |
| DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); |
| DownloadItem* download = |
| @@ -556,7 +561,7 @@ void ChromeDownloadManagerDelegate::CheckDownloadUrlDone( |
| download_history_->CheckVisitedReferrerBefore( |
| download_id, download->GetReferrerUrl(), |
| base::Bind(&ChromeDownloadManagerDelegate::CheckVisitedReferrerBeforeDone, |
| - base::Unretained(this), download_id, danger_type)); |
| + base::Unretained(this), download_id, callback, danger_type)); |
| } |
| void ChromeDownloadManagerDelegate::CheckClientDownloadDone( |
| @@ -614,6 +619,7 @@ void ChromeDownloadManagerDelegate::Observe( |
| void ChromeDownloadManagerDelegate::CheckVisitedReferrerBeforeDone( |
| int32 download_id, |
| + const content::DownloadTargetCallback& callback, |
| content::DownloadDangerType danger_type, |
| bool visited_referrer_before) { |
| DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); |
| @@ -655,8 +661,8 @@ void ChromeDownloadManagerDelegate::CheckVisitedReferrerBeforeDone( |
| // 1) using the default download directory. |
| // 2) prompting the user. |
| FilePath target_directory; |
| - if (should_prompt && !download_manager_->LastDownloadPath().empty()) |
| - target_directory = download_manager_->LastDownloadPath(); |
| + if (should_prompt && !last_download_path_.empty()) |
| + target_directory = last_download_path_; |
| else |
| target_directory = download_prefs_->download_path(); |
| suggested_path = target_directory.Append(generated_name); |
| @@ -699,19 +705,23 @@ void ChromeDownloadManagerDelegate::CheckVisitedReferrerBeforeDone( |
| profile_, suggested_path, download, |
| base::Bind( |
| &ChromeDownloadManagerDelegate::SubstituteGDataDownloadPathCallback, |
| - this, download->GetId(), should_prompt, is_forced_path, danger_type)); |
| + this, download->GetId(), callback, should_prompt, is_forced_path, |
| + danger_type)); |
| #else |
| GetReservedPath( |
| *download, suggested_path, download_prefs_->download_path(), |
| !is_forced_path, |
| base::Bind(&ChromeDownloadManagerDelegate::OnPathReservationAvailable, |
| - this, download->GetId(), should_prompt, danger_type)); |
| + this, download->GetId(), callback, should_prompt, |
| + danger_type)); |
| #endif |
| } |
| #if defined (OS_CHROMEOS) |
| +// TODO(asanka): Merge this logic with the logic in DownloadFilePickerChromeOS. |
| void ChromeDownloadManagerDelegate::SubstituteGDataDownloadPathCallback( |
| int32 download_id, |
| + const content::DownloadTargetCallback& callback, |
| bool should_prompt, |
| bool is_forced_path, |
| content::DownloadDangerType danger_type, |
| @@ -726,30 +736,70 @@ void ChromeDownloadManagerDelegate::SubstituteGDataDownloadPathCallback( |
| *download, suggested_path, download_prefs_->download_path(), |
| !is_forced_path, |
| base::Bind(&ChromeDownloadManagerDelegate::OnPathReservationAvailable, |
| - this, download->GetId(), should_prompt, danger_type)); |
| + this, download->GetId(), callback, should_prompt, |
| + danger_type)); |
| } |
| #endif |
| void ChromeDownloadManagerDelegate::OnPathReservationAvailable( |
| int32 download_id, |
| + const content::DownloadTargetCallback& callback, |
| bool should_prompt, |
| content::DownloadDangerType danger_type, |
| - const FilePath& target_path, |
| - bool target_path_verified) { |
| + const FilePath& reserved_path, |
| + bool reserved_path_verified) { |
| DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); |
| DownloadItem* download = |
| download_manager_->GetActiveDownloadItem(download_id); |
| if (!download) |
| return; |
| - DownloadItem::TargetDisposition disposition; |
| - // If the target path could not be verified then the path was non-existant, |
| - // non writeable or could not be uniquified. Prompt the user. |
| - if (should_prompt || !target_path_verified) |
| - disposition = DownloadItem::TARGET_DISPOSITION_PROMPT; |
| - else |
| - disposition = DownloadItem::TARGET_DISPOSITION_OVERWRITE; |
| - download->OnTargetPathDetermined(target_path, disposition, danger_type); |
| - download_manager_->RestartDownload(download_id); |
| + if (should_prompt || !reserved_path_verified) { |
| + // If the target path could not be verified then the path was non-existant, |
| + // non writeable or could not be uniquified. Prompt the user. |
| + ChooseDownloadPath( |
| + download, reserved_path, |
| + base::Bind(&ChromeDownloadManagerDelegate::OnTargetPathDetermined, |
| + this, download_id, callback, |
| + DownloadItem::TARGET_DISPOSITION_PROMPT, danger_type)); |
| + } else { |
| + OnTargetPathDetermined(download_id, callback, |
| + DownloadItem::TARGET_DISPOSITION_OVERWRITE, |
| + danger_type, reserved_path); |
| + } |
| +} |
| + |
| +void ChromeDownloadManagerDelegate::OnTargetPathDetermined( |
| + int32 download_id, |
| + const content::DownloadTargetCallback& callback, |
| + DownloadItem::TargetDisposition disposition, |
| + content::DownloadDangerType danger_type, |
| + const FilePath& target_path) { |
| + DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); |
| + DownloadItem* download = |
| + download_manager_->GetActiveDownloadItem(download_id); |
| + if (!download) |
| + return; |
| + |
| + // If |target_path| is empty, then that means that the user wants to cancel |
| + // the download. |
| + if (target_path.empty()) { |
| + DCHECK_EQ(DownloadItem::TARGET_DISPOSITION_PROMPT, disposition); |
| + download->Cancel(true); |
| + return; |
| + } |
| + |
| + // Retain the last directory. Exclude temporary downloads since the path |
| + // likely points at the location of a temporary file. |
| + // TODO(asanka): This logic is a hack. DownloadFilePicker should give us a |
| + // directory to persist. Or perhaps, if the GData path |
| + // substitution logic is moved here, then we would have a |
| + // persistable path after the DownloadFilePicker is done. |
| + if (disposition == DownloadItem::TARGET_DISPOSITION_PROMPT && |
| + !download->IsTemporary()) |
| + last_download_path_ = target_path.DirName(); |
| + |
| + FilePath intermediate_path = GetIntermediatePath(target_path, danger_type); |
| + callback.Run(target_path, disposition, danger_type, intermediate_path); |
| } |
| void ChromeDownloadManagerDelegate::OnItemAddedToPersistentStore( |
| @@ -763,3 +813,7 @@ void ChromeDownloadManagerDelegate::OnItemAddedToPersistentStore( |
| db_handle = download_history_->GetNextFakeDbHandle(); |
| download_manager_->OnItemAddedToPersistentStore(download_id, db_handle); |
| } |
| + |
| +void ChromeDownloadManagerDelegate::ClearTransientState() { |
| + last_download_path_.clear(); |
| +} |