| OLD | NEW |
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 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/extensions/api/extension_api.h" | 5 #include "chrome/common/extensions/api/extension_api.h" |
| 6 | 6 |
| 7 #include <algorithm> | 7 #include <algorithm> |
| 8 #include <string> | 8 #include <string> |
| 9 #include <vector> | 9 #include <vector> |
| 10 | 10 |
| (...skipping 107 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 118 | 118 |
| 119 struct Static { | 119 struct Static { |
| 120 Static() | 120 Static() |
| 121 : api(ExtensionAPI::CreateWithDefaultConfiguration()) { | 121 : api(ExtensionAPI::CreateWithDefaultConfiguration()) { |
| 122 } | 122 } |
| 123 scoped_ptr<ExtensionAPI> api; | 123 scoped_ptr<ExtensionAPI> api; |
| 124 }; | 124 }; |
| 125 | 125 |
| 126 base::LazyInstance<Static> g_lazy_instance = LAZY_INSTANCE_INITIALIZER; | 126 base::LazyInstance<Static> g_lazy_instance = LAZY_INSTANCE_INITIALIZER; |
| 127 | 127 |
| 128 // If it exists and does not already specify a namespace, then the value stored |
| 129 // with key |key| in |schema| will be updated to |schema_namespace| + "." + |
| 130 // |schema[key]|. |
| 131 void MaybePrefixFieldWithNamespace(const std::string& schema_namespace, |
| 132 DictionaryValue* schema, |
| 133 const std::string& key) { |
| 134 if (!schema->HasKey(key)) |
| 135 return; |
| 136 |
| 137 std::string old_id; |
| 138 CHECK(schema->GetString(key, &old_id)); |
| 139 if (old_id.find(".") == std::string::npos) |
| 140 schema->SetString(key, schema_namespace + "." + old_id); |
| 141 } |
| 142 |
| 143 // Modify all "$ref" keys anywhere in |schema| to be prefxied by |
| 144 // |schema_namespace| if they do not already specify a namespace. |
| 145 void PrefixRefsWithNamespace(const std::string& schema_namespace, |
| 146 Value* value) { |
| 147 if (value->IsType(Value::TYPE_LIST)) { |
| 148 ListValue* list; |
| 149 CHECK(value->GetAsList(&list)); |
| 150 for (ListValue::iterator i = list->begin(); i != list->end(); ++i) { |
| 151 PrefixRefsWithNamespace(schema_namespace, *i); |
| 152 } |
| 153 } else if (value->IsType(Value::TYPE_DICTIONARY)) { |
| 154 DictionaryValue* dict; |
| 155 CHECK(value->GetAsDictionary(&dict)); |
| 156 MaybePrefixFieldWithNamespace(schema_namespace, dict, "$ref"); |
| 157 for (DictionaryValue::key_iterator i = dict->begin_keys(); |
| 158 i != dict->end_keys(); ++i) { |
| 159 Value* next_value; |
| 160 CHECK(dict->GetWithoutPathExpansion(*i, &next_value)); |
| 161 PrefixRefsWithNamespace(schema_namespace, next_value); |
| 162 } |
| 163 } |
| 164 } |
| 165 |
| 166 // Modify all objects in the "types" section of the schema to be prefixed by |
| 167 // |schema_namespace| if they do not already specify a namespace. |
| 168 void PrefixTypesWithNamespace(const std::string& schema_namespace, |
| 169 DictionaryValue* schema) { |
| 170 if (!schema->HasKey("types")) |
| 171 return; |
| 172 |
| 173 // Add the namespace to all of the types defined in this schema |
| 174 ListValue *types; |
| 175 CHECK(schema->GetList("types", &types)); |
| 176 for (size_t i = 0; i < types->GetSize(); ++i) { |
| 177 DictionaryValue *type; |
| 178 CHECK(types->GetDictionary(i, &type)); |
| 179 MaybePrefixFieldWithNamespace(schema_namespace, type, "id"); |
| 180 MaybePrefixFieldWithNamespace(schema_namespace, type, "customBindings"); |
| 181 } |
| 182 } |
| 183 |
| 184 // Modify the schema so that all types are fully qualified. |
| 185 void PrefixWithNamespace(const std::string& schema_namespace, |
| 186 DictionaryValue* schema) { |
| 187 PrefixTypesWithNamespace(schema_namespace, schema); |
| 188 PrefixRefsWithNamespace(schema_namespace, schema); |
| 189 } |
| 190 |
| 128 } // namespace | 191 } // namespace |
| 129 | 192 |
| 130 // static | 193 // static |
| 131 ExtensionAPI* ExtensionAPI::GetSharedInstance() { | 194 ExtensionAPI* ExtensionAPI::GetSharedInstance() { |
| 132 return g_lazy_instance.Get().api.get(); | 195 return g_lazy_instance.Get().api.get(); |
| 133 } | 196 } |
| 134 | 197 |
| 135 // static | 198 // static |
| 136 ExtensionAPI* ExtensionAPI::CreateWithDefaultConfiguration() { | 199 ExtensionAPI* ExtensionAPI::CreateWithDefaultConfiguration() { |
| 137 ExtensionAPI* api = new ExtensionAPI(); | 200 ExtensionAPI* api = new ExtensionAPI(); |
| (...skipping 16 matching lines...) Expand all Loading... |
| 154 *feature_type = full_name.substr(0, colon_index); | 217 *feature_type = full_name.substr(0, colon_index); |
| 155 *feature_name = full_name.substr(colon_index + 1); | 218 *feature_name = full_name.substr(colon_index + 1); |
| 156 } | 219 } |
| 157 | 220 |
| 158 void ExtensionAPI::LoadSchema(const std::string& name, | 221 void ExtensionAPI::LoadSchema(const std::string& name, |
| 159 const base::StringPiece& schema) { | 222 const base::StringPiece& schema) { |
| 160 scoped_ptr<ListValue> schema_list(LoadSchemaList(name, schema)); | 223 scoped_ptr<ListValue> schema_list(LoadSchemaList(name, schema)); |
| 161 std::string schema_namespace; | 224 std::string schema_namespace; |
| 162 | 225 |
| 163 while (!schema_list->empty()) { | 226 while (!schema_list->empty()) { |
| 164 const DictionaryValue* schema = NULL; | 227 DictionaryValue* schema = NULL; |
| 165 { | 228 { |
| 166 Value* value = NULL; | 229 Value* value = NULL; |
| 167 schema_list->Remove(schema_list->GetSize() - 1, &value); | 230 schema_list->Remove(schema_list->GetSize() - 1, &value); |
| 168 CHECK(value->IsType(Value::TYPE_DICTIONARY)); | 231 CHECK(value->IsType(Value::TYPE_DICTIONARY)); |
| 169 schema = static_cast<const DictionaryValue*>(value); | 232 schema = static_cast<DictionaryValue*>(value); |
| 170 } | 233 } |
| 171 | 234 |
| 172 CHECK(schema->GetString("namespace", &schema_namespace)); | 235 CHECK(schema->GetString("namespace", &schema_namespace)); |
| 236 PrefixWithNamespace(schema_namespace, schema); |
| 173 schemas_[schema_namespace] = make_linked_ptr(schema); | 237 schemas_[schema_namespace] = make_linked_ptr(schema); |
| 174 CHECK_EQ(1u, unloaded_schemas_.erase(schema_namespace)); | 238 CHECK_EQ(1u, unloaded_schemas_.erase(schema_namespace)); |
| 175 | 239 |
| 176 // Populate |{completely,partially}_unprivileged_apis_|. | 240 // Populate |{completely,partially}_unprivileged_apis_|. |
| 177 // | 241 // |
| 178 // For "partially", only need to look at functions/events; even though | 242 // For "partially", only need to look at functions/events; even though |
| 179 // there are unprivileged properties (e.g. in extensions), access to those | 243 // there are unprivileged properties (e.g. in extensions), access to those |
| 180 // never reaches C++ land. | 244 // never reaches C++ land. |
| 181 if (schema->HasKey("unprivileged")) { | 245 if (schema->HasKey("unprivileged")) { |
| 182 completely_unprivileged_apis_.insert(schema_namespace); | 246 completely_unprivileged_apis_.insert(schema_namespace); |
| (...skipping 548 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 731 | 795 |
| 732 void ExtensionAPI::LoadAllSchemas() { | 796 void ExtensionAPI::LoadAllSchemas() { |
| 733 while (unloaded_schemas_.size()) { | 797 while (unloaded_schemas_.size()) { |
| 734 std::map<std::string, base::StringPiece>::iterator it = | 798 std::map<std::string, base::StringPiece>::iterator it = |
| 735 unloaded_schemas_.begin(); | 799 unloaded_schemas_.begin(); |
| 736 LoadSchema(it->first, it->second); | 800 LoadSchema(it->first, it->second); |
| 737 } | 801 } |
| 738 } | 802 } |
| 739 | 803 |
| 740 } // namespace extensions | 804 } // namespace extensions |
| OLD | NEW |