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

Side by Side Diff: chrome/common/pref_service.cc

Issue 27354: Add FilePath setter/getter to pref service.... (Closed) Base URL: svn://chrome-svn/chrome/trunk/src/
Patch Set: '' Created 11 years, 9 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
« no previous file with comments | « chrome/common/pref_service.h ('k') | chrome/common/pref_service_unittest.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2006-2008 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2006-2008 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/common/pref_service.h" 5 #include "chrome/common/pref_service.h"
6 6
7 #include "base/compiler_specific.h" 7 #include "base/compiler_specific.h"
8 #include "base/file_util.h" 8 #include "base/file_util.h"
9 #include "base/logging.h" 9 #include "base/logging.h"
10 #include "base/message_loop.h" 10 #include "base/message_loop.h"
11 #include "base/string_util.h" 11 #include "base/string_util.h"
12 #include "base/task.h" 12 #include "base/task.h"
13 #include "base/thread.h" 13 #include "base/thread.h"
14 #include "chrome/common/json_value_serializer.h" 14 #include "chrome/common/json_value_serializer.h"
15 #include "chrome/common/l10n_util.h" 15 #include "chrome/common/l10n_util.h"
16 #include "chrome/common/notification_service.h" 16 #include "chrome/common/notification_service.h"
17 #include "chrome/common/stl_util-inl.h" 17 #include "chrome/common/stl_util-inl.h"
18 #include "grit/generated_resources.h" 18 #include "grit/generated_resources.h"
19 19
20 namespace { 20 namespace {
21 21
22 // The number of milliseconds we'll wait to do a write of chrome prefs to disk. 22 // The number of milliseconds we'll wait to do a write of chrome prefs to disk.
23 // This lets us batch together write operations. 23 // This lets us batch together write operations.
24 static const int kCommitIntervalMs = 10000; 24 static const int kCommitIntervalMs = 10000;
25 25
26 // Replaces the given file's content with the given data. This allows the 26 // Replaces the given file's content with the given data. This allows the
27 // preferences to be written to disk on a background thread. 27 // preferences to be written to disk on a background thread.
28 class SaveLaterTask : public Task { 28 class SaveLaterTask : public Task {
29 public: 29 public:
30 SaveLaterTask(const std::wstring& file_name, 30 SaveLaterTask(const FilePath& file_name,
31 const std::string& data) 31 const std::string& data)
32 : file_name_(file_name), 32 : file_name_(file_name),
33 data_(data) { 33 data_(data) {
34 } 34 }
35 35
36 void Run() { 36 void Run() {
37 // Write the data to a temp file then rename to avoid data loss if we crash 37 // Write the data to a temp file then rename to avoid data loss if we crash
38 // while writing the file. 38 // while writing the file.
39 std::wstring tmp_file_name = file_name_ + L".tmp"; 39 FilePath tmp_file_name(file_name_.value() + FILE_PATH_LITERAL(".tmp"));
40 int bytes_written = file_util::WriteFile(tmp_file_name, data_.c_str(), 40 int bytes_written = file_util::WriteFile(tmp_file_name, data_.c_str(),
41 static_cast<int>(data_.length())); 41 static_cast<int>(data_.length()));
42 if (bytes_written != -1) { 42 if (bytes_written != -1) {
43 if (!file_util::Move(tmp_file_name, file_name_)) { 43 if (!file_util::Move(tmp_file_name, file_name_)) {
44 // Rename failed. Try again on the off chance someone has locked either 44 // Rename failed. Try again on the off chance someone has locked either
45 // file and hope we're successful the second time through. 45 // file and hope we're successful the second time through.
46 bool move_result = file_util::Move(tmp_file_name, file_name_); 46 bool move_result = file_util::Move(tmp_file_name, file_name_);
47 DCHECK(move_result); 47 DCHECK(move_result);
48 } 48 }
49 } 49 }
50 } 50 }
51 51
52 private: 52 private:
53 std::wstring file_name_; 53 FilePath file_name_;
54 std::string data_; 54 std::string data_;
55 55
56 DISALLOW_COPY_AND_ASSIGN(SaveLaterTask); 56 DISALLOW_COPY_AND_ASSIGN(SaveLaterTask);
57 }; 57 };
58 58
59 // A helper function for RegisterLocalized*Pref that creates a Value* based on 59 // A helper function for RegisterLocalized*Pref that creates a Value* based on
60 // the string value in the locale dll. Because we control the values in a 60 // the string value in the locale dll. Because we control the values in a
61 // locale dll, this should always return a Value of the appropriate type. 61 // locale dll, this should always return a Value of the appropriate type.
62 Value* CreateLocaleDefaultValue(Value::ValueType type, int message_id) { 62 Value* CreateLocaleDefaultValue(Value::ValueType type, int message_id) {
63 std::wstring resource_string = l10n_util::GetString(message_id); 63 std::wstring resource_string = l10n_util::GetString(message_id);
(...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after
98 } 98 }
99 99
100 } // namespace 100 } // namespace
101 101
102 PrefService::PrefService() 102 PrefService::PrefService()
103 : persistent_(new DictionaryValue), 103 : persistent_(new DictionaryValue),
104 transient_(new DictionaryValue), 104 transient_(new DictionaryValue),
105 save_preferences_factory_(NULL) { 105 save_preferences_factory_(NULL) {
106 } 106 }
107 107
108 PrefService::PrefService(const std::wstring& pref_filename) 108 PrefService::PrefService(const FilePath& pref_filename)
109 : persistent_(new DictionaryValue), 109 : persistent_(new DictionaryValue),
110 transient_(new DictionaryValue), 110 transient_(new DictionaryValue),
111 pref_filename_(pref_filename), 111 pref_filename_(pref_filename),
112 ALLOW_THIS_IN_INITIALIZER_LIST(save_preferences_factory_(this)) { 112 ALLOW_THIS_IN_INITIALIZER_LIST(save_preferences_factory_(this)) {
113 LoadPersistentPrefs(pref_filename_); 113 LoadPersistentPrefs(pref_filename_);
114 } 114 }
115 115
116 PrefService::~PrefService() { 116 PrefService::~PrefService() {
117 DCHECK(CalledOnValidThread()); 117 DCHECK(CalledOnValidThread());
118 118
119 // Verify that there are no pref observers when we shut down. 119 // Verify that there are no pref observers when we shut down.
120 for (PrefObserverMap::iterator it = pref_observers_.begin(); 120 for (PrefObserverMap::iterator it = pref_observers_.begin();
121 it != pref_observers_.end(); ++it) { 121 it != pref_observers_.end(); ++it) {
122 NotificationObserverList::Iterator obs_iterator(*(it->second)); 122 NotificationObserverList::Iterator obs_iterator(*(it->second));
123 if (obs_iterator.GetNext()) { 123 if (obs_iterator.GetNext()) {
124 LOG(WARNING) << "pref observer found at shutdown " << it->first; 124 LOG(WARNING) << "pref observer found at shutdown " << it->first;
125 } 125 }
126 } 126 }
127 127
128 STLDeleteContainerPointers(prefs_.begin(), prefs_.end()); 128 STLDeleteContainerPointers(prefs_.begin(), prefs_.end());
129 prefs_.clear(); 129 prefs_.clear();
130 STLDeleteContainerPairSecondPointers(pref_observers_.begin(), 130 STLDeleteContainerPairSecondPointers(pref_observers_.begin(),
131 pref_observers_.end()); 131 pref_observers_.end());
132 pref_observers_.clear(); 132 pref_observers_.clear();
133 } 133 }
134 134
135 bool PrefService::LoadPersistentPrefs(const std::wstring& file_path) { 135 bool PrefService::LoadPersistentPrefs(const FilePath& file_path) {
136 #if defined(OS_WIN) 136 #if defined(OS_WIN)
137 DCHECK(!file_path.empty()); 137 DCHECK(!file_path.empty());
138 #else 138 #else
139 // On non-Windows platforms we haven't gotten round to this yet. 139 // On non-Windows platforms we haven't gotten round to this yet.
140 // TODO(port): remove this exception 140 // TODO(port): remove this exception
141 if (file_path.empty()) { 141 if (file_path.empty()) {
142 NOTIMPLEMENTED(); 142 NOTIMPLEMENTED();
143 return false; 143 return false;
144 } 144 }
145 #endif 145 #endif
146 DCHECK(CalledOnValidThread()); 146 DCHECK(CalledOnValidThread());
147 147
148 JSONFileValueSerializer serializer(file_path); 148 JSONFileValueSerializer serializer(file_path.ToWStringHack());
149 scoped_ptr<Value> root(serializer.Deserialize(NULL)); 149 scoped_ptr<Value> root(serializer.Deserialize(NULL));
150 if (!root.get()) 150 if (!root.get())
151 return false; 151 return false;
152 152
153 // Preferences should always have a dictionary root. 153 // Preferences should always have a dictionary root.
154 if (!root->IsType(Value::TYPE_DICTIONARY)) 154 if (!root->IsType(Value::TYPE_DICTIONARY))
155 return false; 155 return false;
156 156
157 persistent_.reset(static_cast<DictionaryValue*>(root.release())); 157 persistent_.reset(static_cast<DictionaryValue*>(root.release()));
158 return true; 158 return true;
159 } 159 }
160 160
161 void PrefService::ReloadPersistentPrefs() { 161 void PrefService::ReloadPersistentPrefs() {
162 DCHECK(CalledOnValidThread()); 162 DCHECK(CalledOnValidThread());
163 163
164 JSONFileValueSerializer serializer(pref_filename_); 164 JSONFileValueSerializer serializer(pref_filename_.ToWStringHack());
165 scoped_ptr<Value> root(serializer.Deserialize(NULL)); 165 scoped_ptr<Value> root(serializer.Deserialize(NULL));
166 if (!root.get()) 166 if (!root.get())
167 return; 167 return;
168 168
169 // Preferences should always have a dictionary root. 169 // Preferences should always have a dictionary root.
170 if (!root->IsType(Value::TYPE_DICTIONARY)) 170 if (!root->IsType(Value::TYPE_DICTIONARY))
171 return; 171 return;
172 172
173 persistent_.reset(static_cast<DictionaryValue*>(root.release())); 173 persistent_.reset(static_cast<DictionaryValue*>(root.release()));
174 for (PreferenceSet::iterator it = prefs_.begin(); 174 for (PreferenceSet::iterator it = prefs_.begin();
(...skipping 57 matching lines...) Expand 10 before | Expand all | Expand 10 after
232 RegisterPreference(pref); 232 RegisterPreference(pref);
233 } 233 }
234 234
235 void PrefService::RegisterStringPref(const wchar_t* path, 235 void PrefService::RegisterStringPref(const wchar_t* path,
236 const std::wstring& default_value) { 236 const std::wstring& default_value) {
237 Preference* pref = new Preference(persistent_.get(), path, 237 Preference* pref = new Preference(persistent_.get(), path,
238 Value::CreateStringValue(default_value)); 238 Value::CreateStringValue(default_value));
239 RegisterPreference(pref); 239 RegisterPreference(pref);
240 } 240 }
241 241
242 void PrefService::RegisterFilePathPref(const wchar_t* path,
243 const FilePath& default_value) {
244 Preference* pref = new Preference(persistent_.get(), path,
245 Value::CreateStringValue(default_value.value()));
246 RegisterPreference(pref);
247 }
248
242 void PrefService::RegisterListPref(const wchar_t* path) { 249 void PrefService::RegisterListPref(const wchar_t* path) {
243 Preference* pref = new Preference(persistent_.get(), path, 250 Preference* pref = new Preference(persistent_.get(), path,
244 new ListValue); 251 new ListValue);
245 RegisterPreference(pref); 252 RegisterPreference(pref);
246 } 253 }
247 254
248 void PrefService::RegisterDictionaryPref(const wchar_t* path) { 255 void PrefService::RegisterDictionaryPref(const wchar_t* path) {
249 Preference* pref = new Preference(persistent_.get(), path, 256 Preference* pref = new Preference(persistent_.get(), path,
250 new DictionaryValue()); 257 new DictionaryValue());
251 RegisterPreference(pref); 258 RegisterPreference(pref);
(...skipping 98 matching lines...) Expand 10 before | Expand all | Expand 10 after
350 #else 357 #else
351 // TODO(port): remove this exception 358 // TODO(port): remove this exception
352 #endif 359 #endif
353 return result; 360 return result;
354 } 361 }
355 bool rv = pref->GetValue()->GetAsString(&result); 362 bool rv = pref->GetValue()->GetAsString(&result);
356 DCHECK(rv); 363 DCHECK(rv);
357 return result; 364 return result;
358 } 365 }
359 366
367 FilePath PrefService::GetFilePath(const wchar_t* path) const {
368 DCHECK(CalledOnValidThread());
369
370 FilePath::StringType result;
371 if (transient_->GetString(path, &result))
372 return FilePath(result);
373
374 const Preference* pref = FindPreference(path);
375 if (!pref) {
376 #if defined(OS_WIN)
377 DCHECK(false) << "Trying to read an unregistered pref: " << path;
378 #else
379 // TODO(port): remove this exception
380 #endif
381 return FilePath(result);
382 }
383 bool rv = pref->GetValue()->GetAsString(&result);
384 DCHECK(rv);
385 return FilePath(result);
386 }
387
360 bool PrefService::HasPrefPath(const wchar_t* path) const { 388 bool PrefService::HasPrefPath(const wchar_t* path) const {
361 Value* value = NULL; 389 Value* value = NULL;
362 return (transient_->Get(path, &value) || persistent_->Get(path, &value)); 390 return (transient_->Get(path, &value) || persistent_->Get(path, &value));
363 } 391 }
364 392
365 const PrefService::Preference* PrefService::FindPreference( 393 const PrefService::Preference* PrefService::FindPreference(
366 const wchar_t* pref_name) const { 394 const wchar_t* pref_name) const {
367 DCHECK(CalledOnValidThread()); 395 DCHECK(CalledOnValidThread());
368 Preference p(NULL, pref_name, NULL); 396 Preference p(NULL, pref_name, NULL);
369 PreferenceSet::const_iterator it = prefs_.find(&p); 397 PreferenceSet::const_iterator it = prefs_.find(&p);
(...skipping 185 matching lines...) Expand 10 before | Expand all | Expand 10 after
555 return; 583 return;
556 } 584 }
557 585
558 scoped_ptr<Value> old_value(GetPrefCopy(path)); 586 scoped_ptr<Value> old_value(GetPrefCopy(path));
559 bool rv = persistent_->SetString(path, value); 587 bool rv = persistent_->SetString(path, value);
560 DCHECK(rv); 588 DCHECK(rv);
561 589
562 FireObserversIfChanged(path, old_value.get()); 590 FireObserversIfChanged(path, old_value.get());
563 } 591 }
564 592
593 void PrefService::SetFilePath(const wchar_t* path, const FilePath& value) {
594 DCHECK(CalledOnValidThread());
595
596 const Preference* pref = FindPreference(path);
597 if (!pref) {
598 DCHECK(false) << "Trying to write an unregistered pref: " << path;
599 return;
600 }
601 if (pref->type() != Value::TYPE_STRING) {
602 DCHECK(false) << "Wrong type for SetFilePath: " << path;
603 return;
604 }
605
606 scoped_ptr<Value> old_value(GetPrefCopy(path));
607 bool rv = persistent_->SetString(path, value.value());
608 DCHECK(rv);
609
610 FireObserversIfChanged(path, old_value.get());
611 }
612
565 DictionaryValue* PrefService::GetMutableDictionary(const wchar_t* path) { 613 DictionaryValue* PrefService::GetMutableDictionary(const wchar_t* path) {
566 DCHECK(CalledOnValidThread()); 614 DCHECK(CalledOnValidThread());
567 615
568 const Preference* pref = FindPreference(path); 616 const Preference* pref = FindPreference(path);
569 if (!pref) { 617 if (!pref) {
570 DCHECK(false) << "Trying to get an unregistered pref: " << path; 618 DCHECK(false) << "Trying to get an unregistered pref: " << path;
571 return NULL; 619 return NULL;
572 } 620 }
573 if (pref->type() != Value::TYPE_DICTIONARY) { 621 if (pref->type() != Value::TYPE_DICTIONARY) {
574 DCHECK(false) << "Wrong type for GetMutableDictionary: " << path; 622 DCHECK(false) << "Wrong type for GetMutableDictionary: " << path;
(...skipping 103 matching lines...) Expand 10 before | Expand all | Expand 10 after
678 } 726 }
679 727
680 // Pref not found, just return the app default. 728 // Pref not found, just return the app default.
681 return default_value_.get(); 729 return default_value_.get();
682 } 730 }
683 731
684 bool PrefService::Preference::IsDefaultValue() const { 732 bool PrefService::Preference::IsDefaultValue() const {
685 DCHECK(default_value_.get()); 733 DCHECK(default_value_.get());
686 return default_value_->Equals(GetValue()); 734 return default_value_->Equals(GetValue());
687 } 735 }
OLDNEW
« no previous file with comments | « chrome/common/pref_service.h ('k') | chrome/common/pref_service_unittest.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698