OLD | NEW |
---|---|
1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "chrome/browser/ui/views/file_manager_dialog.h" | 5 #include "chrome/browser/ui/views/file_manager_dialog.h" |
6 | 6 |
7 #include "base/file_util.h" | 7 #include "base/file_util.h" |
8 #include "base/logging.h" | 8 #include "base/logging.h" |
9 #include "base/memory/scoped_ptr.h" | 9 #include "base/memory/scoped_ptr.h" |
10 #include "base/path_service.h" | 10 #include "base/path_service.h" |
(...skipping 48 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
59 bool file_selected_; | 59 bool file_selected_; |
60 bool canceled_; | 60 bool canceled_; |
61 FilePath path_; | 61 FilePath path_; |
62 void* params_; | 62 void* params_; |
63 | 63 |
64 DISALLOW_COPY_AND_ASSIGN(MockSelectFileDialogListener); | 64 DISALLOW_COPY_AND_ASSIGN(MockSelectFileDialogListener); |
65 }; | 65 }; |
66 | 66 |
67 class FileManagerDialogBrowserTest : public ExtensionBrowserTest { | 67 class FileManagerDialogBrowserTest : public ExtensionBrowserTest { |
68 public: | 68 public: |
69 enum DialogButtonType { | |
70 DIALOG_BTN_OK, | |
71 DIALOG_BTN_CANCEL | |
72 }; | |
73 | |
69 virtual void SetUp() OVERRIDE { | 74 virtual void SetUp() OVERRIDE { |
70 // Create the dialog wrapper object, but don't show it yet. | 75 // Create the dialog wrapper object, but don't show it yet. |
71 listener_.reset(new MockSelectFileDialogListener()); | 76 listener_.reset(new MockSelectFileDialogListener()); |
72 dialog_ = new FileManagerDialog(listener_.get()); | 77 dialog_ = new FileManagerDialog(listener_.get()); |
78 | |
73 // Must run after our setup because it actually runs the test. | 79 // Must run after our setup because it actually runs the test. |
74 ExtensionBrowserTest::SetUp(); | 80 ExtensionBrowserTest::SetUp(); |
75 } | 81 } |
76 | 82 |
77 virtual void TearDown() OVERRIDE { | 83 virtual void TearDown() OVERRIDE { |
78 ExtensionBrowserTest::TearDown(); | 84 ExtensionBrowserTest::TearDown(); |
79 // Delete the dialog first, as it holds a pointer to the listener. | 85 // Delete the dialog first, as it holds a pointer to the listener. |
80 dialog_ = NULL; | 86 dialog_ = NULL; |
81 listener_.reset(); | 87 listener_.reset(); |
88 | |
89 second_dialog_ = NULL; | |
90 second_listener_.reset(); | |
82 } | 91 } |
83 | 92 |
84 // Creates a file system mount point for a directory. | 93 // Creates a file system mount point for a directory. |
85 void AddMountPoint(const FilePath& path) { | 94 void AddMountPoint(const FilePath& path) { |
86 fileapi::FileSystemPathManager* path_manager = | 95 fileapi::FileSystemPathManager* path_manager = |
87 browser()->profile()->GetFileSystemContext()->path_manager(); | 96 browser()->profile()->GetFileSystemContext()->path_manager(); |
88 fileapi::ExternalFileSystemMountPointProvider* provider = | 97 fileapi::ExternalFileSystemMountPointProvider* provider = |
89 path_manager->external_provider(); | 98 path_manager->external_provider(); |
90 provider->AddMountPoint(path); | 99 provider->AddMountPoint(path); |
91 } | 100 } |
92 | 101 |
102 void OpenDialog(SelectFileDialog::Type dialog_type, | |
103 const FilePath& file_path, | |
104 const gfx::NativeWindow& owning_window, | |
105 const std::string& additional_message) { | |
106 // Spawn a dialog to open a file. The dialog will signal that it is ready | |
107 // via chrome.test.sendMessage() in the extension JavaScript. | |
108 ExtensionTestMessageListener init_listener("worker-initialized", | |
109 false /* will_reply */); | |
110 | |
111 scoped_ptr<ExtensionTestMessageListener> additional_listener; | |
112 if (!additional_message.empty()) { | |
113 additional_listener.reset( | |
114 new ExtensionTestMessageListener(additional_message, false)); | |
115 } | |
116 | |
117 dialog_->SelectFile(dialog_type, | |
118 string16() /* title */, | |
achuithb
2011/11/10 23:30:03
Do you like this commenting style? Have you consid
tbarzic
2011/11/11 03:26:24
Usually not, but when commenting function args I p
| |
119 file_path, | |
120 NULL /* file_types */, | |
121 0 /* file_type_index */, | |
122 FILE_PATH_LITERAL("") /* default_extension */, | |
123 NULL /* source_contents */, | |
124 owning_window, | |
125 this /* params */); | |
126 | |
127 LOG(INFO) << "Waiting for JavaScript ready message."; | |
achuithb
2011/11/10 23:30:03
Is this logging necessary?
tbarzic
2011/11/11 03:26:24
not necessary, but useful
| |
128 ASSERT_TRUE(init_listener.WaitUntilSatisfied()); | |
129 | |
130 if (additional_listener.get()) { | |
131 LOG(INFO) << "Waiting for JavaScript " << additional_message | |
132 << " message."; | |
133 ASSERT_TRUE(additional_listener->WaitUntilSatisfied()); | |
134 } | |
135 | |
136 // Dialog should be running now. | |
137 ASSERT_TRUE(dialog_->IsRunning(owning_window)); | |
138 } | |
139 | |
140 void TryOpeningSecondDialog(const gfx::NativeWindow& owning_window) { | |
141 second_listener_.reset(new MockSelectFileDialogListener()); | |
142 second_dialog_ = new FileManagerDialog(second_listener_.get()); | |
143 | |
144 // At the moment we don't really care about dialog type, but we have to put | |
145 // some dialog type. | |
James Cook
2011/11/10 23:17:18
nit: remove extra space at start of comment
tbarzic
2011/11/11 03:26:24
Done.
| |
146 second_dialog_->SelectFile(SelectFileDialog::SELECT_OPEN_FILE, | |
147 string16() /* title */, | |
148 FilePath() /* default_path */, | |
149 NULL /* file_types */, | |
150 0 /* file_type_index */, | |
151 FILE_PATH_LITERAL("") /* default_extension */, | |
152 NULL /* source_contents */, | |
153 owning_window, | |
154 this /* params */); | |
155 | |
156 | |
157 } | |
158 | |
159 void CloseDialog(DialogButtonType button_type, | |
160 const gfx::NativeWindow& owning_window) { | |
161 // Inject JavaScript to click the cancel button and wait for notification | |
162 // that the window has closed. | |
163 ui_test_utils::WindowedNotificationObserver host_destroyed( | |
164 content::NOTIFICATION_RENDER_WIDGET_HOST_DESTROYED, | |
165 content::NotificationService::AllSources()); | |
166 RenderViewHost* host = dialog_->GetRenderViewHost(); | |
167 string16 main_frame; | |
168 std::string button_class = | |
169 (button_type == DIALOG_BTN_OK) ? ".ok" : ".cancel"; | |
170 string16 script = ASCIIToUTF16( | |
171 "console.log(\'Test JavaScript injected.\');" | |
172 "document.querySelector(\'" + button_class + "\').click();"); | |
173 // The file selection handler closes the dialog and does not return control | |
174 // to JavaScript, so do not wait for return values. | |
175 host->ExecuteJavascriptInWebFrame(main_frame, script); | |
176 LOG(INFO) << "Waiting for window close notification."; | |
177 host_destroyed.Wait(); | |
178 | |
179 // Dialog no longer believes it is running. | |
180 ASSERT_FALSE(dialog_->IsRunning(owning_window)); | |
181 } | |
182 | |
93 scoped_ptr<MockSelectFileDialogListener> listener_; | 183 scoped_ptr<MockSelectFileDialogListener> listener_; |
94 scoped_refptr<FileManagerDialog> dialog_; | 184 scoped_refptr<FileManagerDialog> dialog_; |
185 | |
186 scoped_ptr<MockSelectFileDialogListener> second_listener_; | |
187 scoped_refptr<FileManagerDialog> second_dialog_; | |
95 }; | 188 }; |
96 | 189 |
97 IN_PROC_BROWSER_TEST_F(FileManagerDialogBrowserTest, CreateAndDestroy) { | 190 IN_PROC_BROWSER_TEST_F(FileManagerDialogBrowserTest, CreateAndDestroy) { |
98 // Browser window must be up for us to test dialog window parent. | 191 // Browser window must be up for us to test dialog window parent. |
99 gfx::NativeWindow native_window = browser()->window()->GetNativeHandle(); | 192 gfx::NativeWindow native_window = browser()->window()->GetNativeHandle(); |
100 ASSERT_TRUE(native_window != NULL); | 193 ASSERT_TRUE(native_window != NULL); |
101 | 194 |
102 // Before we call SelectFile, dialog is not running/visible. | 195 // Before we call SelectFile, dialog is not running/visible. |
103 ASSERT_FALSE(dialog_->IsRunning(native_window)); | 196 ASSERT_FALSE(dialog_->IsRunning(native_window)); |
104 } | 197 } |
105 | 198 |
106 IN_PROC_BROWSER_TEST_F(FileManagerDialogBrowserTest, DestroyListener) { | 199 IN_PROC_BROWSER_TEST_F(FileManagerDialogBrowserTest, DestroyListener) { |
107 // Some users of SelectFileDialog destroy their listener before cleaning | 200 // Some users of SelectFileDialog destroy their listener before cleaning |
108 // up the dialog. Make sure we don't crash. | 201 // up the dialog. Make sure we don't crash. |
109 dialog_->ListenerDestroyed(); | 202 dialog_->ListenerDestroyed(); |
110 listener_.reset(); | 203 listener_.reset(); |
111 } | 204 } |
112 | 205 |
113 // TODO(jamescook): Add a test for selecting a file for an <input type='file'/> | 206 // TODO(jamescook): Add a test for selecting a file for an <input type='file'/> |
114 // page element, as that uses different memory management pathways. | 207 // page element, as that uses different memory management pathways. |
115 // crbug.com/98791 | 208 // crbug.com/98791 |
116 IN_PROC_BROWSER_TEST_F(FileManagerDialogBrowserTest, SelectFileAndCancel) { | 209 IN_PROC_BROWSER_TEST_F(FileManagerDialogBrowserTest, SelectFileAndCancel) { |
117 // Add tmp mount point even though this test won't use it directly. | 210 // Add tmp mount point even though this test won't use it directly. |
118 // We need this to make sure that at least one top-level directory exists | 211 // We need this to make sure that at least one top-level directory exists |
119 // in the file browser. | 212 // in the file browser. |
120 FilePath tmp_dir("/tmp"); | 213 FilePath tmp_dir("/tmp"); |
121 AddMountPoint(tmp_dir); | 214 AddMountPoint(tmp_dir); |
122 | 215 |
123 // Spawn a dialog to open a file. The dialog will signal that it is ready | |
124 // via chrome.test.sendMessage() in the extension JavaScript. | |
125 ExtensionTestMessageListener init_listener("worker-initialized", | |
126 false /* will_reply */); | |
127 gfx::NativeWindow owning_window = browser()->window()->GetNativeHandle(); | 216 gfx::NativeWindow owning_window = browser()->window()->GetNativeHandle(); |
128 dialog_->SelectFile(SelectFileDialog::SELECT_OPEN_FILE, | |
129 string16() /* title */, | |
130 FilePath() /* default_path */, | |
131 NULL /* file_types */, | |
132 0 /* file_type_index */, | |
133 FILE_PATH_LITERAL("") /* default_extension */, | |
134 NULL /* source_contents */, | |
135 owning_window, | |
136 this /* params */); | |
137 LOG(INFO) << "Waiting for JavaScript ready message."; | |
138 ASSERT_TRUE(init_listener.WaitUntilSatisfied()); | |
139 | 217 |
140 // Dialog should be running now. | 218 // FilePath() for default path. |
141 ASSERT_TRUE(dialog_->IsRunning(owning_window)); | 219 OpenDialog(SelectFileDialog::SELECT_OPEN_FILE, FilePath(), owning_window, ""); |
142 | 220 |
143 // Inject JavaScript to click the cancel button and wait for notification | 221 // Press cancel button. |
144 // that the window has closed. | 222 CloseDialog(DIALOG_BTN_CANCEL, owning_window); |
145 ui_test_utils::WindowedNotificationObserver host_destroyed( | |
146 content::NOTIFICATION_RENDER_WIDGET_HOST_DESTROYED, | |
147 content::NotificationService::AllSources()); | |
148 RenderViewHost* host = dialog_->GetRenderViewHost(); | |
149 string16 main_frame; | |
150 string16 script = ASCIIToUTF16( | |
151 "console.log(\'Test JavaScript injected.\');" | |
152 "document.querySelector(\'.cancel\').click();"); | |
153 // The file selection handler closes the dialog and does not return control | |
154 // to JavaScript, so do not wait for return values. | |
155 host->ExecuteJavascriptInWebFrame(main_frame, script); | |
156 LOG(INFO) << "Waiting for window close notification."; | |
157 host_destroyed.Wait(); | |
158 | |
159 // Dialog no longer believes it is running. | |
160 ASSERT_FALSE(dialog_->IsRunning(owning_window)); | |
161 | 223 |
162 // Listener should have been informed of the cancellation. | 224 // Listener should have been informed of the cancellation. |
163 ASSERT_FALSE(listener_->file_selected()); | 225 ASSERT_FALSE(listener_->file_selected()); |
164 ASSERT_TRUE(listener_->canceled()); | 226 ASSERT_TRUE(listener_->canceled()); |
165 ASSERT_EQ(this, listener_->params()); | 227 ASSERT_EQ(this, listener_->params()); |
166 } | 228 } |
167 | 229 |
168 IN_PROC_BROWSER_TEST_F(FileManagerDialogBrowserTest, SelectFileAndOpen) { | 230 IN_PROC_BROWSER_TEST_F(FileManagerDialogBrowserTest, SelectFileAndOpen) { |
169 // Allow the tmp directory to be mounted. We explicitly use /tmp because | 231 // Allow the tmp directory to be mounted. We explicitly use /tmp because |
170 // it it whitelisted for file system access on Chrome OS. | 232 // it it whitelisted for file system access on Chrome OS. |
171 FilePath tmp_dir("/tmp"); | 233 FilePath tmp_dir("/tmp"); |
172 AddMountPoint(tmp_dir); | 234 AddMountPoint(tmp_dir); |
173 | 235 |
174 // Create a directory with a single file in it. ScopedTempDir will delete | 236 // Create a directory with a single file in it. ScopedTempDir will delete |
175 // itself and our temp file when it goes out of scope. | 237 // itself and our temp file when it goes out of scope. |
176 ScopedTempDir scoped_temp_dir; | 238 ScopedTempDir scoped_temp_dir; |
177 ASSERT_TRUE(scoped_temp_dir.CreateUniqueTempDirUnderPath(tmp_dir)); | 239 ASSERT_TRUE(scoped_temp_dir.CreateUniqueTempDirUnderPath(tmp_dir)); |
178 FilePath temp_dir = scoped_temp_dir.path(); | 240 FilePath temp_dir = scoped_temp_dir.path(); |
179 FilePath test_file = temp_dir.AppendASCII("file_manager_test.html"); | 241 FilePath test_file = temp_dir.AppendASCII("file_manager_test.html"); |
180 | 242 |
181 // Create an empty file to give us something to select. | 243 // Create an empty file to give us something to select. |
182 FILE* fp = file_util::OpenFile(test_file, "w"); | 244 FILE* fp = file_util::OpenFile(test_file, "w"); |
183 ASSERT_TRUE(fp != NULL); | 245 ASSERT_TRUE(fp != NULL); |
184 ASSERT_TRUE(file_util::CloseFile(fp)); | 246 ASSERT_TRUE(file_util::CloseFile(fp)); |
185 | 247 |
248 gfx::NativeWindow owning_window = browser()->window()->GetNativeHandle(); | |
249 | |
186 // Spawn a dialog to open a file. Provide the path to the file so the dialog | 250 // Spawn a dialog to open a file. Provide the path to the file so the dialog |
187 // will automatically select it. Ensure that the OK button is enabled by | 251 // will automatically select it. Ensure that the OK button is enabled by |
188 // waiting for chrome.test.sendMessage('selection-change-complete'). | 252 // waiting for chrome.test.sendMessage('selection-change-complete'). |
189 // The extension starts a Web Worker to read file metadata, so it may send | 253 // The extension starts a Web Worker to read file metadata, so it may send |
190 // 'selection-change-complete' before 'worker-initialized'. This is OK. | 254 // 'selection-change-complete' before 'worker-initialized'. This is OK. |
191 ExtensionTestMessageListener init_listener("worker-initialized", | 255 OpenDialog(SelectFileDialog::SELECT_OPEN_FILE, test_file, owning_window, |
192 false /* will_reply */); | 256 "selection-change-complete"); |
193 ExtensionTestMessageListener selection_listener("selection-change-complete", | |
194 false /* will_reply */); | |
195 gfx::NativeWindow owning_window = browser()->window()->GetNativeHandle(); | |
196 dialog_->SelectFile(SelectFileDialog::SELECT_OPEN_FILE, | |
197 string16() /* title */, | |
198 test_file, | |
199 NULL /* file_types */, | |
200 0 /* file_type_index */, | |
201 FILE_PATH_LITERAL("") /* default_extension */, | |
202 NULL /* source_contents */, | |
203 owning_window, | |
204 this /* params */); | |
205 LOG(INFO) << "Waiting for JavaScript initialized message."; | |
206 ASSERT_TRUE(init_listener.WaitUntilSatisfied()); | |
207 LOG(INFO) << "Waiting for JavaScript selection-change-complete message."; | |
208 ASSERT_TRUE(selection_listener.WaitUntilSatisfied()); | |
209 | 257 |
210 // Dialog should be running now. | 258 // Click open button. |
211 ASSERT_TRUE(dialog_->IsRunning(owning_window)); | 259 CloseDialog(DIALOG_BTN_OK, owning_window); |
212 | |
213 // Inject JavaScript to click the open button and wait for notification | |
214 // that the window has closed. | |
215 ui_test_utils::WindowedNotificationObserver host_destroyed( | |
216 content::NOTIFICATION_RENDER_WIDGET_HOST_DESTROYED, | |
217 content::NotificationService::AllSources()); | |
218 RenderViewHost* host = dialog_->GetRenderViewHost(); | |
219 string16 main_frame; | |
220 string16 script = ASCIIToUTF16( | |
221 "console.log(\'Test JavaScript injected.\');" | |
222 "document.querySelector('.ok').click();"); | |
223 // The file selection handler closes the dialog and does not return control | |
224 // to JavaScript, so do not wait for return values. | |
225 host->ExecuteJavascriptInWebFrame(main_frame, script); | |
226 LOG(INFO) << "Waiting for window close notification."; | |
227 host_destroyed.Wait(); | |
228 | |
229 // Dialog no longer believes it is running. | |
230 ASSERT_FALSE(dialog_->IsRunning(owning_window)); | |
231 | 260 |
232 // Listener should have been informed that the file was opened. | 261 // Listener should have been informed that the file was opened. |
233 ASSERT_TRUE(listener_->file_selected()); | 262 ASSERT_TRUE(listener_->file_selected()); |
234 ASSERT_FALSE(listener_->canceled()); | 263 ASSERT_FALSE(listener_->canceled()); |
235 ASSERT_EQ(test_file, listener_->path()); | 264 ASSERT_EQ(test_file, listener_->path()); |
236 ASSERT_EQ(this, listener_->params()); | 265 ASSERT_EQ(this, listener_->params()); |
237 } | 266 } |
238 | 267 |
239 IN_PROC_BROWSER_TEST_F(FileManagerDialogBrowserTest, SelectFileAndSave) { | 268 IN_PROC_BROWSER_TEST_F(FileManagerDialogBrowserTest, SelectFileAndSave) { |
240 // Allow the tmp directory to be mounted. We explicitly use /tmp because | 269 // Allow the tmp directory to be mounted. We explicitly use /tmp because |
241 // it it whitelisted for file system access on Chrome OS. | 270 // it it whitelisted for file system access on Chrome OS. |
242 FilePath tmp_dir("/tmp"); | 271 FilePath tmp_dir("/tmp"); |
243 AddMountPoint(tmp_dir); | 272 AddMountPoint(tmp_dir); |
244 | 273 |
245 // Create a directory with a single file in it. ScopedTempDir will delete | 274 // Create a directory with a single file in it. ScopedTempDir will delete |
246 // itself and our temp file when it goes out of scope. | 275 // itself and our temp file when it goes out of scope. |
247 ScopedTempDir scoped_temp_dir; | 276 ScopedTempDir scoped_temp_dir; |
248 ASSERT_TRUE(scoped_temp_dir.CreateUniqueTempDirUnderPath(tmp_dir)); | 277 ASSERT_TRUE(scoped_temp_dir.CreateUniqueTempDirUnderPath(tmp_dir)); |
249 FilePath temp_dir = scoped_temp_dir.path(); | 278 FilePath temp_dir = scoped_temp_dir.path(); |
250 FilePath test_file = temp_dir.AppendASCII("file_manager_test.html"); | 279 FilePath test_file = temp_dir.AppendASCII("file_manager_test.html"); |
251 | 280 |
281 gfx::NativeWindow owning_window = browser()->window()->GetNativeHandle(); | |
282 | |
252 // Spawn a dialog to save a file, providing a suggested path. | 283 // Spawn a dialog to save a file, providing a suggested path. |
253 // Ensure "Save" button is enabled by waiting for notification from | 284 // Ensure "Save" button is enabled by waiting for notification from |
254 // chrome.test.sendMessage(). | 285 // chrome.test.sendMessage(). |
255 // The extension starts a Web Worker to read file metadata, so it may send | 286 // The extension starts a Web Worker to read file metadata, so it may send |
256 // 'directory-change-complete' before 'worker-initialized'. This is OK. | 287 // 'directory-change-complete' before 'worker-initialized'. This is OK. |
257 ExtensionTestMessageListener init_listener("worker-initialized", | 288 OpenDialog(SelectFileDialog::SELECT_SAVEAS_FILE, test_file, owning_window, |
258 false /* will_reply */); | 289 "directory-change-complete"); |
259 ExtensionTestMessageListener dir_change_listener("directory-change-complete", | |
260 false /* will_reply */); | |
261 gfx::NativeWindow owning_window = browser()->window()->GetNativeHandle(); | |
262 dialog_->SelectFile(SelectFileDialog::SELECT_SAVEAS_FILE, | |
263 string16() /* title */, | |
264 test_file, | |
265 NULL /* file_types */, | |
266 0 /* file_type_index */, | |
267 FILE_PATH_LITERAL("") /* default_extension */, | |
268 NULL /* source_contents */, | |
269 owning_window, | |
270 this /* params */); | |
271 LOG(INFO) << "Waiting for JavaScript initialized message."; | |
272 ASSERT_TRUE(init_listener.WaitUntilSatisfied()); | |
273 LOG(INFO) << "Waiting for JavaScript directory-change-complete message."; | |
274 ASSERT_TRUE(dir_change_listener.WaitUntilSatisfied()); | |
275 | 290 |
276 // Dialog should be running now. | 291 // Click save button. |
277 ASSERT_TRUE(dialog_->IsRunning(owning_window)); | 292 CloseDialog(DIALOG_BTN_OK, owning_window); |
278 | |
279 // Inject JavaScript to click the save button and wait for notification | |
280 // that the window has closed. | |
281 ui_test_utils::WindowedNotificationObserver host_destroyed( | |
282 content::NOTIFICATION_RENDER_WIDGET_HOST_DESTROYED, | |
283 content::NotificationService::AllSources()); | |
284 RenderViewHost* host = dialog_->GetRenderViewHost(); | |
285 string16 main_frame; | |
286 string16 script = ASCIIToUTF16( | |
287 "console.log(\'Test JavaScript injected.\');" | |
288 "document.querySelector('.ok').click();"); | |
289 // The file selection handler closes the dialog and does not return control | |
290 // to JavaScript, so do not wait for return values. | |
291 host->ExecuteJavascriptInWebFrame(main_frame, script); | |
292 LOG(INFO) << "Waiting for window close notification."; | |
293 host_destroyed.Wait(); | |
294 | |
295 // Dialog no longer believes it is running. | |
296 ASSERT_FALSE(dialog_->IsRunning(owning_window)); | |
297 | 293 |
298 // Listener should have been informed that the file was selected. | 294 // Listener should have been informed that the file was selected. |
299 ASSERT_TRUE(listener_->file_selected()); | 295 ASSERT_TRUE(listener_->file_selected()); |
300 ASSERT_FALSE(listener_->canceled()); | 296 ASSERT_FALSE(listener_->canceled()); |
301 ASSERT_EQ(test_file, listener_->path()); | 297 ASSERT_EQ(test_file, listener_->path()); |
302 ASSERT_EQ(this, listener_->params()); | 298 ASSERT_EQ(this, listener_->params()); |
303 } | 299 } |
304 | 300 |
305 IN_PROC_BROWSER_TEST_F(FileManagerDialogBrowserTest, | 301 IN_PROC_BROWSER_TEST_F(FileManagerDialogBrowserTest, |
306 OpenSingletonTabAndCancel) { | 302 OpenSingletonTabAndCancel) { |
307 // Add tmp mount point even though this test won't use it directly. | 303 // Add tmp mount point even though this test won't use it directly. |
308 // We need this to make sure that at least one top-level directory exists | 304 // We need this to make sure that at least one top-level directory exists |
309 // in the file browser. | 305 // in the file browser. |
310 FilePath tmp_dir("/tmp"); | 306 FilePath tmp_dir("/tmp"); |
311 AddMountPoint(tmp_dir); | 307 AddMountPoint(tmp_dir); |
312 | 308 |
313 // Spawn a dialog to open a file. The dialog will signal that it is ready | |
314 // via chrome.test.sendMessage() in the extension JavaScript. | |
315 ExtensionTestMessageListener init_listener("worker-initialized", | |
316 false /* will_reply */); | |
317 gfx::NativeWindow owning_window = browser()->window()->GetNativeHandle(); | 309 gfx::NativeWindow owning_window = browser()->window()->GetNativeHandle(); |
318 dialog_->SelectFile(SelectFileDialog::SELECT_OPEN_FILE, | |
319 string16() /* title */, | |
320 FilePath() /* default_path */, | |
321 NULL /* file_types */, | |
322 0 /* file_type_index */, | |
323 FILE_PATH_LITERAL("") /* default_extension */, | |
324 NULL /* source_contents */, | |
325 owning_window, | |
326 this /* params */); | |
327 LOG(INFO) << "Waiting for JavaScript ready message."; | |
328 ASSERT_TRUE(init_listener.WaitUntilSatisfied()); | |
329 | 310 |
330 // Dialog should be running now. | 311 OpenDialog(SelectFileDialog::SELECT_OPEN_FILE, FilePath(), owning_window, ""); |
331 ASSERT_TRUE(dialog_->IsRunning(owning_window)); | |
332 | 312 |
333 // Open a singleton tab in background. | 313 // Open a singleton tab in background. |
334 browser::NavigateParams p(browser(), GURL("www.google.com"), | 314 browser::NavigateParams p(browser(), GURL("www.google.com"), |
335 content::PAGE_TRANSITION_LINK); | 315 content::PAGE_TRANSITION_LINK); |
336 p.window_action = browser::NavigateParams::SHOW_WINDOW; | 316 p.window_action = browser::NavigateParams::SHOW_WINDOW; |
337 p.disposition = SINGLETON_TAB; | 317 p.disposition = SINGLETON_TAB; |
338 browser::Navigate(&p); | 318 browser::Navigate(&p); |
339 | 319 |
340 // Inject JavaScript to click the cancel button and wait for notification | 320 // Press cancel button. |
341 // that the window has closed. | 321 CloseDialog(DIALOG_BTN_CANCEL, owning_window); |
342 ui_test_utils::WindowedNotificationObserver host_destroyed( | |
343 content::NOTIFICATION_RENDER_WIDGET_HOST_DESTROYED, | |
344 content::NotificationService::AllSources()); | |
345 RenderViewHost* host = dialog_->GetRenderViewHost(); | |
346 string16 main_frame; | |
347 string16 script = ASCIIToUTF16( | |
348 "console.log(\'Test JavaScript injected.\');" | |
349 "document.querySelector(\'.cancel\').click();"); | |
350 // The file selection handler closes the dialog and does not return control | |
351 // to JavaScript, so do not wait for return values. | |
352 host->ExecuteJavascriptInWebFrame(main_frame, script); | |
353 LOG(INFO) << "Waiting for window close notification."; | |
354 host_destroyed.Wait(); | |
355 | |
356 // Dialog no longer believes it is running. | |
357 ASSERT_FALSE(dialog_->IsRunning(owning_window)); | |
358 | 322 |
359 // Listener should have been informed of the cancellation. | 323 // Listener should have been informed of the cancellation. |
360 ASSERT_FALSE(listener_->file_selected()); | 324 ASSERT_FALSE(listener_->file_selected()); |
325 ASSERT_TRUE(listener_->canceled()); | |
326 ASSERT_EQ(this, listener_->params()); | |
327 } | |
328 | |
329 IN_PROC_BROWSER_TEST_F(FileManagerDialogBrowserTest, OpenTwoDialogs) { | |
330 // Add tmp mount point even though this test won't use it directly. | |
331 // We need this to make sure that at least one top-level directory exists | |
332 // in the file browser. | |
333 FilePath tmp_dir("/tmp"); | |
334 AddMountPoint(tmp_dir); | |
335 | |
336 gfx::NativeWindow owning_window = browser()->window()->GetNativeHandle(); | |
337 | |
338 OpenDialog(SelectFileDialog::SELECT_OPEN_FILE, FilePath(), owning_window, ""); | |
339 | |
340 TryOpeningSecondDialog(owning_window); | |
341 | |
342 // Second dialog should not be running. | |
343 ASSERT_FALSE(second_dialog_->IsRunning(owning_window)); | |
344 | |
345 // Click cancel button. | |
346 CloseDialog(DIALOG_BTN_CANCEL, owning_window); | |
347 | |
348 // Listener should have been informed of the cancellation. | |
349 ASSERT_FALSE(listener_->file_selected()); | |
361 ASSERT_TRUE(listener_->canceled()); | 350 ASSERT_TRUE(listener_->canceled()); |
362 ASSERT_EQ(this, listener_->params()); | 351 ASSERT_EQ(this, listener_->params()); |
363 } | 352 } |
OLD | NEW |