1 // Copyright (c) 2013 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
5 #ifndef CHROME_BROWSER_CHROMEOS_NET_NETWORK_PORTAL_DETECTOR_IMPL_H_
6 #define CHROME_BROWSER_CHROMEOS_NET_NETWORK_PORTAL_DETECTOR_IMPL_H_
10 #include "base/basictypes.h"
11 #include "base/cancelable_callback.h"
12 #include "base/compiler_specific.h"
13 #include "base/containers/hash_tables.h"
14 #include "base/memory/ref_counted.h"
15 #include "base/memory/scoped_ptr.h"
16 #include "base/memory/weak_ptr.h"
17 #include "base/observer_list.h"
18 #include "base/threading/non_thread_safe.h"
19 #include "base/time/time.h"
20 #include "chrome/browser/chromeos/net/network_portal_detector.h"
21 #include "chrome/browser/chromeos/net/network_portal_detector_strategy.h"
22 #include "chrome/browser/chromeos/net/network_portal_notification_controller.h"
23 #include "chromeos/network/network_state_handler_observer.h"
24 #include "components/captive_portal/captive_portal_detector.h"
25 #include "components/captive_portal/captive_portal_types.h"
26 #include "content/public/browser/notification_observer.h"
27 #include "content/public/browser/notification_registrar.h"
28 #include "net/url_request/url_fetcher.h"
32 class URLRequestContextGetter;
39 // This class handles all notifications about network changes from
40 // NetworkStateHandler and delegates portal detection for the default
41 // network to CaptivePortalService.
42 class NetworkPortalDetectorImpl
43 : public NetworkPortalDetector,
44 public base::NonThreadSafe,
45 public chromeos::NetworkStateHandlerObserver,
46 public content::NotificationObserver,
47 public PortalDetectorStrategy::Delegate {
49 static const char kOobeDetectionResultHistogram[];
50 static const char kOobeDetectionDurationHistogram[];
51 static const char kOobeShillOnlineHistogram[];
52 static const char kOobeShillPortalHistogram[];
53 static const char kOobeShillOfflineHistogram[];
54 static const char kOobePortalToOnlineHistogram[];
56 static const char kSessionDetectionResultHistogram[];
57 static const char kSessionDetectionDurationHistogram[];
58 static const char kSessionShillOnlineHistogram[];
59 static const char kSessionShillPortalHistogram[];
60 static const char kSessionShillOfflineHistogram[];
61 static const char kSessionPortalToOnlineHistogram[];
63 explicit NetworkPortalDetectorImpl(
64 const scoped_refptr<net::URLRequestContextGetter>& request_context);
65 virtual ~NetworkPortalDetectorImpl();
67 // NetworkPortalDetector implementation:
68 virtual void AddObserver(Observer* observer) OVERRIDE;
69 virtual void AddAndFireObserver(Observer* observer) OVERRIDE;
70 virtual void RemoveObserver(Observer* observer) OVERRIDE;
71 virtual CaptivePortalState GetCaptivePortalState(
72 const std::string& service_path) OVERRIDE;
73 virtual bool IsEnabled() OVERRIDE;
74 virtual void Enable(bool start_detection) OVERRIDE;
75 virtual bool StartDetectionIfIdle() OVERRIDE;
76 virtual void SetStrategy(PortalDetectorStrategy::StrategyId id) OVERRIDE;
78 // NetworkStateHandlerObserver implementation:
79 virtual void DefaultNetworkChanged(const NetworkState* network) OVERRIDE;
81 // PortalDetectorStrategy::Delegate implementation:
82 virtual int AttemptCount() OVERRIDE;
83 virtual base::TimeTicks AttemptStartTime() OVERRIDE;
84 virtual base::TimeTicks GetCurrentTimeTicks() OVERRIDE;
87 friend class NetworkPortalDetectorImplTest;
88 friend class NetworkPortalDetectorImplBrowserTest;
90 typedef std::string NetworkId;
91 typedef base::hash_map<NetworkId, CaptivePortalState> CaptivePortalStateMap;
94 // No portal check is running.
96 // Waiting for portal check.
97 STATE_PORTAL_CHECK_PENDING,
98 // Portal check is in progress.
99 STATE_CHECKING_FOR_PORTAL,
102 // Starts detection process.
103 void StartDetection();
105 // Stops whole detection process.
106 void StopDetection();
108 // Internal predicate which describes set of states from which
109 // DetectCaptivePortal() can be called.
110 bool CanPerformAttempt() const;
112 // Initiates Captive Portal detection attempt after |delay|.
113 // You should check CanPerformAttempt() before calling this method.
114 void ScheduleAttempt(const base::TimeDelta& delay);
116 // Starts detection attempt.
119 // Called when portal check is timed out. Cancels portal check and calls
120 // OnPortalDetectionCompleted() with RESULT_NO_RESPONSE as a result.
121 void OnAttemptTimeout();
123 // Called by CaptivePortalDetector when detection attempt completes.
124 void OnAttemptCompleted(
125 const captive_portal::CaptivePortalDetector::Results& results);
127 // content::NotificationObserver implementation:
128 virtual void Observe(int type,
129 const content::NotificationSource& source,
130 const content::NotificationDetails& details) OVERRIDE;
132 // Stores captive portal state for a |network| and notifies observers.
133 void OnDetectionCompleted(const NetworkState* network,
134 const CaptivePortalState& results);
136 // Notifies observers that portal detection is completed for a |network|.
137 void NotifyDetectionCompleted(const NetworkState* network,
138 const CaptivePortalState& state);
140 State state() const { return state_; }
142 bool is_idle() const {
143 return state_ == STATE_IDLE;
145 bool is_portal_check_pending() const {
146 return state_ == STATE_PORTAL_CHECK_PENDING;
148 bool is_checking_for_portal() const {
149 return state_ == STATE_CHECKING_FOR_PORTAL;
152 int attempt_count_for_testing() {
153 return attempt_count_;
156 void set_attempt_count_for_testing(int attempt_count) {
157 attempt_count_ = attempt_count;
160 // Returns delay before next portal check. Used by unit tests.
161 const base::TimeDelta& next_attempt_delay_for_testing() const {
162 return next_attempt_delay_;
165 // Returns true if attempt timeout callback isn't fired or
167 bool AttemptTimeoutIsCancelledForTesting() const;
169 // Record detection stats such as detection duration and detection
171 void RecordDetectionStats(const NetworkState* network,
172 CaptivePortalStatus status);
174 // Sets current test time ticks. Used by unit tests.
175 void set_time_ticks_for_testing(const base::TimeTicks& time_ticks) {
176 time_ticks_for_testing_ = time_ticks;
179 // Advances current test time ticks. Used by unit tests.
180 void advance_time_ticks_for_testing(const base::TimeDelta& delta) {
181 time_ticks_for_testing_ += delta;
184 // Name of the default network.
185 std::string default_network_name_;
187 // Unique identifier of the default network.
188 std::string default_network_id_;
190 // Service path of the default network.
191 std::string default_service_path_;
193 // Connection state of the default network.
194 std::string default_connection_state_;
197 CaptivePortalStateMap portal_state_map_;
198 ObserverList<Observer> observers_;
200 base::CancelableClosure attempt_task_;
201 base::CancelableClosure attempt_timeout_;
203 // URL that returns a 204 response code when connected to the Internet.
206 // Detector for checking default network for a portal state.
207 scoped_ptr<captive_portal::CaptivePortalDetector> captive_portal_detector_;
209 // True if the NetworkPortalDetector is enabled.
212 base::WeakPtrFactory<NetworkPortalDetectorImpl> weak_factory_;
214 // Start time of portal detection.
215 base::TimeTicks detection_start_time_;
217 // Start time of detection attempt.
218 base::TimeTicks attempt_start_time_;
220 // Number of already performed detection attempts.
223 // Delay before next portal detection.
224 base::TimeDelta next_attempt_delay_;
226 // Current detection strategy.
227 scoped_ptr<PortalDetectorStrategy> strategy_;
229 // UI notification controller about captive portal state.
230 NetworkPortalNotificationController notification_controller_;
232 content::NotificationRegistrar registrar_;
234 // Test time ticks used by unit tests.
235 base::TimeTicks time_ticks_for_testing_;
237 DISALLOW_COPY_AND_ASSIGN(NetworkPortalDetectorImpl);
240 } // namespace chromeos
242 #endif // CHROME_BROWSER_CHROMEOS_NET_NETWORK_PORTAL_DETECTOR_IMPL_H_