Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright 2017 The Chromium Authors. All rights reserved. | 1 // Copyright 2017 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 "services/preferences/persistent_pref_store_impl.h" | 5 #include "services/preferences/persistent_pref_store_impl.h" |
| 6 | 6 |
| 7 #include <utility> | 7 #include <utility> |
| 8 | 8 |
| 9 #include "base/auto_reset.h" | 9 #include "base/auto_reset.h" |
| 10 #include "base/memory/ptr_util.h" | 10 #include "base/memory/ptr_util.h" |
| 11 #include "base/stl_util.h" | 11 #include "base/stl_util.h" |
| 12 #include "base/values.h" | 12 #include "base/values.h" |
| 13 #include "components/prefs/persistent_pref_store.h" | 13 #include "components/prefs/persistent_pref_store.h" |
| 14 #include "mojo/common/values_struct_traits.h" | |
| 14 #include "mojo/public/cpp/bindings/binding.h" | 15 #include "mojo/public/cpp/bindings/binding.h" |
| 16 #include "services/preferences/public/cpp/lib/util.h" | |
| 15 | 17 |
| 16 namespace prefs { | 18 namespace prefs { |
| 17 | 19 |
| 18 class PersistentPrefStoreImpl::Connection : public mojom::PersistentPrefStore { | 20 class PersistentPrefStoreImpl::Connection : public mojom::PersistentPrefStore { |
| 19 public: | 21 public: |
| 20 Connection(PersistentPrefStoreImpl* pref_store, | 22 Connection(PersistentPrefStoreImpl* pref_store, |
| 21 mojom::PersistentPrefStoreRequest request, | 23 mojom::PersistentPrefStoreRequest request, |
| 22 mojom::PrefStoreObserverPtr observer, | 24 mojom::PrefStoreObserverPtr observer, |
| 23 ObservedPrefs observed_keys) | 25 ObservedPrefs observed_keys) |
| 24 : pref_store_(pref_store), | 26 : pref_store_(pref_store), |
| 25 binding_(this, std::move(request)), | 27 binding_(this, std::move(request)), |
| 26 observer_(std::move(observer)), | 28 observer_(std::move(observer)), |
| 27 observed_keys_(std::move(observed_keys)) { | 29 observed_keys_(std::move(observed_keys)) { |
| 28 auto error_callback = | 30 auto error_callback = |
| 29 base::Bind(&PersistentPrefStoreImpl::Connection::OnConnectionError, | 31 base::Bind(&PersistentPrefStoreImpl::Connection::OnConnectionError, |
| 30 base::Unretained(this)); | 32 base::Unretained(this)); |
| 31 binding_.set_connection_error_handler(error_callback); | 33 binding_.set_connection_error_handler(error_callback); |
| 32 observer_.set_connection_error_handler(error_callback); | 34 observer_.set_connection_error_handler(error_callback); |
| 33 } | 35 } |
| 34 | 36 |
| 35 ~Connection() override = default; | 37 ~Connection() override = default; |
| 36 | 38 |
| 37 void OnPrefValuesChanged(const std::vector<mojom::PrefUpdatePtr>& updates) { | 39 void OnPrefValuesChanged(const std::vector<mojom::PrefUpdatePtr>& updates) { |
| 38 if (write_in_progress_) | 40 if (write_in_progress_) |
| 39 return; | 41 return; |
| 40 | 42 |
| 41 std::vector<mojom::PrefUpdatePtr> filtered_updates; | 43 std::vector<mojom::PrefUpdatePtr> filtered_updates; |
| 42 for (const auto& update : updates) { | 44 for (const auto& update : updates) { |
| 43 if (base::ContainsKey(observed_keys_, update->key)) { | 45 if (base::ContainsKey(observed_keys_, update->key)) { |
| 44 filtered_updates.push_back(mojom::PrefUpdate::New( | 46 filtered_updates.push_back(update->Clone()); |
| 45 update->key, | |
| 46 update->value ? update->value->CreateDeepCopy() : nullptr, 0)); | |
| 47 } | 47 } |
| 48 } | 48 } |
| 49 if (!filtered_updates.empty()) | 49 if (!filtered_updates.empty()) |
| 50 observer_->OnPrefsChanged(std::move(filtered_updates)); | 50 observer_->OnPrefsChanged(std::move(filtered_updates)); |
| 51 } | 51 } |
| 52 | 52 |
| 53 private: | 53 private: |
| 54 // mojom::PersistentPrefStore: | 54 // mojom::PersistentPrefStore: |
| 55 void SetValues(std::vector<mojom::PrefUpdatePtr> updates) override { | 55 void SetValues(std::vector<mojom::PrefUpdatePtr> updates) override { |
| 56 base::AutoReset<bool> scoped_call_in_progress(&write_in_progress_, true); | 56 base::AutoReset<bool> scoped_call_in_progress(&write_in_progress_, true); |
| (...skipping 69 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 126 initializing_ = false; | 126 initializing_ = false; |
| 127 std::move(on_initialized_).Run(); | 127 std::move(on_initialized_).Run(); |
| 128 } | 128 } |
| 129 | 129 |
| 130 void PersistentPrefStoreImpl::SetValues( | 130 void PersistentPrefStoreImpl::SetValues( |
| 131 std::vector<mojom::PrefUpdatePtr> updates) { | 131 std::vector<mojom::PrefUpdatePtr> updates) { |
| 132 for (auto& entry : connections_) | 132 for (auto& entry : connections_) |
| 133 entry.first->OnPrefValuesChanged(updates); | 133 entry.first->OnPrefValuesChanged(updates); |
| 134 | 134 |
| 135 for (auto& update : updates) { | 135 for (auto& update : updates) { |
| 136 if (update->value) { | 136 if (update->value->is_atomic_update()) { |
| 137 backing_pref_store_->SetValue(update->key, std::move(update->value), | 137 auto& value = update->value->get_atomic_update(); |
| 138 if (value) { | |
| 139 backing_pref_store_->SetValue(update->key, value->CreateDeepCopy(), | |
|
tibell
2017/04/12 07:13:52
Can't we move out value?
| |
| 140 update->flags); | |
| 141 } else { | |
| 142 backing_pref_store_->RemoveValue(update->key, update->flags); | |
| 143 } | |
| 144 continue; | |
| 145 } | |
| 146 | |
| 147 DCHECK(update->value->is_split_updates()); | |
|
tibell
2017/04/12 07:13:52
I'd prefer that this was in an else block without
| |
| 148 base::Value* mutable_value = nullptr; | |
| 149 base::DictionaryValue* dictionary_value = nullptr; | |
| 150 std::unique_ptr<base::DictionaryValue> pending_dictionary; | |
| 151 if (!backing_pref_store_->GetMutableValue(update->key, &mutable_value) || | |
| 152 !mutable_value->GetAsDictionary(&dictionary_value)) { | |
| 153 pending_dictionary = base::MakeUnique<base::DictionaryValue>(); | |
| 154 dictionary_value = pending_dictionary.get(); | |
| 155 } | |
| 156 for (auto& split_update : update->value->get_split_updates()) { | |
| 157 if (split_update->path.empty()) | |
| 158 continue; | |
| 159 | |
| 160 SetValue(dictionary_value, | |
| 161 {split_update->path.begin(), split_update->path.end()}, | |
| 162 std::move(split_update->value)); | |
| 163 } | |
| 164 if (pending_dictionary) { | |
| 165 backing_pref_store_->SetValue(update->key, std::move(pending_dictionary), | |
| 138 update->flags); | 166 update->flags); |
| 139 } else { | 167 } else { |
| 140 backing_pref_store_->RemoveValue(update->key, update->flags); | 168 backing_pref_store_->ReportValueChanged(update->key, update->flags); |
| 141 } | 169 } |
| 142 } | 170 } |
| 143 } | 171 } |
| 144 | 172 |
| 145 void PersistentPrefStoreImpl::CommitPendingWrite() { | 173 void PersistentPrefStoreImpl::CommitPendingWrite() { |
| 146 backing_pref_store_->CommitPendingWrite(); | 174 backing_pref_store_->CommitPendingWrite(); |
| 147 } | 175 } |
| 148 | 176 |
| 149 void PersistentPrefStoreImpl::SchedulePendingLossyWrites() { | 177 void PersistentPrefStoreImpl::SchedulePendingLossyWrites() { |
| 150 backing_pref_store_->SchedulePendingLossyWrites(); | 178 backing_pref_store_->SchedulePendingLossyWrites(); |
| 151 } | 179 } |
| 152 | 180 |
| 153 void PersistentPrefStoreImpl::ClearMutableValues() { | 181 void PersistentPrefStoreImpl::ClearMutableValues() { |
| 154 backing_pref_store_->ClearMutableValues(); | 182 backing_pref_store_->ClearMutableValues(); |
| 155 } | 183 } |
| 156 | 184 |
| 157 void PersistentPrefStoreImpl::OnConnectionError(Connection* connection) { | 185 void PersistentPrefStoreImpl::OnConnectionError(Connection* connection) { |
| 158 connections_.erase(connection); | 186 connections_.erase(connection); |
| 159 } | 187 } |
| 160 | 188 |
| 161 } // namespace prefs | 189 } // namespace prefs |
| OLD | NEW |