Home | History | Annotate | Download | only in fileapi
      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 WEBKIT_BROWSER_FILEAPI_FILE_SYSTEM_OPERATION_H_
      6 #define WEBKIT_BROWSER_FILEAPI_FILE_SYSTEM_OPERATION_H_
      7 
      8 #include <vector>
      9 
     10 #include "base/callback.h"
     11 #include "base/files/file_path.h"
     12 #include "base/platform_file.h"
     13 #include "base/process/process.h"
     14 #include "webkit/common/fileapi/directory_entry.h"
     15 
     16 namespace base {
     17 class Time;
     18 }
     19 
     20 namespace net {
     21 class URLRequest;
     22 }
     23 
     24 namespace webkit_blob {
     25 class ShareableFileReference;
     26 }
     27 
     28 class GURL;
     29 
     30 namespace fileapi {
     31 
     32 class FileSystemURL;
     33 class FileWriterDelegate;
     34 class FileSystemOperationImpl;
     35 
     36 // The interface class for FileSystemOperation implementations.
     37 //
     38 // This interface defines file system operations required to implement
     39 // "File API: Directories and System"
     40 // http://www.w3.org/TR/file-system-api/
     41 //
     42 // DESIGN NOTES
     43 //
     44 // This class is designed to
     45 //
     46 // 1) Serve one-time file system operation per instance.  Only one
     47 // method(CreateFile, CreateDirectory, Copy, Move, DirectoryExists,
     48 // GetMetadata, ReadDirectory and Remove) may be called during the
     49 // lifetime of this object and it should be called no more than once.
     50 //
     51 // 2) Deliver the results of operations to the client via the callback function
     52 // passed as the last parameter of the method.
     53 //
     54 // Note that it is valid to delete an operation while it is running.
     55 // The callback will NOT be fired if the operation is deleted before
     56 // it gets called.
     57 class FileSystemOperation {
     58  public:
     59   virtual ~FileSystemOperation() {}
     60 
     61   // Used for CreateFile(), etc. |result| is the return code of the operation.
     62   typedef base::Callback<void(base::PlatformFileError result)> StatusCallback;
     63 
     64   // Used for GetMetadata(). |result| is the return code of the operation,
     65   // |file_info| is the obtained file info.
     66   typedef base::Callback<
     67       void(base::PlatformFileError result,
     68            const base::PlatformFileInfo& file_info)> GetMetadataCallback;
     69 
     70   // Used for OpenFile(). |result| is the return code of the operation.
     71   // |on_close_callback| will be called after the file is closed in the child
     72   // process. It can be null, if no operation is needed on closing a file.
     73   typedef base::Callback<
     74       void(base::PlatformFileError result,
     75            base::PlatformFile file,
     76            const base::Closure& on_close_callback,
     77            base::ProcessHandle peer_handle)> OpenFileCallback;
     78 
     79   // Used for ReadDirectoryCallback.
     80   typedef std::vector<DirectoryEntry> FileEntryList;
     81 
     82   // Used for ReadDirectory(). |result| is the return code of the operation,
     83   // |file_list| is the list of files read, and |has_more| is true if some files
     84   // are yet to be read.
     85   typedef base::Callback<
     86       void(base::PlatformFileError result,
     87            const FileEntryList& file_list,
     88            bool has_more)> ReadDirectoryCallback;
     89 
     90   // Used for CreateSnapshotFile(). (Please see the comment at
     91   // CreateSnapshotFile() below for how the method is called)
     92   // |result| is the return code of the operation.
     93   // |file_info| is the metadata of the snapshot file created.
     94   // |platform_path| is the path to the snapshot file created.
     95   //
     96   // The snapshot file could simply be of the local file pointed by the given
     97   // filesystem URL in local filesystem cases; remote filesystems
     98   // may want to download the file into a temporary snapshot file and then
     99   // return the metadata of the temporary file.
    100   //
    101   // |file_ref| is used to manage the lifetime of the returned
    102   // snapshot file.  It can be set to let the chromium backend take
    103   // care of the life time of the snapshot file.  Otherwise (if the returned
    104   // file does not require any handling) the implementation can just
    105   // return NULL.  In a more complex case, the implementaiton can manage
    106   // the lifetime of the snapshot file on its own (e.g. by its cache system)
    107   // but also can be notified via the reference when the file becomes no
    108   // longer necessary in the javascript world.
    109   // Please see the comment for ShareableFileReference for details.
    110   //
    111   typedef base::Callback<
    112       void(base::PlatformFileError result,
    113            const base::PlatformFileInfo& file_info,
    114            const base::FilePath& platform_path,
    115            const scoped_refptr<webkit_blob::ShareableFileReference>& file_ref)>
    116           SnapshotFileCallback;
    117 
    118   // Used for Write().
    119   typedef base::Callback<void(base::PlatformFileError result,
    120                               int64 bytes,
    121                               bool complete)> WriteCallback;
    122 
    123   // Creates a file at |path|. If |exclusive| is true, an error is raised
    124   // in case a file is already present at the URL.
    125   virtual void CreateFile(const FileSystemURL& path,
    126                           bool exclusive,
    127                           const StatusCallback& callback) = 0;
    128 
    129   // Creates a directory at |path|. If |exclusive| is true, an error is
    130   // raised in case a directory is already present at the URL. If
    131   // |recursive| is true, create parent directories as needed just like
    132   // mkdir -p does.
    133   virtual void CreateDirectory(const FileSystemURL& path,
    134                                bool exclusive,
    135                                bool recursive,
    136                                const StatusCallback& callback) = 0;
    137 
    138   // Copies a file or directory from |src_path| to |dest_path|. If
    139   // |src_path| is a directory, the contents of |src_path| are copied to
    140   // |dest_path| recursively. A new file or directory is created at
    141   // |dest_path| as needed.
    142   virtual void Copy(const FileSystemURL& src_path,
    143                     const FileSystemURL& dest_path,
    144                     const StatusCallback& callback) = 0;
    145 
    146   // Moves a file or directory from |src_path| to |dest_path|. A new file
    147   // or directory is created at |dest_path| as needed.
    148   virtual void Move(const FileSystemURL& src_path,
    149                     const FileSystemURL& dest_path,
    150                     const StatusCallback& callback) = 0;
    151 
    152   // Checks if a directory is present at |path|.
    153   virtual void DirectoryExists(const FileSystemURL& path,
    154                                const StatusCallback& callback) = 0;
    155 
    156   // Checks if a file is present at |path|.
    157   virtual void FileExists(const FileSystemURL& path,
    158                           const StatusCallback& callback) = 0;
    159 
    160   // Gets the metadata of a file or directory at |path|.
    161   virtual void GetMetadata(const FileSystemURL& path,
    162                            const GetMetadataCallback& callback) = 0;
    163 
    164   // Reads contents of a directory at |path|.
    165   virtual void ReadDirectory(const FileSystemURL& path,
    166                              const ReadDirectoryCallback& callback) = 0;
    167 
    168   // Removes a file or directory at |path|. If |recursive| is true, remove
    169   // all files and directories under the directory at |path| recursively.
    170   virtual void Remove(const FileSystemURL& path, bool recursive,
    171                       const StatusCallback& callback) = 0;
    172 
    173   // Writes the data read from |blob_request| using |writer_delegate|.
    174   virtual void Write(
    175     const FileSystemURL& url,
    176     scoped_ptr<FileWriterDelegate> writer_delegate,
    177     scoped_ptr<net::URLRequest> blob_request,
    178     const WriteCallback& callback) = 0;
    179 
    180   // Truncates a file at |path| to |length|. If |length| is larger than
    181   // the original file size, the file will be extended, and the extended
    182   // part is filled with null bytes.
    183   virtual void Truncate(const FileSystemURL& path, int64 length,
    184                         const StatusCallback& callback) = 0;
    185 
    186   // Tries to cancel the current operation [we support cancelling write or
    187   // truncate only]. Reports failure for the current operation, then reports
    188   // success for the cancel operation itself via the |cancel_dispatcher|.
    189   //
    190   // E.g. a typical cancel implementation would look like:
    191   //
    192   //   virtual void SomeOperationImpl::Cancel(
    193   //       const StatusCallback& cancel_callback) {
    194   //     // Abort the current inflight operation first.
    195   //     ...
    196   //
    197   //     // Dispatch ABORT error for the current operation by invoking
    198   //     // the callback function for the ongoing operation,
    199   //     operation_callback.Run(base::PLATFORM_FILE_ERROR_ABORT, ...);
    200   //
    201   //     // Dispatch 'success' for the cancel (or dispatch appropriate
    202   //     // error code with DidFail() if the cancel has somehow failed).
    203   //     cancel_callback.Run(base::PLATFORM_FILE_OK);
    204   //   }
    205   //
    206   // Note that, for reporting failure, the callback function passed to a
    207   // cancellable operations are kept around with the operation instance
    208   // (as |operation_callback_| in the code example).
    209   virtual void Cancel(const StatusCallback& cancel_callback) = 0;
    210 
    211   // Modifies timestamps of a file or directory at |path| with
    212   // |last_access_time| and |last_modified_time|. The function DOES NOT
    213   // create a file unlike 'touch' command on Linux.
    214   //
    215   // This function is used only by Pepper as of writing.
    216   virtual void TouchFile(const FileSystemURL& path,
    217                          const base::Time& last_access_time,
    218                          const base::Time& last_modified_time,
    219                          const StatusCallback& callback) = 0;
    220 
    221   // Opens a file at |path| with |file_flags|, where flags are OR'ed
    222   // values of base::PlatformFileFlags.
    223   //
    224   // |peer_handle| is the process handle of a pepper plugin process, which
    225   // is necessary for underlying IPC calls with Pepper plugins.
    226   //
    227   // This function is used only by Pepper as of writing.
    228   virtual void OpenFile(const FileSystemURL& path,
    229                         int file_flags,
    230                         base::ProcessHandle peer_handle,
    231                         const OpenFileCallback& callback) = 0;
    232 
    233   // For downcasting to FileSystemOperationImpl.
    234   // TODO(kinuko): this hack should go away once appropriate upload-stream
    235   // handling based on element types is supported.
    236   virtual FileSystemOperationImpl* AsFileSystemOperationImpl() = 0;
    237 
    238   // Creates a local snapshot file for a given |path| and returns the
    239   // metadata and platform path of the snapshot file via |callback|.
    240   // In local filesystem cases the implementation may simply return
    241   // the metadata of the file itself (as well as GetMetadata does),
    242   // while in remote filesystem case the backend may want to download the file
    243   // into a temporary snapshot file and return the metadata of the
    244   // temporary file.  Or if the implementaiton already has the local cache
    245   // data for |path| it can simply return the path to the cache.
    246   virtual void CreateSnapshotFile(const FileSystemURL& path,
    247                                   const SnapshotFileCallback& callback) = 0;
    248 
    249  protected:
    250   // Used only for internal assertions.
    251   enum OperationType {
    252     kOperationNone,
    253     kOperationCreateFile,
    254     kOperationCreateDirectory,
    255     kOperationCreateSnapshotFile,
    256     kOperationCopy,
    257     kOperationCopyInForeignFile,
    258     kOperationMove,
    259     kOperationDirectoryExists,
    260     kOperationFileExists,
    261     kOperationGetMetadata,
    262     kOperationReadDirectory,
    263     kOperationRemove,
    264     kOperationWrite,
    265     kOperationTruncate,
    266     kOperationTouchFile,
    267     kOperationOpenFile,
    268     kOperationCloseFile,
    269     kOperationGetLocalPath,
    270     kOperationCancel,
    271   };
    272 };
    273 
    274 }  // namespace fileapi
    275 
    276 #endif  // WEBKIT_BROWSER_FILEAPI_FILE_SYSTEM_OPERATION_H_
    277