1 // Copyright (c) 2013 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.
5 #include "xwalk/application/common/manifest_handler.h"
9 #include "base/stl_util.h"
10 #include "xwalk/application/common/manifest_handlers/csp_handler.h"
12 #include "xwalk/application/common/manifest_handlers/navigation_handler.h"
13 #include "xwalk/application/common/manifest_handlers/tizen_application_handler.h"
14 #include "xwalk/application/common/manifest_handlers/tizen_metadata_handler.h"
15 #include "xwalk/application/common/manifest_handlers/tizen_setting_handler.h"
17 #include "xwalk/application/common/manifest_handlers/permissions_handler.h"
18 #include "xwalk/application/common/manifest_handlers/warp_handler.h"
19 #include "xwalk/application/common/manifest_handlers/widget_handler.h"
22 namespace application {
24 ManifestHandler::~ManifestHandler() {
27 bool ManifestHandler::Validate(scoped_refptr<const ApplicationData> application,
29 std::vector<InstallWarning>* warnings) const {
33 bool ManifestHandler::AlwaysParseForType(Manifest::Type type) const {
37 bool ManifestHandler::AlwaysValidateForType(Manifest::Type type) const {
41 std::vector<std::string> ManifestHandler::PrerequisiteKeys() const {
42 return std::vector<std::string>();
45 ManifestHandlerRegistry* ManifestHandlerRegistry::xpk_registry_ = NULL;
46 ManifestHandlerRegistry* ManifestHandlerRegistry::widget_registry_ = NULL;
48 ManifestHandlerRegistry::ManifestHandlerRegistry(
49 const std::vector<ManifestHandler*>& handlers) {
50 for (std::vector<ManifestHandler*>::const_iterator it = handlers.begin();
51 it != handlers.end(); ++it) {
55 ReorderHandlersGivenDependencies();
58 ManifestHandlerRegistry::~ManifestHandlerRegistry() {
61 ManifestHandlerRegistry*
62 ManifestHandlerRegistry::GetInstance(Manifest::PackageType package_type) {
63 if (package_type == Manifest::TYPE_WGT)
64 return GetInstanceForWGT();
65 return GetInstanceForXPK();
68 ManifestHandlerRegistry*
69 ManifestHandlerRegistry::GetInstanceForWGT() {
71 return widget_registry_;
73 std::vector<ManifestHandler*> handlers;
74 // We can put WGT specific manifest handlers here.
75 handlers.push_back(new WidgetHandler);
76 handlers.push_back(new WARPHandler);
78 handlers.push_back(new CSPHandler(Manifest::TYPE_WGT));
79 handlers.push_back(new NavigationHandler);
80 handlers.push_back(new TizenApplicationHandler);
81 handlers.push_back(new TizenSettingHandler);
82 handlers.push_back(new TizenMetaDataHandler);
84 widget_registry_ = new ManifestHandlerRegistry(handlers);
85 return widget_registry_;
88 ManifestHandlerRegistry*
89 ManifestHandlerRegistry::GetInstanceForXPK() {
93 std::vector<ManifestHandler*> handlers;
94 // FIXME: Add manifest handlers here like this:
95 // handlers.push_back(new xxxHandler);
96 handlers.push_back(new CSPHandler(Manifest::TYPE_XPK));
97 handlers.push_back(new PermissionsHandler);
98 xpk_registry_ = new ManifestHandlerRegistry(handlers);
102 void ManifestHandlerRegistry::Register(ManifestHandler* handler) {
103 const std::vector<std::string>& keys = handler->Keys();
104 for (size_t i = 0; i < keys.size(); ++i) {
105 handlers_[keys[i]] = handler;
109 bool ManifestHandlerRegistry::ParseAppManifest(
110 scoped_refptr<ApplicationData> application, base::string16* error) {
111 std::map<int, ManifestHandler*> handlers_by_order;
112 for (ManifestHandlerMap::iterator iter = handlers_.begin();
113 iter != handlers_.end(); ++iter) {
114 ManifestHandler* handler = iter->second;
115 if (application->GetManifest()->HasPath(iter->first) ||
116 handler->AlwaysParseForType(application->GetType())) {
117 handlers_by_order[order_map_[handler]] = handler;
120 for (std::map<int, ManifestHandler*>::iterator iter =
121 handlers_by_order.begin();
122 iter != handlers_by_order.end(); ++iter) {
123 if (!(iter->second)->Parse(application, error))
129 bool ManifestHandlerRegistry::ValidateAppManifest(
130 scoped_refptr<const ApplicationData> application,
132 std::vector<InstallWarning>* warnings) {
133 for (ManifestHandlerMap::iterator iter = handlers_.begin();
134 iter != handlers_.end(); ++iter) {
135 ManifestHandler* handler = iter->second;
136 if ((application->GetManifest()->HasPath(iter->first) ||
137 handler->AlwaysValidateForType(application->GetType())) &&
138 !handler->Validate(application, error, warnings))
145 void ManifestHandlerRegistry::SetInstanceForTesting(
146 ManifestHandlerRegistry* registry, Manifest::PackageType package_type) {
147 if (package_type == Manifest::TYPE_WGT) {
148 widget_registry_ = registry;
152 xpk_registry_ = registry;
155 void ManifestHandlerRegistry::ReorderHandlersGivenDependencies() {
156 std::set<ManifestHandler*> unsorted_handlers;
157 for (ManifestHandlerMap::const_iterator iter = handlers_.begin();
158 iter != handlers_.end(); ++iter) {
159 unsorted_handlers.insert(iter->second);
164 std::set<ManifestHandler*> next_unsorted_handlers;
165 for (std::set<ManifestHandler*>::const_iterator iter =
166 unsorted_handlers.begin();
167 iter != unsorted_handlers.end(); ++iter) {
168 ManifestHandler* handler = *iter;
169 const std::vector<std::string>& prerequisites =
170 handler->PrerequisiteKeys();
171 int unsatisfied = prerequisites.size();
172 for (size_t i = 0; i < prerequisites.size(); ++i) {
173 ManifestHandlerMap::const_iterator prereq_iter =
174 handlers_.find(prerequisites[i]);
175 CHECK(prereq_iter != handlers_.end())
176 << "Application manifest handler depends on unrecognized key "
178 // Prerequisite is in our map.
179 if (ContainsKey(order_map_, prereq_iter->second))
182 if (unsatisfied == 0) {
183 order_map_[handler] = order;
186 // Put in the list for next time.
187 next_unsorted_handlers.insert(handler);
190 if (next_unsorted_handlers.size() == unsorted_handlers.size())
192 unsorted_handlers.swap(next_unsorted_handlers);
195 // If there are any leftover unsorted handlers, they must have had
196 // circular dependencies.
197 CHECK(unsorted_handlers.empty()) << "Application manifest handlers have "
198 << "circular dependencies!";
201 } // namespace application