Home | History | Annotate | Download | only in drive
      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
      3 // found in the LICENSE file.
      4 
      5 #ifndef CHROME_BROWSER_DRIVE_DRIVE_UPLOADER_H_
      6 #define CHROME_BROWSER_DRIVE_DRIVE_UPLOADER_H_
      7 
      8 #include <string>
      9 
     10 #include "base/basictypes.h"
     11 #include "base/callback_forward.h"
     12 #include "base/memory/ref_counted.h"
     13 #include "base/memory/weak_ptr.h"
     14 #include "chrome/browser/drive/drive_service_interface.h"
     15 #include "google_apis/drive/gdata_errorcode.h"
     16 
     17 class GURL;
     18 
     19 namespace base {
     20 class FilePath;
     21 class TaskRunner;
     22 }
     23 
     24 namespace google_apis {
     25 struct UploadRangeResponse;
     26 }
     27 
     28 namespace drive {
     29 class DriveServiceInterface;
     30 
     31 // Callback to be invoked once the upload has completed.
     32 // |upload_location| will be returned when the uploading process is started but
     33 // terminated before the completion due to some errors. It can be used to
     34 // resume it.
     35 typedef base::Callback<void(
     36     google_apis::GDataErrorCode error,
     37     const GURL& upload_location,
     38     scoped_ptr<google_apis::FileResource> resource_entry)>
     39     UploadCompletionCallback;
     40 
     41 class DriveUploaderInterface {
     42  public:
     43   typedef DriveServiceInterface::InitiateUploadNewFileOptions
     44       UploadNewFileOptions;
     45   typedef DriveServiceInterface::InitiateUploadExistingFileOptions
     46       UploadExistingFileOptions;
     47 
     48   virtual ~DriveUploaderInterface() {}
     49 
     50   // Uploads a new file to a directory specified by |upload_location|.
     51   // Returns a callback for cancelling the uploading job.
     52   //
     53   // parent_resource_id:
     54   //   resource id of the destination directory.
     55   //
     56   // local_file_path:
     57   //   The path to the local file to be uploaded.
     58   //
     59   // title:
     60   //   The title (file name) of the file to be uploaded.
     61   //
     62   // content_type:
     63   //   The content type of the file to be uploaded.
     64   //
     65   // callback:
     66   //   Called when an upload is done regardless of it was successful or not.
     67   //   Must not be null.
     68   //
     69   // progress_callback:
     70   //   Periodically called back with the total number of bytes sent so far.
     71   //   May be null if the information is not needed.
     72   virtual google_apis::CancelCallback UploadNewFile(
     73       const std::string& parent_resource_id,
     74       const base::FilePath& local_file_path,
     75       const std::string& title,
     76       const std::string& content_type,
     77       const UploadNewFileOptions& options,
     78       const UploadCompletionCallback& callback,
     79       const google_apis::ProgressCallback& progress_callback) = 0;
     80 
     81   // Uploads an existing file (a file that already exists on Drive).
     82   //
     83   // See comments at UploadNewFile about common parameters and the return value.
     84   //
     85   // resource_id:
     86   //   resource id of the existing file to be overwritten.
     87   //
     88   // etag:
     89   //   Expected ETag for the destination file. If it does not match, the upload
     90   //   fails with UPLOAD_ERROR_CONFLICT.
     91   //   If |etag| is empty, the test is skipped.
     92   virtual google_apis::CancelCallback UploadExistingFile(
     93       const std::string& resource_id,
     94       const base::FilePath& local_file_path,
     95       const std::string& content_type,
     96       const UploadExistingFileOptions& options,
     97       const UploadCompletionCallback& callback,
     98       const google_apis::ProgressCallback& progress_callback) = 0;
     99 
    100   // Resumes the uploading process terminated before the completion.
    101   // |upload_location| should be the one returned via UploadCompletionCallback
    102   // for previous invocation. |drive_file_path|, |local_file_path| and
    103   // |content_type| must be set to the same ones for previous invocation.
    104   //
    105   // See comments at UploadNewFile about common parameters and the return value.
    106   virtual google_apis::CancelCallback ResumeUploadFile(
    107       const GURL& upload_location,
    108       const base::FilePath& local_file_path,
    109       const std::string& content_type,
    110       const UploadCompletionCallback& callback,
    111       const google_apis::ProgressCallback& progress_callback) = 0;
    112 };
    113 
    114 class DriveUploader : public DriveUploaderInterface {
    115  public:
    116   DriveUploader(DriveServiceInterface* drive_service,
    117                 base::TaskRunner* blocking_task_runner);
    118   virtual ~DriveUploader();
    119 
    120   // DriveUploaderInterface overrides.
    121   virtual google_apis::CancelCallback UploadNewFile(
    122       const std::string& parent_resource_id,
    123       const base::FilePath& local_file_path,
    124       const std::string& title,
    125       const std::string& content_type,
    126       const UploadNewFileOptions& options,
    127       const UploadCompletionCallback& callback,
    128       const google_apis::ProgressCallback& progress_callback) OVERRIDE;
    129   virtual google_apis::CancelCallback UploadExistingFile(
    130       const std::string& resource_id,
    131       const base::FilePath& local_file_path,
    132       const std::string& content_type,
    133       const UploadExistingFileOptions& options,
    134       const UploadCompletionCallback& callback,
    135       const google_apis::ProgressCallback& progress_callback) OVERRIDE;
    136   virtual google_apis::CancelCallback ResumeUploadFile(
    137       const GURL& upload_location,
    138       const base::FilePath& local_file_path,
    139       const std::string& content_type,
    140       const UploadCompletionCallback& callback,
    141       const google_apis::ProgressCallback& progress_callback) OVERRIDE;
    142 
    143  private:
    144   struct UploadFileInfo;
    145   typedef base::Callback<void(scoped_ptr<UploadFileInfo> upload_file_info)>
    146       StartInitiateUploadCallback;
    147 
    148   // Starts uploading a file with |upload_file_info|.
    149   google_apis::CancelCallback StartUploadFile(
    150       scoped_ptr<UploadFileInfo> upload_file_info,
    151       const StartInitiateUploadCallback& start_initiate_upload_callback);
    152   void StartUploadFileAfterGetFileSize(
    153       scoped_ptr<UploadFileInfo> upload_file_info,
    154       const StartInitiateUploadCallback& start_initiate_upload_callback,
    155       bool get_file_size_result);
    156 
    157   // Starts to initiate the new file uploading.
    158   // Upon completion, OnUploadLocationReceived should be called.
    159   void StartInitiateUploadNewFile(
    160       const std::string& parent_resource_id,
    161       const std::string& title,
    162       const UploadNewFileOptions& options,
    163       scoped_ptr<UploadFileInfo> upload_file_info);
    164 
    165   // Starts to initiate the existing file uploading.
    166   // Upon completion, OnUploadLocationReceived should be called.
    167   void StartInitiateUploadExistingFile(
    168       const std::string& resource_id,
    169       const UploadExistingFileOptions& options,
    170       scoped_ptr<UploadFileInfo> upload_file_info);
    171 
    172   // DriveService callback for InitiateUpload.
    173   void OnUploadLocationReceived(scoped_ptr<UploadFileInfo> upload_file_info,
    174                                 google_apis::GDataErrorCode code,
    175                                 const GURL& upload_location);
    176 
    177   // Starts to get the current upload status for the file uploading.
    178   // Upon completion, OnUploadRangeResponseReceived should be called.
    179   void StartGetUploadStatus(scoped_ptr<UploadFileInfo> upload_file_info);
    180 
    181   // Uploads the next chunk of data from the file.
    182   void UploadNextChunk(scoped_ptr<UploadFileInfo> upload_file_info);
    183 
    184   // DriveService callback for ResumeUpload.
    185   void OnUploadRangeResponseReceived(
    186       scoped_ptr<UploadFileInfo> upload_file_info,
    187       const google_apis::UploadRangeResponse& response,
    188       scoped_ptr<google_apis::FileResource> entry);
    189   void OnUploadProgress(const google_apis::ProgressCallback& callback,
    190                         int64 start_position,
    191                         int64 total_size,
    192                         int64 progress_of_chunk,
    193                         int64 total_of_chunk);
    194 
    195   // Handle failed uploads.
    196   void UploadFailed(scoped_ptr<UploadFileInfo> upload_file_info,
    197                     google_apis::GDataErrorCode error);
    198 
    199   // The lifetime of this object should be guaranteed to exceed that of the
    200   // DriveUploader instance.
    201   DriveServiceInterface* drive_service_;  // Not owned by this class.
    202 
    203   scoped_refptr<base::TaskRunner> blocking_task_runner_;
    204 
    205   // Note: This should remain the last member so it'll be destroyed and
    206   // invalidate its weak pointers before any other members are destroyed.
    207   base::WeakPtrFactory<DriveUploader> weak_ptr_factory_;
    208   DISALLOW_COPY_AND_ASSIGN(DriveUploader);
    209 };
    210 
    211 }  // namespace drive
    212 
    213 #endif  // CHROME_BROWSER_DRIVE_DRIVE_UPLOADER_H_
    214