15821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Copyright (c) 2012 The Chromium Authors. All rights reserved. 25821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be 35821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// found in the LICENSE file. 45821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 55821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/download/download_service.h" 65821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 75821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/callback.h" 85821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/browser_process.h" 95821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/download/chrome_download_manager_delegate.h" 102a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "chrome/browser/download/download_history.h" 115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/download/download_service_factory.h" 125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/download/download_status_updater.h" 132a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "chrome/browser/download/download_ui_controller.h" 142a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "chrome/browser/history/history_service.h" 152a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "chrome/browser/history/history_service_factory.h" 165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/net/chrome_net_log.h" 175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/profiles/profile.h" 185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/profiles/profile_manager.h" 195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "content/public/browser/download_manager.h" 205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2146d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)#if defined(ENABLE_EXTENSIONS) 2246d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)#include "chrome/browser/extensions/api/downloads/downloads_api.h" 2346d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)#endif 2446d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles) 255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using content::BrowserContext; 265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using content::DownloadManager; 275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using content::DownloadManagerDelegate; 285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)DownloadService::DownloadService(Profile* profile) 305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) : download_manager_created_(false), 315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) profile_(profile) { 325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)DownloadService::~DownloadService() {} 355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)ChromeDownloadManagerDelegate* DownloadService::GetDownloadManagerDelegate() { 375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DownloadManager* manager = BrowserContext::GetDownloadManager(profile_); 385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // If we've already created the delegate, just return it. 395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (download_manager_created_) { 405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DCHECK(static_cast<DownloadManagerDelegate*>(manager_delegate_.get()) == 415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) manager->GetDelegate()); 425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return manager_delegate_.get(); 435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) download_manager_created_ = true; 455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // In case the delegate has already been set by 475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // SetDownloadManagerDelegateForTesting. 48868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) if (!manager_delegate_.get()) 495d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) manager_delegate_.reset(new ChromeDownloadManagerDelegate(profile_)); 505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) manager_delegate_->SetDownloadManager(manager); 525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 5346d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)#if defined(ENABLE_EXTENSIONS) 545c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu extension_event_router_.reset( 555c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu new extensions::ExtensionDownloadsEventRouter(profile_, manager)); 562a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#endif 572a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 582a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) if (!profile_->IsOffTheRecord()) { 597dbb3d5cf0c15f500944d211057644d6a2f37371Ben Murdoch HistoryService* history = HistoryServiceFactory::GetForProfile( 602a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) profile_, Profile::EXPLICIT_ACCESS); 615d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) history->GetNextDownloadId( 625d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) manager_delegate_->GetDownloadIdReceiverCallback()); 637dbb3d5cf0c15f500944d211057644d6a2f37371Ben Murdoch download_history_.reset(new DownloadHistory( 647dbb3d5cf0c15f500944d211057644d6a2f37371Ben Murdoch manager, 657dbb3d5cf0c15f500944d211057644d6a2f37371Ben Murdoch scoped_ptr<DownloadHistory::HistoryAdapter>( 667dbb3d5cf0c15f500944d211057644d6a2f37371Ben Murdoch new DownloadHistory::HistoryAdapter(history)))); 672a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) } 682a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 692a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Pass an empty delegate when constructing the DownloadUIController. The 702a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // default delegate does all the notifications we need. 71cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) download_ui_.reset(new DownloadUIController( 72cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) manager, scoped_ptr<DownloadUIController::Delegate>())); 732a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Include this download manager in the set monitored by the 755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // global status updater. 765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) g_browser_process->download_status_updater()->AddManager(manager); 775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return manager_delegate_.get(); 795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 812a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)DownloadHistory* DownloadService::GetDownloadHistory() { 822a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) if (!download_manager_created_) { 832a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) GetDownloadManagerDelegate(); 842a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) } 852a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) DCHECK(download_manager_created_); 862a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) return download_history_.get(); 872a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)} 882a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool DownloadService::HasCreatedDownloadManager() { 905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return download_manager_created_; 915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 938bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)int DownloadService::NonMaliciousDownloadCount() const { 945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (!download_manager_created_) 955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return 0; 968bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles) return BrowserContext::GetDownloadManager(profile_)-> 978bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles) NonMaliciousInProgressCount(); 985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 100a02191e04bc25c4935f804f2c080ae28663d096dBen Murdochvoid DownloadService::CancelDownloads() { 101a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch if (!download_manager_created_) 102a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch return; 103a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch 104a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch DownloadManager* download_manager = 105a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch BrowserContext::GetDownloadManager(profile_); 106a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch DownloadManager::DownloadVector downloads; 107a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch download_manager->GetAllDownloads(&downloads); 108a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch for (DownloadManager::DownloadVector::iterator it = downloads.begin(); 109a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch it != downloads.end(); 110a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch ++it) { 111a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch if ((*it)->GetState() == content::DownloadItem::IN_PROGRESS) 112a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch (*it)->Cancel(false); 113a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch } 114a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch} 115a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch 1165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// static 1178bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)int DownloadService::NonMaliciousDownloadCountAllProfiles() { 1185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) std::vector<Profile*> profiles( 1195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) g_browser_process->profile_manager()->GetLoadedProfiles()); 1205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int count = 0; 1225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) for (std::vector<Profile*>::iterator it = profiles.begin(); 1235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) it < profiles.end(); ++it) { 1248bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles) count += DownloadServiceFactory::GetForBrowserContext(*it)-> 1258bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles) NonMaliciousDownloadCount(); 1265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if ((*it)->HasOffTheRecordProfile()) 127a36e5920737c6adbddd3e43b760e5de8431db6e0Torne (Richard Coles) count += DownloadServiceFactory::GetForBrowserContext( 1288bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles) (*it)->GetOffTheRecordProfile())->NonMaliciousDownloadCount(); 1295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return count; 1325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 1335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 134f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)// static 135f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)void DownloadService::CancelAllDownloads() { 136f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) std::vector<Profile*> profiles( 137f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) g_browser_process->profile_manager()->GetLoadedProfiles()); 138f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) for (std::vector<Profile*>::iterator it = profiles.begin(); 139f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) it < profiles.end(); 140f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) ++it) { 141a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch DownloadService* service = 142a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch DownloadServiceFactory::GetForBrowserContext(*it); 143a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch service->CancelDownloads(); 144f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) } 145f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)} 146f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) 1475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void DownloadService::SetDownloadManagerDelegateForTesting( 1485d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) scoped_ptr<ChromeDownloadManagerDelegate> new_delegate) { 1495d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) manager_delegate_.swap(new_delegate); 1505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DownloadManager* dm = BrowserContext::GetDownloadManager(profile_); 1515d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) dm->SetDelegate(manager_delegate_.get()); 1525d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) manager_delegate_->SetDownloadManager(dm); 1535d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) if (new_delegate) 1545d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) new_delegate->Shutdown(); 1555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 1565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 157a36e5920737c6adbddd3e43b760e5de8431db6e0Torne (Richard Coles)bool DownloadService::IsShelfEnabled() { 158a36e5920737c6adbddd3e43b760e5de8431db6e0Torne (Richard Coles)#if defined(OS_ANDROID) 159a36e5920737c6adbddd3e43b760e5de8431db6e0Torne (Richard Coles) return true; 160a36e5920737c6adbddd3e43b760e5de8431db6e0Torne (Richard Coles)#else 161a36e5920737c6adbddd3e43b760e5de8431db6e0Torne (Richard Coles) return !extension_event_router_ || 162a36e5920737c6adbddd3e43b760e5de8431db6e0Torne (Richard Coles) extension_event_router_->IsShelfEnabled(); 163a36e5920737c6adbddd3e43b760e5de8431db6e0Torne (Richard Coles)#endif 164a36e5920737c6adbddd3e43b760e5de8431db6e0Torne (Richard Coles)} 165a36e5920737c6adbddd3e43b760e5de8431db6e0Torne (Richard Coles) 1665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void DownloadService::Shutdown() { 1675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (download_manager_created_) { 1685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Normally the DownloadManager would be shutdown later, after the Profile 1695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // goes away and BrowserContext's destructor runs. But that would be too 1705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // late for us since we need to use the profile (indirectly through history 1715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // code) when the DownloadManager is shutting down. So we shut it down 1725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // manually earlier. See http://crbug.com/131692 1735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) BrowserContext::GetDownloadManager(profile_)->Shutdown(); 1745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 17546d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)#if defined(ENABLE_EXTENSIONS) 1762a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) extension_event_router_.reset(); 1772a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#endif 1785d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) manager_delegate_.reset(); 1792a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) download_history_.reset(); 1805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 181