Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(600)

Side by Side Diff: chrome/browser/captive_portal/captive_portal_browsertest.cc

Issue 318213002: Add custom interstitial for captive portals. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Expand browser tests Created 6 years ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
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 <map> 5 #include <map>
6 #include <set> 6 #include <set>
7 7
8 #include "base/basictypes.h" 8 #include "base/basictypes.h"
9 #include "base/bind.h" 9 #include "base/bind.h"
10 #include "base/command_line.h" 10 #include "base/command_line.h"
11 #include "base/compiler_specific.h" 11 #include "base/compiler_specific.h"
12 #include "base/files/file_path.h" 12 #include "base/files/file_path.h"
13 #include "base/message_loop/message_loop.h" 13 #include "base/message_loop/message_loop.h"
14 #include "base/path_service.h" 14 #include "base/path_service.h"
15 #include "base/prefs/pref_service.h" 15 #include "base/prefs/pref_service.h"
16 #include "base/strings/utf_string_conversions.h" 16 #include "base/strings/utf_string_conversions.h"
17 #include "chrome/browser/captive_portal/captive_portal_service.h" 17 #include "chrome/browser/captive_portal/captive_portal_service.h"
18 #include "chrome/browser/captive_portal/captive_portal_service_factory.h" 18 #include "chrome/browser/captive_portal/captive_portal_service_factory.h"
19 #include "chrome/browser/captive_portal/captive_portal_tab_helper.h" 19 #include "chrome/browser/captive_portal/captive_portal_tab_helper.h"
20 #include "chrome/browser/captive_portal/captive_portal_tab_reloader.h" 20 #include "chrome/browser/captive_portal/captive_portal_tab_reloader.h"
21 #include "chrome/browser/chrome_notification_types.h" 21 #include "chrome/browser/chrome_notification_types.h"
22 #include "chrome/browser/interstitials/security_interstitial_page.h"
22 #include "chrome/browser/net/url_request_mock_util.h" 23 #include "chrome/browser/net/url_request_mock_util.h"
23 #include "chrome/browser/profiles/profile.h" 24 #include "chrome/browser/profiles/profile.h"
25 #include "chrome/browser/ssl/captive_portal_blocking_page.h"
26 #include "chrome/browser/ssl/ssl_blocking_page.h"
24 #include "chrome/browser/ui/browser.h" 27 #include "chrome/browser/ui/browser.h"
25 #include "chrome/browser/ui/browser_commands.h" 28 #include "chrome/browser/ui/browser_commands.h"
26 #include "chrome/browser/ui/browser_finder.h" 29 #include "chrome/browser/ui/browser_finder.h"
27 #include "chrome/browser/ui/browser_navigator.h" 30 #include "chrome/browser/ui/browser_navigator.h"
28 #include "chrome/browser/ui/tab_contents/tab_contents_iterator.h" 31 #include "chrome/browser/ui/tab_contents/tab_contents_iterator.h"
29 #include "chrome/browser/ui/tabs/tab_strip_model.h" 32 #include "chrome/browser/ui/tabs/tab_strip_model.h"
30 #include "chrome/common/chrome_paths.h" 33 #include "chrome/common/chrome_paths.h"
31 #include "chrome/common/chrome_switches.h" 34 #include "chrome/common/chrome_switches.h"
32 #include "chrome/common/pref_names.h" 35 #include "chrome/common/pref_names.h"
33 #include "chrome/test/base/in_process_browser_test.h" 36 #include "chrome/test/base/in_process_browser_test.h"
34 #include "chrome/test/base/ui_test_utils.h" 37 #include "chrome/test/base/ui_test_utils.h"
35 #include "content/public/browser/browser_thread.h" 38 #include "content/public/browser/browser_thread.h"
39 #include "content/public/browser/interstitial_page.h"
40 #include "content/public/browser/interstitial_page_delegate.h"
36 #include "content/public/browser/navigation_controller.h" 41 #include "content/public/browser/navigation_controller.h"
42 #include "content/public/browser/navigation_entry.h"
37 #include "content/public/browser/notification_observer.h" 43 #include "content/public/browser/notification_observer.h"
38 #include "content/public/browser/notification_registrar.h" 44 #include "content/public/browser/notification_registrar.h"
39 #include "content/public/browser/notification_service.h" 45 #include "content/public/browser/notification_service.h"
40 #include "content/public/browser/notification_types.h" 46 #include "content/public/browser/notification_types.h"
41 #include "content/public/browser/render_frame_host.h" 47 #include "content/public/browser/render_frame_host.h"
48 #include "content/public/browser/render_view_host.h"
42 #include "content/public/browser/web_contents.h" 49 #include "content/public/browser/web_contents.h"
43 #include "content/public/common/url_constants.h" 50 #include "content/public/common/url_constants.h"
51 #include "content/public/test/browser_test_utils.h"
44 #include "net/base/net_errors.h" 52 #include "net/base/net_errors.h"
45 #include "net/http/transport_security_state.h" 53 #include "net/http/transport_security_state.h"
46 #include "net/test/url_request/url_request_failed_job.h" 54 #include "net/test/url_request/url_request_failed_job.h"
47 #include "net/test/url_request/url_request_mock_http_job.h" 55 #include "net/test/url_request/url_request_mock_http_job.h"
48 #include "net/url_request/url_request.h" 56 #include "net/url_request/url_request.h"
49 #include "net/url_request/url_request_context.h" 57 #include "net/url_request/url_request_context.h"
50 #include "net/url_request/url_request_context_getter.h" 58 #include "net/url_request/url_request_context_getter.h"
51 #include "net/url_request/url_request_filter.h" 59 #include "net/url_request/url_request_filter.h"
52 #include "net/url_request/url_request_job.h" 60 #include "net/url_request/url_request_job.h"
53 #include "net/url_request/url_request_status.h" 61 #include "net/url_request/url_request_status.h"
(...skipping 48 matching lines...) Expand 10 before | Expand all | Expand 10 after
102 "https://mock.captive.portal.long.timeout2/title2.html"; 110 "https://mock.captive.portal.long.timeout2/title2.html";
103 111
104 // Same as kMockHttpsUrl, except the timeout happens instantly. 112 // Same as kMockHttpsUrl, except the timeout happens instantly.
105 const char* const kMockHttpsQuickTimeoutUrl = 113 const char* const kMockHttpsQuickTimeoutUrl =
106 "https://mock.captive.portal.quick.timeout/title2.html"; 114 "https://mock.captive.portal.quick.timeout/title2.html";
107 115
108 // Expected title of a tab once an HTTPS load completes, when not behind a 116 // Expected title of a tab once an HTTPS load completes, when not behind a
109 // captive portal. 117 // captive portal.
110 const char* const kInternetConnectedTitle = "Title Of Awesomeness"; 118 const char* const kInternetConnectedTitle = "Title Of Awesomeness";
111 119
120 // Wait until all <script> tags have executed, including jstemplate.
121 // This isn't ideal, but the same trick is used in
122 // SafeBrowsingBlockingPageBrowserTest to wait for the interstitials.
123 bool WaitForPageReady(content::RenderViewHost* rvh) {
124 if (!rvh)
125 return false;
126 std::string ready_state;
127 do {
128 scoped_ptr<base::Value> value = content::ExecuteScriptAndGetValue(
129 rvh->GetMainFrame(), "document.readyState");
130 if (!value.get() || !value->GetAsString(&ready_state))
131 return false;
132 } while (ready_state != "complete");
133 return true;
134 }
135
112 // A URL request job that hangs until FailJobs() is called. Started jobs 136 // A URL request job that hangs until FailJobs() is called. Started jobs
113 // are stored in a static class variable containing a linked list so that 137 // are stored in a static class variable containing a linked list so that
114 // FailJobs() can locate them. 138 // FailJobs() can locate them.
115 class URLRequestTimeoutOnDemandJob : public net::URLRequestJob, 139 class URLRequestTimeoutOnDemandJob : public net::URLRequestJob,
116 public base::NonThreadSafe { 140 public base::NonThreadSafe {
117 public: 141 public:
118 // net::URLRequestJob: 142 // net::URLRequestJob:
119 void Start() override; 143 void Start() override;
120 144
121 // All the public static methods below can be called on any thread. 145 // All the public static methods below can be called on any thread.
122 146
123 // Waits for exactly |num_jobs|. 147 // Waits for exactly |num_jobs|.
124 static void WaitForJobs(int num_jobs); 148 static void WaitForJobs(int num_jobs);
125 149
126 // Fails all active URLRequestTimeoutOnDemandJobs with connection timeouts. 150 // Fails all active URLRequestTimeoutOnDemandJobs with connection timeouts.
127 // There are expected to be exactly |expected_num_jobs| waiting for 151 // There are expected to be exactly |expected_num_jobs| waiting for
128 // failure. The only way to gaurantee this is with an earlier call to 152 // failure. The only way to guarantee this is with an earlier call to
129 // WaitForJobs, so makes sure there has been a matching WaitForJobs call. 153 // WaitForJobs, so makes sure there has been a matching WaitForJobs call.
130 static void FailJobs(int expected_num_jobs); 154 static void FailJobs(int expected_num_jobs);
131 155
156 // Fails all active URLRequestTimeoutOnDemandJobs with SSL cert errors.
157 // |expected_num_jobs| behaves just as in FailJobs.
158 static void FailJobsWithCertError(int expected_num_jobs);
159
132 // Abandon all active URLRequestTimeoutOnDemandJobs. |expected_num_jobs| 160 // Abandon all active URLRequestTimeoutOnDemandJobs. |expected_num_jobs|
133 // behaves just as in FailJobs. 161 // behaves just as in FailJobs.
134 static void AbandonJobs(int expected_num_jobs); 162 static void AbandonJobs(int expected_num_jobs);
135 163
136 private: 164 private:
137 friend class URLRequestMockCaptivePortalJobFactory; 165 friend class URLRequestMockCaptivePortalJobFactory;
138 166
139 // Operation to perform on jobs when removing them from |job_list_|. 167 // Operation to perform on jobs when removing them from |job_list_|.
140 enum EndJobOperation { 168 enum EndJobOperation {
141 FAIL_JOBS, 169 FAIL_JOBS,
142 ABANDON_JOBS, 170 ABANDON_JOBS,
171 FAIL_JOBS_WITH_CERT_ERROR
143 }; 172 };
144 173
145 URLRequestTimeoutOnDemandJob(net::URLRequest* request, 174 URLRequestTimeoutOnDemandJob(net::URLRequest* request,
146 net::NetworkDelegate* network_delegate); 175 net::NetworkDelegate* network_delegate);
147 ~URLRequestTimeoutOnDemandJob() override; 176 ~URLRequestTimeoutOnDemandJob() override;
148 177
149 // Attempts to removes |this| from |jobs_|. Returns true if it was removed 178 // Attempts to removes |this| from |jobs_|. Returns true if it was removed
150 // from the list. 179 // from the list.
151 bool RemoveFromList(); 180 bool RemoveFromList();
152 181
(...skipping 66 matching lines...) Expand 10 before | Expand all | Expand 10 after
219 // static 248 // static
220 void URLRequestTimeoutOnDemandJob::FailJobs(int expected_num_jobs) { 249 void URLRequestTimeoutOnDemandJob::FailJobs(int expected_num_jobs) {
221 content::BrowserThread::PostTask( 250 content::BrowserThread::PostTask(
222 content::BrowserThread::IO, FROM_HERE, 251 content::BrowserThread::IO, FROM_HERE,
223 base::Bind(&URLRequestTimeoutOnDemandJob::FailOrAbandonJobsOnIOThread, 252 base::Bind(&URLRequestTimeoutOnDemandJob::FailOrAbandonJobsOnIOThread,
224 expected_num_jobs, 253 expected_num_jobs,
225 FAIL_JOBS)); 254 FAIL_JOBS));
226 } 255 }
227 256
228 // static 257 // static
258 void URLRequestTimeoutOnDemandJob::FailJobsWithCertError(
259 int expected_num_jobs) {
260 content::BrowserThread::PostTask(
261 content::BrowserThread::IO, FROM_HERE,
262 base::Bind(&URLRequestTimeoutOnDemandJob::FailOrAbandonJobsOnIOThread,
263 expected_num_jobs,
264 FAIL_JOBS_WITH_CERT_ERROR));
265 }
266
267 // static
229 void URLRequestTimeoutOnDemandJob::AbandonJobs(int expected_num_jobs) { 268 void URLRequestTimeoutOnDemandJob::AbandonJobs(int expected_num_jobs) {
230 content::BrowserThread::PostTask( 269 content::BrowserThread::PostTask(
231 content::BrowserThread::IO, FROM_HERE, 270 content::BrowserThread::IO, FROM_HERE,
232 base::Bind(&URLRequestTimeoutOnDemandJob::FailOrAbandonJobsOnIOThread, 271 base::Bind(&URLRequestTimeoutOnDemandJob::FailOrAbandonJobsOnIOThread,
233 expected_num_jobs, 272 expected_num_jobs,
234 ABANDON_JOBS)); 273 ABANDON_JOBS));
235 } 274 }
236 275
237 URLRequestTimeoutOnDemandJob::URLRequestTimeoutOnDemandJob( 276 URLRequestTimeoutOnDemandJob::URLRequestTimeoutOnDemandJob(
238 net::URLRequest* request, net::NetworkDelegate* network_delegate) 277 net::URLRequest* request, net::NetworkDelegate* network_delegate)
(...skipping 67 matching lines...) Expand 10 before | Expand all | Expand 10 after
306 while (job_list_) { 345 while (job_list_) {
307 ++num_jobs; 346 ++num_jobs;
308 URLRequestTimeoutOnDemandJob* job = job_list_; 347 URLRequestTimeoutOnDemandJob* job = job_list_;
309 // Since the error notification may result in the job's destruction, remove 348 // Since the error notification may result in the job's destruction, remove
310 // it from the job list before the error. 349 // it from the job list before the error.
311 EXPECT_TRUE(job->RemoveFromList()); 350 EXPECT_TRUE(job->RemoveFromList());
312 if (end_job_operation == FAIL_JOBS) { 351 if (end_job_operation == FAIL_JOBS) {
313 job->NotifyStartError(net::URLRequestStatus( 352 job->NotifyStartError(net::URLRequestStatus(
314 net::URLRequestStatus::FAILED, 353 net::URLRequestStatus::FAILED,
315 net::ERR_CONNECTION_TIMED_OUT)); 354 net::ERR_CONNECTION_TIMED_OUT));
355 } else if (end_job_operation == FAIL_JOBS_WITH_CERT_ERROR) {
356 DCHECK(job->request()->url().SchemeIs(url::kHttpsScheme));
357 net::SSLInfo info;
358 info.cert_status = net::CERT_STATUS_COMMON_NAME_INVALID;
359 info.cert = new net::X509Certificate(
360 "bad.host", "CA", base::Time::Max(), base::Time::Max());
361 job->NotifySSLCertificateError(info, true);
316 } 362 }
317 } 363 }
318 364
319 EXPECT_EQ(expected_num_jobs, num_jobs_started_); 365 EXPECT_EQ(expected_num_jobs, num_jobs_started_);
320 EXPECT_EQ(expected_num_jobs, num_jobs); 366 EXPECT_EQ(expected_num_jobs, num_jobs);
321 367
322 num_jobs_started_ -= expected_num_jobs; 368 num_jobs_started_ -= expected_num_jobs;
323 } 369 }
324 370
325 // URLRequestCaptivePortalJobFactory emulates captive portal behavior. 371 // URLRequestCaptivePortalJobFactory emulates captive portal behavior.
(...skipping 356 matching lines...) Expand 10 before | Expand all | Expand 10 after
682 base::MessageLoopForUI::current()->Quit(); 728 base::MessageLoopForUI::current()->Quit();
683 } 729 }
684 } 730 }
685 731
686 // An observer for watching the CaptivePortalService. It tracks the last 732 // An observer for watching the CaptivePortalService. It tracks the last
687 // received result and the total number of received results. 733 // received result and the total number of received results.
688 class CaptivePortalObserver : public content::NotificationObserver { 734 class CaptivePortalObserver : public content::NotificationObserver {
689 public: 735 public:
690 explicit CaptivePortalObserver(Profile* profile); 736 explicit CaptivePortalObserver(Profile* profile);
691 737
692 // Runs the message loop until until at exactly |update_count| capitive portal 738 // Runs the message loop until exactly |update_count| captive portal
693 // results have been received, since this creation of |this|. Expects no 739 // results have been received, since the creation of |this|. Expects no
694 // additional captive portal results. 740 // additional captive portal results.
695 void WaitForResults(int num_results_to_wait_for); 741 void WaitForResults(int num_results_to_wait_for);
696 742
697 int num_results_received() const { return num_results_received_; } 743 int num_results_received() const { return num_results_received_; }
698 744
699 CaptivePortalResult captive_portal_result() const { 745 CaptivePortalResult captive_portal_result() const {
700 return captive_portal_result_; 746 return captive_portal_result_;
701 } 747 }
702 748
703 private: 749 private:
(...skipping 105 matching lines...) Expand 10 before | Expand all | Expand 10 after
809 void EnableCaptivePortalDetection(Profile* profile, bool enabled); 855 void EnableCaptivePortalDetection(Profile* profile, bool enabled);
810 856
811 // Sets up the captive portal service for the given profile so that 857 // Sets up the captive portal service for the given profile so that
812 // all checks go to |test_url|. Also disables all timers. 858 // all checks go to |test_url|. Also disables all timers.
813 void SetUpCaptivePortalService(Profile* profile, const GURL& test_url); 859 void SetUpCaptivePortalService(Profile* profile, const GURL& test_url);
814 860
815 // Returns true if |browser|'s profile is currently running a captive portal 861 // Returns true if |browser|'s profile is currently running a captive portal
816 // check. 862 // check.
817 bool CheckPending(Browser* browser); 863 bool CheckPending(Browser* browser);
818 864
865 // Returns the type of the interstitial being shown.
866 const void* GetInterstitialType(WebContents* contents) const;
867
819 // Returns the CaptivePortalTabReloader::State of |web_contents|. 868 // Returns the CaptivePortalTabReloader::State of |web_contents|.
820 CaptivePortalTabReloader::State GetStateOfTabReloader( 869 CaptivePortalTabReloader::State GetStateOfTabReloader(
821 WebContents* web_contents) const; 870 WebContents* web_contents) const;
822 871
823 // Returns the CaptivePortalTabReloader::State of the indicated tab. 872 // Returns the CaptivePortalTabReloader::State of the indicated tab.
824 CaptivePortalTabReloader::State GetStateOfTabReloaderAt(Browser* browser, 873 CaptivePortalTabReloader::State GetStateOfTabReloaderAt(Browser* browser,
825 int index) const; 874 int index) const;
826 875
827 // Returns the number of tabs with the given state, across all profiles. 876 // Returns the number of tabs with the given state, across all profiles.
828 int NumTabsWithState(CaptivePortalTabReloader::State state) const; 877 int NumTabsWithState(CaptivePortalTabReloader::State state) const;
(...skipping 61 matching lines...) Expand 10 before | Expand all | Expand 10 after
890 939
891 // Just like SlowLoadBehindCaptivePortal, except the navigated tab has 940 // Just like SlowLoadBehindCaptivePortal, except the navigated tab has
892 // a connection timeout rather having its time trigger, and the function 941 // a connection timeout rather having its time trigger, and the function
893 // waits until that timeout occurs. 942 // waits until that timeout occurs.
894 void FastTimeoutBehindCaptivePortal(Browser* browser, 943 void FastTimeoutBehindCaptivePortal(Browser* browser,
895 bool expect_open_login_tab); 944 bool expect_open_login_tab);
896 945
897 // Much as above, but accepts a URL parameter and can be used for errors that 946 // Much as above, but accepts a URL parameter and can be used for errors that
898 // trigger captive portal checks other than timeouts. |error_url| should 947 // trigger captive portal checks other than timeouts. |error_url| should
899 // result in an error rather than hanging. 948 // result in an error rather than hanging.
900 void FastErrorBehindCaptivePortal(Browser* browser, 949 void FastErrorBehindCaptivePortal(
901 bool expect_open_login_tab, 950 Browser* browser,
902 const GURL& error_url); 951 bool expect_open_login_tab,
952 const GURL& error_url,
953 bool disable_portal_check_until_interstitial);
954
955 // Navigates the active tab to an SSL error page which triggers an
956 // interstitial timer. Also disables captive portal checks indefinitely, so
957 // the page appears to be hanging.
958 void FastErrorWithInterstitialTimer(Browser* browser,
959 const GURL& cert_error_url);
903 960
904 // Navigates the login tab without logging in. The login tab must be the 961 // Navigates the login tab without logging in. The login tab must be the
905 // specified browser's active tab. Expects no other tab to change state. 962 // specified browser's active tab. Expects no other tab to change state.
906 // |num_loading_tabs| and |num_timed_out_tabs| are used as extra checks 963 // |num_loading_tabs| and |num_timed_out_tabs| are used as extra checks
907 // that nothing has gone wrong prior to the function call. 964 // that nothing has gone wrong prior to the function call.
908 void NavigateLoginTab(Browser* browser, 965 void NavigateLoginTab(Browser* browser,
909 int num_loading_tabs, 966 int num_loading_tabs,
910 int num_timed_out_tabs); 967 int num_timed_out_tabs);
911 968
912 // Simulates a login by updating the URLRequestMockCaptivePortalJob's 969 // Simulates a login by updating the URLRequestMockCaptivePortalJob's
913 // behind captive portal state, and navigating the login tab. Waits for 970 // behind captive portal state, and navigating the login tab. Waits for
914 // all broken but not loading tabs to be reloaded. 971 // all broken but not loading tabs to be reloaded.
915 // |num_loading_tabs| and |num_timed_out_tabs| are used as extra checks 972 // |num_loading_tabs| and |num_timed_out_tabs| are used as extra checks
916 // that nothing has gone wrong prior to the function call. 973 // that nothing has gone wrong prior to the function call.
917 void Login(Browser* browser, int num_loading_tabs, int num_timed_out_tabs); 974 void Login(Browser* browser, int num_loading_tabs, int num_timed_out_tabs);
918 975
976 // Simulates a login when the broken tab shows an SSL or captive portal
977 // interstitial. Can't use Login() in those cases because the interstitial
978 // tab looks like a cross between a hung tab (Load was never committed) and a
979 // tab at an error page (The load was stopped).
980 void LoginCertError(Browser* browser);
981
919 // Makes the slow SSL loads of all active tabs time out at once, and waits for 982 // Makes the slow SSL loads of all active tabs time out at once, and waits for
920 // them to finish both that load and the automatic reload it should trigger. 983 // them to finish both that load and the automatic reload it should trigger.
921 // There should be no timed out tabs when this is called. 984 // There should be no timed out tabs when this is called.
922 void FailLoadsAfterLogin(Browser* browser, int num_loading_tabs); 985 void FailLoadsAfterLogin(Browser* browser, int num_loading_tabs);
923 986
924 // Makes the slow SSL loads of all active tabs time out at once, and waits for 987 // Makes the slow SSL loads of all active tabs time out at once, and waits for
925 // them to finish displaying their error pages. The login tab should be the 988 // them to finish displaying their error pages. The login tab should be the
926 // active tab. There should be no timed out tabs when this is called. 989 // active tab. There should be no timed out tabs when this is called.
927 void FailLoadsWithoutLogin(Browser* browser, int num_loading_tabs); 990 void FailLoadsWithoutLogin(Browser* browser, int num_loading_tabs);
928 991
(...skipping 13 matching lines...) Expand all
942 void RunNavigateLoadingTabToTimeoutTest(Browser* browser, 1005 void RunNavigateLoadingTabToTimeoutTest(Browser* browser,
943 const GURL& starting_url, 1006 const GURL& starting_url,
944 const GURL& interrupted_url, 1007 const GURL& interrupted_url,
945 const GURL& timeout_url); 1008 const GURL& timeout_url);
946 1009
947 // Sets the timeout used by a CaptivePortalTabReloader on slow SSL loads 1010 // Sets the timeout used by a CaptivePortalTabReloader on slow SSL loads
948 // before a captive portal check. 1011 // before a captive portal check.
949 void SetSlowSSLLoadTime(CaptivePortalTabReloader* tab_reloader, 1012 void SetSlowSSLLoadTime(CaptivePortalTabReloader* tab_reloader,
950 base::TimeDelta slow_ssl_load_time); 1013 base::TimeDelta slow_ssl_load_time);
951 1014
1015 void SetSSLErrorDisplayDelay(CaptivePortalTabHelper* tab_helper,
1016 base::TimeDelta ssl_error_delay);
1017
952 CaptivePortalTabReloader* GetTabReloader(WebContents* web_contents) const; 1018 CaptivePortalTabReloader* GetTabReloader(WebContents* web_contents) const;
953 1019
954 private: 1020 private:
955 DISALLOW_COPY_AND_ASSIGN(CaptivePortalBrowserTest); 1021 DISALLOW_COPY_AND_ASSIGN(CaptivePortalBrowserTest);
956 }; 1022 };
957 1023
958 CaptivePortalBrowserTest::CaptivePortalBrowserTest() { 1024 CaptivePortalBrowserTest::CaptivePortalBrowserTest() {
959 } 1025 }
960 1026
961 void CaptivePortalBrowserTest::SetUpOnMainThread() { 1027 void CaptivePortalBrowserTest::SetUpOnMainThread() {
(...skipping 26 matching lines...) Expand all
988 void CaptivePortalBrowserTest::EnableCaptivePortalDetection( 1054 void CaptivePortalBrowserTest::EnableCaptivePortalDetection(
989 Profile* profile, bool enabled) { 1055 Profile* profile, bool enabled) {
990 profile->GetPrefs()->SetBoolean(prefs::kAlternateErrorPagesEnabled, enabled); 1056 profile->GetPrefs()->SetBoolean(prefs::kAlternateErrorPagesEnabled, enabled);
991 } 1057 }
992 1058
993 void CaptivePortalBrowserTest::SetUpCaptivePortalService(Profile* profile, 1059 void CaptivePortalBrowserTest::SetUpCaptivePortalService(Profile* profile,
994 const GURL& test_url) { 1060 const GURL& test_url) {
995 CaptivePortalService* captive_portal_service = 1061 CaptivePortalService* captive_portal_service =
996 CaptivePortalServiceFactory::GetForProfile(profile); 1062 CaptivePortalServiceFactory::GetForProfile(profile);
997 captive_portal_service->set_test_url(test_url); 1063 captive_portal_service->set_test_url(test_url);
1064 captive_portal_service->SetPortalDetectionEnabledForTest(true);
998 1065
999 // Don't use any non-zero timers. Timers are checked in unit tests. 1066 // Don't use any non-zero timers. Timers are checked in unit tests.
1000 CaptivePortalService::RecheckPolicy* recheck_policy = 1067 CaptivePortalService::RecheckPolicy* recheck_policy =
1001 &captive_portal_service->recheck_policy(); 1068 &captive_portal_service->recheck_policy();
1002 recheck_policy->initial_backoff_no_portal_ms = 0; 1069 recheck_policy->initial_backoff_no_portal_ms = 0;
1003 recheck_policy->initial_backoff_portal_ms = 0; 1070 recheck_policy->initial_backoff_portal_ms = 0;
1004 recheck_policy->backoff_policy.maximum_backoff_ms = 0; 1071 recheck_policy->backoff_policy.maximum_backoff_ms = 0;
1005 } 1072 }
1006 1073
1007 bool CaptivePortalBrowserTest::CheckPending(Browser* browser) { 1074 bool CaptivePortalBrowserTest::CheckPending(Browser* browser) {
1008 CaptivePortalService* captive_portal_service = 1075 CaptivePortalService* captive_portal_service =
1009 CaptivePortalServiceFactory::GetForProfile(browser->profile()); 1076 CaptivePortalServiceFactory::GetForProfile(browser->profile());
1010 1077
1011 return captive_portal_service->DetectionInProgress() || 1078 return captive_portal_service->DetectionInProgress() ||
1012 captive_portal_service->TimerRunning(); 1079 captive_portal_service->TimerRunning();
1013 } 1080 }
1014 1081
1082 const void* CaptivePortalBrowserTest::GetInterstitialType(
1083 WebContents* contents) const {
1084 if (!contents->ShowingInterstitialPage())
1085 return NULL;
1086 SecurityInterstitialPage* blocking_page =
1087 static_cast<SecurityInterstitialPage*>(
1088 contents->GetInterstitialPage()->GetDelegateForTesting());
1089 DCHECK(blocking_page);
1090 return blocking_page->GetTypeForTesting();
1091 }
1092
1015 CaptivePortalTabReloader::State CaptivePortalBrowserTest::GetStateOfTabReloader( 1093 CaptivePortalTabReloader::State CaptivePortalBrowserTest::GetStateOfTabReloader(
1016 WebContents* web_contents) const { 1094 WebContents* web_contents) const {
1017 return GetTabReloader(web_contents)->state(); 1095 return GetTabReloader(web_contents)->state();
1018 } 1096 }
1019 1097
1020 CaptivePortalTabReloader::State 1098 CaptivePortalTabReloader::State
1021 CaptivePortalBrowserTest::GetStateOfTabReloaderAt(Browser* browser, 1099 CaptivePortalBrowserTest::GetStateOfTabReloaderAt(Browser* browser,
1022 int index) const { 1100 int index) const {
1023 return GetStateOfTabReloader( 1101 return GetStateOfTabReloader(
1024 browser->tab_strip_model()->GetWebContentsAt(index)); 1102 browser->tab_strip_model()->GetWebContentsAt(index));
(...skipping 212 matching lines...) Expand 10 before | Expand all | Expand 10 after
1237 1315
1238 // Reset the load time to be large, so the timer won't trigger on a reload. 1316 // Reset the load time to be large, so the timer won't trigger on a reload.
1239 SetSlowSSLLoadTime(tab_reloader, base::TimeDelta::FromHours(1)); 1317 SetSlowSSLLoadTime(tab_reloader, base::TimeDelta::FromHours(1));
1240 } 1318 }
1241 1319
1242 void CaptivePortalBrowserTest::FastTimeoutBehindCaptivePortal( 1320 void CaptivePortalBrowserTest::FastTimeoutBehindCaptivePortal(
1243 Browser* browser, 1321 Browser* browser,
1244 bool expect_open_login_tab) { 1322 bool expect_open_login_tab) {
1245 FastErrorBehindCaptivePortal(browser, 1323 FastErrorBehindCaptivePortal(browser,
1246 expect_open_login_tab, 1324 expect_open_login_tab,
1247 GURL(kMockHttpsQuickTimeoutUrl)); 1325 GURL(kMockHttpsQuickTimeoutUrl),
1326 false);
1248 } 1327 }
1249 1328
1250 void CaptivePortalBrowserTest::FastErrorBehindCaptivePortal( 1329 void CaptivePortalBrowserTest::FastErrorBehindCaptivePortal(
1251 Browser* browser, 1330 Browser* browser,
1252 bool expect_open_login_tab, 1331 bool expect_open_login_tab,
1253 const GURL& error_url) { 1332 const GURL& error_url,
1333 bool disable_portal_check_until_interstitial) {
1254 TabStripModel* tab_strip_model = browser->tab_strip_model(); 1334 TabStripModel* tab_strip_model = browser->tab_strip_model();
1255 // Calling this on a tab that's waiting for a load to manually be timed out 1335 // Calling this on a tab that's waiting for a load to manually be timed out
1256 // will result in a hang. 1336 // will result in a hang.
1257 ASSERT_FALSE(tab_strip_model->GetActiveWebContents()->IsLoading()); 1337 ASSERT_FALSE(tab_strip_model->GetActiveWebContents()->IsLoading());
1258 1338
1259 // Set the load time to be large, so the timer won't trigger. The value is 1339 // Set the load time to be large, so the timer won't trigger. The value is
1260 // not restored at the end of the function. 1340 // not restored at the end of the function.
1261 CaptivePortalTabReloader* tab_reloader = 1341 CaptivePortalTabReloader* tab_reloader =
1262 GetTabReloader(tab_strip_model->GetActiveWebContents()); 1342 GetTabReloader(tab_strip_model->GetActiveWebContents());
1263 ASSERT_TRUE(tab_reloader); 1343 ASSERT_TRUE(tab_reloader);
1264 SetSlowSSLLoadTime(tab_reloader, base::TimeDelta::FromHours(1)); 1344 SetSlowSSLLoadTime(tab_reloader, base::TimeDelta::FromHours(1));
1265 1345
1266 // Number of tabs expected to be open after the captive portal checks 1346 // Number of tabs expected to be open after the captive portal checks
1267 // have completed. 1347 // have completed.
1268 int initial_tab_count = tab_strip_model->count(); 1348 int initial_tab_count = tab_strip_model->count();
1269 int initial_active_index = tab_strip_model->active_index(); 1349 int initial_active_index = tab_strip_model->active_index();
1270 int initial_loading_tabs = NumLoadingTabs(); 1350 int initial_loading_tabs = NumLoadingTabs();
1271 int expected_broken_tabs = NumBrokenTabs(); 1351 int expected_broken_tabs = NumBrokenTabs();
1272 if (CaptivePortalTabReloader::STATE_BROKEN_BY_PORTAL != 1352 if (CaptivePortalTabReloader::STATE_BROKEN_BY_PORTAL !=
1273 GetStateOfTabReloader(tab_strip_model->GetActiveWebContents())) { 1353 GetStateOfTabReloader(tab_strip_model->GetActiveWebContents())) {
1274 ++expected_broken_tabs; 1354 ++expected_broken_tabs;
1275 } 1355 }
1276 1356
1357 CaptivePortalService* captive_portal_service =
1358 CaptivePortalServiceFactory::GetForProfile(browser->profile());
1359 if (disable_portal_check_until_interstitial)
1360 captive_portal_service->SetPortalDetectionEnabledForTest(false);
1361
1277 MultiNavigationObserver navigation_observer; 1362 MultiNavigationObserver navigation_observer;
1278 CaptivePortalObserver portal_observer(browser->profile()); 1363 CaptivePortalObserver portal_observer(browser->profile());
1279 ui_test_utils::NavigateToURLWithDisposition(browser, 1364 ui_test_utils::NavigateToURLWithDisposition(browser,
1280 error_url, 1365 error_url,
1281 CURRENT_TAB, 1366 CURRENT_TAB,
1282 ui_test_utils::BROWSER_TEST_NONE); 1367 ui_test_utils::BROWSER_TEST_NONE);
1368
1369 if (disable_portal_check_until_interstitial) {
1370 EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE,
1371 GetStateOfTabReloaderAt(browser, initial_active_index));
1372 // Once the interstitial is attached, probe for captive portal.
1373 WaitForInterstitialAttach(tab_strip_model->GetActiveWebContents());
1374 captive_portal_service->SetPortalDetectionEnabledForTest(true);
1375 captive_portal_service->DetectCaptivePortal();
1376 }
1377
1283 portal_observer.WaitForResults(1); 1378 portal_observer.WaitForResults(1);
1284 1379
1285 if (expect_open_login_tab) { 1380 if (expect_open_login_tab) {
1286 navigation_observer.WaitForNavigations(2); 1381 navigation_observer.WaitForNavigations(2);
1287 ASSERT_EQ(initial_tab_count + 1, tab_strip_model->count()); 1382 ASSERT_EQ(initial_tab_count + 1, tab_strip_model->count());
1288 EXPECT_EQ(initial_tab_count, tab_strip_model->active_index()); 1383 EXPECT_EQ(initial_tab_count, tab_strip_model->active_index());
1289 // Make sure that the originally active tab and the captive portal tab have 1384 // Make sure that the originally active tab and the captive portal tab have
1290 // each loaded once. 1385 // each loaded once.
1291 EXPECT_EQ(1, navigation_observer.NumNavigationsForTab( 1386 EXPECT_EQ(1, navigation_observer.NumNavigationsForTab(
1292 tab_strip_model->GetWebContentsAt(initial_active_index))); 1387 tab_strip_model->GetWebContentsAt(initial_active_index)));
(...skipping 107 matching lines...) Expand 10 before | Expand all | Expand 10 after
1400 EXPECT_EQ(initial_tab_count, tab_strip_model->count()); 1495 EXPECT_EQ(initial_tab_count, tab_strip_model->count());
1401 EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, 1496 EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE,
1402 GetStateOfTabReloaderAt(browser, login_tab_index)); 1497 GetStateOfTabReloaderAt(browser, login_tab_index));
1403 EXPECT_FALSE(IsLoginTab(tab_strip_model->GetWebContentsAt(login_tab_index))); 1498 EXPECT_FALSE(IsLoginTab(tab_strip_model->GetWebContentsAt(login_tab_index)));
1404 1499
1405 // Make sure there were no unexpected navigations of the login tab. 1500 // Make sure there were no unexpected navigations of the login tab.
1406 EXPECT_EQ(1, navigation_observer.NumNavigationsForTab( 1501 EXPECT_EQ(1, navigation_observer.NumNavigationsForTab(
1407 tab_strip_model->GetWebContentsAt(login_tab_index))); 1502 tab_strip_model->GetWebContentsAt(login_tab_index)));
1408 } 1503 }
1409 1504
1505 void CaptivePortalBrowserTest::LoginCertError(Browser* browser) {
1506 TabStripModel* tab_strip_model = browser->tab_strip_model();
1507 URLRequestMockCaptivePortalJobFactory::SetBehindCaptivePortal(false);
1508 MultiNavigationObserver navigation_observer;
1509 CaptivePortalObserver portal_observer(browser->profile());
1510
1511 content::RenderFrameHost* render_frame_host =
1512 tab_strip_model->GetActiveWebContents()->GetMainFrame();
1513 render_frame_host->ExecuteJavaScript(base::ASCIIToUTF16("submitForm()"));
1514
1515 // The captive portal tab navigation will trigger a captive portal check,
1516 // and reloading the original tab will bring up the interstitial page again,
1517 // triggering a second captive portal check.
1518 portal_observer.WaitForResults(2);
1519
1520 // Wait for both tabs to finish loading.
1521 navigation_observer.WaitForNavigations(2);
1522 EXPECT_EQ(2, portal_observer.num_results_received());
1523 EXPECT_FALSE(CheckPending(browser));
1524 EXPECT_EQ(captive_portal::RESULT_INTERNET_CONNECTED,
1525 portal_observer.captive_portal_result());
1526
1527 // Check state of tabs. While the first tab is still displaying an
1528 // interstitial page, since no portal was found, it should be in STATE_NONE,
1529 // as should the login tab.
1530 ASSERT_EQ(2, tab_strip_model->count());
1531 EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE,
1532 GetStateOfTabReloaderAt(browser, 0));
1533 EXPECT_FALSE(IsLoginTab(tab_strip_model->GetWebContentsAt(1)));
1534 EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE,
1535 GetStateOfTabReloaderAt(browser, 1));
1536
1537 // Make sure only one navigation was for the login tab.
1538 EXPECT_EQ(1, navigation_observer.NumNavigationsForTab(
1539 tab_strip_model->GetWebContentsAt(1)));
1540 }
1541
1410 void CaptivePortalBrowserTest::FailLoadsAfterLogin(Browser* browser, 1542 void CaptivePortalBrowserTest::FailLoadsAfterLogin(Browser* browser,
1411 int num_loading_tabs) { 1543 int num_loading_tabs) {
1412 ASSERT_EQ(num_loading_tabs, NumLoadingTabs()); 1544 ASSERT_EQ(num_loading_tabs, NumLoadingTabs());
1413 ASSERT_EQ(num_loading_tabs, NumNeedReloadTabs()); 1545 ASSERT_EQ(num_loading_tabs, NumNeedReloadTabs());
1414 EXPECT_EQ(0, NumBrokenTabs()); 1546 EXPECT_EQ(0, NumBrokenTabs());
1415 1547
1416 TabStripModel* tab_strip_model = browser->tab_strip_model(); 1548 TabStripModel* tab_strip_model = browser->tab_strip_model();
1417 int initial_num_tabs = tab_strip_model->count(); 1549 int initial_num_tabs = tab_strip_model->count();
1418 int initial_active_tab = tab_strip_model->active_index(); 1550 int initial_active_tab = tab_strip_model->active_index();
1419 1551
(...skipping 119 matching lines...) Expand 10 before | Expand all | Expand 10 after
1539 // Timeout occurs, and page is automatically reloaded. 1671 // Timeout occurs, and page is automatically reloaded.
1540 FailLoadsAfterLogin(browser, 1); 1672 FailLoadsAfterLogin(browser, 1);
1541 } 1673 }
1542 1674
1543 void CaptivePortalBrowserTest::SetSlowSSLLoadTime( 1675 void CaptivePortalBrowserTest::SetSlowSSLLoadTime(
1544 CaptivePortalTabReloader* tab_reloader, 1676 CaptivePortalTabReloader* tab_reloader,
1545 base::TimeDelta slow_ssl_load_time) { 1677 base::TimeDelta slow_ssl_load_time) {
1546 tab_reloader->set_slow_ssl_load_time(slow_ssl_load_time); 1678 tab_reloader->set_slow_ssl_load_time(slow_ssl_load_time);
1547 } 1679 }
1548 1680
1681 void CaptivePortalBrowserTest::SetSSLErrorDisplayDelay(
1682 CaptivePortalTabHelper* tab_helper,
1683 base::TimeDelta ssl_error_delay) {
1684 tab_helper->SetSSLErrorDelayForTest(ssl_error_delay);
1685 }
1686
1549 CaptivePortalTabReloader* CaptivePortalBrowserTest::GetTabReloader( 1687 CaptivePortalTabReloader* CaptivePortalBrowserTest::GetTabReloader(
1550 WebContents* web_contents) const { 1688 WebContents* web_contents) const {
1551 return CaptivePortalTabHelper::FromWebContents(web_contents)-> 1689 return CaptivePortalTabHelper::FromWebContents(web_contents)->
1552 GetTabReloaderForTest(); 1690 GetTabReloaderForTest();
1553 } 1691 }
1554 1692
1555 // Make sure there's no test for a captive portal on HTTP timeouts. This will 1693 // Make sure there's no test for a captive portal on HTTP timeouts. This will
1556 // also trigger the link doctor page, which results in the load of a second 1694 // also trigger the link doctor page, which results in the load of a second
1557 // error page. 1695 // error page.
1558 IN_PROC_BROWSER_TEST_F(CaptivePortalBrowserTest, HttpTimeout) { 1696 IN_PROC_BROWSER_TEST_F(CaptivePortalBrowserTest, HttpTimeout) {
(...skipping 139 matching lines...) Expand 10 before | Expand all | Expand 10 after
1698 } 1836 }
1699 1837
1700 // Checks the unlikely case that the tab times out before the timer triggers. 1838 // Checks the unlikely case that the tab times out before the timer triggers.
1701 // This most likely won't happen, but should still work: 1839 // This most likely won't happen, but should still work:
1702 IN_PROC_BROWSER_TEST_F(CaptivePortalBrowserTest, LoginFastTimeout) { 1840 IN_PROC_BROWSER_TEST_F(CaptivePortalBrowserTest, LoginFastTimeout) {
1703 FastTimeoutBehindCaptivePortal(browser(), true); 1841 FastTimeoutBehindCaptivePortal(browser(), true);
1704 Login(browser(), 0, 1); 1842 Login(browser(), 0, 1);
1705 } 1843 }
1706 1844
1707 // A cert error triggers a captive portal check and results in opening a login 1845 // A cert error triggers a captive portal check and results in opening a login
1708 // tab. The user then logs in and the page with the error is reloaded. 1846 // tab.
1709 IN_PROC_BROWSER_TEST_F(CaptivePortalBrowserTest, SSLCertErrorLogin) { 1847 IN_PROC_BROWSER_TEST_F(CaptivePortalBrowserTest,
1710 // Need an HTTP TestServer to handle a dynamically created server redirect. 1848 ShowCaptivePortalInterstitialOnCertError) {
1711 ASSERT_TRUE(test_server()->Start());
1712
1713 net::SpawnedTestServer::SSLOptions https_options; 1849 net::SpawnedTestServer::SSLOptions https_options;
1714 https_options.server_certificate = 1850 https_options.server_certificate =
1715 net::SpawnedTestServer::SSLOptions::CERT_MISMATCHED_NAME; 1851 net::SpawnedTestServer::SSLOptions::CERT_MISMATCHED_NAME;
1716 net::SpawnedTestServer https_server( 1852 net::SpawnedTestServer https_server(
1717 net::SpawnedTestServer::TYPE_HTTPS, https_options, 1853 net::SpawnedTestServer::TYPE_HTTPS, https_options,
1718 base::FilePath(FILE_PATH_LITERAL("chrome/test/data"))); 1854 base::FilePath(FILE_PATH_LITERAL("chrome/test/data")));
1719 ASSERT_TRUE(https_server.Start()); 1855 ASSERT_TRUE(https_server.Start());
1720 1856
1721 // The path does not matter. 1857 // Set SSL interstitial delay long enough so that a captive portal result
1722 GURL cert_error_url = https_server.GetURL(kTestServerLoginPath); 1858 // is guaranteed to arrive during this window, and a captive portal
1859 // error page is displayed instead of an SSL interstitial.
1860 TabStripModel* tab_strip_model = browser()->tab_strip_model();
1861 WebContents* broken_tab_contents = tab_strip_model->GetActiveWebContents();
1862 SetSSLErrorDisplayDelay(
1863 CaptivePortalTabHelper::FromWebContents(broken_tab_contents),
1864 base::TimeDelta::FromHours(1));
1865
1866 // The path does not matter.
1867 GURL cert_error_url = https_server.GetURL(kTestServerLoginPath);
1868 int cert_error_tab_index = tab_strip_model->active_index();
1723 // The interstitial should trigger a captive portal check when it opens, just 1869 // The interstitial should trigger a captive portal check when it opens, just
1724 // like navigating to kMockHttpsQuickTimeoutUrl. 1870 // like navigating to kMockHttpsQuickTimeoutUrl.
1725 FastErrorBehindCaptivePortal(browser(), true, cert_error_url); 1871 FastErrorBehindCaptivePortal(browser(), true, cert_error_url, false);
1726 1872
1727 // Simulate logging in. Can't use Login() because the interstitial tab looks 1873 EXPECT_EQ(CaptivePortalBlockingPage::kTypeForTesting,
1728 // like a cross between a hung tab (Load was never committed) and a tab at an 1874 GetInterstitialType(broken_tab_contents));
1729 // error page (The load was stopped). 1875
1730 URLRequestMockCaptivePortalJobFactory::SetBehindCaptivePortal(false); 1876 int login_tab_index = tab_strip_model->active_index();
1731 MultiNavigationObserver navigation_observer; 1877 // Switch to the interstitial and click the "Connect" button. Should switch
1878 // active tab to the captive portal landing page.
1879 tab_strip_model->ActivateTabAt(cert_error_tab_index, false);
1880
1881 content::RenderViewHost* rvh =
1882 broken_tab_contents->GetInterstitialPage()->GetRenderViewHostForTesting();
1883 EXPECT_TRUE(WaitForPageReady(rvh));
1884 EXPECT_TRUE(
1885 content::ExecuteScript(
1886 rvh->GetMainFrame(),
1887 "document.getElementById('primary-button').click();"));
1888 EXPECT_EQ(login_tab_index, tab_strip_model->active_index());
1889
1890 LoginCertError(browser());
1891
1892 // Once logged in, broken tab should reload and display the SSL interstitial.
1893 WaitForInterstitialAttach(broken_tab_contents);
1894 tab_strip_model->ActivateTabAt(cert_error_tab_index, false);
1895
1896 EXPECT_EQ(SSLBlockingPage::kTypeForTesting,
1897 GetInterstitialType(tab_strip_model->GetActiveWebContents()));
1898
1899 // Trigger another captive portal check while the SSL interstitial is showing.
1900 // At this point the user is logged in to the captive portal, so the captive
1901 // portal interstitial shouldn't get recreated.
1732 CaptivePortalObserver portal_observer(browser()->profile()); 1902 CaptivePortalObserver portal_observer(browser()->profile());
1733 1903 CaptivePortalService* captive_portal_service =
1734 TabStripModel* tab_strip_model = browser()->tab_strip_model(); 1904 CaptivePortalServiceFactory::GetForProfile(browser()->profile());
1735 content::RenderFrameHost* render_frame_host = 1905 captive_portal_service->DetectCaptivePortal();
1736 tab_strip_model->GetActiveWebContents()->GetMainFrame(); 1906 portal_observer.WaitForResults(1);
1737 render_frame_host->ExecuteJavaScript(base::ASCIIToUTF16("submitForm()")); 1907 EXPECT_EQ(SSLBlockingPage::kTypeForTesting,
1738 1908 GetInterstitialType(broken_tab_contents));
1739 // The captive portal tab navigation will trigger a captive portal check, 1909
1740 // and reloading the original tab will bring up the interstitial page again, 1910 // A captive portal appears. Trigger a final captive portal check. The
1741 // triggering a second captive portal check. 1911 // captive portal interstitial should still not get recreated.
1742 portal_observer.WaitForResults(2); 1912 URLRequestMockCaptivePortalJobFactory::SetBehindCaptivePortal(true);
1743 1913 CaptivePortalObserver final_portal_observer(browser()->profile());
1744 // Wait for both tabs to finish loading. 1914 captive_portal_service->DetectCaptivePortal();
1745 navigation_observer.WaitForNavigations(2); 1915 final_portal_observer.WaitForResults(1);
1746 EXPECT_EQ(2, portal_observer.num_results_received()); 1916 EXPECT_EQ(SSLBlockingPage::kTypeForTesting,
1747 EXPECT_FALSE(CheckPending(browser())); 1917 GetInterstitialType(broken_tab_contents));
1748 EXPECT_EQ(captive_portal::RESULT_INTERNET_CONNECTED, 1918 }
1749 portal_observer.captive_portal_result()); 1919
1750 1920 void CaptivePortalBrowserTest::FastErrorWithInterstitialTimer(
1751 // Check state of tabs. While the first tab is still displaying an 1921 Browser* browser,
1752 // interstitial page, since no portal was found, it should be in STATE_NONE, 1922 const GURL& cert_error_url) {
1753 // as should the login tab. 1923 TabStripModel* tab_strip_model = browser->tab_strip_model();
1754 ASSERT_EQ(2, tab_strip_model->count()); 1924 WebContents* broken_tab_contents = tab_strip_model->GetActiveWebContents();
1755 EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, 1925
1756 GetStateOfTabReloaderAt(browser(), 0)); 1926 // Disable captive portal checks indefinitely.
1757 EXPECT_FALSE(IsLoginTab(tab_strip_model->GetWebContentsAt(1))); 1927 CaptivePortalService* captive_portal_service =
1758 EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, 1928 CaptivePortalServiceFactory::GetForProfile(browser->profile());
1759 GetStateOfTabReloaderAt(browser(), 1)); 1929 captive_portal_service->SetPortalDetectionEnabledForTest(false);
1760 1930
1761 // Make sure only one navigation was for the login tab. 1931 content::WindowedNotificationObserver signal(
1762 EXPECT_EQ(1, navigation_observer.NumNavigationsForTab( 1932 chrome::NOTIFICATION_SSL_INTERSTITIAL_TIMER_FIRED,
1763 tab_strip_model->GetWebContentsAt(1))); 1933 content::Source<WebContents>(broken_tab_contents));
1934 ui_test_utils::NavigateToURLWithDisposition(browser,
1935 cert_error_url,
1936 CURRENT_TAB,
1937 ui_test_utils::BROWSER_TEST_NONE);
1938 signal.Wait();
1939 ASSERT_EQ(broken_tab_contents,
1940 content::Source<WebContents>(signal.source()).ptr());
1941
1942 // The tab should be in loading state, waiting for the interstitial timer to
1943 // expire or a captive portal result to arrive. Since captive portal checks
1944 // are disabled and timer set to expire after a very long time, the tab should
1945 // hang indefinitely.
1946 EXPECT_TRUE(broken_tab_contents->IsLoading());
1947 EXPECT_EQ(1, NumLoadingTabs());
1948 }
1949
1950 // Tests this scenario:
1951 // - Portal checks are disabled.
1952 // - A cert error triggers an interstitial timer with a very long timeout.
1953 // - No captive portal results arrive, causing the tab to appear as loading
1954 // indefinitely.
1955 // - Stopping the page load shouldn't result in any interstitials.
1956 IN_PROC_BROWSER_TEST_F(CaptivePortalBrowserTest,
1957 InterstitialTimerStopNavigationWhileLoading) {
1958 net::SpawnedTestServer::SSLOptions https_options;
1959 https_options.server_certificate =
1960 net::SpawnedTestServer::SSLOptions::CERT_MISMATCHED_NAME;
1961 net::SpawnedTestServer https_server(
1962 net::SpawnedTestServer::TYPE_HTTPS, https_options,
1963 base::FilePath(FILE_PATH_LITERAL("chrome/test/data")));
1964 ASSERT_TRUE(https_server.Start());
1965 // The path does not matter.
1966 GURL cert_error_url = https_server.GetURL(kTestServerLoginPath);
1967
1968 TabStripModel* tab_strip_model = browser()->tab_strip_model();
1969 WebContents* broken_tab_contents = tab_strip_model->GetActiveWebContents();
1970 SetSSLErrorDisplayDelay(
1971 CaptivePortalTabHelper::FromWebContents(broken_tab_contents),
1972 base::TimeDelta::FromHours(1));
1973
1974 CaptivePortalObserver portal_observer1(browser()->profile());
1975 FastErrorWithInterstitialTimer(browser(), cert_error_url);
1976
1977 // Page appears loading. Stop the navigation. There should be no interstitial.
1978 MultiNavigationObserver test_navigation_observer;
1979 broken_tab_contents->Stop();
1980 test_navigation_observer.WaitForNavigations(1);
1981
1982 EXPECT_FALSE(broken_tab_contents->ShowingInterstitialPage());
1983 EXPECT_FALSE(broken_tab_contents->IsLoading());
1984 EXPECT_EQ(0, portal_observer1.num_results_received());
1985 EXPECT_EQ(0, NumLoadingTabs());
1986 EXPECT_FALSE(CheckPending(browser()));
1987 EXPECT_EQ(1, browser()->tab_strip_model()->count());
1988 EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE,
1989 GetStateOfTabReloaderAt(browser(), 0));
1990
1991 // Re-enable captive portal checks and fire one. The result should be ignored.
1992 CaptivePortalObserver portal_observer2(browser()->profile());
1993 CaptivePortalService* captive_portal_service =
1994 CaptivePortalServiceFactory::GetForProfile(browser()->profile());
1995 captive_portal_service->SetPortalDetectionEnabledForTest(true);
1996 captive_portal_service->DetectCaptivePortal();
1997 portal_observer2.WaitForResults(1);
1998
1999 EXPECT_FALSE(broken_tab_contents->ShowingInterstitialPage());
2000 EXPECT_FALSE(broken_tab_contents->IsLoading());
2001 EXPECT_EQ(1, portal_observer2.num_results_received());
2002 EXPECT_EQ(captive_portal::RESULT_BEHIND_CAPTIVE_PORTAL,
2003 portal_observer2.captive_portal_result());
2004 EXPECT_EQ(0, NumLoadingTabs());
2005 EXPECT_FALSE(CheckPending(browser()));
2006 EXPECT_EQ(1, browser()->tab_strip_model()->count());
2007 EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE,
2008 GetStateOfTabReloaderAt(browser(), 0));
2009 }
2010
2011 // Same as above, but instead of stopping, the loading page is reloaded. The end
2012 // result is the same. (i.e. page load stops, no interstitials shown)
2013 IN_PROC_BROWSER_TEST_F(CaptivePortalBrowserTest,
2014 InterstitialTimerReloadWhileLoading) {
2015 net::SpawnedTestServer::SSLOptions https_options;
2016 https_options.server_certificate =
2017 net::SpawnedTestServer::SSLOptions::CERT_MISMATCHED_NAME;
2018 net::SpawnedTestServer https_server(
2019 net::SpawnedTestServer::TYPE_HTTPS, https_options,
2020 base::FilePath(FILE_PATH_LITERAL("chrome/test/data")));
2021 ASSERT_TRUE(https_server.Start());
2022 // The path does not matter.
2023 GURL cert_error_url = https_server.GetURL(kTestServerLoginPath);
2024
2025 // Set SSL interstitial delay long enough so that a captive portal result
2026 // is guaranteed to arrive during this window, and a captive portal
2027 // error page is displayed instead of an SSL interstitial.
2028 TabStripModel* tab_strip_model = browser()->tab_strip_model();
2029 WebContents* broken_tab_contents = tab_strip_model->GetActiveWebContents();
2030 SetSSLErrorDisplayDelay(
2031 CaptivePortalTabHelper::FromWebContents(broken_tab_contents),
2032 base::TimeDelta::FromHours(1));
2033
2034 CaptivePortalObserver portal_observer(browser()->profile());
2035 FastErrorWithInterstitialTimer(browser(), cert_error_url);
2036
2037 // Page appears loading. Reloading should cancel the navigation and there
2038 // should be no interstitial.
2039 MultiNavigationObserver test_navigation_observer;
2040 chrome::Reload(browser(), CURRENT_TAB);
2041 test_navigation_observer.WaitForNavigations(2);
2042
2043 EXPECT_FALSE(broken_tab_contents->ShowingInterstitialPage());
2044 EXPECT_FALSE(broken_tab_contents->IsLoading());
2045 EXPECT_EQ(0, portal_observer.num_results_received());
2046 EXPECT_EQ(2, test_navigation_observer.num_navigations());
2047 EXPECT_EQ(0, NumLoadingTabs());
2048 EXPECT_FALSE(CheckPending(browser()));
2049 EXPECT_EQ(1, browser()->tab_strip_model()->count());
2050 EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE,
2051 GetStateOfTabReloaderAt(browser(), 0));
2052
2053 // Re-enable captive portal checks and fire one. The result should be ignored.
2054 CaptivePortalObserver portal_observer2(browser()->profile());
2055 CaptivePortalService* captive_portal_service =
2056 CaptivePortalServiceFactory::GetForProfile(browser()->profile());
2057 captive_portal_service->SetPortalDetectionEnabledForTest(true);
2058 captive_portal_service->DetectCaptivePortal();
2059 portal_observer2.WaitForResults(1);
2060
2061 EXPECT_FALSE(broken_tab_contents->ShowingInterstitialPage());
2062 EXPECT_FALSE(broken_tab_contents->IsLoading());
2063 EXPECT_EQ(1, portal_observer2.num_results_received());
2064 EXPECT_EQ(captive_portal::RESULT_BEHIND_CAPTIVE_PORTAL,
2065 portal_observer2.captive_portal_result());
2066 EXPECT_EQ(0, NumLoadingTabs());
2067 EXPECT_FALSE(CheckPending(browser()));
2068 EXPECT_EQ(1, browser()->tab_strip_model()->count());
2069 EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE,
2070 GetStateOfTabReloaderAt(browser(), 0));
2071 }
2072
2073 // Same as above, but instead of reloading, the page is navigated away. The new
2074 // page should load, and no interstitials shoudl be shown.
2075 IN_PROC_BROWSER_TEST_F(CaptivePortalBrowserTest,
2076 InterstitialTimerNavigateAwayWhileLoading) {
2077 net::SpawnedTestServer::SSLOptions https_options;
2078 https_options.server_certificate =
2079 net::SpawnedTestServer::SSLOptions::CERT_MISMATCHED_NAME;
2080 net::SpawnedTestServer https_server(
2081 net::SpawnedTestServer::TYPE_HTTPS, https_options,
2082 base::FilePath(FILE_PATH_LITERAL("chrome/test/data")));
2083 ASSERT_TRUE(https_server.Start());
2084 // The path does not matter.
2085 GURL cert_error_url = https_server.GetURL(kTestServerLoginPath);
2086
2087 // Set SSL interstitial delay long enough so that a captive portal result
2088 // is guaranteed to arrive during this window, and a captive portal
2089 // error page is displayed instead of an SSL interstitial.
2090 TabStripModel* tab_strip_model = browser()->tab_strip_model();
2091 WebContents* broken_tab_contents = tab_strip_model->GetActiveWebContents();
2092 SetSSLErrorDisplayDelay(
2093 CaptivePortalTabHelper::FromWebContents(broken_tab_contents),
2094 base::TimeDelta::FromHours(1));
2095
2096 CaptivePortalObserver portal_observer(browser()->profile());
2097 FastErrorWithInterstitialTimer(browser(), cert_error_url);
2098
2099 // Page appears loading. Navigating away shouldn't result in any interstitial.
2100 // Can't use ui_test_utils::NavigateToURLWithDisposition because it waits for
2101 // a load stop notification before starting a new navigation.
2102 MultiNavigationObserver test_navigation_observer;
2103 browser()->OpenURL(content::OpenURLParams(
2104 URLRequestMockHTTPJob::GetMockUrl(
2105 base::FilePath(FILE_PATH_LITERAL("title2.html"))),
2106 content::Referrer(),
2107 CURRENT_TAB,
2108 ui::PAGE_TRANSITION_TYPED, false));
2109 test_navigation_observer.WaitForNavigations(2);
2110
2111 EXPECT_FALSE(broken_tab_contents->ShowingInterstitialPage());
2112 EXPECT_FALSE(broken_tab_contents->IsLoading());
2113 EXPECT_EQ(0, portal_observer.num_results_received());
2114 EXPECT_EQ(2, test_navigation_observer.num_navigations());
2115 EXPECT_EQ(0, NumLoadingTabs());
2116 EXPECT_FALSE(CheckPending(browser()));
2117 EXPECT_EQ(1, browser()->tab_strip_model()->count());
2118 EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE,
2119 GetStateOfTabReloaderAt(browser(), 0));
2120
2121 // Re-enable captive portal checks and fire one. The result should be ignored.
2122 CaptivePortalObserver portal_observer2(browser()->profile());
2123 CaptivePortalService* captive_portal_service =
2124 CaptivePortalServiceFactory::GetForProfile(browser()->profile());
2125 captive_portal_service->SetPortalDetectionEnabledForTest(true);
2126 captive_portal_service->DetectCaptivePortal();
2127 portal_observer2.WaitForResults(1);
2128
2129 EXPECT_FALSE(broken_tab_contents->ShowingInterstitialPage());
2130 EXPECT_FALSE(broken_tab_contents->IsLoading());
2131 EXPECT_EQ(1, portal_observer2.num_results_received());
2132 EXPECT_EQ(captive_portal::RESULT_BEHIND_CAPTIVE_PORTAL,
2133 portal_observer2.captive_portal_result());
2134 EXPECT_EQ(0, NumLoadingTabs());
2135 EXPECT_FALSE(CheckPending(browser()));
2136 EXPECT_EQ(1, browser()->tab_strip_model()->count());
2137 EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE,
2138 GetStateOfTabReloaderAt(browser(), 0));
2139 }
2140
2141 // A cert error triggers a captive portal check and results in opening a login
2142 // tab. The user then logs in and the page with the error is reloaded.
2143 IN_PROC_BROWSER_TEST_F(CaptivePortalBrowserTest, SSLCertErrorLogin) {
2144 // Need an HTTP TestServer to handle a dynamically created server redirect.
2145 ASSERT_TRUE(test_server()->Start());
2146
2147 net::SpawnedTestServer::SSLOptions https_options;
2148 https_options.server_certificate =
2149 net::SpawnedTestServer::SSLOptions::CERT_MISMATCHED_NAME;
2150 net::SpawnedTestServer https_server(
2151 net::SpawnedTestServer::TYPE_HTTPS, https_options,
2152 base::FilePath(FILE_PATH_LITERAL("chrome/test/data")));
2153 ASSERT_TRUE(https_server.Start());
2154
2155 // Set SSL interstitial delay to zero so that a captive portal result can not
2156 // arrive during this window, so an SSL interstitial is displayed instead
2157 // of a captive portal error page.
2158 TabStripModel* tab_strip_model = browser()->tab_strip_model();
2159 WebContents* broken_tab_contents = tab_strip_model->GetActiveWebContents();
2160 SetSSLErrorDisplayDelay(
2161 CaptivePortalTabHelper::FromWebContents(broken_tab_contents),
2162 base::TimeDelta());
2163
2164 // Setting the delay to zero above has a race condition: A captive portal
2165 // result triggered by a cert error can arrive before the SSL interstitial
2166 // display timer is fired, even though it's set to zero.
2167 // To avoid this, disable captive portal checks until the SSL interstitial is
2168 // displayed. Once it's displayed, enable portal checks and fire one.
2169 bool disable_portal_check_until_interstitial = true;
2170
2171 // The path does not matter.
2172 GURL cert_error_url = https_server.GetURL(kTestServerLoginPath);
2173 // The interstitial should trigger a captive portal check when it opens, just
2174 // like navigating to kMockHttpsQuickTimeoutUrl.
2175 FastErrorBehindCaptivePortal(
2176 browser(),
2177 true,
2178 cert_error_url,
2179 disable_portal_check_until_interstitial);
2180
2181 EXPECT_EQ(SSLBlockingPage::kTypeForTesting,
2182 GetInterstitialType(broken_tab_contents));
2183
2184 LoginCertError(browser());
1764 } 2185 }
1765 2186
1766 // Tries navigating both the tab that encounters an SSL timeout and the 2187 // Tries navigating both the tab that encounters an SSL timeout and the
1767 // login tab twice, only logging in the second time. 2188 // login tab twice, only logging in the second time.
1768 IN_PROC_BROWSER_TEST_F(CaptivePortalBrowserTest, LoginExtraNavigations) { 2189 IN_PROC_BROWSER_TEST_F(CaptivePortalBrowserTest, LoginExtraNavigations) {
1769 FastTimeoutBehindCaptivePortal(browser(), true); 2190 FastTimeoutBehindCaptivePortal(browser(), true);
1770 2191
1771 // Activate the timed out tab and navigate it to a timeout again. 2192 // Activate the timed out tab and navigate it to a timeout again.
1772 TabStripModel* tab_strip_model = browser()->tab_strip_model(); 2193 TabStripModel* tab_strip_model = browser()->tab_strip_model();
1773 tab_strip_model->ActivateTabAt(0, true); 2194 tab_strip_model->ActivateTabAt(0, true);
(...skipping 432 matching lines...) Expand 10 before | Expand all | Expand 10 after
2206 content::BrowserThread::PostTask( 2627 content::BrowserThread::PostTask(
2207 content::BrowserThread::IO, FROM_HERE, 2628 content::BrowserThread::IO, FROM_HERE,
2208 base::Bind(&AddHstsHost, 2629 base::Bind(&AddHstsHost,
2209 make_scoped_refptr(browser()->profile()->GetRequestContext()), 2630 make_scoped_refptr(browser()->profile()->GetRequestContext()),
2210 http_timeout_url.host())); 2631 http_timeout_url.host()));
2211 2632
2212 SlowLoadBehindCaptivePortal(browser(), true, http_timeout_url, 1, 1); 2633 SlowLoadBehindCaptivePortal(browser(), true, http_timeout_url, 1, 1);
2213 Login(browser(), 1, 0); 2634 Login(browser(), 1, 0);
2214 FailLoadsAfterLogin(browser(), 1); 2635 FailLoadsAfterLogin(browser(), 1);
2215 } 2636 }
2637
2638 // A slow SSL load starts. The reloader triggers a captive portal check, finds a
2639 // captive portal. The SSL commits with a cert error, triggering another captive
2640 // portal check.
2641 // The second check finds no captive portal. The reloader triggers a reload at
2642 // the same time SSL error handler tries to show an interstitial. Should result
2643 // in an SSL interstitial.
2644 IN_PROC_BROWSER_TEST_F(CaptivePortalBrowserTest,
2645 InterstitialTimerCertErrorAfterSlowLoad) {
2646 // Use a url that triggers a slow load, instead of creating an https server.
2647 GURL cert_error_url = GURL(kMockHttpsUrl);
2648
2649 TabStripModel* tab_strip_model = browser()->tab_strip_model();
2650 int broken_tab_index = tab_strip_model->active_index();
2651 WebContents* broken_tab_contents = tab_strip_model->GetActiveWebContents();
2652 CaptivePortalTabReloader* tab_reloader = GetTabReloader(broken_tab_contents);
2653 SetSlowSSLLoadTime(tab_reloader, base::TimeDelta());
2654
2655 SlowLoadBehindCaptivePortal(browser(), true, cert_error_url, 1, 1);
2656
2657 // No longer behind a captive portal. Committing the SSL page should trigger
2658 // an SSL interstitial which triggers a new captive portal check. Since there
2659 // is no captive portal anymore, should end up with an SSL interstitial.
2660 URLRequestMockCaptivePortalJobFactory::SetBehindCaptivePortal(false);
2661
2662 CaptivePortalObserver portal_observer(browser()->profile());
2663 MultiNavigationObserver navigation_observer;
2664 URLRequestTimeoutOnDemandJob::FailJobsWithCertError(1);
2665 navigation_observer.WaitForNavigations(1);
2666
2667 EXPECT_EQ(CaptivePortalTabReloader::STATE_NEEDS_RELOAD,
2668 GetStateOfTabReloaderAt(browser(), broken_tab_index));
2669
2670 WaitForInterstitialAttach(broken_tab_contents);
2671 portal_observer.WaitForResults(1);
2672
2673 EXPECT_EQ(SSLBlockingPage::kTypeForTesting,
2674 GetInterstitialType(broken_tab_contents));
2675 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698