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

Side by Side Diff: chrome/browser/policy/policy_service_impl.cc

Issue 10236003: Added RefreshPolicies to PolicyService. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Fix chromeos build (this time I mean it) Created 8 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "chrome/browser/policy/policy_service_impl.h" 5 #include "chrome/browser/policy/policy_service_impl.h"
6 6
7 #include "base/bind.h"
8 #include "base/bind_helpers.h"
7 #include "base/observer_list.h" 9 #include "base/observer_list.h"
8 #include "base/stl_util.h" 10 #include "base/stl_util.h"
11 #include "content/public/browser/browser_thread.h"
12
13 using content::BrowserThread;
9 14
10 namespace policy { 15 namespace policy {
11 16
12 struct PolicyServiceImpl::Entry { 17 struct PolicyServiceImpl::Entry {
13 PolicyMap policies; 18 PolicyMap policies;
14 ObserverList<PolicyService::Observer, true> observers; 19 ObserverList<PolicyService::Observer, true> observers;
15 }; 20 };
16 21
17 struct PolicyServiceImpl::ProviderData { 22 struct PolicyServiceImpl::ProviderData {
18 ConfigurationPolicyProvider* provider; 23 ConfigurationPolicyProvider* provider;
19 ConfigurationPolicyObserverRegistrar registrar; 24 ConfigurationPolicyObserverRegistrar registrar;
20 PolicyMap policies; 25 PolicyMap policies;
26 bool refresh_pending;
21 }; 27 };
22 28
23 PolicyServiceImpl::PolicyServiceImpl(const Providers& providers) { 29 PolicyServiceImpl::PolicyServiceImpl(const Providers& providers) {
24 initialization_complete_ = true; 30 initialization_complete_ = true;
25 for (size_t i = 0; i < providers.size(); ++i) { 31 for (size_t i = 0; i < providers.size(); ++i) {
26 ConfigurationPolicyProvider* provider = providers[i]; 32 ConfigurationPolicyProvider* provider = providers[i];
27 ProviderData* data = new ProviderData; 33 ProviderData* data = new ProviderData;
28 data->provider = provider; 34 data->provider = provider;
29 data->registrar.Init(provider, this); 35 data->registrar.Init(provider, this);
36 data->refresh_pending = false;
30 if (provider->IsInitializationComplete()) 37 if (provider->IsInitializationComplete())
31 provider->Provide(&data->policies); 38 provider->Provide(&data->policies);
32 else 39 else
33 initialization_complete_ = false; 40 initialization_complete_ = false;
34 providers_.push_back(data); 41 providers_.push_back(data);
35 } 42 }
36 // There are no observers yet, but calls to GetPolicies() should already get 43 // There are no observers yet, but calls to GetPolicies() should already get
37 // the processed policy values. 44 // the processed policy values.
38 MergeAndTriggerUpdates(); 45 MergeAndTriggerUpdates(false);
39 } 46 }
40 47
41 PolicyServiceImpl::~PolicyServiceImpl() { 48 PolicyServiceImpl::~PolicyServiceImpl() {
42 STLDeleteElements(&providers_); 49 STLDeleteElements(&providers_);
43 STLDeleteValues(&entries_); 50 STLDeleteValues(&entries_);
44 } 51 }
45 52
46 void PolicyServiceImpl::AddObserver(PolicyDomain domain, 53 void PolicyServiceImpl::AddObserver(PolicyDomain domain,
47 const std::string& component_id, 54 const std::string& component_id,
48 PolicyService::Observer* observer) { 55 PolicyService::Observer* observer) {
(...skipping 19 matching lines...) Expand all
68 const std::string& component_id) const { 75 const std::string& component_id) const {
69 PolicyNamespace ns = std::make_pair(domain, component_id); 76 PolicyNamespace ns = std::make_pair(domain, component_id);
70 EntryMap::const_iterator it = entries_.find(ns); 77 EntryMap::const_iterator it = entries_.find(ns);
71 return it == entries_.end() ? NULL : &it->second->policies; 78 return it == entries_.end() ? NULL : &it->second->policies;
72 } 79 }
73 80
74 bool PolicyServiceImpl::IsInitializationComplete() const { 81 bool PolicyServiceImpl::IsInitializationComplete() const {
75 return initialization_complete_; 82 return initialization_complete_;
76 } 83 }
77 84
85 void PolicyServiceImpl::RefreshPolicies(const base::Closure& callback) {
86 if (!callback.is_null())
87 refresh_callbacks_.push_back(callback);
88
89 // Some providers might invoke OnUpdatePolicy synchronously while handling
90 // RefreshPolicies. Flag all with refresh_pending before starting to refresh.
91 ProviderList::iterator it;
92 for (it = providers_.begin(); it != providers_.end(); ++it)
93 (*it)->refresh_pending = true;
94 for (it = providers_.begin(); it != providers_.end(); ++it)
95 (*it)->provider->RefreshPolicies();
Mattias Nissler (ping if slow) 2012/04/27 09:03:27 What if providers_ is empty?
Joao da Silva 2012/04/27 11:24:12 Nice catch :-) Fixed.
96 }
97
78 void PolicyServiceImpl::OnUpdatePolicy(ConfigurationPolicyProvider* provider) { 98 void PolicyServiceImpl::OnUpdatePolicy(ConfigurationPolicyProvider* provider) {
79 ProviderList::iterator it = GetProviderData(provider); 99 ProviderList::iterator it = GetProviderData(provider);
80 if (it == providers_.end()) 100 if (it == providers_.end())
81 return; 101 return;
82 provider->Provide(&(*it)->policies); 102 provider->Provide(&(*it)->policies);
83 MergeAndTriggerUpdates(); 103 bool did_refresh = (*it)->refresh_pending;
104 (*it)->refresh_pending = false;
105 MergeAndTriggerUpdates(did_refresh);
84 } 106 }
85 107
86 void PolicyServiceImpl::OnProviderGoingAway( 108 void PolicyServiceImpl::OnProviderGoingAway(
87 ConfigurationPolicyProvider* provider) { 109 ConfigurationPolicyProvider* provider) {
88 ProviderList::iterator it = GetProviderData(provider); 110 ProviderList::iterator it = GetProviderData(provider);
89 if (it == providers_.end()) 111 if (it == providers_.end())
90 return; 112 return;
113 bool did_refresh = (*it)->refresh_pending;
91 delete *it; 114 delete *it;
92 providers_.erase(it); 115 providers_.erase(it);
93 MergeAndTriggerUpdates(); 116 MergeAndTriggerUpdates(did_refresh);
94 } 117 }
95 118
96 PolicyServiceImpl::Entry* PolicyServiceImpl::GetOrCreate( 119 PolicyServiceImpl::Entry* PolicyServiceImpl::GetOrCreate(
97 const PolicyNamespace& ns) { 120 const PolicyNamespace& ns) {
98 Entry*& entry = entries_[ns]; 121 Entry*& entry = entries_[ns];
99 if (!entry) 122 if (!entry)
100 entry = new Entry; 123 entry = new Entry;
101 return entry; 124 return entry;
102 } 125 }
103 126
(...skipping 11 matching lines...) Expand all
115 void PolicyServiceImpl::MaybeCleanup(const PolicyNamespace& ns) { 138 void PolicyServiceImpl::MaybeCleanup(const PolicyNamespace& ns) {
116 EntryMap::iterator it = entries_.find(ns); 139 EntryMap::iterator it = entries_.find(ns);
117 if (it != entries_.end() && 140 if (it != entries_.end() &&
118 it->second->policies.empty() && 141 it->second->policies.empty() &&
119 it->second->observers.size() == 0) { 142 it->second->observers.size() == 0) {
120 delete it->second; 143 delete it->second;
121 entries_.erase(it); 144 entries_.erase(it);
122 } 145 }
123 } 146 }
124 147
125 void PolicyServiceImpl::MergeAndTriggerUpdates() { 148 void PolicyServiceImpl::MergeAndTriggerUpdates(bool is_refresh) {
126 // TODO(joaodasilva): do this for each namespace once the providers also 149 // TODO(joaodasilva): do this for each namespace once the providers also
127 // provide policy for more namespaces. 150 // provide policy for more namespaces.
151
128 PolicyMap policies; 152 PolicyMap policies;
153 bool refresh_pending = false;
129 for (ProviderList::iterator it = providers_.begin(); 154 for (ProviderList::iterator it = providers_.begin();
130 it != providers_.end(); ++it) { 155 it != providers_.end(); ++it) {
131 policies.MergeFrom((*it)->policies); 156 policies.MergeFrom((*it)->policies);
157 refresh_pending |= (*it)->refresh_pending;
132 } 158 }
133 159
134 Entry* entry = GetOrCreate(std::make_pair(POLICY_DOMAIN_CHROME, "")); 160 Entry* entry = GetOrCreate(std::make_pair(POLICY_DOMAIN_CHROME, ""));
135 if (!policies.Equals(entry->policies)) { 161 if (!policies.Equals(entry->policies)) {
136 // Swap first, so that observers that call GetPolicies() see the current 162 // Swap first, so that observers that call GetPolicies() see the current
137 // values. 163 // values.
138 entry->policies.Swap(&policies); 164 entry->policies.Swap(&policies);
139 FOR_EACH_OBSERVER( 165 FOR_EACH_OBSERVER(
140 PolicyService::Observer, 166 PolicyService::Observer,
141 entry->observers, 167 entry->observers,
(...skipping 11 matching lines...) Expand all
153 } 179 }
154 } 180 }
155 if (initialization_complete_) { 181 if (initialization_complete_) {
156 for (EntryMap::iterator i = entries_.begin(); i != entries_.end(); ++i) { 182 for (EntryMap::iterator i = entries_.begin(); i != entries_.end(); ++i) {
157 FOR_EACH_OBSERVER(PolicyService::Observer, 183 FOR_EACH_OBSERVER(PolicyService::Observer,
158 i->second->observers, 184 i->second->observers,
159 OnPolicyServiceInitialized()); 185 OnPolicyServiceInitialized());
160 } 186 }
161 } 187 }
162 } 188 }
189
190 // Invoke all the callbacks if a refresh has just fully completed.
191 if (is_refresh && !refresh_pending) {
192 std::vector<base::Closure> callbacks;
193 callbacks.swap(refresh_callbacks_);
194 for (size_t i = 0; i < callbacks.size(); ++i)
195 callbacks[i].Run();
196 }
163 } 197 }
164 198
165 } // namespace policy 199 } // namespace policy
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698