Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright 2016 The Chromium Authors. All rights reserved. | 1 // Copyright 2016 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 "mojo/services/catalog/catalog.h" | 5 #include "mojo/services/catalog/catalog.h" |
| 6 | 6 |
| 7 #include "base/bind.h" | 7 #include "base/bind.h" |
| 8 #include "base/json/json_file_value_serializer.h" | 8 #include "base/json/json_file_value_serializer.h" |
| 9 #include "base/strings/string_split.h" | 9 #include "base/strings/string_split.h" |
| 10 #include "base/task_runner_util.h" | 10 #include "base/task_runner_util.h" |
| (...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 42 #if defined OS_WIN | 42 #if defined OS_WIN |
| 43 std::string extension = ".exe"; | 43 std::string extension = ".exe"; |
| 44 #else | 44 #else |
| 45 std::string extension; | 45 std::string extension; |
| 46 #endif | 46 #endif |
| 47 return package_dir.AppendASCII(mojo::GetNamePath(name) + extension); | 47 return package_dir.AppendASCII(mojo::GetNamePath(name) + extension); |
| 48 } | 48 } |
| 49 return base::FilePath(); | 49 return base::FilePath(); |
| 50 } | 50 } |
| 51 | 51 |
| 52 scoped_ptr<ReadManifestResult> ReadManifest(const base::FilePath& package_dir, | 52 scoped_ptr<ReadManifestResult> ReadManifest( |
| 53 const std::string& name) { | 53 const base::FilePath& user_package_dir, |
| 54 base::FilePath manifest_path = GetManifestPath(package_dir, name); | 54 const base::FilePath& system_package_dir, |
| 55 const std::string& name) { | |
| 56 base::FilePath manifest_path = GetManifestPath(system_package_dir, name); | |
| 55 JSONFileValueDeserializer deserializer(manifest_path); | 57 JSONFileValueDeserializer deserializer(manifest_path); |
| 56 int error = 0; | 58 int error = 0; |
| 57 std::string message; | 59 std::string message; |
| 58 // TODO(beng): probably want to do more detailed error checking. This should | 60 // TODO(beng): probably want to do more detailed error checking. This should |
| 59 // be done when figuring out if to unblock connection completion. | 61 // be done when figuring out if to unblock connection completion. |
| 60 scoped_ptr<ReadManifestResult> result(new ReadManifestResult); | 62 scoped_ptr<ReadManifestResult> result(new ReadManifestResult); |
| 61 result->manifest_root = deserializer.Deserialize(&error, &message); | 63 result->manifest_root = deserializer.Deserialize(&error, &message); |
| 62 result->package_dir = package_dir; | 64 result->package_dir = system_package_dir; |
| 63 return result; | 65 return result; |
| 64 } | 66 } |
| 65 | 67 |
| 66 } // namespace | 68 } // namespace |
| 67 | 69 |
| 68 ReadManifestResult::ReadManifestResult() {} | 70 ReadManifestResult::ReadManifestResult() {} |
| 69 ReadManifestResult::~ReadManifestResult() {} | 71 ReadManifestResult::~ReadManifestResult() {} |
| 70 | 72 |
| 71 //////////////////////////////////////////////////////////////////////////////// | 73 //////////////////////////////////////////////////////////////////////////////// |
| 72 // Catalog, public: | 74 // Catalog, public: |
| 73 | 75 |
| 74 Catalog::Catalog(scoped_ptr<Store> store, base::TaskRunner* file_task_runner) | 76 Catalog::Catalog(scoped_ptr<Store> store, |
| 77 base::TaskRunner* file_task_runner, | |
| 78 EntryCache* system_catalog) | |
| 75 : store_(std::move(store)), | 79 : store_(std::move(store)), |
| 76 file_task_runner_(file_task_runner), | 80 file_task_runner_(file_task_runner), |
| 81 system_catalog_(system_catalog), | |
| 77 weak_factory_(this) { | 82 weak_factory_(this) { |
| 78 PathService::Get(base::DIR_MODULE, &system_package_dir_); | 83 PathService::Get(base::DIR_MODULE, &system_package_dir_); |
| 79 DeserializeCatalog(); | 84 DeserializeCatalog(); |
| 80 } | 85 } |
| 81 | 86 |
| 82 Catalog::~Catalog() {} | 87 Catalog::~Catalog() {} |
| 83 | 88 |
| 84 void Catalog::BindResolver(mojom::ResolverRequest request) { | 89 void Catalog::BindResolver(mojom::ResolverRequest request) { |
| 85 resolver_bindings_.AddBinding(this, std::move(request)); | 90 resolver_bindings_.AddBinding(this, std::move(request)); |
| 86 } | 91 } |
| (...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 123 | 128 |
| 124 void Catalog::ResolveMojoName(const mojo::String& mojo_name, | 129 void Catalog::ResolveMojoName(const mojo::String& mojo_name, |
| 125 const ResolveMojoNameCallback& callback) { | 130 const ResolveMojoNameCallback& callback) { |
| 126 std::string type = mojo::GetNameType(mojo_name); | 131 std::string type = mojo::GetNameType(mojo_name); |
| 127 if (type != "mojo" && type != "exe") { | 132 if (type != "mojo" && type != "exe") { |
| 128 scoped_ptr<Entry> entry(new Entry(mojo_name)); | 133 scoped_ptr<Entry> entry(new Entry(mojo_name)); |
| 129 callback.Run(mojo::shell::mojom::ResolveResult::From(*entry)); | 134 callback.Run(mojo::shell::mojom::ResolveResult::From(*entry)); |
| 130 return; | 135 return; |
| 131 } | 136 } |
| 132 | 137 |
| 133 auto entry = catalog_.find(mojo_name); | 138 auto entry = user_catalog_.find(mojo_name); |
| 134 if (entry != catalog_.end()) { | 139 if (entry != user_catalog_.end()) { |
| 135 callback.Run(mojo::shell::mojom::ResolveResult::From(*entry->second)); | 140 callback.Run(mojo::shell::mojom::ResolveResult::From(*entry->second)); |
| 136 } else { | 141 return; |
| 137 base::PostTaskAndReplyWithResult( | |
| 138 file_task_runner_, FROM_HERE, | |
| 139 base::Bind(&ReadManifest, system_package_dir_, mojo_name), | |
| 140 base::Bind(&Catalog::OnReadManifest, weak_factory_.GetWeakPtr(), | |
| 141 mojo_name, callback)); | |
| 142 } | 142 } |
| 143 entry = system_catalog_->find(mojo_name); | |
| 144 if (entry != system_catalog_->end()) { | |
| 145 callback.Run(mojo::shell::mojom::ResolveResult::From(*entry->second)); | |
| 146 return; | |
| 147 } | |
| 148 base::PostTaskAndReplyWithResult( | |
| 149 file_task_runner_, FROM_HERE, | |
| 150 base::Bind(&ReadManifest, base::FilePath(), system_package_dir_, | |
| 151 mojo_name), | |
| 152 base::Bind(&Catalog::OnReadManifest, weak_factory_.GetWeakPtr(), | |
| 153 mojo_name, callback)); | |
| 143 } | 154 } |
| 144 | 155 |
| 145 //////////////////////////////////////////////////////////////////////////////// | 156 //////////////////////////////////////////////////////////////////////////////// |
| 146 // Catalog, mojom::Catalog: | 157 // Catalog, mojom::Catalog: |
| 147 | 158 |
| 148 void Catalog::GetEntries(mojo::Array<mojo::String> names, | 159 void Catalog::GetEntries(mojo::Array<mojo::String> names, |
| 149 const GetEntriesCallback& callback) { | 160 const GetEntriesCallback& callback) { |
| 150 mojo::Map<mojo::String, mojom::CatalogEntryPtr> entries; | 161 mojo::Map<mojo::String, mojom::CatalogEntryPtr> entries; |
| 151 std::vector<mojo::String> names_vec = names.PassStorage(); | 162 std::vector<mojo::String> names_vec = names.PassStorage(); |
| 152 for (const std::string& name : names_vec) { | 163 for (const std::string& name : names_vec) { |
| 153 if (catalog_.find(name) == catalog_.end()) | 164 Entry* entry = nullptr; |
| 165 if (user_catalog_.find(name) != user_catalog_.end()) | |
| 166 entry = user_catalog_[name].get(); | |
| 167 else if (system_catalog_->find(name) != system_catalog_->end()) | |
| 168 entry = (*system_catalog_)[name].get(); | |
| 169 else | |
| 154 continue; | 170 continue; |
| 155 const Entry& entry = *catalog_[name]; | |
| 156 mojom::CatalogEntryPtr entry_ptr(mojom::CatalogEntry::New()); | 171 mojom::CatalogEntryPtr entry_ptr(mojom::CatalogEntry::New()); |
| 157 entry_ptr->display_name = entry.display_name(); | 172 entry_ptr->display_name = entry->display_name(); |
| 158 entries[entry.name()] = std::move(entry_ptr); | 173 entries[entry->name()] = std::move(entry_ptr); |
| 159 } | 174 } |
| 160 callback.Run(std::move(entries)); | 175 callback.Run(std::move(entries)); |
| 161 } | 176 } |
| 162 | 177 |
| 163 //////////////////////////////////////////////////////////////////////////////// | 178 //////////////////////////////////////////////////////////////////////////////// |
| 164 // Catalog, private: | 179 // Catalog, private: |
| 165 | 180 |
| 166 void Catalog::DeserializeCatalog() { | 181 void Catalog::DeserializeCatalog() { |
| 167 if (!store_) | 182 if (!store_) |
| 168 return; | 183 return; |
| 169 const base::ListValue* catalog = store_->GetStore(); | 184 const base::ListValue* catalog = store_->GetStore(); |
| 170 CHECK(catalog); | 185 CHECK(catalog); |
| 171 // TODO(sky): make this handle aliases. | 186 // TODO(sky): make this handle aliases. |
| 187 // TODO(beng): implement this properly! | |
| 172 for (auto it = catalog->begin(); it != catalog->end(); ++it) { | 188 for (auto it = catalog->begin(); it != catalog->end(); ++it) { |
| 173 const base::DictionaryValue* dictionary = nullptr; | 189 const base::DictionaryValue* dictionary = nullptr; |
| 174 const base::Value* v = *it; | 190 const base::Value* v = *it; |
| 175 CHECK(v->GetAsDictionary(&dictionary)); | 191 CHECK(v->GetAsDictionary(&dictionary)); |
| 176 scoped_ptr<Entry> entry = Entry::Deserialize(*dictionary); | 192 scoped_ptr<Entry> entry = Entry::Deserialize(*dictionary); |
| 177 if (entry) | 193 if (entry) |
| 178 catalog_[entry->name()] = std::move(entry); | 194 user_catalog_[entry->name()] = std::move(entry); |
| 179 } | 195 } |
| 180 } | 196 } |
| 181 | 197 |
| 182 void Catalog::SerializeCatalog() { | 198 void Catalog::SerializeCatalog() { |
| 199 // TODO(beng): system catalog? | |
| 183 scoped_ptr<base::ListValue> catalog(new base::ListValue); | 200 scoped_ptr<base::ListValue> catalog(new base::ListValue); |
| 184 for (const auto& entry : catalog_) | 201 for (const auto& entry : user_catalog_) |
| 185 catalog->Append(entry.second->Serialize()); | 202 catalog->Append(entry.second->Serialize()); |
| 186 if (store_) | 203 if (store_) |
| 187 store_->UpdateStore(std::move(catalog)); | 204 store_->UpdateStore(std::move(catalog)); |
| 188 } | 205 } |
| 189 | 206 |
| 190 // static | 207 // static |
| 191 void Catalog::OnReadManifest(base::WeakPtr<Catalog> catalog, | 208 void Catalog::OnReadManifest(base::WeakPtr<Catalog> catalog, |
| 192 const std::string& name, | 209 const std::string& name, |
| 193 const ResolveMojoNameCallback& callback, | 210 const ResolveMojoNameCallback& callback, |
| 194 scoped_ptr<ReadManifestResult> result) { | 211 scoped_ptr<ReadManifestResult> result) { |
| 195 scoped_ptr<Entry> entry(new Entry(name)); | 212 scoped_ptr<Entry> entry(new Entry(name)); |
| 196 if (result->manifest_root) { | 213 if (result->manifest_root) { |
| 197 const base::DictionaryValue* dictionary = nullptr; | 214 const base::DictionaryValue* dictionary = nullptr; |
| 198 CHECK(result->manifest_root->GetAsDictionary(&dictionary)); | 215 CHECK(result->manifest_root->GetAsDictionary(&dictionary)); |
| 199 entry = Entry::Deserialize(*dictionary); | 216 entry = Entry::Deserialize(*dictionary); |
| 200 } | 217 } |
| 201 entry->set_path(GetPackagePath(result->package_dir, name)); | 218 entry->set_path(GetPackagePath(result->package_dir, name)); |
| 202 | 219 |
| 203 callback.Run(mojo::shell::mojom::ResolveResult::From(*entry)); | 220 callback.Run(mojo::shell::mojom::ResolveResult::From(*entry)); |
| 204 if (catalog) | 221 if (catalog) { |
| 205 catalog->AddEntryToCatalog(std::move(entry)); | 222 catalog->AddEntryToCatalog( |
| 223 std::move(entry), | |
| 224 result->package_dir == catalog->system_package_dir_); | |
|
sky
2016/03/30 18:46:01
nit: spacing is off.
| |
| 225 } | |
| 206 } | 226 } |
| 207 | 227 |
| 208 void Catalog::AddEntryToCatalog(scoped_ptr<Entry> entry) { | 228 void Catalog::AddEntryToCatalog(scoped_ptr<Entry> entry, |
| 229 bool is_system_catalog) { | |
| 209 DCHECK(entry); | 230 DCHECK(entry); |
| 210 if (catalog_.end() != catalog_.find(entry->name())) | 231 EntryCache* catalog = is_system_catalog ? system_catalog_ : &user_catalog_; |
| 232 if (catalog->end() != catalog->find(entry->name())) | |
| 211 return; | 233 return; |
| 212 for (auto child : entry->applications()) | 234 for (auto child : entry->applications()) |
| 213 AddEntryToCatalog(make_scoped_ptr(child)); | 235 AddEntryToCatalog(make_scoped_ptr(child), is_system_catalog); |
| 214 catalog_[entry->name()] = std::move(entry); | 236 (*catalog)[entry->name()] = std::move(entry); |
| 215 SerializeCatalog(); | 237 SerializeCatalog(); |
| 216 } | 238 } |
| 217 | 239 |
| 218 } // namespace catalog | 240 } // namespace catalog |
| OLD | NEW |