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_EXTENSIONS_API_FILE_SYSTEM_FILE_SYSTEM_API_H_ 6 #define CHROME_BROWSER_EXTENSIONS_API_FILE_SYSTEM_FILE_SYSTEM_API_H_ 7 8 #include "chrome/browser/extensions/chrome_extension_function.h" 9 #include "chrome/common/extensions/api/file_system.h" 10 #include "ui/shell_dialogs/select_file_dialog.h" 11 12 namespace base { 13 class FilePath; 14 } 15 16 namespace extensions { 17 class ExtensionPrefs; 18 19 namespace file_system_api { 20 21 // Methods to get and set the path of the directory containing the last file 22 // chosen by the user in response to a chrome.fileSystem.chooseEntry() call for 23 // the given extension. 24 25 // Returns an empty path on failure. 26 base::FilePath GetLastChooseEntryDirectory(const ExtensionPrefs* prefs, 27 const std::string& extension_id); 28 29 void SetLastChooseEntryDirectory(ExtensionPrefs* prefs, 30 const std::string& extension_id, 31 const base::FilePath& path); 32 33 } // namespace file_system_api 34 35 class FileSystemGetDisplayPathFunction : public ChromeSyncExtensionFunction { 36 public: 37 DECLARE_EXTENSION_FUNCTION("fileSystem.getDisplayPath", 38 FILESYSTEM_GETDISPLAYPATH) 39 40 protected: 41 virtual ~FileSystemGetDisplayPathFunction() {} 42 virtual bool RunImpl() OVERRIDE; 43 }; 44 45 class FileSystemEntryFunction : public ChromeAsyncExtensionFunction { 46 protected: 47 FileSystemEntryFunction(); 48 49 virtual ~FileSystemEntryFunction() {} 50 51 // This is called when writable file entries are being returned. The function 52 // will ensure the files exist, creating them if necessary, and also check 53 // that none of the files are links. If it succeeds it proceeds to 54 // RegisterFileSystemsAndSendResponse, otherwise to HandleWritableFileError. 55 void CheckWritableFiles(const std::vector<base::FilePath>& path); 56 57 // This will finish the choose file process. This is either called directly 58 // from FilesSelected, or from WritableFileChecker. It is called on the UI 59 // thread. 60 void RegisterFileSystemsAndSendResponse( 61 const std::vector<base::FilePath>& path); 62 63 // Creates a response dictionary and sets it as the response to be sent. 64 void CreateResponse(); 65 66 // Adds an entry to the response dictionary. 67 void AddEntryToResponse(const base::FilePath& path, 68 const std::string& id_override); 69 70 // called on the UI thread if there is a problem checking a writable file. 71 void HandleWritableFileError(const base::FilePath& error_path); 72 73 // Whether multiple entries have been requested. 74 bool multiple_; 75 76 // Whether a directory has been requested. 77 bool is_directory_; 78 79 // The dictionary to send as the response. 80 base::DictionaryValue* response_; 81 }; 82 83 class FileSystemGetWritableEntryFunction : public FileSystemEntryFunction { 84 public: 85 DECLARE_EXTENSION_FUNCTION("fileSystem.getWritableEntry", 86 FILESYSTEM_GETWRITABLEENTRY) 87 88 protected: 89 virtual ~FileSystemGetWritableEntryFunction() {} 90 virtual bool RunImpl() OVERRIDE; 91 92 private: 93 void CheckPermissionAndSendResponse(); 94 void SetIsDirectoryOnFileThread(); 95 96 // The path to the file for which a writable entry has been requested. 97 base::FilePath path_; 98 }; 99 100 class FileSystemIsWritableEntryFunction : public ChromeSyncExtensionFunction { 101 public: 102 DECLARE_EXTENSION_FUNCTION("fileSystem.isWritableEntry", 103 FILESYSTEM_ISWRITABLEENTRY) 104 105 protected: 106 virtual ~FileSystemIsWritableEntryFunction() {} 107 virtual bool RunImpl() OVERRIDE; 108 }; 109 110 class FileSystemChooseEntryFunction : public FileSystemEntryFunction { 111 public: 112 // Allow picker UI to be skipped in testing. 113 static void SkipPickerAndAlwaysSelectPathForTest(base::FilePath* path); 114 static void SkipPickerAndAlwaysSelectPathsForTest( 115 std::vector<base::FilePath>* paths); 116 static void SkipPickerAndSelectSuggestedPathForTest(); 117 static void SkipPickerAndAlwaysCancelForTest(); 118 static void StopSkippingPickerForTest(); 119 // Allow directory access confirmation UI to be skipped in testing. 120 static void SkipDirectoryConfirmationForTest(); 121 static void AutoCancelDirectoryConfirmationForTest(); 122 static void StopSkippingDirectoryConfirmationForTest(); 123 // Call this with the directory for test file paths. On Chrome OS, accessed 124 // path needs to be explicitly registered for smooth integration with Google 125 // Drive support. 126 static void RegisterTempExternalFileSystemForTest(const std::string& name, 127 const base::FilePath& path); 128 129 DECLARE_EXTENSION_FUNCTION("fileSystem.chooseEntry", FILESYSTEM_CHOOSEENTRY) 130 131 typedef std::vector<linked_ptr<extensions::api::file_system::AcceptOption> > 132 AcceptOptions; 133 134 static void BuildFileTypeInfo( 135 ui::SelectFileDialog::FileTypeInfo* file_type_info, 136 const base::FilePath::StringType& suggested_extension, 137 const AcceptOptions* accepts, 138 const bool* acceptsAllTypes); 139 static void BuildSuggestion(const std::string* opt_name, 140 base::FilePath* suggested_name, 141 base::FilePath::StringType* suggested_extension); 142 143 protected: 144 class FilePicker; 145 146 virtual ~FileSystemChooseEntryFunction() {} 147 virtual bool RunImpl() OVERRIDE; 148 void ShowPicker(const ui::SelectFileDialog::FileTypeInfo& file_type_info, 149 ui::SelectFileDialog::Type picker_type); 150 151 private: 152 void SetInitialPathOnFileThread(const base::FilePath& suggested_name, 153 const base::FilePath& previous_path); 154 155 // FilesSelected and FileSelectionCanceled are called by the file picker. 156 void FilesSelected(const std::vector<base::FilePath>& path); 157 void FileSelectionCanceled(); 158 159 // Check if the chosen directory is or is an ancestor of a sensitive 160 // directory. If so, show a dialog to confirm that the user wants to open the 161 // directory. Calls OnDirectoryAccessConfirmed if the directory isn't 162 // sensitive or the user chooses to open it. Otherwise, calls 163 // FileSelectionCanceled. 164 void ConfirmDirectoryAccessOnFileThread( 165 const std::vector<base::FilePath>& paths, 166 content::WebContents* web_contents); 167 void OnDirectoryAccessConfirmed(const std::vector<base::FilePath>& paths); 168 169 base::FilePath initial_path_; 170 }; 171 172 class FileSystemRetainEntryFunction : public ChromeAsyncExtensionFunction { 173 public: 174 DECLARE_EXTENSION_FUNCTION("fileSystem.retainEntry", FILESYSTEM_RETAINENTRY) 175 176 protected: 177 virtual ~FileSystemRetainEntryFunction() {} 178 virtual bool RunImpl() OVERRIDE; 179 180 private: 181 // Retains the file entry referenced by |entry_id| in apps::SavedFilesService. 182 // |entry_id| must refer to an entry in an isolated file system. 183 void RetainFileEntry(const std::string& entry_id); 184 185 void SetIsDirectoryOnFileThread(); 186 187 // Whether the file being retained is a directory. 188 bool is_directory_; 189 190 // The path to the file to retain. 191 base::FilePath path_; 192 }; 193 194 class FileSystemIsRestorableFunction : public ChromeSyncExtensionFunction { 195 public: 196 DECLARE_EXTENSION_FUNCTION("fileSystem.isRestorable", FILESYSTEM_ISRESTORABLE) 197 198 protected: 199 virtual ~FileSystemIsRestorableFunction() {} 200 virtual bool RunImpl() OVERRIDE; 201 }; 202 203 class FileSystemRestoreEntryFunction : public FileSystemEntryFunction { 204 public: 205 DECLARE_EXTENSION_FUNCTION("fileSystem.restoreEntry", FILESYSTEM_RESTOREENTRY) 206 207 protected: 208 virtual ~FileSystemRestoreEntryFunction() {} 209 virtual bool RunImpl() OVERRIDE; 210 }; 211 212 } // namespace extensions 213 214 #endif // CHROME_BROWSER_EXTENSIONS_API_FILE_SYSTEM_FILE_SYSTEM_API_H_ 215