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/google/google_url_tracker.h" | 5 #include "chrome/browser/google/google_url_tracker.h" |
6 | 6 |
7 #include <vector> | 7 #include <vector> |
8 | 8 |
9 #include "base/bind.h" | 9 #include "base/bind.h" |
10 #include "base/command_line.h" | 10 #include "base/command_line.h" |
(...skipping 14 matching lines...) Expand all Loading... | |
25 #include "content/public/browser/notification_service.h" | 25 #include "content/public/browser/notification_service.h" |
26 #include "content/public/browser/web_contents.h" | 26 #include "content/public/browser/web_contents.h" |
27 #include "content/public/common/url_fetcher.h" | 27 #include "content/public/common/url_fetcher.h" |
28 #include "grit/generated_resources.h" | 28 #include "grit/generated_resources.h" |
29 #include "net/base/load_flags.h" | 29 #include "net/base/load_flags.h" |
30 #include "net/base/net_util.h" | 30 #include "net/base/net_util.h" |
31 #include "net/url_request/url_request_context_getter.h" | 31 #include "net/url_request/url_request_context_getter.h" |
32 #include "net/url_request/url_request_status.h" | 32 #include "net/url_request/url_request_status.h" |
33 #include "ui/base/l10n/l10n_util.h" | 33 #include "ui/base/l10n/l10n_util.h" |
34 | 34 |
35 using content::NavigationController; | |
36 using content::OpenURLParams; | |
37 using content::Referrer; | |
38 using content::WebContents; | |
39 | |
40 namespace { | 35 namespace { |
41 | 36 |
42 InfoBarDelegate* CreateInfoBar(InfoBarTabHelper* infobar_helper, | 37 GoogleURLTrackerInfoBarDelegate* CreateInfoBar( |
43 GoogleURLTracker* google_url_tracker, | 38 InfoBarTabHelper* infobar_helper, |
44 const GURL& new_google_url) { | 39 const GURL& search_url, |
45 InfoBarDelegate* infobar = new GoogleURLTrackerInfoBarDelegate(infobar_helper, | 40 GoogleURLTracker* google_url_tracker, |
41 const GURL& new_google_url) { | |
42 return new GoogleURLTrackerInfoBarDelegate(infobar_helper, search_url, | |
46 google_url_tracker, new_google_url); | 43 google_url_tracker, new_google_url); |
47 infobar_helper->AddInfoBar(infobar); | |
48 return infobar; | |
49 } | 44 } |
50 | 45 |
51 } // namespace | 46 } // namespace |
52 | 47 |
53 // GoogleURLTrackerInfoBarDelegate -------------------------------------------- | 48 // GoogleURLTrackerInfoBarDelegate -------------------------------------------- |
54 | 49 |
55 GoogleURLTrackerInfoBarDelegate::GoogleURLTrackerInfoBarDelegate( | 50 GoogleURLTrackerInfoBarDelegate::GoogleURLTrackerInfoBarDelegate( |
56 InfoBarTabHelper* infobar_helper, | 51 InfoBarTabHelper* infobar_helper, |
52 const GURL& search_url, | |
57 GoogleURLTracker* google_url_tracker, | 53 GoogleURLTracker* google_url_tracker, |
58 const GURL& new_google_url) | 54 const GURL& new_google_url) |
59 : ConfirmInfoBarDelegate(infobar_helper), | 55 : ConfirmInfoBarDelegate(infobar_helper), |
56 map_key_(infobar_helper), | |
57 search_url_(search_url), | |
60 google_url_tracker_(google_url_tracker), | 58 google_url_tracker_(google_url_tracker), |
61 new_google_url_(new_google_url) { | 59 new_google_url_(new_google_url), |
60 showing_(false) { | |
62 } | 61 } |
63 | 62 |
64 bool GoogleURLTrackerInfoBarDelegate::Accept() { | 63 bool GoogleURLTrackerInfoBarDelegate::Accept() { |
65 google_url_tracker_->AcceptGoogleURL(new_google_url_); | 64 google_url_tracker_->AcceptGoogleURL(new_google_url_); |
66 google_url_tracker_->RedoSearch(); | 65 return false; |
67 return true; | |
68 } | 66 } |
69 | 67 |
70 bool GoogleURLTrackerInfoBarDelegate::Cancel() { | 68 bool GoogleURLTrackerInfoBarDelegate::Cancel() { |
71 google_url_tracker_->CancelGoogleURL(new_google_url_); | 69 google_url_tracker_->CancelGoogleURL(new_google_url_); |
72 return true; | 70 return false; |
73 } | 71 } |
74 | 72 |
75 string16 GoogleURLTrackerInfoBarDelegate::GetLinkText() const { | 73 string16 GoogleURLTrackerInfoBarDelegate::GetLinkText() const { |
76 return l10n_util::GetStringUTF16(IDS_LEARN_MORE); | 74 return l10n_util::GetStringUTF16(IDS_LEARN_MORE); |
77 } | 75 } |
78 | 76 |
79 bool GoogleURLTrackerInfoBarDelegate::LinkClicked( | 77 bool GoogleURLTrackerInfoBarDelegate::LinkClicked( |
80 WindowOpenDisposition disposition) { | 78 WindowOpenDisposition disposition) { |
81 OpenURLParams params( | 79 content::OpenURLParams params(google_util::AppendGoogleLocaleParam(GURL( |
82 google_util::AppendGoogleLocaleParam(GURL( | 80 "https://www.google.com/support/chrome/bin/answer.py?answer=1618699")), |
83 "https://www.google.com/support/chrome/bin/answer.py?answer=1618699")) , | 81 content::Referrer(), |
84 Referrer(), | |
85 (disposition == CURRENT_TAB) ? NEW_FOREGROUND_TAB : disposition, | 82 (disposition == CURRENT_TAB) ? NEW_FOREGROUND_TAB : disposition, |
86 content::PAGE_TRANSITION_LINK, false); | 83 content::PAGE_TRANSITION_LINK, false); |
87 owner()->web_contents()->OpenURL(params); | 84 owner()->web_contents()->OpenURL(params); |
88 return false; | 85 return false; |
89 } | 86 } |
90 | 87 |
88 void GoogleURLTrackerInfoBarDelegate::Show() { | |
89 owner()->AddInfoBar(this); | |
90 showing_ = true; | |
91 } | |
92 | |
93 void GoogleURLTrackerInfoBarDelegate::Close(bool redo_search) { | |
94 if (!showing_) { | |
95 // We haven't been added to a tab, so just delete ourselves. | |
96 delete this; | |
97 return; | |
98 } | |
99 | |
100 // Synchronously remove ourselves from the URL tracker's list, because the | |
101 // RemoveInfoBar() call below may result in either a synchronous or an | |
102 // asynchronous call back to InfoBarClosed(), and it's easier to handle when | |
103 // we just guarantee the removal is synchronous. | |
104 google_url_tracker_->InfoBarClosed(map_key_); | |
105 google_url_tracker_ = NULL; | |
106 | |
107 // If we were showing in a background tab that was then closed, we could have | |
108 // been leaked, and subsequently reached here due to | |
109 // GoogleURLTracker::CloseAllInfoBars(). In this case our owner is now NULL | |
110 // so we should just do nothing. | |
111 // TODO(pkasting): This can go away once the InfoBar ownership model is fixed | |
112 // so that infobars in background tabs don't leak on tab closure. | |
Ilya Sherman
2012/04/24 00:30:47
nit: Is there a bug tracking this that we could li
| |
113 if (!owner()) | |
114 return; | |
115 | |
116 if (redo_search) { | |
117 // Re-do the user's search on the new domain. | |
118 url_canon::Replacements<char> replacements; | |
119 const std::string& host(new_google_url_.host()); | |
120 replacements.SetHost(host.data(), url_parse::Component(0, host.length())); | |
121 GURL new_search_url(search_url_.ReplaceComponents(replacements)); | |
122 if (new_search_url.is_valid()) { | |
123 content::OpenURLParams params(new_search_url, content::Referrer(), | |
124 CURRENT_TAB, content::PAGE_TRANSITION_GENERATED, false); | |
125 owner()->web_contents()->OpenURL(params); | |
126 } | |
127 } | |
128 | |
129 owner()->RemoveInfoBar(this); | |
130 } | |
131 | |
91 GoogleURLTrackerInfoBarDelegate::~GoogleURLTrackerInfoBarDelegate() { | 132 GoogleURLTrackerInfoBarDelegate::~GoogleURLTrackerInfoBarDelegate() { |
92 google_url_tracker_->InfoBarClosed(); | 133 if (google_url_tracker_) |
Ilya Sherman
2012/04/24 00:30:47
nit: Should this also check the state of |showing_
Peter Kasting
2012/04/24 01:53:01
No. The infobar is present in the tracker's map r
| |
134 google_url_tracker_->InfoBarClosed(map_key_); | |
93 } | 135 } |
94 | 136 |
95 string16 GoogleURLTrackerInfoBarDelegate::GetMessageText() const { | 137 string16 GoogleURLTrackerInfoBarDelegate::GetMessageText() const { |
96 return l10n_util::GetStringFUTF16(IDS_GOOGLE_URL_TRACKER_INFOBAR_MESSAGE, | 138 return l10n_util::GetStringFUTF16(IDS_GOOGLE_URL_TRACKER_INFOBAR_MESSAGE, |
97 GetHost(true), GetHost(false)); | 139 GetHost(true), GetHost(false)); |
98 } | 140 } |
99 | 141 |
100 string16 GoogleURLTrackerInfoBarDelegate::GetButtonLabel( | 142 string16 GoogleURLTrackerInfoBarDelegate::GetButtonLabel( |
101 InfoBarButton button) const { | 143 InfoBarButton button) const { |
102 bool new_host = (button == BUTTON_OK); | 144 bool new_host = (button == BUTTON_OK); |
(...skipping 18 matching lines...) Expand all Loading... | |
121 GoogleURLTracker::GoogleURLTracker(Mode mode) | 163 GoogleURLTracker::GoogleURLTracker(Mode mode) |
122 : infobar_creator_(&CreateInfoBar), | 164 : infobar_creator_(&CreateInfoBar), |
123 google_url_(mode == UNIT_TEST_MODE ? kDefaultGoogleHomepage : | 165 google_url_(mode == UNIT_TEST_MODE ? kDefaultGoogleHomepage : |
124 g_browser_process->local_state()->GetString( | 166 g_browser_process->local_state()->GetString( |
125 prefs::kLastKnownGoogleURL)), | 167 prefs::kLastKnownGoogleURL)), |
126 ALLOW_THIS_IN_INITIALIZER_LIST(weak_ptr_factory_(this)), | 168 ALLOW_THIS_IN_INITIALIZER_LIST(weak_ptr_factory_(this)), |
127 fetcher_id_(0), | 169 fetcher_id_(0), |
128 in_startup_sleep_(true), | 170 in_startup_sleep_(true), |
129 already_fetched_(false), | 171 already_fetched_(false), |
130 need_to_fetch_(false), | 172 need_to_fetch_(false), |
131 need_to_prompt_(false), | 173 need_to_prompt_(false) { |
132 controller_(NULL), | |
133 infobar_(NULL) { | |
134 net::NetworkChangeNotifier::AddIPAddressObserver(this); | 174 net::NetworkChangeNotifier::AddIPAddressObserver(this); |
135 | 175 |
136 // Because this function can be called during startup, when kicking off a URL | 176 // Because this function can be called during startup, when kicking off a URL |
137 // fetch can eat up 20 ms of time, we delay five seconds, which is hopefully | 177 // fetch can eat up 20 ms of time, we delay five seconds, which is hopefully |
138 // long enough to be after startup, but still get results back quickly. | 178 // long enough to be after startup, but still get results back quickly. |
139 // Ideally, instead of this timer, we'd do something like "check if the | 179 // Ideally, instead of this timer, we'd do something like "check if the |
140 // browser is starting up, and if so, come back later", but there is currently | 180 // browser is starting up, and if so, come back later", but there is currently |
141 // no function to do this. | 181 // no function to do this. |
142 // | 182 // |
143 // In UNIT_TEST mode, where we want to explicitly control when the tracker | 183 // In UNIT_TEST mode, where we want to explicitly control when the tracker |
144 // "wakes up", we do nothing at all. | 184 // "wakes up", we do nothing at all. |
145 if (mode == NORMAL_MODE) { | 185 if (mode == NORMAL_MODE) { |
146 static const int kStartFetchDelayMS = 5000; | 186 static const int kStartFetchDelayMS = 5000; |
147 MessageLoop::current()->PostDelayedTask(FROM_HERE, | 187 MessageLoop::current()->PostDelayedTask(FROM_HERE, |
148 base::Bind(&GoogleURLTracker::FinishSleep, | 188 base::Bind(&GoogleURLTracker::FinishSleep, |
149 weak_ptr_factory_.GetWeakPtr()), | 189 weak_ptr_factory_.GetWeakPtr()), |
150 base::TimeDelta::FromMilliseconds(kStartFetchDelayMS)); | 190 base::TimeDelta::FromMilliseconds(kStartFetchDelayMS)); |
151 } | 191 } |
152 } | 192 } |
153 | 193 |
154 GoogleURLTracker::~GoogleURLTracker() { | 194 GoogleURLTracker::~GoogleURLTracker() { |
155 net::NetworkChangeNotifier::RemoveIPAddressObserver(this); | 195 net::NetworkChangeNotifier::RemoveIPAddressObserver(this); |
196 // We should only reach here after any tabs and their infobars have been torn | |
197 // down. | |
198 DCHECK(infobars_.empty()); | |
156 } | 199 } |
157 | 200 |
158 // static | 201 // static |
159 GURL GoogleURLTracker::GoogleURL() { | 202 GURL GoogleURLTracker::GoogleURL() { |
160 const GoogleURLTracker* const tracker = | 203 const GoogleURLTracker* tracker = g_browser_process->google_url_tracker(); |
161 g_browser_process->google_url_tracker(); | |
162 return tracker ? tracker->google_url_ : GURL(kDefaultGoogleHomepage); | 204 return tracker ? tracker->google_url_ : GURL(kDefaultGoogleHomepage); |
163 } | 205 } |
164 | 206 |
165 // static | 207 // static |
166 void GoogleURLTracker::RequestServerCheck() { | 208 void GoogleURLTracker::RequestServerCheck() { |
167 GoogleURLTracker* const tracker = g_browser_process->google_url_tracker(); | 209 GoogleURLTracker* tracker = g_browser_process->google_url_tracker(); |
168 if (tracker) | 210 if (tracker) |
169 tracker->SetNeedToFetch(); | 211 tracker->SetNeedToFetch(); |
170 } | 212 } |
171 | 213 |
172 // static | 214 // static |
173 void GoogleURLTracker::RegisterPrefs(PrefService* prefs) { | 215 void GoogleURLTracker::RegisterPrefs(PrefService* prefs) { |
174 prefs->RegisterStringPref(prefs::kLastKnownGoogleURL, | 216 prefs->RegisterStringPref(prefs::kLastKnownGoogleURL, |
175 kDefaultGoogleHomepage); | 217 kDefaultGoogleHomepage); |
176 prefs->RegisterStringPref(prefs::kLastPromptedGoogleURL, std::string()); | 218 prefs->RegisterStringPref(prefs::kLastPromptedGoogleURL, std::string()); |
177 } | 219 } |
178 | 220 |
179 // static | 221 // static |
180 void GoogleURLTracker::GoogleURLSearchCommitted() { | 222 void GoogleURLTracker::GoogleURLSearchCommitted() { |
181 GoogleURLTracker* tracker = g_browser_process->google_url_tracker(); | 223 GoogleURLTracker* tracker = g_browser_process->google_url_tracker(); |
182 if (tracker) | 224 if (tracker) |
183 tracker->SearchCommitted(); | 225 tracker->SearchCommitted(); |
184 } | 226 } |
185 | 227 |
186 void GoogleURLTracker::AcceptGoogleURL(const GURL& new_google_url) { | 228 void GoogleURLTracker::AcceptGoogleURL(const GURL& new_google_url) { |
187 google_url_ = new_google_url; | 229 google_url_ = new_google_url; |
188 PrefService* prefs = g_browser_process->local_state(); | 230 PrefService* prefs = g_browser_process->local_state(); |
189 prefs->SetString(prefs::kLastKnownGoogleURL, google_url_.spec()); | 231 prefs->SetString(prefs::kLastKnownGoogleURL, google_url_.spec()); |
190 prefs->SetString(prefs::kLastPromptedGoogleURL, google_url_.spec()); | 232 prefs->SetString(prefs::kLastPromptedGoogleURL, google_url_.spec()); |
191 content::NotificationService::current()->Notify( | 233 content::NotificationService::current()->Notify( |
192 chrome::NOTIFICATION_GOOGLE_URL_UPDATED, | 234 chrome::NOTIFICATION_GOOGLE_URL_UPDATED, |
193 content::NotificationService::AllSources(), | 235 content::NotificationService::AllSources(), |
194 content::NotificationService::NoDetails()); | 236 content::NotificationService::NoDetails()); |
195 need_to_prompt_ = false; | 237 need_to_prompt_ = false; |
238 CloseAllInfoBars(true); | |
196 } | 239 } |
197 | 240 |
198 void GoogleURLTracker::CancelGoogleURL(const GURL& new_google_url) { | 241 void GoogleURLTracker::CancelGoogleURL(const GURL& new_google_url) { |
199 g_browser_process->local_state()->SetString(prefs::kLastPromptedGoogleURL, | 242 g_browser_process->local_state()->SetString(prefs::kLastPromptedGoogleURL, |
200 new_google_url.spec()); | 243 new_google_url.spec()); |
201 need_to_prompt_ = false; | 244 need_to_prompt_ = false; |
245 CloseAllInfoBars(false); | |
202 } | 246 } |
203 | 247 |
204 void GoogleURLTracker::InfoBarClosed() { | 248 void GoogleURLTracker::InfoBarClosed(const InfoBarTabHelper* infobar_helper) { |
205 registrar_.RemoveAll(); | 249 InfoBars::iterator i(infobars_.find(infobar_helper)); |
Ilya Sherman
2012/04/24 00:30:47
nit: Unless you're particularly attached to "i" he
| |
206 controller_ = NULL; | 250 DCHECK(i != infobars_.end()); |
207 infobar_ = NULL; | 251 infobars_.erase(i); |
208 search_url_ = GURL(); | |
209 } | |
210 | |
211 void GoogleURLTracker::RedoSearch() { | |
212 // Re-do the user's search on the new domain. | |
213 DCHECK(controller_); | |
214 url_canon::Replacements<char> replacements; | |
215 replacements.SetHost(google_url_.host().data(), | |
216 url_parse::Component(0, google_url_.host().length())); | |
217 GURL new_search_url(search_url_.ReplaceComponents(replacements)); | |
218 if (new_search_url.is_valid()) { | |
219 OpenURLParams params(new_search_url, Referrer(), CURRENT_TAB, | |
220 content::PAGE_TRANSITION_GENERATED, false); | |
221 controller_->GetWebContents()->OpenURL(params); | |
222 } | |
223 } | 252 } |
224 | 253 |
225 void GoogleURLTracker::SetNeedToFetch() { | 254 void GoogleURLTracker::SetNeedToFetch() { |
226 need_to_fetch_ = true; | 255 need_to_fetch_ = true; |
227 StartFetchIfDesirable(); | 256 StartFetchIfDesirable(); |
228 } | 257 } |
229 | 258 |
230 void GoogleURLTracker::FinishSleep() { | 259 void GoogleURLTracker::FinishSleep() { |
231 in_startup_sleep_ = false; | 260 in_startup_sleep_ = false; |
232 StartFetchIfDesirable(); | 261 StartFetchIfDesirable(); |
(...skipping 51 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
284 source->GetResponseAsString(&url_str); | 313 source->GetResponseAsString(&url_str); |
285 TrimWhitespace(url_str, TRIM_ALL, &url_str); | 314 TrimWhitespace(url_str, TRIM_ALL, &url_str); |
286 | 315 |
287 if (!StartsWithASCII(url_str, ".google.", false)) | 316 if (!StartsWithASCII(url_str, ".google.", false)) |
288 return; | 317 return; |
289 | 318 |
290 fetched_google_url_ = GURL("http://www" + url_str); | 319 fetched_google_url_ = GURL("http://www" + url_str); |
291 GURL last_prompted_url( | 320 GURL last_prompted_url( |
292 g_browser_process->local_state()->GetString( | 321 g_browser_process->local_state()->GetString( |
293 prefs::kLastPromptedGoogleURL)); | 322 prefs::kLastPromptedGoogleURL)); |
294 need_to_prompt_ = false; | |
295 | 323 |
296 if (last_prompted_url.is_empty()) { | 324 if (last_prompted_url.is_empty()) { |
297 // On the very first run of Chrome, when we've never looked up the URL at | 325 // On the very first run of Chrome, when we've never looked up the URL at |
298 // all, we should just silently switch over to whatever we get immediately. | 326 // all, we should just silently switch over to whatever we get immediately. |
299 AcceptGoogleURL(fetched_google_url_); | 327 AcceptGoogleURL(fetched_google_url_); |
300 return; | 328 return; |
301 } | 329 } |
302 | 330 |
303 // If the URL hasn't changed, then whether |need_to_prompt_| is true or false, | 331 // If the URL hasn't changed, then whether |need_to_prompt_| is true or false, |
304 // nothing has changed, so just bail. | 332 // nothing has changed, so just bail. |
305 if (fetched_google_url_ == last_prompted_url) | 333 if (fetched_google_url_ == last_prompted_url) |
306 return; | 334 return; |
307 | 335 |
308 if (fetched_google_url_ == google_url_) { | 336 if (fetched_google_url_ == google_url_) { |
309 // The user came back to their original location after having temporarily | 337 // The user came back to their original location after having temporarily |
310 // moved. Reset the prompted URL so we'll prompt again if they move again. | 338 // moved. Reset the prompted URL so we'll prompt again if they move again. |
311 CancelGoogleURL(fetched_google_url_); | 339 CancelGoogleURL(fetched_google_url_); |
312 return; | 340 return; |
313 } | 341 } |
314 | 342 |
315 need_to_prompt_ = true; | 343 need_to_prompt_ = true; |
344 | |
345 // Any open infobars are pointing at the wrong Google URL. (This can happen | |
346 // if an infobar has been sitting open and then our IP address changes.) | |
347 CloseAllInfoBars(false); | |
316 } | 348 } |
317 | 349 |
318 void GoogleURLTracker::Observe(int type, | 350 void GoogleURLTracker::Observe(int type, |
319 const content::NotificationSource& source, | 351 const content::NotificationSource& source, |
320 const content::NotificationDetails& details) { | 352 const content::NotificationDetails& details) { |
321 switch (type) { | 353 switch (type) { |
322 case content::NOTIFICATION_NAV_ENTRY_PENDING: { | 354 case content::NOTIFICATION_NAV_ENTRY_PENDING: { |
323 NavigationController* controller = | 355 content::NavigationController* controller = |
324 content::Source<NavigationController>(source).ptr(); | 356 content::Source<content::NavigationController>(source).ptr(); |
325 OnNavigationPending(source, controller->GetPendingEntry()->GetURL()); | 357 content::WebContents* contents = controller->GetWebContents(); |
358 OnNavigationPending(source, | |
359 content::Source<content::WebContents>(contents), | |
360 TabContentsWrapper::GetCurrentWrapperForContents(contents)-> | |
361 infobar_tab_helper(), controller->GetPendingEntry()->GetURL()); | |
Ilya Sherman
2012/04/24 00:30:47
nit: Maybe move the last arg to a new line, since
| |
326 break; | 362 break; |
327 } | 363 } |
328 | 364 |
329 case content::NOTIFICATION_NAV_ENTRY_COMMITTED: | 365 case content::NOTIFICATION_NAV_ENTRY_COMMITTED: { |
366 content::WebContents* contents = | |
367 content::Source<content::NavigationController>(source)-> | |
368 GetWebContents(); | |
369 OnNavigationCommittedOrTabClosed(source, | |
370 content::Source<content::WebContents>(contents), | |
371 TabContentsWrapper::GetCurrentWrapperForContents(contents)-> | |
372 infobar_tab_helper(), type); | |
373 break; | |
374 } | |
375 | |
376 case content::NOTIFICATION_WEB_CONTENTS_DESTROYED: { | |
377 content::WebContents* contents = | |
378 content::Source<content::WebContents>(source).ptr(); | |
330 OnNavigationCommittedOrTabClosed( | 379 OnNavigationCommittedOrTabClosed( |
331 content::Source<NavigationController>(source).ptr()-> | 380 content::Source<content::NavigationController>(&contents-> |
332 GetWebContents(), type); | 381 GetController()), source, |
382 TabContentsWrapper::GetCurrentWrapperForContents(contents)-> | |
383 infobar_tab_helper(), type); | |
333 break; | 384 break; |
334 | 385 } |
335 case content::NOTIFICATION_WEB_CONTENTS_DESTROYED: | |
336 OnNavigationCommittedOrTabClosed( | |
337 content::Source<content::WebContents>(source).ptr(), type); | |
338 break; | |
339 | 386 |
340 default: | 387 default: |
341 NOTREACHED() << "Unknown notification received:" << type; | 388 NOTREACHED() << "Unknown notification received:" << type; |
342 } | 389 } |
343 } | 390 } |
344 | 391 |
345 void GoogleURLTracker::OnIPAddressChanged() { | 392 void GoogleURLTracker::OnIPAddressChanged() { |
346 already_fetched_ = false; | 393 already_fetched_ = false; |
347 StartFetchIfDesirable(); | 394 StartFetchIfDesirable(); |
348 } | 395 } |
349 | 396 |
350 void GoogleURLTracker::SearchCommitted() { | 397 void GoogleURLTracker::SearchCommitted() { |
351 if (registrar_.IsEmpty() && (need_to_prompt_ || fetcher_.get())) { | 398 if (need_to_prompt_) { |
352 // This notification will fire a bit later in the same call chain we're | 399 // This notification will fire a bit later in the same call chain we're |
353 // currently in. | 400 // currently in. |
354 registrar_.Add(this, content::NOTIFICATION_NAV_ENTRY_PENDING, | 401 registrar_.Add(this, content::NOTIFICATION_NAV_ENTRY_PENDING, |
355 content::NotificationService::AllBrowserContextsAndSources()); | 402 content::NotificationService::AllBrowserContextsAndSources()); |
356 } | 403 } |
357 } | 404 } |
358 | 405 |
359 void GoogleURLTracker::OnNavigationPending( | 406 void GoogleURLTracker::OnNavigationPending( |
360 const content::NotificationSource& source, | 407 const content::NotificationSource& source, |
361 const GURL& pending_url) { | 408 const content::NotificationSource& contents_source, |
362 controller_ = content::Source<NavigationController>(source).ptr(); | 409 InfoBarTabHelper* infobar_helper, |
363 search_url_ = pending_url; | 410 const GURL& search_url) { |
364 registrar_.Remove(this, content::NOTIFICATION_NAV_ENTRY_PENDING, | 411 registrar_.Remove(this, content::NOTIFICATION_NAV_ENTRY_PENDING, |
365 content::NotificationService::AllBrowserContextsAndSources()); | 412 content::NotificationService::AllBrowserContextsAndSources()); |
366 // Start listening for the commit notification. We also need to listen for the | 413 |
367 // tab close command since that means the load will never commit. | 414 if (registrar_.IsRegistered(this, |
368 registrar_.Add(this, content::NOTIFICATION_NAV_ENTRY_COMMITTED, | 415 content::NOTIFICATION_WEB_CONTENTS_DESTROYED, contents_source)) { |
369 content::Source<NavigationController>(controller_)); | 416 // If the previous load hasn't committed and the user triggers a new load, |
370 registrar_.Add( | 417 // we don't need to re-register our listeners; just kill the old, |
371 this, | 418 // never-shown infobar (to be replaced by a new one below). |
372 content::NOTIFICATION_WEB_CONTENTS_DESTROYED, | 419 InfoBars::iterator i(infobars_.find(infobar_helper)); |
373 content::Source<content::WebContents>(controller_->GetWebContents())); | 420 DCHECK(i != infobars_.end()); |
421 i->second->Close(false); | |
422 } else { | |
423 // Start listening for the commit notification. We also need to listen for | |
424 // the tab close command since that means the load will never commit. Note | |
425 // that in this case we don't need to close any previous infobar for this | |
426 // tab since this navigation will close it. | |
427 registrar_.Add(this, content::NOTIFICATION_NAV_ENTRY_COMMITTED, source); | |
428 registrar_.Add(this, content::NOTIFICATION_WEB_CONTENTS_DESTROYED, | |
429 contents_source); | |
430 } | |
431 | |
432 infobars_[infobar_helper] = (*infobar_creator_)(infobar_helper, search_url, | |
433 this, fetched_google_url_); | |
374 } | 434 } |
375 | 435 |
376 void GoogleURLTracker::OnNavigationCommittedOrTabClosed( | 436 void GoogleURLTracker::OnNavigationCommittedOrTabClosed( |
377 WebContents* web_contents, | 437 const content::NotificationSource& source, |
438 const content::NotificationSource& contents_source, | |
439 InfoBarTabHelper* infobar_helper, | |
378 int type) { | 440 int type) { |
379 registrar_.RemoveAll(); | 441 registrar_.Remove(this, content::NOTIFICATION_NAV_ENTRY_COMMITTED, source); |
442 registrar_.Remove(this, content::NOTIFICATION_WEB_CONTENTS_DESTROYED, | |
443 contents_source); | |
380 | 444 |
381 if (type == content::NOTIFICATION_NAV_ENTRY_COMMITTED) { | 445 InfoBars::iterator i(infobars_.find(infobar_helper)); |
382 ShowGoogleURLInfoBarIfNecessary(web_contents); | 446 DCHECK(i != infobars_.end()); |
383 } else { | 447 DCHECK(need_to_prompt_); |
384 controller_ = NULL; | 448 if (type == content::NOTIFICATION_NAV_ENTRY_COMMITTED) |
385 infobar_ = NULL; | 449 i->second->Show(); |
386 } | 450 else |
451 i->second->Close(false); // Close manually since it's not added to a tab. | |
387 } | 452 } |
388 | 453 |
389 void GoogleURLTracker::ShowGoogleURLInfoBarIfNecessary( | 454 void GoogleURLTracker::CloseAllInfoBars(bool redo_searches) { |
390 WebContents* web_contents) { | 455 // Close all infobars, whether they've been added to tabs or not. |
391 if (!need_to_prompt_) | 456 while (!infobars_.empty()) |
392 return; | 457 infobars_.begin()->second->Close(redo_searches); |
393 DCHECK(!fetched_google_url_.is_empty()); | |
394 | 458 |
395 // |tab_contents| can be NULL during tests. | 459 // Any registered listeners for NAV_ENTRY_COMMITTED and TAB_CLOSED are now |
396 InfoBarTabHelper* infobar_helper = NULL; | 460 // irrelevant as the associated infobars are gone. |
Ilya Sherman
2012/04/24 00:30:47
nit: You don't mention NAV_ENTRY_PENDING in this c
Peter Kasting
2012/04/24 01:53:01
The reason for that is that it's (supposed to be)
| |
397 if (web_contents) { | 461 registrar_.RemoveAll(); |
398 TabContentsWrapper* wrapper = | |
399 TabContentsWrapper::GetCurrentWrapperForContents(web_contents); | |
400 infobar_helper = wrapper->infobar_tab_helper(); | |
401 } | |
402 infobar_ = (*infobar_creator_)(infobar_helper, this, fetched_google_url_); | |
403 } | 462 } |
OLD | NEW |