blob: 7032be99d9a3e64fafb9209aa5db53906cbf7150 [file] [log] [blame]
[email protected]9a8c4022011-01-25 14:25:331// Copyright (c) 2011 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.
4
5#include "chrome/browser/extensions/extension_pref_value_map.h"
6
7#include "base/stl_util-inl.h"
8#include "base/values.h"
9#include "chrome/browser/prefs/pref_value_map.h"
10
[email protected]0865c1342011-01-28 20:29:3711struct ExtensionPrefValueMap::ExtensionEntry {
12 // Installation time of the extension.
13 base::Time install_time;
14 // Whether extension is enabled in the profile.
15 bool enabled;
16 // Regular preferences.
17 PrefValueMap reg_preferences;
18 // Incognito preferences, empty for regular ExtensionPrefStore.
19 PrefValueMap inc_preferences;
20};
21
[email protected]9a8c4022011-01-25 14:25:3322ExtensionPrefValueMap::ExtensionPrefValueMap() {
23}
24
25ExtensionPrefValueMap::~ExtensionPrefValueMap() {
26 NotifyOfDestruction();
27 STLDeleteValues(&entries_);
28 entries_.clear();
29}
30
31void ExtensionPrefValueMap::SetExtensionPref(const std::string& ext_id,
32 const std::string& key,
33 bool incognito,
34 Value* value) {
35 PrefValueMap* prefs = GetExtensionPrefValueMap(ext_id, incognito);
36
37 if (prefs->SetValue(key, value))
38 NotifyPrefValueChanged(key);
39}
40
41void ExtensionPrefValueMap::RemoveExtensionPref(const std::string& ext_id,
42 const std::string& key,
43 bool incognito) {
44 PrefValueMap* prefs = GetExtensionPrefValueMap(ext_id, incognito);
45 if (prefs->RemoveValue(key))
46 NotifyPrefValueChanged(key);
47}
48
[email protected]9a28f132011-02-24 21:15:1649bool ExtensionPrefValueMap::CanExtensionControlPref(
50 const std::string& extension_id,
51 const std::string& pref_key,
52 bool incognito) const {
53 ExtensionEntryMap::const_iterator ext = entries_.find(extension_id);
54 if (ext == entries_.end()) {
55 NOTREACHED();
56 return false;
57 }
58
59 ExtensionEntryMap::const_iterator winner =
[email protected]c0793562011-03-09 15:31:0360 GetEffectivePrefValueController(pref_key, incognito, NULL);
[email protected]9a28f132011-02-24 21:15:1661 if (winner == entries_.end())
62 return true;
63
64 return winner->second->install_time <= ext->second->install_time;
65}
66
67bool ExtensionPrefValueMap::DoesExtensionControlPref(
68 const std::string& extension_id,
69 const std::string& pref_key,
70 bool incognito) const {
71 ExtensionEntryMap::const_iterator winner =
[email protected]c0793562011-03-09 15:31:0372 GetEffectivePrefValueController(pref_key, incognito, NULL);
[email protected]9a28f132011-02-24 21:15:1673 if (winner == entries_.end())
74 return false;
75 return winner->first == extension_id;
76}
77
[email protected]9a8c4022011-01-25 14:25:3378void ExtensionPrefValueMap::RegisterExtension(const std::string& ext_id,
79 const base::Time& install_time,
80 bool is_enabled) {
81 if (entries_.find(ext_id) != entries_.end())
82 UnregisterExtension(ext_id);
83 entries_[ext_id] = new ExtensionEntry;
84 entries_[ext_id]->install_time = install_time;
85 entries_[ext_id]->enabled = is_enabled;
86}
87
88void ExtensionPrefValueMap::UnregisterExtension(const std::string& ext_id) {
89 ExtensionEntryMap::iterator i = entries_.find(ext_id);
90 if (i == entries_.end())
91 return;
92 std::set<std::string> keys; // keys set by this extension
93 GetExtensionControlledKeys(*(i->second), &keys);
94
95 delete i->second;
96 entries_.erase(i);
97
98 NotifyPrefValueChanged(keys);
99}
100
101void ExtensionPrefValueMap::SetExtensionState(const std::string& ext_id,
102 bool is_enabled) {
103 ExtensionEntryMap::const_iterator i = entries_.find(ext_id);
[email protected]06f92562011-04-29 19:27:31104 // This may happen when sync sets the extension state for an
105 // extension that is not installed.
106 if (i == entries_.end())
107 return;
[email protected]9a8c4022011-01-25 14:25:33108 if (i->second->enabled == is_enabled)
109 return;
110 std::set<std::string> keys; // keys set by this extension
111 GetExtensionControlledKeys(*(i->second), &keys);
112 i->second->enabled = is_enabled;
113 NotifyPrefValueChanged(keys);
114}
115
116PrefValueMap* ExtensionPrefValueMap::GetExtensionPrefValueMap(
117 const std::string& ext_id,
118 bool incognito) {
119 ExtensionEntryMap::const_iterator i = entries_.find(ext_id);
120 CHECK(i != entries_.end());
121 return incognito ? &(i->second->inc_preferences)
122 : &(i->second->reg_preferences);
123}
124
125const PrefValueMap* ExtensionPrefValueMap::GetExtensionPrefValueMap(
126 const std::string& ext_id,
127 bool incognito) const {
128 ExtensionEntryMap::const_iterator i = entries_.find(ext_id);
129 CHECK(i != entries_.end());
130 return incognito ? &(i->second->inc_preferences)
131 : &(i->second->reg_preferences);
132}
133
134void ExtensionPrefValueMap::GetExtensionControlledKeys(
135 const ExtensionEntry& entry,
136 std::set<std::string>* out) const {
137 PrefValueMap::const_iterator i;
138
139 const PrefValueMap& reg_prefs = entry.reg_preferences;
140 for (i = reg_prefs.begin(); i != reg_prefs.end(); ++i)
141 out->insert(i->first);
142
143 const PrefValueMap& inc_prefs = entry.inc_preferences;
144 for (i = inc_prefs.begin(); i != inc_prefs.end(); ++i)
145 out->insert(i->first);
146}
147
148const Value* ExtensionPrefValueMap::GetEffectivePrefValue(
149 const std::string& key,
[email protected]c0793562011-03-09 15:31:03150 bool incognito,
151 bool* from_incognito) const {
[email protected]9a28f132011-02-24 21:15:16152 ExtensionEntryMap::const_iterator winner =
[email protected]c0793562011-03-09 15:31:03153 GetEffectivePrefValueController(key, incognito, from_incognito);
[email protected]9a28f132011-02-24 21:15:16154 if (winner == entries_.end())
155 return NULL;
156
[email protected]68bf41a2011-03-25 16:38:31157 const Value* value = NULL;
[email protected]9a28f132011-02-24 21:15:16158 const std::string& ext_id = winner->first;
159 if (incognito)
160 GetExtensionPrefValueMap(ext_id, true)->GetValue(key, &value);
161 if (!value)
162 GetExtensionPrefValueMap(ext_id, false)->GetValue(key, &value);
163 return value;
164}
165
166ExtensionPrefValueMap::ExtensionEntryMap::const_iterator
167ExtensionPrefValueMap::GetEffectivePrefValueController(
168 const std::string& key,
[email protected]c0793562011-03-09 15:31:03169 bool incognito,
170 bool* from_incognito) const {
[email protected]9a28f132011-02-24 21:15:16171 ExtensionEntryMap::const_iterator winner = entries_.end();
[email protected]9a8c4022011-01-25 14:25:33172 base::Time winners_install_time;
173
174 ExtensionEntryMap::const_iterator i;
175 for (i = entries_.begin(); i != entries_.end(); ++i) {
176 const std::string& ext_id = i->first;
177 const base::Time& install_time = i->second->install_time;
178 const bool enabled = i->second->enabled;
179
180 if (!enabled)
181 continue;
182 if (install_time < winners_install_time)
183 continue;
184
[email protected]68bf41a2011-03-25 16:38:31185 const Value* value = NULL;
[email protected]9a8c4022011-01-25 14:25:33186 const PrefValueMap* prefs = GetExtensionPrefValueMap(ext_id, false);
187 if (prefs->GetValue(key, &value)) {
[email protected]9a28f132011-02-24 21:15:16188 winner = i;
[email protected]9a8c4022011-01-25 14:25:33189 winners_install_time = install_time;
[email protected]c0793562011-03-09 15:31:03190 if (from_incognito)
191 *from_incognito = false;
[email protected]9a8c4022011-01-25 14:25:33192 }
193
194 if (!incognito)
195 continue;
196
197 prefs = GetExtensionPrefValueMap(ext_id, true);
198 if (prefs->GetValue(key, &value)) {
[email protected]9a28f132011-02-24 21:15:16199 winner = i;
[email protected]9a8c4022011-01-25 14:25:33200 winners_install_time = install_time;
[email protected]c0793562011-03-09 15:31:03201 if (from_incognito)
202 *from_incognito = true;
[email protected]9a8c4022011-01-25 14:25:33203 }
204 }
205 return winner;
206}
207
208void ExtensionPrefValueMap::AddObserver(
209 ExtensionPrefValueMap::Observer* observer) {
210 observers_.AddObserver(observer);
211
212 // Collect all currently used keys and notify the new observer.
213 std::set<std::string> keys;
214 ExtensionEntryMap::const_iterator i;
215 for (i = entries_.begin(); i != entries_.end(); ++i)
216 GetExtensionControlledKeys(*(i->second), &keys);
217
218 std::set<std::string>::const_iterator j;
219 for (j = keys.begin(); j != keys.end(); ++j)
220 observer->OnPrefValueChanged(*j);
221}
222
223void ExtensionPrefValueMap::RemoveObserver(
224 ExtensionPrefValueMap::Observer* observer) {
225 observers_.RemoveObserver(observer);
226}
227
228void ExtensionPrefValueMap::NotifyInitializationCompleted() {
229 FOR_EACH_OBSERVER(ExtensionPrefValueMap::Observer, observers_,
230 OnInitializationCompleted());
231}
232
233void ExtensionPrefValueMap::NotifyPrefValueChanged(
234 const std::set<std::string>& keys) {
235 std::set<std::string>::const_iterator i;
236 for (i = keys.begin(); i != keys.end(); ++i)
237 NotifyPrefValueChanged(*i);
238}
239
240void ExtensionPrefValueMap::NotifyPrefValueChanged(const std::string& key) {
241 FOR_EACH_OBSERVER(ExtensionPrefValueMap::Observer, observers_,
242 OnPrefValueChanged(key));
243}
244
245void ExtensionPrefValueMap::NotifyOfDestruction() {
246 FOR_EACH_OBSERVER(ExtensionPrefValueMap::Observer, observers_,
247 OnExtensionPrefValueMapDestruction());
248}