summaryrefslogtreecommitdiffstats
path: root/chrome/browser/net/pref_proxy_config_service.h
blob: d98fa6f9f154a33fc0b5eed23d1b5521184019f8 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
// Copyright (c) 2011 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#ifndef CHROME_BROWSER_NET_PREF_PROXY_CONFIG_SERVICE_H_
#define CHROME_BROWSER_NET_PREF_PROXY_CONFIG_SERVICE_H_
#pragma once

#include "base/basictypes.h"
#include "base/memory/ref_counted.h"
#include "base/memory/scoped_ptr.h"
#include "base/observer_list.h"
#include "chrome/browser/prefs/proxy_config_dictionary.h"
#include "content/common/notification_observer.h"
#include "net/proxy/proxy_config.h"
#include "net/proxy/proxy_config_service.h"

class PrefService;
class PrefSetObserver;

// A helper class that tracks proxy preferences. It translates the configuration
// to net::ProxyConfig and proxies the result over to the IO thread for
// PrefProxyConfigService to use.
class PrefProxyConfigTracker
    : public base::RefCountedThreadSafe<PrefProxyConfigTracker>,
      public NotificationObserver {
 public:
  // Observer interface used to send out notifications on the IO thread about
  // changes to the proxy configuration.
  class Observer {
   public:
    virtual ~Observer() {}
    virtual void OnPrefProxyConfigChanged() = 0;
  };

  // Return codes for GetProxyConfig.
  enum ConfigState {
    // Configuration is valid and present.
    CONFIG_PRESENT,
    // There is a fallback configuration present.
    CONFIG_FALLBACK,
    // Configuration is known to be not set.
    CONFIG_UNSET,
  };

  explicit PrefProxyConfigTracker(PrefService* pref_service);

  // Observer manipulation is only valid on the IO thread.
  void AddObserver(Observer* observer);
  void RemoveObserver(Observer* observer);

  // Get the proxy configuration currently defined by preferences. Status is
  // indicated in the return value. Writes the configuration to |config| unless
  // the return value is CONFIG_UNSET, in which case |config| is not touched.
  ConfigState GetProxyConfig(net::ProxyConfig* config);

  // Notifies the tracker that the pref service passed upon construction is
  // about to go away. This must be called from the UI thread.
  void DetachFromPrefService();

 private:
  friend class base::RefCountedThreadSafe<PrefProxyConfigTracker>;
  virtual ~PrefProxyConfigTracker();

  // NotificationObserver implementation:
  virtual void Observe(NotificationType type,
                       const NotificationSource& source,
                       const NotificationDetails& details);

  // Install a new configuration. This is invoked on the IO thread to update
  // the internal state after handling a pref change on the UI thread.
  // |config_state| indicates the new state we're switching to, and |config| is
  // the new preference-based proxy configuration if |config_state| is different
  // from CONFIG_UNSET.
  void InstallProxyConfig(const net::ProxyConfig& config, ConfigState state);

  // Creates a proxy configuration from proxy-related preferences. Configuration
  // is stored in |config| and the return value indicates whether the
  // configuration is valid.
  ConfigState ReadPrefConfig(net::ProxyConfig* config);

  // Converts a ProxyConfigDictionary to net::ProxyConfig representation.
  // Returns true if the data from in the dictionary is valid, false otherwise.
  static bool PrefConfigToNetConfig(const ProxyConfigDictionary& proxy_dict,
                                    net::ProxyConfig* config);

  // Configuration as defined by prefs. Only to be accessed from the IO thread
  // (except for construction).
  net::ProxyConfig pref_config_;

  // Tracks configuration state. |pref_config_| is valid only if |config_state_|
  // is not CONFIG_UNSET.
  ConfigState config_state_;

  // List of observers, accessed exclusively from the IO thread.
  ObserverList<Observer, true> observers_;

  // Pref-related members that should only be accessed from the UI thread.
  PrefService* pref_service_;
  scoped_ptr<PrefSetObserver> proxy_prefs_observer_;

  DISALLOW_COPY_AND_ASSIGN(PrefProxyConfigTracker);
};

// A net::ProxyConfigService implementation that applies preference proxy
// settings as overrides to the proxy configuration determined by a baseline
// delegate ProxyConfigService.
class PrefProxyConfigService
    : public net::ProxyConfigService,
      public net::ProxyConfigService::Observer,
      public PrefProxyConfigTracker::Observer {
 public:
  // Takes ownership of the passed |base_service|.
  PrefProxyConfigService(PrefProxyConfigTracker* tracker,
                         net::ProxyConfigService* base_service);
  virtual ~PrefProxyConfigService();

  // ProxyConfigService implementation:
  virtual void AddObserver(net::ProxyConfigService::Observer* observer);
  virtual void RemoveObserver(net::ProxyConfigService::Observer* observer);
  virtual ConfigAvailability GetLatestProxyConfig(net::ProxyConfig* config);
  virtual void OnLazyPoll();

  static void RegisterPrefs(PrefService* user_prefs);

 private:
  // ProxyConfigService::Observer implementation:
  virtual void OnProxyConfigChanged(const net::ProxyConfig& config,
                                    ConfigAvailability availability);

  // PrefProxyConfigTracker::Observer implementation:
  virtual void OnPrefProxyConfigChanged();

  // Makes sure that the observer registrations with the base service and the
  // tracker object are set up.
  void RegisterObservers();

  scoped_ptr<net::ProxyConfigService> base_service_;
  ObserverList<net::ProxyConfigService::Observer, true> observers_;
  scoped_refptr<PrefProxyConfigTracker> pref_config_tracker_;

  // Indicates whether the base service and tracker registrations are done.
  bool registered_observers_;

  DISALLOW_COPY_AND_ASSIGN(PrefProxyConfigService);
};

#endif  // CHROME_BROWSER_NET_PREF_PROXY_CONFIG_SERVICE_H_