summaryrefslogtreecommitdiffstats
path: root/chrome/browser/chromeos/extensions/networking_private_event_router.cc
blob: 6d7656d87e98f6128f3c4a14cfdf652c8dfbc0a4 (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
// Copyright (c) 2013 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.

#include "chrome/browser/chromeos/extensions/networking_private_event_router.h"

#include "base/json/json_writer.h"
#include "chrome/browser/browser_process.h"
#include "chrome/browser/chromeos/extensions/networking_private_api.h"
#include "chrome/browser/extensions/event_names.h"
#include "chrome/browser/extensions/event_router_forwarder.h"
#include "chrome/browser/extensions/extension_system.h"
#include "chrome/browser/extensions/extension_system_factory.h"
#include "chrome/browser/profiles/profile.h"
#include "chrome/common/extensions/api/networking_private.h"
#include "chromeos/network/network_state.h"
#include "chromeos/network/network_state_handler.h"
#include "chromeos/network/onc/onc_constants.h"
#include "chromeos/network/onc/onc_signature.h"
#include "chromeos/network/onc/onc_translator.h"
#include "components/browser_context_keyed_service/browser_context_dependency_manager.h"
#include "third_party/cros_system_api/dbus/service_constants.h"

using extensions::event_names::kOnNetworkListChanged;
using extensions::event_names::kOnNetworksChanged;
using extensions::EventRouter;
using extensions::ExtensionSystem;
namespace api = extensions::api::networking_private;

namespace chromeos {

NetworkingPrivateEventRouter::NetworkingPrivateEventRouter(Profile* profile)
    : profile_(profile), listening_(false) {
  // Register with the event router so we know when renderers are listening to
  // our events. We first check and see if there *is* an event router, because
  // some unit tests try to create all profile services, but don't initialize
  // the event router first.
  EventRouter* event_router = ExtensionSystem::Get(profile_)->event_router();
  if (event_router) {
    event_router->RegisterObserver(
        this, extensions::event_names::kOnNetworksChanged);
    event_router->RegisterObserver(
        this, extensions::event_names::kOnNetworkListChanged);
    StartOrStopListeningForNetworkChanges();
  }
}

NetworkingPrivateEventRouter::~NetworkingPrivateEventRouter() {
  DCHECK(!listening_);
}

void NetworkingPrivateEventRouter::Shutdown() {
  // Unregister with the event router. We first check and see if there *is* an
  // event router, because some unit tests try to shutdown all profile services,
  // but didn't initialize the event router first.
  EventRouter* event_router = ExtensionSystem::Get(profile_)->event_router();
  if (event_router)
    event_router->UnregisterObserver(this);

  if (listening_) {
    NetworkHandler::Get()->network_state_handler()->RemoveObserver(
        this, FROM_HERE);
  }
  listening_ = false;
}

void NetworkingPrivateEventRouter::OnListenerAdded(
    const extensions::EventListenerInfo& details) {
  // Start listening to events from the network state handler.
  StartOrStopListeningForNetworkChanges();
}

void NetworkingPrivateEventRouter::OnListenerRemoved(
    const extensions::EventListenerInfo& details) {
  // Stop listening to events from the network state handler if there are no
  // more listeners.
  StartOrStopListeningForNetworkChanges();
}

void NetworkingPrivateEventRouter::StartOrStopListeningForNetworkChanges() {
  EventRouter* event_router = ExtensionSystem::Get(profile_)->event_router();
  bool should_listen = event_router->HasEventListener(kOnNetworksChanged) ||
      event_router->HasEventListener(kOnNetworkListChanged);

  if (should_listen && !listening_) {
    NetworkHandler::Get()->network_state_handler()->AddObserver(
        this, FROM_HERE);
  } else if (!should_listen && listening_) {
    NetworkHandler::Get()->network_state_handler()->RemoveObserver(
        this, FROM_HERE);
  }
  listening_ = should_listen;
}

void NetworkingPrivateEventRouter::NetworkListChanged() {
  EventRouter* event_router = ExtensionSystem::Get(profile_)->event_router();
  NetworkStateList networks;
  NetworkHandler::Get()->network_state_handler()->GetNetworkList(&networks);
  if (!event_router->HasEventListener(kOnNetworkListChanged))
    return;

  std::vector<std::string> changes;
  for (NetworkStateList::const_iterator iter = networks.begin();
      iter != networks.end(); ++iter) {
    // TODO(gspencer): Currently the "GUID" is actually the service path. Fix
    // this to be the real GUID once we're using
    // ManagedNetworkConfigurationManager.
    changes.push_back((*iter)->path());
  }

  scoped_ptr<base::ListValue> args(api::OnNetworkListChanged::Create(changes));
  scoped_ptr<extensions::Event> extension_event(new extensions::Event(
      kOnNetworkListChanged, args.Pass()));
  event_router->BroadcastEvent(extension_event.Pass());
}

void NetworkingPrivateEventRouter::NetworkPropertiesUpdated(
    const NetworkState* network) {
  EventRouter* event_router = ExtensionSystem::Get(profile_)->event_router();
  if (!event_router->HasEventListener(kOnNetworksChanged))
    return;

  scoped_ptr<base::ListValue> args(api::OnNetworksChanged::Create(
      std::vector<std::string>(1, network->path())));
  scoped_ptr<extensions::Event> extension_event(
      new extensions::Event(kOnNetworksChanged, args.Pass()));
  event_router->BroadcastEvent(extension_event.Pass());
}

}  // namespace chromeos