15821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Copyright (c) 2012 The Chromium Authors. All rights reserved.
25821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be
35821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// found in the LICENSE file.
45821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
55821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/captive_portal/captive_portal_tab_reloader.h"
65821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
75821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/callback.h"
89ab5563a3196760eb381d102cbb2bc0f7abc6a50Ben Murdoch#include "base/message_loop/message_loop.h"
95821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/captive_portal/captive_portal_service.h"
105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/test/base/chrome_render_view_host_test_harness.h"
115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "content/public/browser/interstitial_page.h"
125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "content/public/browser/interstitial_page_delegate.h"
135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "content/public/browser/web_contents.h"
145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "net/base/net_errors.h"
15c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)#include "net/cert/cert_status_flags.h"
162a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "net/ssl/ssl_info.h"
175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "testing/gmock/include/gmock/gmock.h"
185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "testing/gtest/include/gtest/gtest.h"
19eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch#include "url/gurl.h"
205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
215c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liuusing captive_portal::CaptivePortalResult;
225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Used for testing CaptivePortalTabReloader in isolation from the observer.
245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Exposes a number of private functions and mocks out others.
255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class TestCaptivePortalTabReloader : public CaptivePortalTabReloader {
265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public:
275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  explicit TestCaptivePortalTabReloader(content::WebContents* web_contents)
285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      : CaptivePortalTabReloader(NULL,
295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                 web_contents,
305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                 base::Callback<void(void)>()) {
315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  virtual ~TestCaptivePortalTabReloader() {
345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool TimerRunning() {
375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return slow_ssl_load_timer_.IsRunning();
385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The following methods are aliased so they can be publicly accessed by the
415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // unit tests.
425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  State state() const {
445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return CaptivePortalTabReloader::state();
455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  void set_slow_ssl_load_time(base::TimeDelta slow_ssl_load_time) {
485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    EXPECT_FALSE(TimerRunning());
495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    CaptivePortalTabReloader::set_slow_ssl_load_time(slow_ssl_load_time);
505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // CaptivePortalTabReloader:
535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  MOCK_METHOD0(ReloadTab, void());
545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  MOCK_METHOD0(MaybeOpenCaptivePortalLoginTab, void());
555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  MOCK_METHOD0(CheckForCaptivePortal, void());
565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) private:
585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DISALLOW_COPY_AND_ASSIGN(TestCaptivePortalTabReloader);
595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)};
605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Used to test behavior when a WebContents is showing an interstitial page.
625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class MockInterstitialPageDelegate : public content::InterstitialPageDelegate {
635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public:
645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The newly created MockInterstitialPageDelegate will be owned by the
655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // WebContents' InterstitialPage, and cleaned up when the WebContents
665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // destroys it.
675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  explicit MockInterstitialPageDelegate(
685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      content::WebContents* web_contents) {
695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    content::InterstitialPage* interstitial_page =
705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        content::InterstitialPage::Create(
715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            web_contents, true, GURL("http://blah"), this);
725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    interstitial_page->DontCreateViewForTesting();
735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    interstitial_page->Show();
745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  virtual ~MockInterstitialPageDelegate() {
775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) private:
805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // InterstitialPageDelegate implementation:
815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  virtual std::string GetHTMLContents() OVERRIDE {
825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return "HTML Contents";
835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DISALLOW_COPY_AND_ASSIGN(MockInterstitialPageDelegate);
865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)};
875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class CaptivePortalTabReloaderTest : public ChromeRenderViewHostTestHarness {
895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public:
905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // testing::Test:
915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  virtual void SetUp() OVERRIDE {
925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ChromeRenderViewHostTestHarness::SetUp();
935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    tab_reloader_.reset(new testing::StrictMock<TestCaptivePortalTabReloader>(
945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        web_contents()));
955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // Most tests don't run the message loop, so don't use a timer for them.
975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    tab_reloader_->set_slow_ssl_load_time(base::TimeDelta());
985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  virtual void TearDown() OVERRIDE {
1015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    EXPECT_FALSE(tab_reloader().TimerRunning());
1025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    tab_reloader_.reset(NULL);
1035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ChromeRenderViewHostTestHarness::TearDown();
1045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
1055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  TestCaptivePortalTabReloader& tab_reloader() { return *tab_reloader_.get(); }
1075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) private:
1095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  scoped_ptr<TestCaptivePortalTabReloader> tab_reloader_;
1105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)};
1115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Simulates a slow SSL load when the Internet is connected.
1135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TEST_F(CaptivePortalTabReloaderTest, InternetConnected) {
1145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
1155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadStart(true);
1175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_TIMER_RUNNING,
1185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
1195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_TRUE(tab_reloader().TimerRunning());
1205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_CALL(tab_reloader(), CheckForCaptivePortal()).Times(1);
12290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  base::MessageLoop::current()->RunUntilIdle();
1235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_FALSE(tab_reloader().TimerRunning());
1245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_MAYBE_BROKEN_BY_PORTAL,
1255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
1265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1275c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  tab_reloader().OnCaptivePortalResults(
1285c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_INTERNET_CONNECTED,
1295c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_INTERNET_CONNECTED);
1305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
1325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_FALSE(tab_reloader().TimerRunning());
1335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadCommitted(net::OK);
1355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
1365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Simulates a slow SSL load when the Internet is connected.  In this case,
1395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// the timeout error occurs before the timer triggers.  Unlikely to happen
1405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// in practice, but best if it still works.
1415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TEST_F(CaptivePortalTabReloaderTest, InternetConnectedTimeout) {
1425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
1435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadStart(true);
1455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_TIMER_RUNNING,
1465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
1475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_TRUE(tab_reloader().TimerRunning());
1485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_CALL(tab_reloader(), CheckForCaptivePortal()).Times(1);
1505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadCommitted(net::ERR_CONNECTION_TIMED_OUT);
1515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_FALSE(tab_reloader().TimerRunning());
1525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_MAYBE_BROKEN_BY_PORTAL,
1535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
1545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1555c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  tab_reloader().OnCaptivePortalResults(
1565c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_INTERNET_CONNECTED,
1575c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_INTERNET_CONNECTED);
1585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
1605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Simulates a slow SSL load when captive portal checks return no response.
1635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TEST_F(CaptivePortalTabReloaderTest, NoResponse) {
1645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
1655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadStart(true);
1675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_TIMER_RUNNING,
1685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
1695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_TRUE(tab_reloader().TimerRunning());
1705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_CALL(tab_reloader(), CheckForCaptivePortal()).Times(1);
17290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  base::MessageLoop::current()->RunUntilIdle();
1735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_FALSE(tab_reloader().TimerRunning());
1745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_MAYBE_BROKEN_BY_PORTAL,
1755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
1765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1775c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  tab_reloader().OnCaptivePortalResults(captive_portal::RESULT_NO_RESPONSE,
1785c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu                                        captive_portal::RESULT_NO_RESPONSE);
1795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
1815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_FALSE(tab_reloader().TimerRunning());
1825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadCommitted(net::OK);
1845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
1855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Simulates a slow HTTP load when behind a captive portal, that eventually.
1885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// tiems out.  Since it's HTTP, the TabReloader should do nothing.
1895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TEST_F(CaptivePortalTabReloaderTest, DoesNothingOnHttp) {
1905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadStart(false);
1915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_FALSE(tab_reloader().TimerRunning());
1925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
1935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1945c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  tab_reloader().OnCaptivePortalResults(
1955c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_INTERNET_CONNECTED,
1965c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_BEHIND_CAPTIVE_PORTAL);
1975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
1985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The user logs in.
2005c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  tab_reloader().OnCaptivePortalResults(
2015c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_BEHIND_CAPTIVE_PORTAL,
2025c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_INTERNET_CONNECTED);
2035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
2045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The page times out.
2065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadCommitted(net::ERR_CONNECTION_TIMED_OUT);
2075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
2085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
2095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Simulate the normal login process.  The user logs in before the error page
2115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// in the original tab commits.
2125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TEST_F(CaptivePortalTabReloaderTest, Login) {
2135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadStart(true);
2145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_CALL(tab_reloader(), CheckForCaptivePortal()).Times(1);
21690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  base::MessageLoop::current()->RunUntilIdle();
2175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_FALSE(tab_reloader().TimerRunning());
2185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_MAYBE_BROKEN_BY_PORTAL,
2195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
2205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The captive portal service detects a captive portal.  The TabReloader
2225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // should try and create a new login tab in response.
2235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_CALL(tab_reloader(), MaybeOpenCaptivePortalLoginTab()).Times(1);
2245c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  tab_reloader().OnCaptivePortalResults(
2255c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_INTERNET_CONNECTED,
2265c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_BEHIND_CAPTIVE_PORTAL);
2275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_BROKEN_BY_PORTAL,
2285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
2295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_FALSE(tab_reloader().TimerRunning());
2305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The user logs on from another tab, and a captive portal check is triggered.
2325c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  tab_reloader().OnCaptivePortalResults(
2335c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_BEHIND_CAPTIVE_PORTAL,
2345c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_INTERNET_CONNECTED);
2355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NEEDS_RELOAD,
2365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
2375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The error page commits, which should start an asynchronous reload.
2395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadCommitted(net::ERR_CONNECTION_TIMED_OUT);
2405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NEEDS_RELOAD,
2415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
2425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_CALL(tab_reloader(), ReloadTab()).Times(1);
24490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  base::MessageLoop::current()->RunUntilIdle();
2455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
2465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
2475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Simulate the normal login process.  The user logs in after the tab finishes
2495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// loading the error page.
2505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TEST_F(CaptivePortalTabReloaderTest, LoginLate) {
2515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadStart(true);
2525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_CALL(tab_reloader(), CheckForCaptivePortal()).Times(1);
25490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  base::MessageLoop::current()->RunUntilIdle();
2555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_FALSE(tab_reloader().TimerRunning());
2565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_MAYBE_BROKEN_BY_PORTAL,
2575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
2585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The captive portal service detects a captive portal.  The TabReloader
2605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // should try and create a new login tab in response.
2615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_CALL(tab_reloader(), MaybeOpenCaptivePortalLoginTab()).Times(1);
2625c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  tab_reloader().OnCaptivePortalResults(
2635c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_INTERNET_CONNECTED,
2645c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_BEHIND_CAPTIVE_PORTAL);
2655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_BROKEN_BY_PORTAL,
2665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
2675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_FALSE(tab_reloader().TimerRunning());
2685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The error page commits.
2705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadCommitted(net::ERR_CONNECTION_TIMED_OUT);
2715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_BROKEN_BY_PORTAL,
2725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
2735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The user logs on from another tab, and a captive portal check is triggered.
2755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_CALL(tab_reloader(), ReloadTab()).Times(1);
2765c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  tab_reloader().OnCaptivePortalResults(
2775c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_BEHIND_CAPTIVE_PORTAL,
2785c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_INTERNET_CONNECTED);
2795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
2805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
2815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Simulate a login after the tab times out unexpectedly quickly.
2835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TEST_F(CaptivePortalTabReloaderTest, TimeoutFast) {
2845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadStart(true);
2855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The error page commits, which should trigger a captive portal check,
2875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // since the timer's still running.
2885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_CALL(tab_reloader(), CheckForCaptivePortal()).Times(1);
2895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadCommitted(net::ERR_CONNECTION_TIMED_OUT);
2905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_MAYBE_BROKEN_BY_PORTAL,
2915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
2925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The captive portal service detects a captive portal.  The TabReloader
2945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // should try and create a new login tab in response.
2955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_CALL(tab_reloader(), MaybeOpenCaptivePortalLoginTab()).Times(1);
2965c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  tab_reloader().OnCaptivePortalResults(
2975c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_INTERNET_CONNECTED,
2985c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_BEHIND_CAPTIVE_PORTAL);
2995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_BROKEN_BY_PORTAL,
3005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
3015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_FALSE(tab_reloader().TimerRunning());
3025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The user logs on from another tab, and a captive portal check is triggered.
3045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_CALL(tab_reloader(), ReloadTab()).Times(1);
3055c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  tab_reloader().OnCaptivePortalResults(
3065c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_BEHIND_CAPTIVE_PORTAL,
3075c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_INTERNET_CONNECTED);
3085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
3095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
3105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// An SSL protocol error triggers a captive portal check behind a captive
3125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// portal.  The user then logs in.
3135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TEST_F(CaptivePortalTabReloaderTest, SSLProtocolError) {
3145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadStart(true);
3155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The error page commits, which should trigger a captive portal check,
3175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // since the timer's still running.
3185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_CALL(tab_reloader(), CheckForCaptivePortal()).Times(1);
3195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadCommitted(net::ERR_SSL_PROTOCOL_ERROR);
3205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_MAYBE_BROKEN_BY_PORTAL,
3215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
3225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The captive portal service detects a captive portal.  The TabReloader
3245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // should try and create a new login tab in response.
3255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_CALL(tab_reloader(), MaybeOpenCaptivePortalLoginTab()).Times(1);
3265c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  tab_reloader().OnCaptivePortalResults(
3275c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_INTERNET_CONNECTED,
3285c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_BEHIND_CAPTIVE_PORTAL);
3295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_BROKEN_BY_PORTAL,
3305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
3315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_FALSE(tab_reloader().TimerRunning());
3325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The user logs on from another tab, and a captive portal check is triggered.
3345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_CALL(tab_reloader(), ReloadTab()).Times(1);
3355c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  tab_reloader().OnCaptivePortalResults(
3365c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_BEHIND_CAPTIVE_PORTAL,
3375c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_INTERNET_CONNECTED);
3385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
3395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
3405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// An SSL protocol error triggers a captive portal check behind a captive
3425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// portal.  The user logs in before the results from the captive portal check
3435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// completes.
3445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TEST_F(CaptivePortalTabReloaderTest, SSLProtocolErrorFastLogin) {
3455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadStart(true);
3465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The error page commits, which should trigger a captive portal check,
3485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // since the timer's still running.
3495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_CALL(tab_reloader(), CheckForCaptivePortal()).Times(1);
3505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadCommitted(net::ERR_SSL_PROTOCOL_ERROR);
3515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_MAYBE_BROKEN_BY_PORTAL,
3525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
3535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The user has logged in from another tab.  The tab automatically reloads.
3555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_CALL(tab_reloader(), ReloadTab()).Times(1);
3565c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  tab_reloader().OnCaptivePortalResults(
3575c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_BEHIND_CAPTIVE_PORTAL,
3585c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_INTERNET_CONNECTED);
3595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
3605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
3615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// An SSL protocol error triggers a captive portal check behind a captive
3635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// portal.  The user logs in before the results from the captive portal check
3645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// completes.  This case is probably not too likely, but should be handled.
3655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TEST_F(CaptivePortalTabReloaderTest, SSLProtocolErrorAlreadyLoggedIn) {
3665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadStart(true);
3675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The user logs in from another tab before the tab errors out.
3695c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  tab_reloader().OnCaptivePortalResults(
3705c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_BEHIND_CAPTIVE_PORTAL,
3715c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_INTERNET_CONNECTED);
3725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NEEDS_RELOAD,
3735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
3745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The error page commits, which should trigger a reload.
3765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_CALL(tab_reloader(), ReloadTab()).Times(1);
3775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadCommitted(net::ERR_SSL_PROTOCOL_ERROR);
37890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  base::MessageLoop::current()->RunUntilIdle();
3795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
3805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
3815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Simulate the case that a user has already logged in before the tab receives a
3835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// captive portal result, but a RESULT_BEHIND_CAPTIVE_PORTAL was received
3845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// before the tab started loading.
3855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TEST_F(CaptivePortalTabReloaderTest, AlreadyLoggedIn) {
3865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadStart(true);
3875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_CALL(tab_reloader(), CheckForCaptivePortal()).Times(1);
38990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  base::MessageLoop::current()->RunUntilIdle();
3905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_FALSE(tab_reloader().TimerRunning());
3915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_MAYBE_BROKEN_BY_PORTAL,
3925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
3935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The user has already logged in.  Since the last result found a captive
3955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // portal, the tab will be reloaded if a timeout is committed.
3965c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  tab_reloader().OnCaptivePortalResults(
3975c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_BEHIND_CAPTIVE_PORTAL,
3985c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_INTERNET_CONNECTED);
3995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NEEDS_RELOAD,
4005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
4015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The error page commits, which should start an asynchronous reload.
4035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadCommitted(net::ERR_CONNECTION_TIMED_OUT);
4045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NEEDS_RELOAD,
4055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
4065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_CALL(tab_reloader(), ReloadTab()).Times(1);
40890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  base::MessageLoop::current()->RunUntilIdle();
4095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
4105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
4115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Same as above, except the result is received even before the timer triggers,
4135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// due to a captive portal test request from some external source, like a login
4145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// tab.
4155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TEST_F(CaptivePortalTabReloaderTest, AlreadyLoggedInBeforeTimerTriggers) {
4165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadStart(true);
4175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The user has already logged in.  Since the last result indicated there is
4195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // a captive portal, the tab will be reloaded if it times out.
4205c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  tab_reloader().OnCaptivePortalResults(
4215c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_BEHIND_CAPTIVE_PORTAL,
4225c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_INTERNET_CONNECTED);
4235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NEEDS_RELOAD,
4245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
4255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_FALSE(tab_reloader().TimerRunning());
4265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The error page commits, which should start an asynchronous reload.
4285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadCommitted(net::ERR_CONNECTION_TIMED_OUT);
4295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NEEDS_RELOAD,
4305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
4315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_CALL(tab_reloader(), ReloadTab()).Times(1);
43390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  base::MessageLoop::current()->RunUntilIdle();
4345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
4355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
4365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Simulate the user logging in while the timer is still running.  May happen
4385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// if the tab is reloaded just before logging in on another tab.
4395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TEST_F(CaptivePortalTabReloaderTest, LoginWhileTimerRunning) {
4405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadStart(true);
4415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_TIMER_RUNNING,
4425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
4435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_TRUE(tab_reloader().TimerRunning());
4445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The user has already logged in.
4465c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  tab_reloader().OnCaptivePortalResults(
4475c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_BEHIND_CAPTIVE_PORTAL,
4485c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_INTERNET_CONNECTED);
4495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NEEDS_RELOAD,
4505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
4515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The error page commits, which should start an asynchronous reload.
4535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadCommitted(net::ERR_CONNECTION_TIMED_OUT);
4545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NEEDS_RELOAD,
4555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
4565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_CALL(tab_reloader(), ReloadTab()).Times(1);
45890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  base::MessageLoop::current()->RunUntilIdle();
4595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
4605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
4615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Simulate a captive portal being detected while the time is still running.
4635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// The captive portal check triggered by the timer detects the captive portal
4645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// again, and then the user logs in.
4655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TEST_F(CaptivePortalTabReloaderTest, BehindPortalResultWhileTimerRunning) {
4665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadStart(true);
4675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_TIMER_RUNNING,
4685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
4695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_TRUE(tab_reloader().TimerRunning());
4705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The user is behind a captive portal, but since the tab hasn't timed out,
4725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // the message is ignored.
4735c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  tab_reloader().OnCaptivePortalResults(
4745c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_INTERNET_CONNECTED,
4755c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_BEHIND_CAPTIVE_PORTAL);
4765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_TIMER_RUNNING,
4775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
4785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The rest proceeds as normal.
4805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_CALL(tab_reloader(), CheckForCaptivePortal()).Times(1);
48190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  base::MessageLoop::current()->RunUntilIdle();
4825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_MAYBE_BROKEN_BY_PORTAL,
4835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
4845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The captive portal service detects a captive portal, and this time the
4865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // tab tries to create a login tab.
4875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_CALL(tab_reloader(), MaybeOpenCaptivePortalLoginTab()).Times(1);
4885c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  tab_reloader().OnCaptivePortalResults(
4895c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_BEHIND_CAPTIVE_PORTAL,
4905c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_BEHIND_CAPTIVE_PORTAL);
4915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_BROKEN_BY_PORTAL,
4925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
4935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_FALSE(tab_reloader().TimerRunning());
4945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The user logs on from another tab, and a captive portal check is triggered.
4965c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  tab_reloader().OnCaptivePortalResults(
4975c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_BEHIND_CAPTIVE_PORTAL,
4985c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_INTERNET_CONNECTED);
4995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NEEDS_RELOAD,
5005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
5015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The error page commits, which should start an asynchronous reload.
5035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadCommitted(net::ERR_CONNECTION_TIMED_OUT);
5045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NEEDS_RELOAD,
5055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
5065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_CALL(tab_reloader(), ReloadTab()).Times(1);
50890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  base::MessageLoop::current()->RunUntilIdle();
5095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
5105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
5115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// The CaptivePortalService detects the user has logged in to a captive portal
5135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// while the timer is still running, but the original load succeeds, so no
5145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// reload is done.
5155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TEST_F(CaptivePortalTabReloaderTest, LogInWhileTimerRunningNoError) {
5165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadStart(true);
5175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_TIMER_RUNNING,
5185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
5195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_TRUE(tab_reloader().TimerRunning());
5205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The user has already logged in.
5225c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  tab_reloader().OnCaptivePortalResults(
5235c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_BEHIND_CAPTIVE_PORTAL,
5245c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_INTERNET_CONNECTED);
5255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_FALSE(tab_reloader().TimerRunning());
5265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NEEDS_RELOAD,
5275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
5285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The page successfully commits, so no reload is triggered.
5305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadCommitted(net::OK);
5315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
5325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
5335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Simulate the login process when there's an SSL certificate error.
5355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TEST_F(CaptivePortalTabReloaderTest, SSLCertErrorLogin) {
5365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadStart(true);
5375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_TIMER_RUNNING,
5385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
5395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The load is interrupted by an interstitial page.  The interstitial page
5415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // is created after the TabReloader is notified.
5425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_CALL(tab_reloader(), CheckForCaptivePortal());
5435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  net::SSLInfo ssl_info;
5445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ssl_info.SetCertError(net::CERT_STATUS_COMMON_NAME_INVALID);
5455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnSSLCertError(ssl_info);
5465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_MAYBE_BROKEN_BY_PORTAL,
5475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
5485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_FALSE(tab_reloader().TimerRunning());
5495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The MockInterstitialPageDelegate will cleaned up by the WebContents.
5505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new MockInterstitialPageDelegate(web_contents());
5515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Captive portal probe finds a captive portal.
5535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_CALL(tab_reloader(), MaybeOpenCaptivePortalLoginTab()).Times(1);
5545c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  tab_reloader().OnCaptivePortalResults(
5555c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_INTERNET_CONNECTED,
5565c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_BEHIND_CAPTIVE_PORTAL);
5575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The user logs in.  Since the interstitial is showing, the page should
5595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // be reloaded, despite still having a provisional load.
5605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_CALL(tab_reloader(), ReloadTab()).Times(1);
5615c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  tab_reloader().OnCaptivePortalResults(
5625c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_BEHIND_CAPTIVE_PORTAL,
5635c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_INTERNET_CONNECTED);
5645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
5655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Simulate an HTTP redirect to HTTPS, when the Internet is connected.
5675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TEST_F(CaptivePortalTabReloaderTest, HttpToHttpsRedirectInternetConnected) {
5685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadStart(false);
5695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // There should be no captive portal check pending.
57090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  base::MessageLoop::current()->RunUntilIdle();
5715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // HTTP to HTTPS redirect.
5735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnRedirect(true);
5745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_TIMER_RUNNING,
5755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
5765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_TRUE(tab_reloader().TimerRunning());
5775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_CALL(tab_reloader(), CheckForCaptivePortal()).Times(1);
57990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  base::MessageLoop::current()->RunUntilIdle();
5805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_FALSE(tab_reloader().TimerRunning());
5815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_MAYBE_BROKEN_BY_PORTAL,
5825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
5835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5845c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  tab_reloader().OnCaptivePortalResults(
5855c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_INTERNET_CONNECTED,
5865c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_INTERNET_CONNECTED);
5875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
5895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_FALSE(tab_reloader().TimerRunning());
5905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadCommitted(net::OK);
5925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
5935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
5945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Simulate an HTTP redirect to HTTPS and subsequent Login, when the user logs
5965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// in before the original page commits.
5975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TEST_F(CaptivePortalTabReloaderTest, HttpToHttpsRedirectLogin) {
5985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadStart(false);
5995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // There should be no captive portal check pending.
60090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  base::MessageLoop::current()->RunUntilIdle();
6015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // HTTP to HTTPS redirect.
6035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnRedirect(true);
6045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_TIMER_RUNNING,
6055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
6065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_CALL(tab_reloader(), CheckForCaptivePortal()).Times(1);
60890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  base::MessageLoop::current()->RunUntilIdle();
6095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_FALSE(tab_reloader().TimerRunning());
6105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_MAYBE_BROKEN_BY_PORTAL,
6115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
6125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The captive portal service detects a captive portal.  The TabReloader
6145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // should try and create a new login tab in response.
6155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_CALL(tab_reloader(), MaybeOpenCaptivePortalLoginTab()).Times(1);
6165c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  tab_reloader().OnCaptivePortalResults(
6175c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_INTERNET_CONNECTED,
6185c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_BEHIND_CAPTIVE_PORTAL);
6195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_BROKEN_BY_PORTAL,
6205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
6215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_FALSE(tab_reloader().TimerRunning());
6225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The user logs on from another tab, and a captive portal check is triggered.
6245c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  tab_reloader().OnCaptivePortalResults(
6255c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_BEHIND_CAPTIVE_PORTAL,
6265c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_INTERNET_CONNECTED);
6275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NEEDS_RELOAD,
6285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
6295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The error page commits, which should start an asynchronous reload.
6315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadCommitted(net::ERR_CONNECTION_TIMED_OUT);
6325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NEEDS_RELOAD,
6335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
6345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_CALL(tab_reloader(), ReloadTab()).Times(1);
63690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  base::MessageLoop::current()->RunUntilIdle();
6375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
6385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
6395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Simulate the case where an HTTPs page redirects to an HTTPS page, before
6415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// the timer triggers.
6425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TEST_F(CaptivePortalTabReloaderTest, HttpsToHttpRedirect) {
6435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadStart(true);
6445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_TIMER_RUNNING,
6455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
6465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnRedirect(false);
6485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
6495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_FALSE(tab_reloader().TimerRunning());
6505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // There should be no captive portal check pending after the redirect.
65290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  base::MessageLoop::current()->RunUntilIdle();
6535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Logging in shouldn't do anything.
6555c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  tab_reloader().OnCaptivePortalResults(
6565c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_BEHIND_CAPTIVE_PORTAL,
6575c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_INTERNET_CONNECTED);
6585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
6595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
6605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Check that an HTTPS to HTTPS redirect results in no timer running.
6625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TEST_F(CaptivePortalTabReloaderTest, HttpsToHttpsRedirect) {
6635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadStart(true);
6645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_TIMER_RUNNING,
6655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
6665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnRedirect(true);
6685c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
6695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_FALSE(tab_reloader().TimerRunning());
6705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Nothing should happen.
67190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  base::MessageLoop::current()->RunUntilIdle();
6725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
6735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Check that an HTTPS to HTTP to HTTPS redirect results in no timer running.
6755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TEST_F(CaptivePortalTabReloaderTest, HttpsToHttpToHttpsRedirect) {
6765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadStart(true);
6775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_TIMER_RUNNING,
6785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_reloader().state());
6795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnRedirect(false);
6815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
6825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_FALSE(tab_reloader().TimerRunning());
6835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnRedirect(true);
6855c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
6865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_FALSE(tab_reloader().TimerRunning());
6875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Nothing should happen.
68890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  base::MessageLoop::current()->RunUntilIdle();
6895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
6905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Check that an HTTP to HTTP redirect results in the timer not running.
6925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TEST_F(CaptivePortalTabReloaderTest, HttpToHttpRedirect) {
6935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnLoadStart(false);
6945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
6955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  tab_reloader().OnRedirect(false);
6975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
6985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_FALSE(tab_reloader().TimerRunning());
6995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // There should be no captive portal check pending after the redirect.
70190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  base::MessageLoop::current()->RunUntilIdle();
7025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Logging in shouldn't do anything.
7045c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  tab_reloader().OnCaptivePortalResults(
7055c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_BEHIND_CAPTIVE_PORTAL,
7065c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      captive_portal::RESULT_INTERNET_CONNECTED);
7075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(CaptivePortalTabReloader::STATE_NONE, tab_reloader().state());
7085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
709