Index: chrome/browser/policy/cloud/component_cloud_policy_service.cc |
diff --git a/chrome/browser/policy/cloud/component_cloud_policy_service.cc b/chrome/browser/policy/cloud/component_cloud_policy_service.cc |
index 3be5cd7619eb28d71443d71d1e7a03beb6640d62..f9e76d779f90d610e78bc3bef8bdda985d442c73 100644 |
--- a/chrome/browser/policy/cloud/component_cloud_policy_service.cc |
+++ b/chrome/browser/policy/cloud/component_cloud_policy_service.cc |
@@ -4,6 +4,8 @@ |
#include "chrome/browser/policy/cloud/component_cloud_policy_service.h" |
+#include <map> |
+ |
#include "base/bind.h" |
#include "base/bind_helpers.h" |
#include "base/location.h" |
@@ -16,30 +18,28 @@ |
#include "chrome/browser/policy/cloud/component_cloud_policy_updater.h" |
#include "chrome/browser/policy/cloud/external_policy_data_fetcher.h" |
#include "chrome/browser/policy/cloud/resource_cache.h" |
-#include "chrome/browser/policy/policy_domain_descriptor.h" |
#include "chrome/browser/policy/proto/cloud/device_management_backend.pb.h" |
+#include "chrome/browser/policy/schema_map.h" |
+#include "components/policy/core/common/schema.h" |
#include "net/url_request/url_request_context_getter.h" |
namespace em = enterprise_management; |
namespace policy { |
+const char ComponentCloudPolicyService::kComponentNamespaceCache[] = |
+ "component-namespace-cache"; |
+ |
namespace { |
-void GetComponentIds(scoped_refptr<const PolicyDomainDescriptor>& descriptor, |
- std::set<std::string>* set) { |
- const PolicyDomainDescriptor::SchemaMap& map = descriptor->components(); |
- for (PolicyDomainDescriptor::SchemaMap::const_iterator it = map.begin(); |
- it != map.end(); ++it) { |
- set->insert(it->first); |
- } |
+bool NotInSchemaMap(const scoped_refptr<SchemaMap> schema_map, |
+ PolicyDomain domain, |
+ const std::string& component_id) { |
+ return schema_map->GetSchema(PolicyNamespace(domain, component_id)) == NULL; |
} |
} // namespace |
-const char ComponentCloudPolicyService::kComponentNamespaceCache[] = |
- "component-namespace-cache"; |
- |
ComponentCloudPolicyService::Delegate::~Delegate() {} |
// Owns the objects that live on the background thread, and posts back to the |
@@ -84,16 +84,12 @@ class ComponentCloudPolicyService::Backend |
// ComponentCloudPolicyStore::Delegate implementation: |
virtual void OnComponentCloudPolicyStoreUpdated() OVERRIDE; |
- // Passes the current descriptor of a domain, so that the disk cache |
- // can purge components that aren't being tracked anymore. |
- void RegisterPolicyDomain( |
- scoped_refptr<const PolicyDomainDescriptor> descriptor); |
+ // Passes the current SchemaMap so that the disk cache can purge components |
+ // that aren't being tracked anymore. |
+ void OnSchemasUpdated(scoped_refptr<SchemaMap> schema_map); |
private: |
- typedef std::map<PolicyDomain, scoped_refptr<const PolicyDomainDescriptor> > |
- DomainMap; |
- |
- scoped_ptr<ComponentMap> ReadCachedComponents(); |
+ scoped_ptr<PolicyNamespaceKeys> ReadCachedComponents(); |
// The ComponentCloudPolicyService that owns |this|. Used to inform the |
// |service_| when policy changes. |
@@ -109,7 +105,7 @@ class ComponentCloudPolicyService::Backend |
scoped_ptr<ResourceCache> cache_; |
scoped_ptr<ComponentCloudPolicyStore> store_; |
scoped_ptr<ComponentCloudPolicyUpdater> updater_; |
- DomainMap domain_map_; |
+ scoped_refptr<SchemaMap> schema_map_; |
DISALLOW_COPY_AND_ASSIGN(Backend); |
}; |
@@ -132,9 +128,8 @@ void ComponentCloudPolicyService::Backend::Init() { |
} |
void ComponentCloudPolicyService::Backend::FinalizeInit() { |
- // Read the components that were cached in the last RegisterPolicyDomain() |
- // calls for each domain. |
- scoped_ptr<ComponentMap> components = ReadCachedComponents(); |
+ // Read the components that were cached in the last OnSchemasUpdated() call. |
+ scoped_ptr<PolicyNamespaceKeys> components = ReadCachedComponents(); |
// Read the initial policy. |
store_->Load(); |
@@ -175,13 +170,14 @@ void ComponentCloudPolicyService::Backend::UpdateExternalPolicy( |
void ComponentCloudPolicyService::Backend:: |
OnComponentCloudPolicyStoreUpdated() { |
- scoped_ptr<PolicyBundle> bundle(new PolicyBundle); |
- bundle->CopyFrom(store_->policy()); |
- for (DomainMap::iterator it = domain_map_.begin(); |
- it != domain_map_.end(); ++it) { |
- it->second->FilterBundle(bundle.get()); |
+ if (!schema_map_) { |
+ // No schemas have been registered yet, so keep serving the initial policy. |
bartfab (slow)
2013/11/05 15:53:04
Is the initial policy just blank? Could you docume
Joao da Silva
2013/11/07 13:15:00
Done. It's not blank, it's loaded synchronously in
|
+ return; |
} |
+ scoped_ptr<PolicyBundle> bundle(new PolicyBundle); |
+ bundle->CopyFrom(store_->policy()); |
+ schema_map_->FilterBundle(bundle.get()); |
service_task_runner_->PostTask( |
FROM_HERE, |
base::Bind(&ComponentCloudPolicyService::OnPolicyUpdated, |
@@ -189,49 +185,56 @@ void ComponentCloudPolicyService::Backend:: |
base::Passed(&bundle))); |
} |
-void ComponentCloudPolicyService::Backend::RegisterPolicyDomain( |
- scoped_refptr<const PolicyDomainDescriptor> descriptor) { |
+void ComponentCloudPolicyService::Backend::OnSchemasUpdated( |
+ scoped_refptr<SchemaMap> schema_map) { |
+ schema_map_ = schema_map; |
+ |
// Store the current list of components in the cache. |
- StringSet ids; |
- std::string policy_type; |
- if (ComponentCloudPolicyStore::GetPolicyType(descriptor->domain(), |
- &policy_type)) { |
- GetComponentIds(descriptor, &ids); |
+ const DomainMap& domains = schema_map->GetDomains(); |
+ for (DomainMap::const_iterator domain = domains.begin(); |
+ domain != domains.end(); ++domain) { |
+ std::string domain_policy_type; |
+ if (!ComponentCloudPolicyStore::GetPolicyType(domain->first, |
+ &domain_policy_type)) { |
+ continue; |
+ } |
Pickle pickle; |
- for (StringSet::const_iterator it = ids.begin(); it != ids.end(); ++it) |
- pickle.WriteString(*it); |
+ const ComponentMap& components = domain->second; |
+ for (ComponentMap::const_iterator comp = components.begin(); |
+ comp != components.end(); ++comp) { |
+ pickle.WriteString(comp->first); |
+ } |
std::string data(reinterpret_cast<const char*>(pickle.data()), |
pickle.size()); |
- cache_->Store(kComponentNamespaceCache, policy_type, data); |
- } |
- |
- domain_map_[descriptor->domain()] = descriptor; |
+ cache_->Store(kComponentNamespaceCache, domain_policy_type, data); |
- // Purge any components that have been removed. |
- if (store_) |
- store_->Purge(descriptor->domain(), ids); |
+ // Purge any components that have been removed. |
+ if (store_) { |
+ store_->Purge(domain->first, |
+ base::Bind(&NotInSchemaMap, schema_map, domain->first)); |
+ } |
+ } |
} |
-scoped_ptr<ComponentCloudPolicyService::ComponentMap> |
+scoped_ptr<ComponentCloudPolicyService::PolicyNamespaceKeys> |
ComponentCloudPolicyService::Backend::ReadCachedComponents() { |
- scoped_ptr<ComponentMap> components(new ComponentMap); |
+ scoped_ptr<PolicyNamespaceKeys> keys(new PolicyNamespaceKeys()); |
bartfab (slow)
2013/11/05 15:53:04
No: No need for ().
Joao da Silva
2013/11/07 13:15:00
Done.
|
std::map<std::string, std::string> contents; |
cache_->LoadAllSubkeys(kComponentNamespaceCache, &contents); |
for (std::map<std::string, std::string>::iterator it = contents.begin(); |
it != contents.end(); ++it) { |
PolicyDomain domain; |
if (ComponentCloudPolicyStore::GetPolicyDomain(it->first, &domain)) { |
- StringSet& set = (*components)[domain]; |
const Pickle pickle(it->second.data(), it->second.size()); |
PickleIterator pickit(pickle); |
std::string id; |
while (pickit.ReadString(&id)) |
- set.insert(id); |
+ keys->insert(std::make_pair(it->first, id)); |
bartfab (slow)
2013/11/05 15:53:04
Nit: #include <utility>
Joao da Silva
2013/11/07 13:15:00
Done.
|
} else { |
cache_->Delete(kComponentNamespaceCache, it->first); |
} |
} |
- return components.Pass(); |
+ return keys.Pass(); |
} |
ComponentCloudPolicyService::ComponentCloudPolicyService( |
@@ -246,6 +249,7 @@ ComponentCloudPolicyService::ComponentCloudPolicyService( |
client_(NULL), |
store_(store), |
is_initialized_(false), |
+ has_initial_keys_(false), |
weak_ptr_factory_(this) { |
store_->AddObserver(this); |
@@ -300,10 +304,7 @@ void ComponentCloudPolicyService::Disconnect() { |
DCHECK(CalledOnValidThread()); |
if (client_) { |
// Unregister all the current components. |
- for (ComponentMap::iterator it = registered_components_.begin(); |
- it != registered_components_.end(); ++it) { |
- RemoveNamespacesToFetch(it->first, it->second); |
- } |
+ RemoveNamespacesToFetch(keys_); |
client_->RemoveObserver(this); |
client_ = NULL; |
@@ -316,29 +317,41 @@ void ComponentCloudPolicyService::Disconnect() { |
} |
} |
-void ComponentCloudPolicyService::RegisterPolicyDomain( |
- scoped_refptr<const PolicyDomainDescriptor> descriptor) { |
+void ComponentCloudPolicyService::OnSchemasUpdated( |
+ const scoped_refptr<SchemaMap>& schema_map) { |
DCHECK(CalledOnValidThread()); |
- DCHECK(SupportsDomain(descriptor->domain())); |
- // Send the new descriptor to the backend, to purge the cache. |
+ // Send the new schemas to the backend, to purge the cache. |
backend_task_runner_->PostTask(FROM_HERE, |
- base::Bind(&Backend::RegisterPolicyDomain, |
+ base::Bind(&Backend::OnSchemasUpdated, |
base::Unretained(backend_.get()), |
- descriptor)); |
+ schema_map)); |
+ |
+ // Register the current list of components for supported domains at the |
+ // |client_|. |
+ PolicyNamespaceKeys new_keys; |
+ const DomainMap& domains = schema_map->GetDomains(); |
+ for (DomainMap::const_iterator domain = domains.begin(); |
+ domain != domains.end(); ++domain) { |
+ std::string domain_policy_type; |
+ if (!ComponentCloudPolicyStore::GetPolicyType(domain->first, |
+ &domain_policy_type)) { |
+ continue; |
+ } |
+ const ComponentMap& components = domain->second; |
+ for (ComponentMap::const_iterator comp = components.begin(); |
+ comp != components.end(); ++comp) { |
+ new_keys.insert(std::make_pair(domain_policy_type, comp->first)); |
+ } |
+ } |
- // Register the current list of components for |domain| at the |client_|. |
- StringSet current_ids; |
- GetComponentIds(descriptor, ¤t_ids); |
- StringSet& registered_ids = registered_components_[descriptor->domain()]; |
if (client_ && is_initialized()) { |
bartfab (slow)
2013/11/05 15:53:04
Why the nested conditional?
Joao da Silva
2013/11/07 13:15:00
No reason for it, simplified.
|
- if (UpdateClientNamespaces( |
- descriptor->domain(), registered_ids, current_ids)) { |
+ if (UpdateClientNamespaces(keys_, new_keys)) |
delegate_->OnComponentCloudPolicyRefreshNeeded(); |
- } |
} |
- registered_ids = current_ids; |
+ keys_.swap(new_keys); |
+ has_initial_keys_ = true; |
} |
void ComponentCloudPolicyService::OnPolicyFetched(CloudPolicyClient* client) { |
@@ -350,9 +363,7 @@ void ComponentCloudPolicyService::OnPolicyFetched(CloudPolicyClient* client) { |
for (CloudPolicyClient::ResponseMap::const_iterator it = responses.begin(); |
it != responses.end(); ++it) { |
const PolicyNamespaceKey& key(it->first); |
- PolicyDomain domain; |
- if (ComponentCloudPolicyStore::GetPolicyDomain(key.first, &domain) && |
- ContainsKey(registered_components_[domain], key.second)) { |
+ if (ContainsKey(keys_, key)) { |
scoped_ptr<em::PolicyFetchResponse> response( |
new em::PolicyFetchResponse(*it->second)); |
backend_task_runner_->PostTask( |
@@ -409,7 +420,7 @@ void ComponentCloudPolicyService::InitializeBackend() { |
} |
void ComponentCloudPolicyService::OnBackendInitialized( |
- scoped_ptr<ComponentMap> cached_components, |
+ scoped_ptr<PolicyNamespaceKeys> initial_keys, |
scoped_ptr<PolicyBundle> initial_policy) { |
DCHECK(CalledOnValidThread()); |
// InitializeBackend() may be called multiple times if the |store_| fires |
@@ -417,16 +428,10 @@ void ComponentCloudPolicyService::OnBackendInitialized( |
if (is_initialized()) |
return; |
- // RegisterPolicyDomain() may have been called while the backend was |
- // initializing; only update |registered_components_| from |cached_components| |
- // for domains that haven't registered yet. |
- for (ComponentMap::iterator it = cached_components->begin(); |
- it != cached_components->end(); ++it) { |
- // Lookup without inserting an empty set. |
- if (registered_components_.find(it->first) != registered_components_.end()) |
- continue; // Ignore the cached list if a more recent one was registered. |
- registered_components_[it->first].swap(it->second); |
- } |
+ // OnSchemasUpdated() may have been called while the backend was initializing; |
+ // in that case ignore the cached keys. |
+ if (!has_initial_keys_) |
+ keys_.swap(*initial_keys); |
// A client may have already connected while the backend was initializing. |
if (client_) |
@@ -440,16 +445,11 @@ void ComponentCloudPolicyService::OnBackendInitialized( |
void ComponentCloudPolicyService::InitializeClient() { |
DCHECK(CalledOnValidThread()); |
// Register all the current components. |
- bool added = false; |
- for (ComponentMap::iterator it = registered_components_.begin(); |
- it != registered_components_.end(); ++it) { |
- added |= !it->second.empty(); |
- AddNamespacesToFetch(it->first, it->second); |
- } |
+ AddNamespacesToFetch(keys_); |
// The client may already have PolicyFetchResponses for registered components; |
// load them now. |
OnPolicyFetched(client_); |
- if (added && is_initialized()) |
+ if (!keys_.empty() && is_initialized()) |
delegate_->OnComponentCloudPolicyRefreshNeeded(); |
} |
@@ -482,35 +482,33 @@ void ComponentCloudPolicyService::SetCredentialsAndReloadClient() { |
} |
bool ComponentCloudPolicyService::UpdateClientNamespaces( |
- PolicyDomain domain, |
- const StringSet& old_set, |
- const StringSet& new_set) { |
+ const PolicyNamespaceKeys& old_keys, |
+ const PolicyNamespaceKeys& new_keys) { |
DCHECK(CalledOnValidThread()); |
- StringSet added = base::STLSetDifference<StringSet>(new_set, old_set); |
- StringSet removed = base::STLSetDifference<StringSet>(old_set, new_set); |
- AddNamespacesToFetch(domain, added); |
- RemoveNamespacesToFetch(domain, removed); |
+ PolicyNamespaceKeys added = |
+ base::STLSetDifference<PolicyNamespaceKeys>(new_keys, old_keys); |
+ PolicyNamespaceKeys removed = |
+ base::STLSetDifference<PolicyNamespaceKeys>(old_keys, new_keys); |
+ AddNamespacesToFetch(added); |
+ RemoveNamespacesToFetch(removed); |
return !added.empty(); |
} |
-void ComponentCloudPolicyService::AddNamespacesToFetch(PolicyDomain domain, |
- const StringSet& set) { |
+void ComponentCloudPolicyService::AddNamespacesToFetch( |
+ const PolicyNamespaceKeys& keys) { |
DCHECK(CalledOnValidThread()); |
- std::string policy_type; |
- if (ComponentCloudPolicyStore::GetPolicyType(domain, &policy_type)) { |
- for (StringSet::const_iterator it = set.begin(); it != set.end(); ++it) |
- client_->AddNamespaceToFetch(PolicyNamespaceKey(policy_type, *it)); |
+ for (PolicyNamespaceKeys::const_iterator it = keys.begin(); |
+ it != keys.end(); ++it) { |
+ client_->AddNamespaceToFetch(*it); |
} |
} |
void ComponentCloudPolicyService::RemoveNamespacesToFetch( |
- PolicyDomain domain, |
- const StringSet& set) { |
+ const PolicyNamespaceKeys& keys) { |
DCHECK(CalledOnValidThread()); |
- std::string policy_type; |
- if (ComponentCloudPolicyStore::GetPolicyType(domain, &policy_type)) { |
- for (StringSet::const_iterator it = set.begin(); it != set.end(); ++it) |
- client_->RemoveNamespaceToFetch(PolicyNamespaceKey(policy_type, *it)); |
+ for (PolicyNamespaceKeys::const_iterator it = keys.begin(); |
+ it != keys.end(); ++it) { |
+ client_->RemoveNamespaceToFetch(*it); |
} |
} |