OLD | NEW |
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 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 | 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/app_modal_dialogs/javascript_dialog_creator.h" | 5 #include "chrome/browser/ui/app_modal_dialogs/javascript_dialog_manager.h" |
6 | 6 |
7 #include <map> | 7 #include <map> |
8 | 8 |
9 #include "base/compiler_specific.h" | 9 #include "base/compiler_specific.h" |
10 #include "base/i18n/rtl.h" | 10 #include "base/i18n/rtl.h" |
11 #include "base/memory/singleton.h" | 11 #include "base/memory/singleton.h" |
12 #include "base/utf_string_conversions.h" | 12 #include "base/utf_string_conversions.h" |
13 #include "chrome/browser/extensions/extension_host.h" | 13 #include "chrome/browser/extensions/extension_host.h" |
14 #include "chrome/browser/extensions/extension_service.h" | 14 #include "chrome/browser/extensions/extension_service.h" |
15 #include "chrome/browser/ui/app_modal_dialogs/app_modal_dialog_queue.h" | 15 #include "chrome/browser/ui/app_modal_dialogs/app_modal_dialog_queue.h" |
16 #include "chrome/browser/ui/app_modal_dialogs/javascript_app_modal_dialog.h" | 16 #include "chrome/browser/ui/app_modal_dialogs/javascript_app_modal_dialog.h" |
17 #include "chrome/common/chrome_constants.h" | 17 #include "chrome/common/chrome_constants.h" |
18 #include "chrome/common/chrome_notification_types.h" | 18 #include "chrome/common/chrome_notification_types.h" |
19 #include "content/public/browser/notification_observer.h" | 19 #include "content/public/browser/notification_observer.h" |
20 #include "content/public/browser/notification_registrar.h" | 20 #include "content/public/browser/notification_registrar.h" |
21 #include "content/public/browser/notification_service.h" | 21 #include "content/public/browser/notification_service.h" |
22 #include "content/public/common/content_client.h" | 22 #include "content/public/common/content_client.h" |
23 #include "content/public/common/javascript_message_type.h" | 23 #include "content/public/common/javascript_message_type.h" |
24 #include "grit/generated_resources.h" | 24 #include "grit/generated_resources.h" |
25 #include "net/base/net_util.h" | 25 #include "net/base/net_util.h" |
26 #include "ui/base/l10n/l10n_util.h" | 26 #include "ui/base/l10n/l10n_util.h" |
27 | 27 |
28 using content::JavaScriptDialogCreator; | 28 using content::JavaScriptDialogManager; |
29 using content::WebContents; | 29 using content::WebContents; |
30 | 30 |
31 namespace { | 31 namespace { |
32 | 32 |
33 class ChromeJavaScriptDialogCreator : public JavaScriptDialogCreator, | 33 class ChromeJavaScriptDialogManager : public JavaScriptDialogManager, |
34 public content::NotificationObserver { | 34 public content::NotificationObserver { |
35 public: | 35 public: |
36 static ChromeJavaScriptDialogCreator* GetInstance(); | 36 static ChromeJavaScriptDialogManager* GetInstance(); |
37 | 37 |
38 explicit ChromeJavaScriptDialogCreator( | 38 explicit ChromeJavaScriptDialogManager( |
39 extensions::ExtensionHost* extension_host); | 39 extensions::ExtensionHost* extension_host); |
40 virtual ~ChromeJavaScriptDialogCreator(); | 40 virtual ~ChromeJavaScriptDialogManager(); |
41 | 41 |
42 virtual void RunJavaScriptDialog( | 42 virtual void RunJavaScriptDialog( |
43 WebContents* web_contents, | 43 WebContents* web_contents, |
44 const GURL& origin_url, | 44 const GURL& origin_url, |
45 const std::string& accept_lang, | 45 const std::string& accept_lang, |
46 content::JavaScriptMessageType message_type, | 46 content::JavaScriptMessageType message_type, |
47 const string16& message_text, | 47 const string16& message_text, |
48 const string16& default_prompt_text, | 48 const string16& default_prompt_text, |
49 const DialogClosedCallback& callback, | 49 const DialogClosedCallback& callback, |
50 bool* did_suppress_message) OVERRIDE; | 50 bool* did_suppress_message) OVERRIDE; |
51 | 51 |
52 virtual void RunBeforeUnloadDialog( | 52 virtual void RunBeforeUnloadDialog( |
53 WebContents* web_contents, | 53 WebContents* web_contents, |
54 const string16& message_text, | 54 const string16& message_text, |
55 bool is_reload, | 55 bool is_reload, |
56 const DialogClosedCallback& callback) OVERRIDE; | 56 const DialogClosedCallback& callback) OVERRIDE; |
57 | 57 |
58 virtual void ResetJavaScriptState(WebContents* web_contents) OVERRIDE; | 58 virtual void ResetJavaScriptState(WebContents* web_contents) OVERRIDE; |
59 | 59 |
60 private: | 60 private: |
61 ChromeJavaScriptDialogCreator(); | 61 ChromeJavaScriptDialogManager(); |
62 | 62 |
63 friend struct DefaultSingletonTraits<ChromeJavaScriptDialogCreator>; | 63 friend struct DefaultSingletonTraits<ChromeJavaScriptDialogManager>; |
64 | 64 |
65 // Overridden from content::NotificationObserver: | 65 // Overridden from content::NotificationObserver: |
66 virtual void Observe(int type, | 66 virtual void Observe(int type, |
67 const content::NotificationSource& source, | 67 const content::NotificationSource& source, |
68 const content::NotificationDetails& details) OVERRIDE; | 68 const content::NotificationDetails& details) OVERRIDE; |
69 | 69 |
70 string16 GetTitle(const GURL& origin_url, | 70 string16 GetTitle(const GURL& origin_url, |
71 const std::string& accept_lang, | 71 const std::string& accept_lang, |
72 bool is_alert); | 72 bool is_alert); |
73 | 73 |
74 void CancelPendingDialogs(WebContents* web_contents); | 74 void CancelPendingDialogs(WebContents* web_contents); |
75 | 75 |
76 // Wrapper around a DialogClosedCallback so that we can intercept it before | 76 // Wrapper around a DialogClosedCallback so that we can intercept it before |
77 // passing it onto the original callback. | 77 // passing it onto the original callback. |
78 void OnDialogClosed(DialogClosedCallback callback, | 78 void OnDialogClosed(DialogClosedCallback callback, |
79 bool success, | 79 bool success, |
80 const string16& user_input); | 80 const string16& user_input); |
81 | 81 |
82 // Mapping between the WebContents and their extra data. The key | 82 // Mapping between the WebContents and their extra data. The key |
83 // is a void* because the pointer is just a cookie and is never dereferenced. | 83 // is a void* because the pointer is just a cookie and is never dereferenced. |
84 typedef std::map<void*, ChromeJavaScriptDialogExtraData> | 84 typedef std::map<void*, ChromeJavaScriptDialogExtraData> |
85 JavaScriptDialogExtraDataMap; | 85 JavaScriptDialogExtraDataMap; |
86 JavaScriptDialogExtraDataMap javascript_dialog_extra_data_; | 86 JavaScriptDialogExtraDataMap javascript_dialog_extra_data_; |
87 | 87 |
88 // Extension Host which owns the ChromeJavaScriptDialogCreator instance. | 88 // Extension Host which owns the ChromeJavaScriptDialogManager instance. |
89 // It's used to get a extension name from a URL. | 89 // It's used to get a extension name from a URL. |
90 // If it's not owned by any Extension, it should be NULL. | 90 // If it's not owned by any Extension, it should be NULL. |
91 extensions::ExtensionHost* extension_host_; | 91 extensions::ExtensionHost* extension_host_; |
92 | 92 |
93 content::NotificationRegistrar registrar_; | 93 content::NotificationRegistrar registrar_; |
94 | 94 |
95 DISALLOW_COPY_AND_ASSIGN(ChromeJavaScriptDialogCreator); | 95 DISALLOW_COPY_AND_ASSIGN(ChromeJavaScriptDialogManager); |
96 }; | 96 }; |
97 | 97 |
98 //////////////////////////////////////////////////////////////////////////////// | 98 //////////////////////////////////////////////////////////////////////////////// |
99 // ChromeJavaScriptDialogCreator, public: | 99 // ChromeJavaScriptDialogManager, public: |
100 | 100 |
101 ChromeJavaScriptDialogCreator::ChromeJavaScriptDialogCreator() | 101 ChromeJavaScriptDialogManager::ChromeJavaScriptDialogManager() |
102 : extension_host_(NULL) { | 102 : extension_host_(NULL) { |
103 } | 103 } |
104 | 104 |
105 ChromeJavaScriptDialogCreator::~ChromeJavaScriptDialogCreator() { | 105 ChromeJavaScriptDialogManager::~ChromeJavaScriptDialogManager() { |
106 extension_host_ = NULL; | 106 extension_host_ = NULL; |
107 } | 107 } |
108 | 108 |
109 ChromeJavaScriptDialogCreator::ChromeJavaScriptDialogCreator( | 109 ChromeJavaScriptDialogManager::ChromeJavaScriptDialogManager( |
110 extensions::ExtensionHost* extension_host) | 110 extensions::ExtensionHost* extension_host) |
111 : extension_host_(extension_host) { | 111 : extension_host_(extension_host) { |
112 registrar_.Add(this, chrome::NOTIFICATION_EXTENSION_HOST_DESTROYED, | 112 registrar_.Add(this, chrome::NOTIFICATION_EXTENSION_HOST_DESTROYED, |
113 content::Source<Profile>(extension_host_->profile())); | 113 content::Source<Profile>(extension_host_->profile())); |
114 } | 114 } |
115 | 115 |
116 // static | 116 // static |
117 ChromeJavaScriptDialogCreator* ChromeJavaScriptDialogCreator::GetInstance() { | 117 ChromeJavaScriptDialogManager* ChromeJavaScriptDialogManager::GetInstance() { |
118 return Singleton<ChromeJavaScriptDialogCreator>::get(); | 118 return Singleton<ChromeJavaScriptDialogManager>::get(); |
119 } | 119 } |
120 | 120 |
121 void ChromeJavaScriptDialogCreator::RunJavaScriptDialog( | 121 void ChromeJavaScriptDialogManager::RunJavaScriptDialog( |
122 WebContents* web_contents, | 122 WebContents* web_contents, |
123 const GURL& origin_url, | 123 const GURL& origin_url, |
124 const std::string& accept_lang, | 124 const std::string& accept_lang, |
125 content::JavaScriptMessageType message_type, | 125 content::JavaScriptMessageType message_type, |
126 const string16& message_text, | 126 const string16& message_text, |
127 const string16& default_prompt_text, | 127 const string16& default_prompt_text, |
128 const DialogClosedCallback& callback, | 128 const DialogClosedCallback& callback, |
129 bool* did_suppress_message) { | 129 bool* did_suppress_message) { |
130 *did_suppress_message = false; | 130 *did_suppress_message = false; |
131 | 131 |
(...skipping 25 matching lines...) Expand all Loading... |
157 AppModalDialogQueue::GetInstance()->AddDialog(new JavaScriptAppModalDialog( | 157 AppModalDialogQueue::GetInstance()->AddDialog(new JavaScriptAppModalDialog( |
158 web_contents, | 158 web_contents, |
159 extra_data, | 159 extra_data, |
160 dialog_title, | 160 dialog_title, |
161 message_type, | 161 message_type, |
162 message_text, | 162 message_text, |
163 default_prompt_text, | 163 default_prompt_text, |
164 display_suppress_checkbox, | 164 display_suppress_checkbox, |
165 false, // is_before_unload_dialog | 165 false, // is_before_unload_dialog |
166 false, // is_reload | 166 false, // is_reload |
167 base::Bind(&ChromeJavaScriptDialogCreator::OnDialogClosed, | 167 base::Bind(&ChromeJavaScriptDialogManager::OnDialogClosed, |
168 base::Unretained(this), callback))); | 168 base::Unretained(this), callback))); |
169 } | 169 } |
170 | 170 |
171 void ChromeJavaScriptDialogCreator::RunBeforeUnloadDialog( | 171 void ChromeJavaScriptDialogManager::RunBeforeUnloadDialog( |
172 WebContents* web_contents, | 172 WebContents* web_contents, |
173 const string16& message_text, | 173 const string16& message_text, |
174 bool is_reload, | 174 bool is_reload, |
175 const DialogClosedCallback& callback) { | 175 const DialogClosedCallback& callback) { |
176 ChromeJavaScriptDialogExtraData* extra_data = | 176 ChromeJavaScriptDialogExtraData* extra_data = |
177 &javascript_dialog_extra_data_[web_contents]; | 177 &javascript_dialog_extra_data_[web_contents]; |
178 | 178 |
179 const string16 title = l10n_util::GetStringUTF16(is_reload ? | 179 const string16 title = l10n_util::GetStringUTF16(is_reload ? |
180 IDS_BEFORERELOAD_MESSAGEBOX_TITLE : IDS_BEFOREUNLOAD_MESSAGEBOX_TITLE); | 180 IDS_BEFORERELOAD_MESSAGEBOX_TITLE : IDS_BEFOREUNLOAD_MESSAGEBOX_TITLE); |
181 const string16 footer = l10n_util::GetStringUTF16(is_reload ? | 181 const string16 footer = l10n_util::GetStringUTF16(is_reload ? |
182 IDS_BEFORERELOAD_MESSAGEBOX_FOOTER : IDS_BEFOREUNLOAD_MESSAGEBOX_FOOTER); | 182 IDS_BEFORERELOAD_MESSAGEBOX_FOOTER : IDS_BEFOREUNLOAD_MESSAGEBOX_FOOTER); |
183 | 183 |
184 string16 full_message = message_text + ASCIIToUTF16("\n\n") + footer; | 184 string16 full_message = message_text + ASCIIToUTF16("\n\n") + footer; |
185 | 185 |
186 if (extension_host_) | 186 if (extension_host_) |
187 extension_host_->WillRunJavaScriptDialog(); | 187 extension_host_->WillRunJavaScriptDialog(); |
188 | 188 |
189 AppModalDialogQueue::GetInstance()->AddDialog(new JavaScriptAppModalDialog( | 189 AppModalDialogQueue::GetInstance()->AddDialog(new JavaScriptAppModalDialog( |
190 web_contents, | 190 web_contents, |
191 extra_data, | 191 extra_data, |
192 title, | 192 title, |
193 content::JAVASCRIPT_MESSAGE_TYPE_CONFIRM, | 193 content::JAVASCRIPT_MESSAGE_TYPE_CONFIRM, |
194 full_message, | 194 full_message, |
195 string16(), // default_prompt_text | 195 string16(), // default_prompt_text |
196 false, // display_suppress_checkbox | 196 false, // display_suppress_checkbox |
197 true, // is_before_unload_dialog | 197 true, // is_before_unload_dialog |
198 is_reload, | 198 is_reload, |
199 base::Bind(&ChromeJavaScriptDialogCreator::OnDialogClosed, | 199 base::Bind(&ChromeJavaScriptDialogManager::OnDialogClosed, |
200 base::Unretained(this), callback))); | 200 base::Unretained(this), callback))); |
201 } | 201 } |
202 | 202 |
203 void ChromeJavaScriptDialogCreator::ResetJavaScriptState( | 203 void ChromeJavaScriptDialogManager::ResetJavaScriptState( |
204 WebContents* web_contents) { | 204 WebContents* web_contents) { |
205 CancelPendingDialogs(web_contents); | 205 CancelPendingDialogs(web_contents); |
206 javascript_dialog_extra_data_.erase(web_contents); | 206 javascript_dialog_extra_data_.erase(web_contents); |
207 } | 207 } |
208 | 208 |
209 void ChromeJavaScriptDialogCreator::Observe( | 209 void ChromeJavaScriptDialogManager::Observe( |
210 int type, | 210 int type, |
211 const content::NotificationSource& source, | 211 const content::NotificationSource& source, |
212 const content::NotificationDetails& details) { | 212 const content::NotificationDetails& details) { |
213 DCHECK_EQ(type, chrome::NOTIFICATION_EXTENSION_HOST_DESTROYED); | 213 DCHECK_EQ(type, chrome::NOTIFICATION_EXTENSION_HOST_DESTROYED); |
214 extension_host_ = NULL; | 214 extension_host_ = NULL; |
215 } | 215 } |
216 | 216 |
217 string16 ChromeJavaScriptDialogCreator::GetTitle(const GURL& origin_url, | 217 string16 ChromeJavaScriptDialogManager::GetTitle(const GURL& origin_url, |
218 const std::string& accept_lang, | 218 const std::string& accept_lang, |
219 bool is_alert) { | 219 bool is_alert) { |
220 // If the URL hasn't any host, return the default string. | 220 // If the URL hasn't any host, return the default string. |
221 if (!origin_url.has_host()) { | 221 if (!origin_url.has_host()) { |
222 return l10n_util::GetStringUTF16( | 222 return l10n_util::GetStringUTF16( |
223 is_alert ? IDS_JAVASCRIPT_ALERT_DEFAULT_TITLE | 223 is_alert ? IDS_JAVASCRIPT_ALERT_DEFAULT_TITLE |
224 : IDS_JAVASCRIPT_MESSAGEBOX_DEFAULT_TITLE); | 224 : IDS_JAVASCRIPT_MESSAGEBOX_DEFAULT_TITLE); |
225 } | 225 } |
226 | 226 |
227 // If the URL is a chrome extension one, return the extension name. | 227 // If the URL is a chrome extension one, return the extension name. |
228 if (extension_host_) { | 228 if (extension_host_) { |
229 const extensions::Extension* extension = extension_host_-> | 229 const extensions::Extension* extension = extension_host_-> |
230 profile()->GetExtensionService()->extensions()-> | 230 profile()->GetExtensionService()->extensions()-> |
231 GetExtensionOrAppByURL(ExtensionURLInfo(origin_url)); | 231 GetExtensionOrAppByURL(ExtensionURLInfo(origin_url)); |
232 if (extension) { | 232 if (extension) { |
233 return UTF8ToUTF16(base::StringPiece(extension->name())); | 233 return UTF8ToUTF16(base::StringPiece(extension->name())); |
234 } | 234 } |
235 } | 235 } |
236 | 236 |
237 // Otherwise, return the formatted URL. | 237 // Otherwise, return the formatted URL. |
238 // In this case, force URL to have LTR directionality. | 238 // In this case, force URL to have LTR directionality. |
239 string16 url_string = net::FormatUrl(origin_url, accept_lang); | 239 string16 url_string = net::FormatUrl(origin_url, accept_lang); |
240 return l10n_util::GetStringFUTF16( | 240 return l10n_util::GetStringFUTF16( |
241 is_alert ? IDS_JAVASCRIPT_ALERT_TITLE | 241 is_alert ? IDS_JAVASCRIPT_ALERT_TITLE |
242 : IDS_JAVASCRIPT_MESSAGEBOX_TITLE, | 242 : IDS_JAVASCRIPT_MESSAGEBOX_TITLE, |
243 base::i18n::GetDisplayStringInLTRDirectionality(url_string)); | 243 base::i18n::GetDisplayStringInLTRDirectionality(url_string)); |
244 } | 244 } |
245 | 245 |
246 void ChromeJavaScriptDialogCreator::CancelPendingDialogs( | 246 void ChromeJavaScriptDialogManager::CancelPendingDialogs( |
247 WebContents* web_contents) { | 247 WebContents* web_contents) { |
248 AppModalDialogQueue* queue = AppModalDialogQueue::GetInstance(); | 248 AppModalDialogQueue* queue = AppModalDialogQueue::GetInstance(); |
249 AppModalDialog* active_dialog = queue->active_dialog(); | 249 AppModalDialog* active_dialog = queue->active_dialog(); |
250 if (active_dialog && active_dialog->web_contents() == web_contents) | 250 if (active_dialog && active_dialog->web_contents() == web_contents) |
251 active_dialog->Invalidate(); | 251 active_dialog->Invalidate(); |
252 for (AppModalDialogQueue::iterator i = queue->begin(); | 252 for (AppModalDialogQueue::iterator i = queue->begin(); |
253 i != queue->end(); ++i) { | 253 i != queue->end(); ++i) { |
254 if ((*i)->web_contents() == web_contents) | 254 if ((*i)->web_contents() == web_contents) |
255 (*i)->Invalidate(); | 255 (*i)->Invalidate(); |
256 } | 256 } |
257 } | 257 } |
258 | 258 |
259 void ChromeJavaScriptDialogCreator::OnDialogClosed( | 259 void ChromeJavaScriptDialogManager::OnDialogClosed( |
260 DialogClosedCallback callback, | 260 DialogClosedCallback callback, |
261 bool success, | 261 bool success, |
262 const string16& user_input) { | 262 const string16& user_input) { |
263 if (extension_host_) | 263 if (extension_host_) |
264 extension_host_->DidCloseJavaScriptDialog(); | 264 extension_host_->DidCloseJavaScriptDialog(); |
265 callback.Run(success, user_input); | 265 callback.Run(success, user_input); |
266 } | 266 } |
267 | 267 |
268 } // namespace | 268 } // namespace |
269 | 269 |
270 content::JavaScriptDialogCreator* GetJavaScriptDialogCreatorInstance() { | 270 content::JavaScriptDialogManager* GetJavaScriptDialogManagerInstance() { |
271 return ChromeJavaScriptDialogCreator::GetInstance(); | 271 return ChromeJavaScriptDialogManager::GetInstance(); |
272 } | 272 } |
273 | 273 |
274 content::JavaScriptDialogCreator* CreateJavaScriptDialogCreatorInstance( | 274 content::JavaScriptDialogManager* CreateJavaScriptDialogManagerInstance( |
275 extensions::ExtensionHost* extension_host) { | 275 extensions::ExtensionHost* extension_host) { |
276 return new ChromeJavaScriptDialogCreator(extension_host); | 276 return new ChromeJavaScriptDialogManager(extension_host); |
277 } | 277 } |
OLD | NEW |