context_->pkg_path.set(install_path.string());
// FIXME: correctly order app's data.
- // If there is 1 app in package, app's data are stored in <pkg_path>/<app_id>
- // If there are >1 apps in package, app's data are stored in <pkg_path>
+ // If there is 1 app in package, the app's data are stored in
+ // <pkg_path>/<app_id>/
+ // If there are >1 apps in the package, app's data are stored in <pkg_path>
// considering that multiple apps data are already separated in folders.
- if (context_->manifest_data.get()->uiapplication &&
- !context_->manifest_data.get()->uiapplication->next)
+ manifest_x *m = context_->manifest_data.get();
+ if ((m->uiapplication && !m->uiapplication->next && !m->serviceapplication) ||
+ (m->serviceapplication && !m->serviceapplication->next &&
+ !m->uiapplication)) {
install_path /= bf::path(context_->manifest_data.get()->mainapp_id);
+ }
bs::error_code error;
bf::create_directories(install_path.parent_path(), error);
namespace common_installer {
namespace generate_xml {
+static void _writeUIApplicationAttributes(
+ xmlTextWriterPtr writer, uiapplication_x *app) {
+ xmlTextWriterWriteAttribute(writer, BAD_CAST "taskmanage",
+ BAD_CAST "true");
+}
+
+static void _writeServiceApplicationAttributes(
+ xmlTextWriterPtr writer, serviceapplication_x *app) {
+ xmlTextWriterWriteAttribute(writer, BAD_CAST "auto-restart",
+ BAD_CAST(app->autorestart ? app->autorestart : "false"));
+ xmlTextWriterWriteAttribute(writer, BAD_CAST "on-boot",
+ BAD_CAST(app->onboot ? app->onboot : "false"));
+ xmlTextWriterWriteAttribute(writer, BAD_CAST "permission-type",
+ BAD_CAST(app->permission_type ? app->permission_type : ""));
+}
+
template <typename T>
Step::Status StepGenerateXml::GenerateApplicationCommonXml(T* app,
xmlTextWriterPtr writer) {
fs::path default_icon(
tzplatform_mkpath(TZ_SYS_RW_ICONS, "app-installers.png"));
+
+ // common appributes among uiapplication_x and serviceapplication_x
xmlTextWriterWriteAttribute(writer, BAD_CAST "appid", BAD_CAST app->appid);
// binary is a symbolic link named <appid> and is located in <pkgid>/<appid>
else
xmlTextWriterWriteAttribute(writer, BAD_CAST "type", BAD_CAST "capp");
+ // app-specific attributes
if (std::is_same<T, uiapplication_x>::value)
- xmlTextWriterWriteAttribute(writer, BAD_CAST "taskmanage",
- BAD_CAST "true");
+ _writeUIApplicationAttributes(
+ writer, reinterpret_cast<uiapplication_x *>(app));
+ if (std::is_same<T, serviceapplication_x>::value)
+ _writeServiceApplicationAttributes(
+ writer, reinterpret_cast<serviceapplication_x *>(app));
label_x* label = nullptr;
LISTHEAD(app->label, label);
bool StepParse::SetContextByManifestParser(XmlTree* tree) {
// Get required elements
XmlElement* manifest,
- * ui_application, * label;
+ * ui_application, * service_application, * label;
// manifest
if (nullptr == (manifest = tree->GetRootElement())) {
"' package='" << manifest->attr("package") <<
"' versionr='" << manifest->attr("version") << "'";
- // ui_application
- if (nullptr == (ui_application = Get1stChild(tree,
- manifest, "ui-application"))) {
- LOG(ERROR) << "No mandatory ui-application element in manifest xml";
+ // At least one of ui_application or service_application must be given
+ ui_application = Get1stChild(tree, manifest, "ui-application");
+ service_application = Get1stChild(tree, manifest, "service-application");
+ if (nullptr == ui_application && nullptr == service_application) {
+ LOG(ERROR) << "Neither <ui-application> nor <service-application>" <<
+ " element is found in manifest xml";
return false;
}
- if (nullptr == (label = Get1stChild(tree, ui_application, "label"))) {
- LOG(ERROR) << "No mandatory label element in manifest xml";
+ // label must be given
+ label = ui_application ? Get1stChild(tree, ui_application, "label") :
+ Get1stChild(tree, service_application, "label");
+ if (nullptr == label) {
+ LOG(ERROR) << "No mandatory <label> element in manifest xml";
return false;
}
// set context_
context_->config_data.get().application_name.set(label->content());
context_->config_data.get().required_version.set(
- manifest->attr("api_version"));
+ manifest->attr("api-version"));
context_->pkgid.set(manifest->attr("package"));
context_->manifest_data.set(static_cast<manifest_x*>(
calloc(1, sizeof(manifest_x))));
// Get required elements
XmlElement* ui_application = Get1stChild(tree, manifest, "ui-application");
- if (!ui_application) {
- LOG(ERROR) << "No <ui-application> element is found in manifest xml";
+ XmlElement* service_application = Get1stChild(tree, manifest,
+ "service-application");
+ if (!(ui_application || service_application)) { // mandatory check
+ LOG(ERROR) << "Neither <ui-application> nor <service-application>" <<
+ " element is found in manifest xml";
return false;
}
m->version = string_strdup(manifest->attr("version"));
m->installlocation = string_strdup(manifest->attr("install-location"));
- m->mainapp_id = string_strdup(ui_application->attr("appid"));
+ // Choose main app among ui-application or service-application
+ // NOTE: main app must have appid attribute
+ XmlElement* main_app = ui_application ? ui_application : service_application;
+ m->mainapp_id = string_strdup(main_app->attr("appid"));
// manifest' attribute from children's values
- XmlElement* label = Get1stChild(tree, ui_application, "label");
+ XmlElement* label = Get1stChild(tree, main_app, "label");
if (label) {
m->label = static_cast<label_x*>(calloc(1, sizeof(label_x)));
m->label->name = string_strdup(label->content());
return SetPkgInfoChildren(m, tree, manifest);
}
-// Read and feel struct hierarchy
+// Read and fill struct hierarchy
// The spec of tizen-manifest is referred from Tizen 2.2.1 header.
bool StepParse::SetPkgInfoChildren(manifest_x* m,
XmlTree* tree, XmlElement* manifest) {