Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: support base custom application installation location #729

Open
wants to merge 1 commit into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions api/schema/v1.json
Original file line number Diff line number Diff line change
Expand Up @@ -615,6 +615,10 @@
"compatible_version": {
"type": "string",
"description": "record linyaps package is compatible with linyaps component version"
},
"app_prefix": {
"type": "string",
"description": "application install location. The field is intended solely for the use of the base, indicating the installation path of applications built using that base."
}
}
},
Expand Down
3 changes: 3 additions & 0 deletions api/schema/v1.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -495,6 +495,9 @@ $defs:
compatible_version:
type: string
description: record linyaps package is compatible with linyaps component version
app_prefix:
type: string
description: application install location. The field is intended solely for the use of the base, indicating the installation path of applications built using that base.
PackageInfo:
title: PackageInfo
description: this is the each item output of ll-cli list --json
Expand Down
6 changes: 2 additions & 4 deletions apps/generators/05-initialize/src/main.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -58,10 +58,8 @@ int main()
});

mounts.push_back(
{ { "destination",
std::filesystem::path("/opt/apps") / annotations["org.deepin.linglong.appID"]
/ "files" },
{ "options", nlohmann::json::array({ "rbind", "rw" }) },
{ { "destination", annotations["org.deepin.linglong.appPrefix"] },
{ "options", nlohmann::json::array({ "rbind", "ro" }) },
{ "source",
std::filesystem::path(annotations["org.deepin.linglong.appDir"].get<std::string>())
/ "files" },
Expand Down
9 changes: 6 additions & 3 deletions apps/generators/25-host-env/src/main.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@

#include <filesystem>
#include <iostream>
#include <string>

extern char **environ;

Expand Down Expand Up @@ -79,9 +80,11 @@ int main()
}

auto annotations = content.at("annotations");
env.push_back("LINGLONG_APPID="
+ annotations.at("org.deepin.linglong.appID").get<std::string>());

auto appID = annotations.at("org.deepin.linglong.appID").get<std::string>();
// appPrefix
auto appPrefix = annotations.at("org.deepin.linglong.appPrefix").get<std::string>();
env.push_back("LINGLONG_APPID=" + appID);
env.push_back("LINGLONG_APP_PREFIX=" + appPrefix);
std::cout << content.dump() << std::endl;
return 0;
}
5 changes: 5 additions & 0 deletions apps/uab/loader/src/main.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -641,6 +641,11 @@ int main([[maybe_unused]] int argc, [[maybe_unused]] char **argv)
auto appDir = std::filesystem::path{ layerFilesDir }.parent_path();

annotations["org.deepin.linglong.appDir"] = appDir.string();
if (opts.appPrefix) {
annotations["org.deepin.linglong.appPrefix"] = *opts.appPrefix;
} else {
annotations["org.deepin.linglong.appPrefix"] = "/opt/apps/" + opts.appID + "/files";
}
config.annotations = std::move(annotations);

// replace commands
Expand Down
4 changes: 4 additions & 0 deletions libs/api/src/linglong/api/types/v1/Generators.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -567,6 +567,7 @@ j["version"] = x.version;
}

inline void from_json(const json & j, PackageInfoV2& x) {
x.appPrefix = get_stack_optional<std::string>(j, "app_prefix");
x.arch = j.at("arch").get<std::vector<std::string>>();
x.base = j.at("base").get<std::string>();
x.channel = j.at("channel").get<std::string>();
Expand All @@ -587,6 +588,9 @@ x.version = j.at("version").get<std::string>();

inline void to_json(json & j, const PackageInfoV2 & x) {
j = json::object();
if (x.appPrefix) {
j["app_prefix"] = x.appPrefix;
}
j["arch"] = x.arch;
j["base"] = x.base;
j["channel"] = x.channel;
Expand Down
5 changes: 5 additions & 0 deletions libs/api/src/linglong/api/types/v1/PackageInfoV2.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,11 @@ using nlohmann::json;
*/
struct PackageInfoV2 {
/**
* application install location. The field is intended solely for the use of the base,
* indicating the installation path of applications built using that base.
*/
std::optional<std::string> appPrefix;
/**
* arch of package info
*/
std::vector<std::string> arch;
Expand Down
22 changes: 20 additions & 2 deletions libs/linglong/src/linglong/builder/linglong_builder.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -271,7 +271,7 @@ utils::error::Result<package::Reference> pullDependency(const package::FuzzyRefe

auto tmpTask = service::PackageTask::createTemporaryTask();
auto partChanged = [&ref, module](const uint fetched, const uint requested) {
auto percentage = (uint)((((double)fetched) / requested) * 100);
auto percentage = (uint)((((double)fetched) / requested) * 100);
auto progress = QString("(%1/%2 %3%)").arg(fetched).arg(requested).arg(percentage);
printReplacedText(QString("%1%2%3%4 %5")
.arg(ref->id, -25) // NOLINT
Expand Down Expand Up @@ -491,6 +491,7 @@ utils::error::Result<void> Builder::build(const QStringList &args) noexcept
if (!baseRef) {
return LINGLONG_ERR("pull base binary", baseRef);
}
auto baseInfo = baseLayerDir->info();
printReplacedText(QString("%1%2%3%4")
.arg(baseRef->id, -25) // NOLINT
.arg(baseRef->version.toString(), -15) // NOLINT
Expand Down Expand Up @@ -639,6 +640,7 @@ set -e
.runtimeDir = {},
.baseDir = *baseLayerDir,
.appDir = {},
.appPrefix = baseInfo->appPrefix,
.patches = {},
.mounts = {},
.masks = {},
Expand All @@ -649,7 +651,12 @@ set -e
// 构建安装路径
QString installPrefix = "/runtime";
if (this->project.package.kind != "runtime") {
installPrefix = QString::fromStdString("/opt/apps/" + this->project.package.id + "/files");
if (baseInfo->appPrefix) {
installPrefix = QString::fromStdString(*baseInfo->appPrefix);
} else {
installPrefix =
QString::fromStdString("/opt/apps/" + this->project.package.id + "/files");
}
}
opts.mounts.push_back({
.destination = installPrefix.toStdString(),
Expand Down Expand Up @@ -1096,6 +1103,10 @@ utils::error::Result<void> Builder::exportUAB(const QString &destination, const
if (!baseDir) {
return LINGLONG_ERR(baseDir);
}
auto info = baseDir->info();
if (info->appPrefix) {
packager.setappPrefix(*info->appPrefix);
}
packager.appendLayer(*baseDir);

if (this->project.runtime) {
Expand Down Expand Up @@ -1278,6 +1289,13 @@ utils::error::Result<void> Builder::run(const QStringList &modules,
if (!baseRef) {
return LINGLONG_ERR(baseRef);
}
auto baseDir = this->repo.getLayerDir(*baseRef, "binary");
if (!baseDir) {
return LINGLONG_ERR(baseDir);
}
auto baseInfo = baseDir->info();
options.baseDir = QDir(baseDir->absolutePath());
options.appPrefix = baseInfo->appPrefix;

if (this->project.runtime) {
auto ref = pullDependency(QString::fromStdString(*this->project.runtime),
Expand Down
2 changes: 2 additions & 0 deletions libs/linglong/src/linglong/cli/cli.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -386,6 +386,7 @@ int Cli::run()
this->printer.printErr(LINGLONG_ERRV(baseLayerDir));
return -1;
}
auto baseInfo = baseLayerDir->info();

auto commands = options.commands;
if (commands.empty()) {
Expand Down Expand Up @@ -539,6 +540,7 @@ int Cli::run()
.runtimeDir = runtimeLayerDir,
.baseDir = *baseLayerDir,
.appDir = *appLayerDir,
.appPrefix = baseInfo->appPrefix,
.patches = {},
.mounts = std::move(applicationMounts),
.masks = {},
Expand Down
16 changes: 14 additions & 2 deletions libs/linglong/src/linglong/package/uab_packager.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@
#include <QStandardPaths>

#include <fstream>
#include <string>
#include <unordered_set>
#include <utility>

Expand Down Expand Up @@ -167,6 +168,12 @@ utils::error::Result<void> UABPackager::setIcon(const QFileInfo &newIcon) noexce
return LINGLONG_OK;
}

// set app install dir, default is /opt/apps/$appid/files
void UABPackager::setAppPrefix(const std::string &appPrefix) noexcept
{
m_appPrefix = appPrefix;
}

utils::error::Result<void> UABPackager::appendLayer(const LayerDir &layer) noexcept
{
LINGLONG_TRACE("append layer to uab")
Expand Down Expand Up @@ -546,8 +553,13 @@ utils::error::Result<void> UABPackager::prepareBundle(const QDir &bundleDir) noe
QTextStream stream{ &ldConf };
stream << "/runtime/lib" << Qt::endl;
stream << "/runtime/lib/" + arch->getTriplet() << Qt::endl;
stream << "/opt/apps/" + appID + "/files/lib" << Qt::endl;
stream << "/opt/apps/" + appID + "/files/lib/" + arch->getTriplet() << Qt::endl;
auto appPrefix = "/opt/apps/" + appID + "/files";
if (m_appPrefix) {
appPrefix = QString::fromStdString(*m_appPrefix);
}
stream << appPrefix + "/lib" << Qt::endl;
stream << appPrefix + "/lib/" + arch->getTriplet() << Qt::endl;

stream.flush();

// copy ll-box
Expand Down
3 changes: 3 additions & 0 deletions libs/linglong/src/linglong/package/uab_packager.h
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@
#include <QUuid>

#include <filesystem>
#include <string>
#include <unordered_set>

namespace linglong::package {
Expand Down Expand Up @@ -68,6 +69,7 @@ class UABPackager
UABPackager(UABPackager &&) = delete;

utils::error::Result<void> setIcon(const QFileInfo &icon) noexcept;
void setAppPrefix(const std::string &appPrefix) noexcept;
utils::error::Result<void> appendLayer(const LayerDir &layer) noexcept;
utils::error::Result<void> pack(const QString &uabFilename) noexcept;
utils::error::Result<void> exclude(const std::vector<std::string> &files) noexcept;
Expand All @@ -86,6 +88,7 @@ class UABPackager
std::unordered_set<std::string> excludeFiles;
std::unordered_set<std::string> includeFiles;
std::optional<QFileInfo> icon{ std::nullopt };
std::optional<std::string> m_appPrefix;
api::types::v1::UabMetaInfo meta;
QDir buildDir;
};
Expand Down
14 changes: 10 additions & 4 deletions libs/linglong/src/linglong/runtime/container.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -151,10 +151,16 @@ Container::run(const ocppi::runtime::config::types::Process &process) noexcept

ofs << "/runtime/lib" << std::endl;
ofs << "/runtime/lib/" + arch->getTriplet().toStdString() << std::endl;
ofs << "/opt/apps/" + this->appID.toStdString() + "/files/lib" << std::endl;
ofs << "/opt/apps/" + this->appID.toStdString() + "/files/lib/"
+ arch->getTriplet().toStdString()
<< std::endl;

auto appPrefix = "/opt/apps/" + this->appID.toStdString() + "/files";
if (cfg.annotations) {
auto annotations = *cfg.annotations;
if (annotations.find("org.deepin.linglong.appPrefix") != annotations.end()) {
appPrefix = annotations["org.deepin.linglong.appPrefix"];
}
}
ofs << appPrefix + "/lib" << std::endl;
ofs << appPrefix + "/lib/" + arch->getTriplet().toStdString() << std::endl;
}
this->cfg.mounts->push_back(ocppi::runtime::config::types::Mount{
.destination = "/etc/ld.so.conf.d/zz_deepin-linglong-app.conf",
Expand Down
6 changes: 6 additions & 0 deletions libs/linglong/src/linglong/runtime/container_builder.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -248,6 +248,12 @@ auto getOCIConfig(const ContainerOptions &opts) noexcept
if (opts.appDir) {
annotations["org.deepin.linglong.appDir"] = opts.appDir->absolutePath().toStdString();
}
if (opts.appPrefix) {
annotations["org.deepin.linglong.appPrefix"] = *opts.appPrefix;
} else {
annotations["org.deepin.linglong.appPrefix"] =
"/opt/apps/" + opts.appID.toStdString() + "/files";
}
config->annotations = std::move(annotations);

QDir configDotDDir = QFileInfo(containerConfigFilePath).dir().filePath("config.d");
Expand Down
7 changes: 4 additions & 3 deletions libs/linglong/src/linglong/runtime/container_builder.h
Original file line number Diff line number Diff line change
Expand Up @@ -21,9 +21,10 @@ struct ContainerOptions
QString appID;
QString containerID;

std::optional<QDir> runtimeDir; // mount to /runtime
QDir baseDir; // mount to /
std::optional<QDir> appDir; // mount to /opt/apps/${info.appid}/files
std::optional<QDir> runtimeDir; // mount to /runtime
QDir baseDir; // mount to /
std::optional<QDir> appDir; // mount to /opt/apps/${info.appid}/files
std::optional<std::string> appPrefix; // if appPrefix exists, mount appDir to appPrefix

std::vector<api::types::v1::OciConfigurationPatch> patches;
std::vector<ocppi::runtime::config::types::Mount> mounts; // extra mounts
Expand Down
Loading