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