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

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

Issue 214363002: drive: Return cancel closure from FileSystem::GetFileContent (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Created 6 years, 9 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 2013 The Chromium Authors. All rights reserved. 1 // Copyright 2013 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/drive_file_stream_reader.h" 5 #include "chrome/browser/chromeos/drive/drive_file_stream_reader.h"
6 6
7 #include <algorithm> 7 #include <algorithm>
8 #include <cstring> 8 #include <cstring>
9 9
10 #include "base/callback_helpers.h" 10 #include "base/callback_helpers.h"
(...skipping 11 matching lines...) Expand all
22 using content::BrowserThread; 22 using content::BrowserThread;
23 23
24 namespace drive { 24 namespace drive {
25 namespace { 25 namespace {
26 26
27 // Converts FileError code to net::Error code. 27 // Converts FileError code to net::Error code.
28 int FileErrorToNetError(FileError error) { 28 int FileErrorToNetError(FileError error) {
29 return net::FileErrorToNetError(FileErrorToBaseFileError(error)); 29 return net::FileErrorToNetError(FileErrorToBaseFileError(error));
30 } 30 }
31 31
32 // Runs task on UI thread.
33 void RunTaskOnUIThread(const base::Closure& task) {
34 google_apis::RunTaskOnThread(
35 BrowserThread::GetMessageLoopProxyForThread(BrowserThread::UI), task);
36 }
37
38 // Computes the concrete |start| offset and the |length| of |range| in a file 32 // Computes the concrete |start| offset and the |length| of |range| in a file
39 // of |total| size. 33 // of |total| size.
40 // 34 //
41 // This is a thin wrapper of HttpByteRange::ComputeBounds, extended to allow 35 // This is a thin wrapper of HttpByteRange::ComputeBounds, extended to allow
42 // an empty range at the end of the file, like "Range: bytes 0-" on a zero byte 36 // an empty range at the end of the file, like "Range: bytes 0-" on a zero byte
43 // file. This is for convenience in unifying implementation with the seek 37 // file. This is for convenience in unifying implementation with the seek
44 // operation of stream reader. HTTP doesn't allow such ranges but we want to 38 // operation of stream reader. HTTP doesn't allow such ranges but we want to
45 // treat such seeking as valid. 39 // treat such seeking as valid.
46 bool ComputeConcretePosition(net::HttpByteRange range, int64 total, 40 bool ComputeConcretePosition(net::HttpByteRange range, int64 total,
47 int64* start, int64* length) { 41 int64* start, int64* length) {
(...skipping 218 matching lines...) Expand 10 before | Expand all | Expand 10 after
266 base::ResetAndReturn(&callback_).Run(error_code_); 260 base::ResetAndReturn(&callback_).Run(error_code_);
267 } 261 }
268 262
269 } // namespace internal 263 } // namespace internal
270 264
271 namespace { 265 namespace {
272 266
273 // Calls FileSystemInterface::GetFileContent if the file system 267 // Calls FileSystemInterface::GetFileContent if the file system
274 // is available. If not, the |completion_callback| is invoked with 268 // is available. If not, the |completion_callback| is invoked with
275 // FILE_ERROR_FAILED. 269 // FILE_ERROR_FAILED.
276 void GetFileContentOnUIThread( 270 base::Closure GetFileContentOnUIThread(
277 const DriveFileStreamReader::FileSystemGetter& file_system_getter, 271 const DriveFileStreamReader::FileSystemGetter& file_system_getter,
278 const base::FilePath& drive_file_path, 272 const base::FilePath& drive_file_path,
279 const GetFileContentInitializedCallback& initialized_callback, 273 const GetFileContentInitializedCallback& initialized_callback,
280 const google_apis::GetContentCallback& get_content_callback, 274 const google_apis::GetContentCallback& get_content_callback,
281 const FileOperationCallback& completion_callback) { 275 const FileOperationCallback& completion_callback) {
282 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); 276 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
283 277
284 FileSystemInterface* file_system = file_system_getter.Run(); 278 FileSystemInterface* file_system = file_system_getter.Run();
285 if (!file_system) { 279 if (!file_system) {
286 completion_callback.Run(FILE_ERROR_FAILED); 280 completion_callback.Run(FILE_ERROR_FAILED);
287 return; 281 return base::Closure();
288 } 282 }
289 283
290 file_system->GetFileContent(drive_file_path, 284 return google_apis::CreateRelayCallback(
291 initialized_callback, 285 file_system->GetFileContent(drive_file_path,
292 get_content_callback, 286 initialized_callback,
293 completion_callback); 287 get_content_callback,
288 completion_callback));
294 } 289 }
295 290
296 // Helper to run FileSystemInterface::GetFileContent on UI thread. 291 // Helper to run FileSystemInterface::GetFileContent on UI thread.
297 void GetFileContent( 292 void GetFileContent(
298 const DriveFileStreamReader::FileSystemGetter& file_system_getter, 293 const DriveFileStreamReader::FileSystemGetter& file_system_getter,
299 const base::FilePath& drive_file_path, 294 const base::FilePath& drive_file_path,
300 const GetFileContentInitializedCallback& initialized_callback, 295 const GetFileContentInitializedCallback& initialized_callback,
301 const google_apis::GetContentCallback& get_content_callback, 296 const google_apis::GetContentCallback& get_content_callback,
302 const FileOperationCallback& completion_callback) { 297 const FileOperationCallback& completion_callback,
298 const base::Callback<void(const base::Closure&)>& reply_callback) {
303 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO)); 299 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO));
304 300
305 BrowserThread::PostTask( 301 BrowserThread::PostTaskAndReplyWithResult(
306 BrowserThread::UI, 302 BrowserThread::UI,
307 FROM_HERE, 303 FROM_HERE,
308 base::Bind(&GetFileContentOnUIThread, 304 base::Bind(&GetFileContentOnUIThread,
309 file_system_getter, 305 file_system_getter,
310 drive_file_path, 306 drive_file_path,
311 google_apis::CreateRelayCallback(initialized_callback), 307 google_apis::CreateRelayCallback(initialized_callback),
312 google_apis::CreateRelayCallback(get_content_callback), 308 google_apis::CreateRelayCallback(get_content_callback),
313 google_apis::CreateRelayCallback(completion_callback))); 309 google_apis::CreateRelayCallback(completion_callback)),
310 reply_callback);
314 } 311 }
315 312
316 } // namespace 313 } // namespace
317 314
318 DriveFileStreamReader::DriveFileStreamReader( 315 DriveFileStreamReader::DriveFileStreamReader(
319 const FileSystemGetter& file_system_getter, 316 const FileSystemGetter& file_system_getter,
320 base::SequencedTaskRunner* file_task_runner) 317 base::SequencedTaskRunner* file_task_runner)
321 : file_system_getter_(file_system_getter), 318 : file_system_getter_(file_system_getter),
322 file_task_runner_(file_task_runner), 319 file_task_runner_(file_task_runner),
323 weak_ptr_factory_(this) { 320 weak_ptr_factory_(this) {
(...skipping 20 matching lines...) Expand all
344 drive_file_path, 341 drive_file_path,
345 base::Bind(&DriveFileStreamReader 342 base::Bind(&DriveFileStreamReader
346 ::InitializeAfterGetFileContentInitialized, 343 ::InitializeAfterGetFileContentInitialized,
347 weak_ptr_factory_.GetWeakPtr(), 344 weak_ptr_factory_.GetWeakPtr(),
348 byte_range, 345 byte_range,
349 callback), 346 callback),
350 base::Bind(&DriveFileStreamReader::OnGetContent, 347 base::Bind(&DriveFileStreamReader::OnGetContent,
351 weak_ptr_factory_.GetWeakPtr()), 348 weak_ptr_factory_.GetWeakPtr()),
352 base::Bind(&DriveFileStreamReader::OnGetFileContentCompletion, 349 base::Bind(&DriveFileStreamReader::OnGetFileContentCompletion,
353 weak_ptr_factory_.GetWeakPtr(), 350 weak_ptr_factory_.GetWeakPtr(),
354 callback)); 351 callback),
352 base::Bind(&DriveFileStreamReader::StoreCancelDownloadClosure,
353 weak_ptr_factory_.GetWeakPtr()));
355 } 354 }
356 355
357 int DriveFileStreamReader::Read(net::IOBuffer* buffer, int buffer_length, 356 int DriveFileStreamReader::Read(net::IOBuffer* buffer, int buffer_length,
358 const net::CompletionCallback& callback) { 357 const net::CompletionCallback& callback) {
359 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO)); 358 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO));
360 DCHECK(reader_proxy_); 359 DCHECK(reader_proxy_);
361 DCHECK(buffer); 360 DCHECK(buffer);
362 DCHECK(!callback.is_null()); 361 DCHECK(!callback.is_null());
363 return reader_proxy_->Read(buffer, buffer_length, callback); 362 return reader_proxy_->Read(buffer, buffer_length, callback);
364 } 363 }
365 364
365 void DriveFileStreamReader::StoreCancelDownloadClosure(
366 const base::Closure& cancel_download_closure) {
367 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO));
368 cancel_download_closure_ = cancel_download_closure;
369 }
370
366 void DriveFileStreamReader::InitializeAfterGetFileContentInitialized( 371 void DriveFileStreamReader::InitializeAfterGetFileContentInitialized(
367 const net::HttpByteRange& byte_range, 372 const net::HttpByteRange& byte_range,
368 const InitializeCompletionCallback& callback, 373 const InitializeCompletionCallback& callback,
369 FileError error, 374 FileError error,
370 scoped_ptr<ResourceEntry> entry,
371 const base::FilePath& local_cache_file_path, 375 const base::FilePath& local_cache_file_path,
372 const base::Closure& ui_cancel_download_closure) { 376 scoped_ptr<ResourceEntry> entry) {
373 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO)); 377 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO));
378 DCHECK(!cancel_download_closure_.is_null());
kinaba 2014/03/28 08:25:43 nit: Could you add some short comment on why we ca
hashimoto 2014/03/28 09:34:21 Done.
374 379
375 if (error != FILE_ERROR_OK) { 380 if (error != FILE_ERROR_OK) {
376 callback.Run(FileErrorToNetError(error), scoped_ptr<ResourceEntry>()); 381 callback.Run(FileErrorToNetError(error), scoped_ptr<ResourceEntry>());
377 return; 382 return;
378 } 383 }
379 DCHECK(entry); 384 DCHECK(entry);
380 385
381 int64 range_start = 0, range_length = 0; 386 int64 range_start = 0, range_length = 0;
382 if (!ComputeConcretePosition(byte_range, entry->file_info().size(), 387 if (!ComputeConcretePosition(byte_range, entry->file_info().size(),
383 &range_start, &range_length)) { 388 &range_start, &range_length)) {
384 // If |byte_range| is invalid (e.g. out of bounds), return with an error. 389 // If |byte_range| is invalid (e.g. out of bounds), return with an error.
385 // At the same time, we cancel the in-flight downloading operation if 390 // At the same time, we cancel the in-flight downloading operation if
386 // needed and and invalidate weak pointers so that we won't 391 // needed and and invalidate weak pointers so that we won't
387 // receive unwanted callbacks. 392 // receive unwanted callbacks.
388 if (!ui_cancel_download_closure.is_null()) 393 cancel_download_closure_.Run();
389 RunTaskOnUIThread(ui_cancel_download_closure);
390 weak_ptr_factory_.InvalidateWeakPtrs(); 394 weak_ptr_factory_.InvalidateWeakPtrs();
391 callback.Run( 395 callback.Run(
392 net::ERR_REQUEST_RANGE_NOT_SATISFIABLE, scoped_ptr<ResourceEntry>()); 396 net::ERR_REQUEST_RANGE_NOT_SATISFIABLE, scoped_ptr<ResourceEntry>());
393 return; 397 return;
394 } 398 }
395 399
396 if (local_cache_file_path.empty()) { 400 if (local_cache_file_path.empty()) {
397 // The file is not cached, and being downloaded. 401 // The file is not cached, and being downloaded.
398 DCHECK(!ui_cancel_download_closure.is_null());
399 reader_proxy_.reset( 402 reader_proxy_.reset(
400 new internal::NetworkReaderProxy( 403 new internal::NetworkReaderProxy(
401 range_start, range_length, 404 range_start, range_length, cancel_download_closure_));
402 base::Bind(&RunTaskOnUIThread, ui_cancel_download_closure)));
403 callback.Run(net::OK, entry.Pass()); 405 callback.Run(net::OK, entry.Pass());
404 return; 406 return;
405 } 407 }
406 408
407 // Otherwise, open the stream for file. 409 // Otherwise, open the stream for file.
408 scoped_ptr<util::LocalFileReader> file_reader( 410 scoped_ptr<util::LocalFileReader> file_reader(
409 new util::LocalFileReader(file_task_runner_.get())); 411 new util::LocalFileReader(file_task_runner_.get()));
410 util::LocalFileReader* file_reader_ptr = file_reader.get(); 412 util::LocalFileReader* file_reader_ptr = file_reader.get();
411 file_reader_ptr->Open( 413 file_reader_ptr->Open(
412 local_cache_file_path, 414 local_cache_file_path,
(...skipping 50 matching lines...) Expand 10 before | Expand all | Expand 10 after
463 // Note: due to the same reason, LocalReaderProxy::OnCompleted may 465 // Note: due to the same reason, LocalReaderProxy::OnCompleted may
464 // or may not be called. This is timing issue, and it is difficult to avoid 466 // or may not be called. This is timing issue, and it is difficult to avoid
465 // unfortunately. 467 // unfortunately.
466 if (error != FILE_ERROR_OK) { 468 if (error != FILE_ERROR_OK) {
467 callback.Run(FileErrorToNetError(error), scoped_ptr<ResourceEntry>()); 469 callback.Run(FileErrorToNetError(error), scoped_ptr<ResourceEntry>());
468 } 470 }
469 } 471 }
470 } 472 }
471 473
472 } // namespace drive 474 } // namespace drive
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698