Home | History | Annotate | Download | only in drive
      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
      3 // found in the LICENSE file.
      4 
      5 #ifndef CHROME_BROWSER_CHROMEOS_DRIVE_DRIVE_FILE_STREAM_READER_H_
      6 #define CHROME_BROWSER_CHROMEOS_DRIVE_DRIVE_FILE_STREAM_READER_H_
      7 
      8 #include <string>
      9 
     10 #include "base/basictypes.h"
     11 #include "base/callback.h"
     12 #include "base/memory/ref_counted.h"
     13 #include "base/memory/scoped_ptr.h"
     14 #include "base/memory/scoped_vector.h"
     15 #include "chrome/browser/chromeos/drive/file_errors.h"
     16 #include "google_apis/drive/gdata_errorcode.h"
     17 #include "net/base/completion_callback.h"
     18 
     19 namespace base {
     20 class SequencedTaskRunner;
     21 }  // namespace base
     22 
     23 namespace net {
     24 class HttpByteRange;
     25 class IOBuffer;
     26 }  // namespace net
     27 
     28 namespace drive {
     29 namespace util {
     30 class LocalFileReader;
     31 }  // namespace util
     32 
     33 namespace internal {
     34 
     35 // An interface to dispatch the reading operation. If the file is locally
     36 // cached, LocalReaderProxy defined below will be used. Otherwise (i.e. the
     37 // file is being downloaded from the server), NetworkReaderProxy will be used.
     38 class ReaderProxy {
     39  public:
     40   virtual ~ReaderProxy() {}
     41 
     42   // Called from DriveFileStreamReader::Read method.
     43   virtual int Read(net::IOBuffer* buffer, int buffer_length,
     44                    const net::CompletionCallback& callback) = 0;
     45 
     46   // Called when the data from the server is received.
     47   virtual void OnGetContent(scoped_ptr<std::string> data) = 0;
     48 
     49   // Called when the accessing to the file system is completed.
     50   virtual void OnCompleted(FileError error) = 0;
     51 };
     52 
     53 // The read operation implementation for the locally cached files.
     54 class LocalReaderProxy : public ReaderProxy {
     55  public:
     56   // The |file_reader| should be the instance which is already opened.
     57   // This class takes its ownership.
     58   // |length| is the number of bytes to be read. It must be equal or
     59   // smaller than the remaining data size in the |file_reader|.
     60   LocalReaderProxy(
     61       scoped_ptr<util::LocalFileReader> file_reader, int64 length);
     62   virtual ~LocalReaderProxy();
     63 
     64   // ReaderProxy overrides.
     65   virtual int Read(net::IOBuffer* buffer, int buffer_length,
     66                    const net::CompletionCallback& callback) OVERRIDE;
     67   virtual void OnGetContent(scoped_ptr<std::string> data) OVERRIDE;
     68   virtual void OnCompleted(FileError error) OVERRIDE;
     69 
     70  private:
     71   scoped_ptr<util::LocalFileReader> file_reader_;
     72 
     73   // Callback for the LocalFileReader::Read.
     74   void OnReadCompleted(
     75       const net::CompletionCallback& callback, int read_result);
     76 
     77   // The number of remaining bytes to be read.
     78   int64 remaining_length_;
     79 
     80   // This should remain the last member so it'll be destroyed first and
     81   // invalidate its weak pointers before other members are destroyed.
     82   base::WeakPtrFactory<LocalReaderProxy> weak_ptr_factory_;
     83   DISALLOW_COPY_AND_ASSIGN(LocalReaderProxy);
     84 };
     85 
     86 // The read operation implementation for the file which is being downloaded.
     87 class NetworkReaderProxy : public ReaderProxy {
     88  public:
     89   // If the instance is deleted during the download process, it is necessary
     90   // to cancel the job. |job_canceller| should be the callback to run the
     91   // cancelling. |full_content_length| is necessary for determining whether the
     92   // deletion is done in the middle of download process.
     93   NetworkReaderProxy(
     94       int64 offset, int64 content_length, int64 full_content_length,
     95       const base::Closure& job_canceller);
     96   virtual ~NetworkReaderProxy();
     97 
     98   // ReaderProxy overrides.
     99   virtual int Read(net::IOBuffer* buffer, int buffer_length,
    100                    const net::CompletionCallback& callback) OVERRIDE;
    101   virtual void OnGetContent(scoped_ptr<std::string> data) OVERRIDE;
    102   virtual void OnCompleted(FileError error) OVERRIDE;
    103 
    104  private:
    105   // The data received from the server, but not yet read.
    106   ScopedVector<std::string> pending_data_;
    107 
    108   // The number of bytes to be skipped.
    109   int64 remaining_offset_;
    110 
    111   // The number of bytes of remaining data (including the data not yet
    112   // received from the server).
    113   int64 remaining_content_length_;
    114 
    115   // Flag to remember whether this read request is for reading till the end of
    116   // the file.
    117   const bool is_full_download_;
    118 
    119   int error_code_;
    120 
    121   // To support pending Read(), it is necessary to keep its arguments.
    122   scoped_refptr<net::IOBuffer> buffer_;
    123   int buffer_length_;
    124   net::CompletionCallback callback_;
    125 
    126   // Keeps the closure to cancel downloading job if necessary.
    127   // Will be reset when the job is completed (regardless whether the job is
    128   // successfully done or not).
    129   base::Closure job_canceller_;
    130 
    131   DISALLOW_COPY_AND_ASSIGN(NetworkReaderProxy);
    132 };
    133 
    134 }  // namespace internal
    135 
    136 class FileSystemInterface;
    137 class ResourceEntry;
    138 
    139 // The stream reader for a file in FileSystem. Instances of this class
    140 // should live on IO thread.
    141 // Operations to communicate with a locally cached file will run on
    142 // |file_task_runner| specified by the constructor.
    143 class DriveFileStreamReader {
    144  public:
    145   // Callback to return the FileSystemInterface instance. This is an
    146   // injecting point for testing.
    147   // Note that the callback will be copied between threads (IO and UI), and
    148   // will be called on UI thread.
    149   typedef base::Callback<FileSystemInterface*()> FileSystemGetter;
    150 
    151   // Callback to return the result of Initialize().
    152   // |error| is net::Error code.
    153   typedef base::Callback<void(int error, scoped_ptr<ResourceEntry> entry)>
    154       InitializeCompletionCallback;
    155 
    156   DriveFileStreamReader(const FileSystemGetter& file_system_getter,
    157                         base::SequencedTaskRunner* file_task_runner);
    158   ~DriveFileStreamReader();
    159 
    160   // Returns true if the reader is initialized.
    161   bool IsInitialized() const;
    162 
    163   // Initializes the stream for the |drive_file_path|.
    164   // |callback| must not be null.
    165   void Initialize(const base::FilePath& drive_file_path,
    166                   const net::HttpByteRange& byte_range,
    167                   const InitializeCompletionCallback& callback);
    168 
    169   // Reads the data into |buffer| at most |buffer_length|, and returns
    170   // the number of bytes. If an error happened, returns an error code.
    171   // If no data is available yet, returns net::ERR_IO_PENDING immediately,
    172   // and when the data is available the actual Read operation is done
    173   // and |callback| will be run with the result.
    174   // The Read() method must not be called before the Initialize() is completed
    175   // successfully, or if there is pending read operation.
    176   // Neither |buffer| nor |callback| must be null.
    177   int Read(net::IOBuffer* buffer, int buffer_length,
    178            const net::CompletionCallback& callback);
    179 
    180  private:
    181   // Used to store the cancel closure returned by FileSystemInterface.
    182   void StoreCancelDownloadClosure(const base::Closure& cancel_download_closure);
    183 
    184   // Part of Initialize. Called after GetFileContent's initialization
    185   // is done.
    186   void InitializeAfterGetFileContentInitialized(
    187       const net::HttpByteRange& byte_range,
    188       const InitializeCompletionCallback& callback,
    189       FileError error,
    190       const base::FilePath& local_cache_file_path,
    191       scoped_ptr<ResourceEntry> entry);
    192 
    193   // Part of Initialize. Called when the local file open process is done.
    194   void InitializeAfterLocalFileOpen(
    195       int64 length,
    196       const InitializeCompletionCallback& callback,
    197       scoped_ptr<ResourceEntry> entry,
    198       scoped_ptr<util::LocalFileReader> file_reader,
    199       int open_result);
    200 
    201   // Called when the data is received from the server.
    202   void OnGetContent(google_apis::GDataErrorCode error_code,
    203                     scoped_ptr<std::string> data);
    204 
    205   // Called when GetFileContent is completed.
    206   void OnGetFileContentCompletion(
    207       const InitializeCompletionCallback& callback,
    208       FileError error);
    209 
    210   const FileSystemGetter file_system_getter_;
    211   scoped_refptr<base::SequencedTaskRunner> file_task_runner_;
    212   base::Closure cancel_download_closure_;
    213   scoped_ptr<internal::ReaderProxy> reader_proxy_;
    214 
    215   // This should remain the last member so it'll be destroyed first and
    216   // invalidate its weak pointers before other members are destroyed.
    217   base::WeakPtrFactory<DriveFileStreamReader> weak_ptr_factory_;
    218   DISALLOW_COPY_AND_ASSIGN(DriveFileStreamReader);
    219 };
    220 
    221 }  // namespace drive
    222 
    223 #endif  // CHROME_BROWSER_CHROMEOS_DRIVE_DRIVE_FILE_STREAM_READER_H_
    224