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

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

Issue 10263019: DownloadManagerDelegate::ShouldCompleteDownload(callback) (Closed) Base URL: http://git.chromium.org/git/chromium.git@trunk
Patch Set: cleanup Created 8 years, 7 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"
11 #include "base/callback.h" 11 #include "base/callback.h"
12 #include "base/file_util.h" 12 #include "base/file_util.h"
13 #include "base/path_service.h" 13 #include "base/path_service.h"
14 #include "base/rand_util.h" 14 #include "base/rand_util.h"
15 #include "base/stringprintf.h" 15 #include "base/stringprintf.h"
16 #include "base/time.h" 16 #include "base/time.h"
17 #include "base/utf_string_conversions.h" 17 #include "base/utf_string_conversions.h"
18 #include "chrome/browser/browser_process.h" 18 #include "chrome/browser/browser_process.h"
19 #include "chrome/browser/download/download_completion_blocker.h"
19 #include "chrome/browser/download/download_crx_util.h" 20 #include "chrome/browser/download/download_crx_util.h"
20 #include "chrome/browser/download/download_extensions.h" 21 #include "chrome/browser/download/download_extensions.h"
21 #include "chrome/browser/download/download_file_picker.h" 22 #include "chrome/browser/download/download_file_picker.h"
22 #include "chrome/browser/download/download_history.h" 23 #include "chrome/browser/download/download_history.h"
23 #include "chrome/browser/download/download_prefs.h" 24 #include "chrome/browser/download/download_prefs.h"
24 #include "chrome/browser/download/download_status_updater.h" 25 #include "chrome/browser/download/download_status_updater.h"
25 #include "chrome/browser/download/download_util.h" 26 #include "chrome/browser/download/download_util.h"
26 #include "chrome/browser/download/save_package_file_picker.h" 27 #include "chrome/browser/download/save_package_file_picker.h"
27 #include "chrome/browser/extensions/crx_installer.h" 28 #include "chrome/browser/extensions/crx_installer.h"
28 #include "chrome/browser/extensions/extension_service.h" 29 #include "chrome/browser/extensions/extension_service.h"
(...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after
62 using content::WebContents; 63 using content::WebContents;
63 using safe_browsing::DownloadProtectionService; 64 using safe_browsing::DownloadProtectionService;
64 65
65 namespace { 66 namespace {
66 67
67 // String pointer used for identifying safebrowing data associated with 68 // String pointer used for identifying safebrowing data associated with
68 // a download item. 69 // a download item.
69 static const char safe_browsing_id[] = "Safe Browsing ID"; 70 static const char safe_browsing_id[] = "Safe Browsing ID";
70 71
71 // The state of a safebrowsing check. 72 // The state of a safebrowsing check.
72 struct SafeBrowsingState : public DownloadItem::ExternalData { 73 class SafeBrowsingState : public DownloadCompletionBlocker {
73 // If true the SafeBrowsing check is not done yet. 74 public:
74 bool pending; 75 SafeBrowsingState()
75 // The verdict that we got from calling CheckClientDownload. 76 : verdict_(DownloadProtectionService::SAFE) {
76 safe_browsing::DownloadProtectionService::DownloadCheckResult verdict; 77 }
78
79 virtual ~SafeBrowsingState();
80
81 // The verdict that we got from calling CheckClientDownload. Only valid to
82 // call if |is_complete()|.
83 DownloadProtectionService::DownloadCheckResult verdict() const {
84 return verdict_;
85 }
86
87 void SetVerdict(DownloadProtectionService::DownloadCheckResult result) {
88 verdict_ = result;
89 CompleteDownload();
90 }
91
92 private:
93 DownloadProtectionService::DownloadCheckResult verdict_;
94
95 DISALLOW_COPY_AND_ASSIGN(SafeBrowsingState);
77 }; 96 };
78 97
98 SafeBrowsingState::~SafeBrowsingState() {}
99
79 } // namespace 100 } // namespace
80 101
81 ChromeDownloadManagerDelegate::ChromeDownloadManagerDelegate(Profile* profile) 102 ChromeDownloadManagerDelegate::ChromeDownloadManagerDelegate(Profile* profile)
82 : profile_(profile), 103 : profile_(profile),
83 next_download_id_(0), 104 next_download_id_(0),
84 download_prefs_(new DownloadPrefs(profile->GetPrefs())) { 105 download_prefs_(new DownloadPrefs(profile->GetPrefs())) {
85 } 106 }
86 107
87 ChromeDownloadManagerDelegate::~ChromeDownloadManagerDelegate() { 108 ChromeDownloadManagerDelegate::~ChromeDownloadManagerDelegate() {
88 } 109 }
(...skipping 106 matching lines...) Expand 10 before | Expand all | Expand 10 after
195 DCHECK(extension[0] == FilePath::kExtensionSeparator); 216 DCHECK(extension[0] == FilePath::kExtensionSeparator);
196 extension.erase(0, 1); 217 extension.erase(0, 1);
197 return download_prefs_->IsAutoOpenEnabledForExtension(extension); 218 return download_prefs_->IsAutoOpenEnabledForExtension(extension);
198 } 219 }
199 220
200 // static 221 // static
201 void ChromeDownloadManagerDelegate::DisableSafeBrowsing(DownloadItem* item) { 222 void ChromeDownloadManagerDelegate::DisableSafeBrowsing(DownloadItem* item) {
202 #if defined(ENABLE_SAFE_BROWSING) 223 #if defined(ENABLE_SAFE_BROWSING)
203 SafeBrowsingState* state = static_cast<SafeBrowsingState*>( 224 SafeBrowsingState* state = static_cast<SafeBrowsingState*>(
204 item->GetExternalData(&safe_browsing_id)); 225 item->GetExternalData(&safe_browsing_id));
205 DCHECK(state == NULL); 226 DCHECK(!state);
206 if (state == NULL) { 227 if (!state)
207 state = new SafeBrowsingState(); 228 state = new SafeBrowsingState();
208 item->SetExternalData(&safe_browsing_id, state); 229 state->SetVerdict(DownloadProtectionService::SAFE);
209 } 230 item->SetExternalData(&safe_browsing_id, state);
210 state->pending = false;
211 state->verdict = DownloadProtectionService::SAFE;
212 #endif 231 #endif
213 } 232 }
214 233
215 bool ChromeDownloadManagerDelegate::ShouldCompleteDownload(DownloadItem* item) { 234 bool ChromeDownloadManagerDelegate::IsDownloadReadyForCompletion(
235 DownloadItem* item,
236 const base::Closure& internal_complete_callback) {
216 #if defined(ENABLE_SAFE_BROWSING) 237 #if defined(ENABLE_SAFE_BROWSING)
217 // See if there is already a pending SafeBrowsing check for that download.
218 SafeBrowsingState* state = static_cast<SafeBrowsingState*>( 238 SafeBrowsingState* state = static_cast<SafeBrowsingState*>(
219 item->GetExternalData(&safe_browsing_id)); 239 item->GetExternalData(&safe_browsing_id));
220 // Don't complete the download until we have an answer. 240 if (!state) {
221 if (state && state->pending)
222 return false;
223
224 if (state == NULL) {
225 // Begin the safe browsing download protection check. 241 // Begin the safe browsing download protection check.
226 DownloadProtectionService* service = GetDownloadProtectionService(); 242 DownloadProtectionService* service = GetDownloadProtectionService();
227 if (service) { 243 if (service) {
228 VLOG(2) << __FUNCTION__ << "() Start SB download check for download = " 244 VLOG(2) << __FUNCTION__ << "() Start SB download check for download = "
229 << item->DebugString(false); 245 << item->DebugString(false);
230 state = new SafeBrowsingState(); 246 state = new SafeBrowsingState();
231 state->pending = true; 247 state->set_callback(internal_complete_callback);
232 state->verdict = DownloadProtectionService::SAFE;
233 item->SetExternalData(&safe_browsing_id, state); 248 item->SetExternalData(&safe_browsing_id, state);
234 service->CheckClientDownload( 249 service->CheckClientDownload(
235 DownloadProtectionService::DownloadInfo::FromDownloadItem(*item), 250 DownloadProtectionService::DownloadInfo::FromDownloadItem(*item),
236 base::Bind( 251 base::Bind(
237 &ChromeDownloadManagerDelegate::CheckClientDownloadDone, 252 &ChromeDownloadManagerDelegate::CheckClientDownloadDone,
238 this, 253 this,
239 item->GetId())); 254 item->GetId()));
240 return false; 255 return false;
241 } 256 }
257 } else if (!state->is_complete()) {
258 // Don't complete the download until we have an answer.
259 state->set_callback(internal_complete_callback);
260 return false;
242 } 261 }
243 #endif 262 #endif
244 263
245 #if defined(OS_CHROMEOS) 264 #if defined(OS_CHROMEOS)
246 // If there's a GData upload associated with this download, we wait until that 265 // If there's a GData upload associated with this download, we wait until that
247 // is complete before allowing the download item to complete. 266 // is complete before allowing the download item to complete.
248 if (!gdata::GDataDownloadObserver::IsReadyToComplete(item)) 267 if (!gdata::GDataDownloadObserver::IsReadyToComplete(
268 item, internal_complete_callback))
249 return false; 269 return false;
250 #endif 270 #endif
251 return true; 271 return true;
252 } 272 }
253 273
274 void ChromeDownloadManagerDelegate::ShouldCompleteDownloadInternal(
275 DownloadItem* item,
276 const base::Closure& user_complete_callback) {
277 if (IsDownloadReadyForCompletion(item, base::Bind(
278 &ChromeDownloadManagerDelegate::ShouldCompleteDownloadInternal, this,
279 item, user_complete_callback)))
asanka 2012/05/16 19:26:32 Is the DownloadItem* guaranteed to outlive the cal
benjhayden 2012/05/16 19:42:30 Good catch! How're those weak pointers coming? :-)
280 user_complete_callback.Run();
281 }
282
283 // ShouldCompleteDownloadInternal() will never be called directly by a user, it
284 // will only be called asynchronously, so it should run
285 // |user_complete_callback|. ShouldCompleteDownload() will only be called
286 // directly by a user, so it does not need to run |user_complete_callback|
287 // because it can return true synchronously.
Randy Smith (Not in Mondays) 2012/05/16 19:04:53 nit: Shouldn't this comment be in front of ShouldC
benjhayden 2012/05/16 19:42:30 Done.
288
289 bool ChromeDownloadManagerDelegate::ShouldCompleteDownload(
290 DownloadItem* item,
291 const base::Closure& user_complete_callback) {
292 return IsDownloadReadyForCompletion(item, base::Bind(
293 &ChromeDownloadManagerDelegate::ShouldCompleteDownloadInternal, this,
294 item, user_complete_callback));
295 }
296
254 bool ChromeDownloadManagerDelegate::ShouldOpenDownload(DownloadItem* item) { 297 bool ChromeDownloadManagerDelegate::ShouldOpenDownload(DownloadItem* item) {
255 if (IsExtensionDownload(item)) { 298 if (IsExtensionDownload(item)) {
256 scoped_refptr<CrxInstaller> crx_installer = 299 scoped_refptr<CrxInstaller> crx_installer =
257 download_crx_util::OpenChromeExtension(profile_, *item); 300 download_crx_util::OpenChromeExtension(profile_, *item);
258 301
259 // CRX_INSTALLER_DONE will fire when the install completes. Observe() 302 // CRX_INSTALLER_DONE will fire when the install completes. Observe()
260 // will call DelayedDownloadOpened() on this item. If this DownloadItem is 303 // will call DelayedDownloadOpened() on this item. If this DownloadItem is
261 // not around when CRX_INSTALLER_DONE fires, Complete() will not be called. 304 // not around when CRX_INSTALLER_DONE fires, Complete() will not be called.
262 registrar_.Add(this, 305 registrar_.Add(this,
263 chrome::NOTIFICATION_CRX_INSTALLER_DONE, 306 chrome::NOTIFICATION_CRX_INSTALLER_DONE,
(...skipping 195 matching lines...) Expand 10 before | Expand all | Expand 10 after
459 item->SetDangerType(content::DOWNLOAD_DANGER_TYPE_DANGEROUS_CONTENT); 502 item->SetDangerType(content::DOWNLOAD_DANGER_TYPE_DANGEROUS_CONTENT);
460 break; 503 break;
461 case DownloadProtectionService::UNCOMMON: 504 case DownloadProtectionService::UNCOMMON:
462 item->SetDangerType(content::DOWNLOAD_DANGER_TYPE_UNCOMMON_CONTENT); 505 item->SetDangerType(content::DOWNLOAD_DANGER_TYPE_UNCOMMON_CONTENT);
463 break; 506 break;
464 } 507 }
465 } 508 }
466 509
467 SafeBrowsingState* state = static_cast<SafeBrowsingState*>( 510 SafeBrowsingState* state = static_cast<SafeBrowsingState*>(
468 item->GetExternalData(&safe_browsing_id)); 511 item->GetExternalData(&safe_browsing_id));
469 DCHECK(state); 512 state->SetVerdict(result);
470 if (state) {
471 state->pending = false;
472 state->verdict = result;
473 }
474 item->MaybeCompleteDownload();
475 } 513 }
476 514
477 // content::NotificationObserver implementation. 515 // content::NotificationObserver implementation.
478 void ChromeDownloadManagerDelegate::Observe( 516 void ChromeDownloadManagerDelegate::Observe(
479 int type, 517 int type,
480 const content::NotificationSource& source, 518 const content::NotificationSource& source,
481 const content::NotificationDetails& details) { 519 const content::NotificationDetails& details) {
482 DCHECK(type == chrome::NOTIFICATION_CRX_INSTALLER_DONE); 520 DCHECK(type == chrome::NOTIFICATION_CRX_INSTALLER_DONE);
483 521
484 registrar_.Remove(this, 522 registrar_.Remove(this,
(...skipping 234 matching lines...) Expand 10 before | Expand all | Expand 10 after
719 int32 download_id, int64 db_handle) { 757 int32 download_id, int64 db_handle) {
720 // It's not immediately obvious, but HistoryBackend::CreateDownload() can 758 // It's not immediately obvious, but HistoryBackend::CreateDownload() can
721 // call this function with an invalid |db_handle|. For instance, this can 759 // call this function with an invalid |db_handle|. For instance, this can
722 // happen when the history database is offline. We cannot have multiple 760 // happen when the history database is offline. We cannot have multiple
723 // DownloadItems with the same invalid db_handle, so we need to assign a 761 // DownloadItems with the same invalid db_handle, so we need to assign a
724 // unique |db_handle| here. 762 // unique |db_handle| here.
725 if (db_handle == DownloadItem::kUninitializedHandle) 763 if (db_handle == DownloadItem::kUninitializedHandle)
726 db_handle = download_history_->GetNextFakeDbHandle(); 764 db_handle = download_history_->GetNextFakeDbHandle();
727 download_manager_->OnItemAddedToPersistentStore(download_id, db_handle); 765 download_manager_->OnItemAddedToPersistentStore(download_id, db_handle);
728 } 766 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698