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

Side by Side Diff: chrome/browser/chromeos/drive/download_handler.cc

Issue 1414753005: Evict drive cache with file download from website if necessary. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Fix nits. Created 5 years, 1 month 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
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/chromeos/drive/download_handler.h" 5 #include "chrome/browser/chromeos/drive/download_handler.h"
6 6
7 #include "base/bind.h" 7 #include "base/bind.h"
8 #include "base/files/file_util.h" 8 #include "base/files/file_util.h"
9 #include "base/strings/string_util.h" 9 #include "base/strings/string_util.h"
10 #include "base/supports_user_data.h" 10 #include "base/supports_user_data.h"
11 #include "base/thread_task_runner_handle.h"
11 #include "base/threading/sequenced_worker_pool.h" 12 #include "base/threading/sequenced_worker_pool.h"
12 #include "chrome/browser/chromeos/drive/drive_integration_service.h" 13 #include "chrome/browser/chromeos/drive/drive_integration_service.h"
13 #include "chrome/browser/chromeos/drive/file_system_util.h" 14 #include "chrome/browser/chromeos/drive/file_system_util.h"
14 #include "chrome/browser/chromeos/drive/write_on_cache_file.h" 15 #include "chrome/browser/chromeos/drive/write_on_cache_file.h"
15 #include "chrome/browser/download/download_history.h" 16 #include "chrome/browser/download/download_history.h"
16 #include "chrome/browser/download/download_service.h" 17 #include "chrome/browser/download/download_service.h"
17 #include "chrome/browser/download/download_service_factory.h" 18 #include "chrome/browser/download/download_service_factory.h"
18 #include "components/drive/drive.pb.h" 19 #include "components/drive/drive.pb.h"
19 #include "components/drive/file_system_interface.h" 20 #include "components/drive/file_system_interface.h"
20 #include "content/public/browser/browser_thread.h" 21 #include "content/public/browser/browser_thread.h"
21 22
22 using content::BrowserThread; 23 using content::BrowserThread;
23 using content::DownloadManager; 24 using content::DownloadManager;
24 using content::DownloadItem; 25 using content::DownloadItem;
25 26
26 namespace drive { 27 namespace drive {
27 namespace { 28 namespace {
28 29
29 // Key for base::SupportsUserData::Data. 30 // Key for base::SupportsUserData::Data.
30 const char kDrivePathKey[] = "DrivePath"; 31 const char kDrivePathKey[] = "DrivePath";
31 32
32 // Mime types that we better not trust. If the file was downloade with these 33 // Mime types that we better not trust. If the file was downloade with these
33 // mime types, while uploading to Drive we ignore it at guess by our own logic. 34 // mime types, while uploading to Drive we ignore it at guess by our own logic.
34 const char* kGenericMimeTypes[] = {"text/html", "text/plain", 35 const char* kGenericMimeTypes[] = {"text/html", "text/plain",
35 "application/octet-stream"}; 36 "application/octet-stream"};
36 37
38 // Longer is better. But at the same time, this value should be short enough as
39 // drive::internal::kMinFreeSpaceInBytes is not used up by file download in this
40 // interval.
41 const base::TimeDelta kFreeDiskSpaceDelay = base::TimeDelta::FromSeconds(3);
42
37 // User Data stored in DownloadItem for drive path. 43 // User Data stored in DownloadItem for drive path.
38 class DriveUserData : public base::SupportsUserData::Data { 44 class DriveUserData : public base::SupportsUserData::Data {
39 public: 45 public:
40 explicit DriveUserData(const base::FilePath& path) : file_path_(path), 46 explicit DriveUserData(const base::FilePath& path) : file_path_(path),
41 is_complete_(false) {} 47 is_complete_(false) {}
42 ~DriveUserData() override {} 48 ~DriveUserData() override {}
43 49
44 const base::FilePath& file_path() const { return file_path_; } 50 const base::FilePath& file_path() const { return file_path_; }
45 const base::FilePath& cache_file_path() const { return cache_file_path_; } 51 const base::FilePath& cache_file_path() const { return cache_file_path_; }
46 void set_cache_file_path(const base::FilePath& path) { 52 void set_cache_file_path(const base::FilePath& path) {
(...skipping 71 matching lines...) Expand 10 before | Expand all | Expand 10 after
118 // 'default' fallback choice on the HTTP server. In such a case, we ignore the 124 // 'default' fallback choice on the HTTP server. In such a case, we ignore the
119 // type so that our logic can guess by its own while uploading to Drive. 125 // type so that our logic can guess by its own while uploading to Drive.
120 std::string FilterOutGenericMimeType(const std::string& mime_type) { 126 std::string FilterOutGenericMimeType(const std::string& mime_type) {
121 for (size_t i = 0; i < arraysize(kGenericMimeTypes); ++i) { 127 for (size_t i = 0; i < arraysize(kGenericMimeTypes); ++i) {
122 if (base::LowerCaseEqualsASCII(mime_type, kGenericMimeTypes[i])) 128 if (base::LowerCaseEqualsASCII(mime_type, kGenericMimeTypes[i]))
123 return std::string(); 129 return std::string();
124 } 130 }
125 return mime_type; 131 return mime_type;
126 } 132 }
127 133
134 void IgnoreFreeDiskSpaceIfNeededForCallback(bool /*result*/) {}
135
128 } // namespace 136 } // namespace
129 137
130 DownloadHandler::DownloadHandler(FileSystemInterface* file_system) 138 DownloadHandler::DownloadHandler(FileSystemInterface* file_system)
131 : file_system_(file_system), 139 : file_system_(file_system),
132 weak_ptr_factory_(this) { 140 has_pending_free_disk_space_(false),
133 } 141 free_disk_space_delay_(kFreeDiskSpaceDelay),
142 weak_ptr_factory_(this) {}
134 143
135 DownloadHandler::~DownloadHandler() { 144 DownloadHandler::~DownloadHandler() {
136 } 145 }
137 146
138 // static 147 // static
139 DownloadHandler* DownloadHandler::GetForProfile(Profile* profile) { 148 DownloadHandler* DownloadHandler::GetForProfile(Profile* profile) {
140 DriveIntegrationService* service = 149 DriveIntegrationService* service =
141 DriveIntegrationServiceFactory::FindForProfile(profile); 150 DriveIntegrationServiceFactory::FindForProfile(profile);
142 if (!service || !service->IsMounted()) 151 if (!service || !service->IsMounted())
143 return NULL; 152 return NULL;
(...skipping 86 matching lines...) Expand 10 before | Expand all | Expand 10 after
230 239
231 void DownloadHandler::CheckForFileExistence( 240 void DownloadHandler::CheckForFileExistence(
232 const DownloadItem* download, 241 const DownloadItem* download,
233 const content::CheckForFileExistenceCallback& callback) { 242 const content::CheckForFileExistenceCallback& callback) {
234 file_system_->GetResourceEntry( 243 file_system_->GetResourceEntry(
235 util::ExtractDrivePath(GetTargetPath(download)), 244 util::ExtractDrivePath(GetTargetPath(download)),
236 base::Bind(&ContinueCheckingForFileExistence, 245 base::Bind(&ContinueCheckingForFileExistence,
237 callback)); 246 callback));
238 } 247 }
239 248
249 void DownloadHandler::SetFreeDiskSpaceDelayForTesting(
250 const base::TimeDelta& delay) {
251 free_disk_space_delay_ = delay;
252 }
253
254 int64 DownloadHandler::CalculateRequestSpace(
255 const DownloadManager::DownloadVector& downloads) {
256 int64 request_space = 0;
257
258 for (const auto* download : downloads) {
259 if (download->IsDone())
260 continue;
261
262 const int64 total_bytes = download->GetTotalBytes();
263 // Skip unknown size download. Since drive cache tries to keep
264 // drive::internal::kMinFreeSpaceInBytes, we can continue download with
265 // using the space temporally.
266 if (total_bytes == 0)
267 continue;
268
269 request_space += total_bytes - download->GetReceivedBytes();
270 }
271
272 return request_space;
273 }
274
275 void DownloadHandler::FreeDiskSpaceIfNeeded() {
276 if (has_pending_free_disk_space_)
277 return;
278
279 base::ThreadTaskRunnerHandle::Get()->PostDelayedTask(
280 FROM_HERE, base::Bind(&DownloadHandler::FreeDiskSpaceIfNeededImmediately,
281 weak_ptr_factory_.GetWeakPtr()),
282 free_disk_space_delay_);
283
284 has_pending_free_disk_space_ = true;
285 }
286
287 void DownloadHandler::FreeDiskSpaceIfNeededImmediately() {
288 DownloadManager::DownloadVector downloads;
289
290 // Get all downloads of current profile and its off-the-record profile.
291 // TODO(yawano): support multi profiles.
292 if (notifier_ && notifier_->GetManager()) {
293 notifier_->GetManager()->GetAllDownloads(&downloads);
294 }
295 if (notifier_incognito_ && notifier_incognito_->GetManager()) {
296 notifier_incognito_->GetManager()->GetAllDownloads(&downloads);
297 }
298
299 // Free disk space even if request size is 0 byte in order to make drive cache
300 // keep drive::internal::kMinFreeSpaceInBytes.
301 file_system_->FreeDiskSpaceIfNeededFor(
302 CalculateRequestSpace(downloads),
303 base::Bind(&IgnoreFreeDiskSpaceIfNeededForCallback));
304
305 has_pending_free_disk_space_ = false;
306 }
307
240 void DownloadHandler::OnDownloadCreated(DownloadManager* manager, 308 void DownloadHandler::OnDownloadCreated(DownloadManager* manager,
241 DownloadItem* download) { 309 DownloadItem* download) {
310 FreeDiskSpaceIfNeededImmediately();
311
242 // Remove any persisted Drive DownloadItem. crbug.com/171384 312 // Remove any persisted Drive DownloadItem. crbug.com/171384
243 if (IsPersistedDriveDownload(drive_tmp_download_path_, download)) { 313 if (IsPersistedDriveDownload(drive_tmp_download_path_, download)) {
244 // Remove download later, since doing it here results in a crash. 314 // Remove download later, since doing it here results in a crash.
245 BrowserThread::PostTask(BrowserThread::UI, 315 BrowserThread::PostTask(BrowserThread::UI,
246 FROM_HERE, 316 FROM_HERE,
247 base::Bind(&DownloadHandler::RemoveDownload, 317 base::Bind(&DownloadHandler::RemoveDownload,
248 weak_ptr_factory_.GetWeakPtr(), 318 weak_ptr_factory_.GetWeakPtr(),
249 static_cast<void*>(manager), 319 static_cast<void*>(manager),
250 download->GetId())); 320 download->GetId()));
251 } 321 }
252 } 322 }
253 323
254 void DownloadHandler::RemoveDownload(void* manager_id, int id) { 324 void DownloadHandler::RemoveDownload(void* manager_id, int id) {
255 DownloadManager* manager = GetDownloadManager(manager_id); 325 DownloadManager* manager = GetDownloadManager(manager_id);
256 if (!manager) 326 if (!manager)
257 return; 327 return;
258 DownloadItem* download = manager->GetDownload(id); 328 DownloadItem* download = manager->GetDownload(id);
259 if (!download) 329 if (!download)
260 return; 330 return;
261 download->Remove(); 331 download->Remove();
262 } 332 }
263 333
264 void DownloadHandler::OnDownloadUpdated( 334 void DownloadHandler::OnDownloadUpdated(
265 DownloadManager* manager, DownloadItem* download) { 335 DownloadManager* manager, DownloadItem* download) {
266 DCHECK_CURRENTLY_ON(BrowserThread::UI); 336 DCHECK_CURRENTLY_ON(BrowserThread::UI);
267 337
338 FreeDiskSpaceIfNeeded();
339
268 // Only accept downloads that have the Drive meta data associated with them. 340 // Only accept downloads that have the Drive meta data associated with them.
269 DriveUserData* data = GetDriveUserData(download); 341 DriveUserData* data = GetDriveUserData(download);
270 if (!drive_tmp_download_path_.IsParent(download->GetTargetFilePath()) || 342 if (!drive_tmp_download_path_.IsParent(download->GetTargetFilePath()) ||
271 !data || 343 !data ||
272 data->is_complete()) 344 data->is_complete())
273 return; 345 return;
274 346
275 switch (download->GetState()) { 347 switch (download->GetState()) {
276 case DownloadItem::IN_PROGRESS: 348 case DownloadItem::IN_PROGRESS:
277 break; 349 break;
(...skipping 69 matching lines...) Expand 10 before | Expand all | Expand 10 after
347 419
348 DownloadManager* DownloadHandler::GetDownloadManager(void* manager_id) { 420 DownloadManager* DownloadHandler::GetDownloadManager(void* manager_id) {
349 if (manager_id == notifier_->GetManager()) 421 if (manager_id == notifier_->GetManager())
350 return notifier_->GetManager(); 422 return notifier_->GetManager();
351 if (notifier_incognito_ && manager_id == notifier_incognito_->GetManager()) 423 if (notifier_incognito_ && manager_id == notifier_incognito_->GetManager())
352 return notifier_incognito_->GetManager(); 424 return notifier_incognito_->GetManager();
353 return NULL; 425 return NULL;
354 } 426 }
355 427
356 } // namespace drive 428 } // namespace drive
OLDNEW
« no previous file with comments | « chrome/browser/chromeos/drive/download_handler.h ('k') | chrome/browser/chromeos/drive/download_handler_unittest.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698