feat: change dbus interface api
1. remove method: Application, Launch. (ApplicationManager1) 2. add property: IconName, DisplayName. (Application1) 3. refact the way of construct ApplicationService. 4. if Desktop Entry Key `Hidden` is true, this application wouldn't export to DBus. Signed-off-by: ComixHe <heyuming@deepin.org>
This commit is contained in:
parent
a3dd315e33
commit
bb83716d27
@ -17,6 +17,10 @@
|
|||||||
|
|
||||||
<property name="AutoStart" type="b" access="readwrite"/>
|
<property name="AutoStart" type="b" access="readwrite"/>
|
||||||
|
|
||||||
|
<property name="IconName" type="s" access="read"/>
|
||||||
|
|
||||||
|
<property name="DisplayName" type="s" access="read"/>
|
||||||
|
|
||||||
<property name="Instances" type="ao" access="read">
|
<property name="Instances" type="ao" access="read">
|
||||||
<annotation
|
<annotation
|
||||||
name="org.freedesktop.DBus.Description"
|
name="org.freedesktop.DBus.Description"
|
||||||
|
@ -12,11 +12,6 @@
|
|||||||
/>
|
/>
|
||||||
</method>
|
</method>
|
||||||
|
|
||||||
<method name="Application">
|
|
||||||
<arg type="s" name="id" direction="in" />
|
|
||||||
<arg type="o" name="application" direction="out" />
|
|
||||||
</method>
|
|
||||||
|
|
||||||
<method name="Identify">
|
<method name="Identify">
|
||||||
<arg type="h" name="pidfd" direction="in" />
|
<arg type="h" name="pidfd" direction="in" />
|
||||||
|
|
||||||
@ -36,22 +31,5 @@
|
|||||||
/>
|
/>
|
||||||
</method>
|
</method>
|
||||||
|
|
||||||
<method name="Launch">
|
|
||||||
<arg type="s" name="id" direction="in" />
|
|
||||||
<arg type="s" name="action" direction="in" />
|
|
||||||
<arg type="as" name="fields" direction="in" />
|
|
||||||
<arg type="a{sv}" name="options" direction="in" />
|
|
||||||
<arg type="o" name="job" direction="out" />
|
|
||||||
<annotation name="org.qtproject.QtDBus.QtTypeName.In3" value="QVariantMap"/>
|
|
||||||
<annotation
|
|
||||||
name="org.freedesktop.DBus.Description"
|
|
||||||
value="Given a desktop file id,
|
|
||||||
this method will launch a desktop application.
|
|
||||||
|
|
||||||
Check description of the `Launch` method in
|
|
||||||
`org.desktopspec.ApplicationManager1.Application`
|
|
||||||
interface for futher infomation."
|
|
||||||
/>
|
|
||||||
</method>
|
|
||||||
</interface>
|
</interface>
|
||||||
</node>
|
</node>
|
||||||
|
@ -16,10 +16,7 @@ constexpr auto DDEApplicationManager1ServiceName =
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
constexpr auto DDEApplicationManager1ObjectPath = u8"/org/deepin/dde/ApplicationManager1";
|
constexpr auto DDEApplicationManager1ObjectPath = u8"/org/deepin/dde/ApplicationManager1";
|
||||||
constexpr auto DDEApplicationManager1ApplicationObjectPath = u8"/org/deepin/dde/ApplicationManager1/Application/";
|
|
||||||
constexpr auto DDEApplicationManager1InstanceObjectPath = u8"/org/deepin/dde/ApplicationManager1/Instance/";
|
|
||||||
constexpr auto DDEApplicationManager1JobManagerObjectPath = u8"/org/deepin/dde/ApplicationManager1/JobManager1";
|
constexpr auto DDEApplicationManager1JobManagerObjectPath = u8"/org/deepin/dde/ApplicationManager1/JobManager1";
|
||||||
constexpr auto DDEApplicationManager1JobObjectPath = u8"/org/deepin/dde/ApplicationManager1/JobManager1/Job/";
|
|
||||||
constexpr auto DesktopFileEntryKey = u8"Desktop Entry";
|
constexpr auto DesktopFileEntryKey = u8"Desktop Entry";
|
||||||
constexpr auto DesktopFileActionKey = u8"Desktop Action ";
|
constexpr auto DesktopFileActionKey = u8"Desktop Action ";
|
||||||
|
|
||||||
|
@ -110,18 +110,6 @@ void ApplicationManager1Service::removeAllApplication()
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
QDBusObjectPath ApplicationManager1Service::Application(const QString &id) const
|
|
||||||
{
|
|
||||||
auto ret = std::find_if(m_applicationList.cbegin(), m_applicationList.cend(), [&id](const auto &app) {
|
|
||||||
return static_cast<bool>(app->id() == id);
|
|
||||||
});
|
|
||||||
|
|
||||||
if (ret != m_applicationList.cend()) {
|
|
||||||
return ret.key();
|
|
||||||
}
|
|
||||||
return {};
|
|
||||||
}
|
|
||||||
|
|
||||||
QString ApplicationManager1Service::Identify(const QDBusUnixFileDescriptor &pidfd,
|
QString ApplicationManager1Service::Identify(const QDBusUnixFileDescriptor &pidfd,
|
||||||
QDBusObjectPath &application,
|
QDBusObjectPath &application,
|
||||||
QDBusObjectPath &application_instance)
|
QDBusObjectPath &application_instance)
|
||||||
@ -174,20 +162,6 @@ QString ApplicationManager1Service::Identify(const QDBusUnixFileDescriptor &pidf
|
|||||||
return ret.ApplicationId;
|
return ret.ApplicationId;
|
||||||
}
|
}
|
||||||
|
|
||||||
QDBusObjectPath ApplicationManager1Service::Launch(const QString &id,
|
|
||||||
const QString &actions,
|
|
||||||
const QStringList &fields,
|
|
||||||
const QVariantMap &options)
|
|
||||||
{
|
|
||||||
auto app = Application(id);
|
|
||||||
if (app.path().isEmpty()) {
|
|
||||||
qWarning() << "No such application.";
|
|
||||||
return {};
|
|
||||||
}
|
|
||||||
const auto &value = m_applicationList.value(app);
|
|
||||||
return value->Launch(actions, fields, options);
|
|
||||||
}
|
|
||||||
|
|
||||||
void ApplicationManager1Service::updateApplication(const QSharedPointer<ApplicationService> &destApp,
|
void ApplicationManager1Service::updateApplication(const QSharedPointer<ApplicationService> &destApp,
|
||||||
const DesktopFile &desktopFile) noexcept
|
const DesktopFile &desktopFile) noexcept
|
||||||
{
|
{
|
||||||
|
@ -30,15 +30,18 @@ public:
|
|||||||
|
|
||||||
Q_PROPERTY(QList<QDBusObjectPath> List READ list)
|
Q_PROPERTY(QList<QDBusObjectPath> List READ list)
|
||||||
[[nodiscard]] QList<QDBusObjectPath> list() const;
|
[[nodiscard]] QList<QDBusObjectPath> list() const;
|
||||||
|
|
||||||
template <typename T>
|
template <typename T>
|
||||||
bool addApplication(T &&desktopFileSource)
|
bool addApplication(T &&desktopFileSource)
|
||||||
{
|
{
|
||||||
QSharedPointer<ApplicationService> application{new ApplicationService{std::forward<T>(desktopFileSource), this}};
|
QSharedPointer<ApplicationService> application = makeApplication(std::forward<T>(desktopFileSource), this);
|
||||||
if (!application) {
|
if (!application) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
auto *ptr = application.data();
|
auto *ptr = application.data();
|
||||||
new ApplicationAdaptor{ptr};
|
new ApplicationAdaptor{ptr};
|
||||||
|
|
||||||
if (!registerObjectToDBus(ptr, application->m_applicationPath.path(), getDBusInterface<ApplicationAdaptor>())) {
|
if (!registerObjectToDBus(ptr, application->m_applicationPath.path(), getDBusInterface<ApplicationAdaptor>())) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
@ -53,9 +56,7 @@ public:
|
|||||||
JobManager1Service &jobManager() noexcept { return *m_jobManager; }
|
JobManager1Service &jobManager() noexcept { return *m_jobManager; }
|
||||||
|
|
||||||
public Q_SLOTS:
|
public Q_SLOTS:
|
||||||
[[nodiscard]] QDBusObjectPath Application(const QString &id) const;
|
|
||||||
QString Identify(const QDBusUnixFileDescriptor &pidfd, QDBusObjectPath &application, QDBusObjectPath &application_instance);
|
QString Identify(const QDBusUnixFileDescriptor &pidfd, QDBusObjectPath &application, QDBusObjectPath &application_instance);
|
||||||
QDBusObjectPath Launch(const QString &id, const QString &action, const QStringList &fields, const QVariantMap &options);
|
|
||||||
void UpdateApplicationInfo(const QStringList &appIdList);
|
void UpdateApplicationInfo(const QStringList &appIdList);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
@ -19,7 +19,9 @@ ApplicationService::~ApplicationService()
|
|||||||
m_desktopSource.destruct(m_isPersistence);
|
m_desktopSource.destruct(m_isPersistence);
|
||||||
for (auto &instance : m_Instances.values()) {
|
for (auto &instance : m_Instances.values()) {
|
||||||
instance->m_Application = QDBusObjectPath{"/"};
|
instance->m_Application = QDBusObjectPath{"/"};
|
||||||
instance->setParent(qApp); // detach all instances to qApp
|
auto *ptr = instance.get();
|
||||||
|
instance.reset(nullptr);
|
||||||
|
ptr->setParent(qApp); // detach all instances to qApp
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -132,8 +134,10 @@ QDBusObjectPath ApplicationService::Launch(QString action, QStringList fields, Q
|
|||||||
m_applicationPath.path(),
|
m_applicationPath.path(),
|
||||||
[this, binary = std::move(bin), commands = std::move(cmds)](QVariant variantValue) mutable -> QVariant {
|
[this, binary = std::move(bin), commands = std::move(cmds)](QVariant variantValue) mutable -> QVariant {
|
||||||
auto resourceFile = variantValue.toString();
|
auto resourceFile = variantValue.toString();
|
||||||
|
auto instanceRandomUUID = QUuid::createUuid().toString(QUuid::Id128);
|
||||||
|
auto objectPath = m_applicationPath.path() + "/" + instanceRandomUUID;
|
||||||
|
|
||||||
if (resourceFile.isEmpty()) {
|
if (resourceFile.isEmpty()) {
|
||||||
auto instanceRandomUUID = QUuid::createUuid().toString(QUuid::Id128);
|
|
||||||
commands.push_front(QString{R"(--unitName=app-DDE-%1@%2.service)"}.arg(
|
commands.push_front(QString{R"(--unitName=app-DDE-%1@%2.service)"}.arg(
|
||||||
escapeApplicationId(this->id()), instanceRandomUUID)); // launcher should use this instanceId
|
escapeApplicationId(this->id()), instanceRandomUUID)); // launcher should use this instanceId
|
||||||
QProcess process;
|
QProcess process;
|
||||||
@ -143,7 +147,7 @@ QDBusObjectPath ApplicationService::Launch(QString action, QStringList fields, Q
|
|||||||
qWarning() << "Launch Application Failed. exitCode:" << code;
|
qWarning() << "Launch Application Failed. exitCode:" << code;
|
||||||
return QString{""};
|
return QString{""};
|
||||||
}
|
}
|
||||||
return DDEApplicationManager1InstanceObjectPath + instanceRandomUUID;
|
return objectPath;
|
||||||
}
|
}
|
||||||
|
|
||||||
int location{0};
|
int location{0};
|
||||||
@ -163,7 +167,6 @@ QDBusObjectPath ApplicationService::Launch(QString action, QStringList fields, Q
|
|||||||
// resourceFile must be available in the following contexts
|
// resourceFile must be available in the following contexts
|
||||||
auto tmp = commands;
|
auto tmp = commands;
|
||||||
tmp.insert(location, resourceFile);
|
tmp.insert(location, resourceFile);
|
||||||
auto instanceRandomUUID = QUuid::createUuid().toString(QUuid::Id128);
|
|
||||||
tmp.push_front(QString{R"(--unitName=DDE-%1@%2.service)"}.arg(this->id(), instanceRandomUUID));
|
tmp.push_front(QString{R"(--unitName=DDE-%1@%2.service)"}.arg(this->id(), instanceRandomUUID));
|
||||||
QProcess process;
|
QProcess process;
|
||||||
process.start(getApplicationLauncherBinary(), tmp);
|
process.start(getApplicationLauncherBinary(), tmp);
|
||||||
@ -173,7 +176,7 @@ QDBusObjectPath ApplicationService::Launch(QString action, QStringList fields, Q
|
|||||||
qWarning() << "Launch Application Failed:" << binary << tmp;
|
qWarning() << "Launch Application Failed:" << binary << tmp;
|
||||||
return QString{""};
|
return QString{""};
|
||||||
}
|
}
|
||||||
return DDEApplicationManager1InstanceObjectPath + instanceRandomUUID;
|
return objectPath;
|
||||||
},
|
},
|
||||||
std::move(res));
|
std::move(res));
|
||||||
}
|
}
|
||||||
@ -239,11 +242,55 @@ QList<QDBusObjectPath> ApplicationService::instances() const noexcept
|
|||||||
return m_Instances.keys();
|
return m_Instances.keys();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
QString ApplicationService::iconName() const noexcept
|
||||||
|
{
|
||||||
|
if (m_entry.isNull()) {
|
||||||
|
qWarning() << "desktop entry is empty, isPersistence:" << m_isPersistence;
|
||||||
|
return {};
|
||||||
|
}
|
||||||
|
|
||||||
|
const auto &actions = m_entry->value(DesktopFileEntryKey, "Icon");
|
||||||
|
if (!actions) {
|
||||||
|
return {};
|
||||||
|
}
|
||||||
|
|
||||||
|
bool ok{false};
|
||||||
|
const auto &icon = actions->toIconString(ok);
|
||||||
|
if (!ok) {
|
||||||
|
qWarning() << "Icon convert to String failed.";
|
||||||
|
return {};
|
||||||
|
}
|
||||||
|
|
||||||
|
return icon;
|
||||||
|
}
|
||||||
|
|
||||||
|
QString ApplicationService::displayName() const noexcept
|
||||||
|
{
|
||||||
|
if (m_entry.isNull()) {
|
||||||
|
qWarning() << "desktop entry is empty, isPersistence:" << m_isPersistence;
|
||||||
|
return {};
|
||||||
|
}
|
||||||
|
|
||||||
|
const auto &actions = m_entry->value(DesktopFileEntryKey, "Name");
|
||||||
|
if (!actions) {
|
||||||
|
return {};
|
||||||
|
}
|
||||||
|
|
||||||
|
bool ok{false};
|
||||||
|
const auto &name = actions->toString(ok);
|
||||||
|
if (!ok) {
|
||||||
|
qWarning() << "Icon convert to String failed.";
|
||||||
|
return {};
|
||||||
|
}
|
||||||
|
|
||||||
|
return name;
|
||||||
|
}
|
||||||
|
|
||||||
bool ApplicationService::addOneInstance(const QString &instanceId, const QString &application, const QString &systemdUnitPath)
|
bool ApplicationService::addOneInstance(const QString &instanceId, const QString &application, const QString &systemdUnitPath)
|
||||||
{
|
{
|
||||||
auto service = new InstanceService{instanceId, application, systemdUnitPath};
|
auto service = new InstanceService{instanceId, application, systemdUnitPath};
|
||||||
auto adaptor = new InstanceAdaptor(service);
|
auto adaptor = new InstanceAdaptor(service);
|
||||||
QString objectPath{DDEApplicationManager1InstanceObjectPath + instanceId};
|
QString objectPath{m_applicationPath.path() + "/" + instanceId};
|
||||||
|
|
||||||
if (registerObjectToDBus(service, objectPath, getDBusInterface<InstanceAdaptor>())) {
|
if (registerObjectToDBus(service, objectPath, getDBusInterface<InstanceAdaptor>())) {
|
||||||
m_Instances.insert(QDBusObjectPath{objectPath}, QSharedPointer<InstanceService>{service});
|
m_Instances.insert(QDBusObjectPath{objectPath}, QSharedPointer<InstanceService>{service});
|
||||||
|
@ -14,6 +14,7 @@
|
|||||||
#include <QUuid>
|
#include <QUuid>
|
||||||
#include <QTextStream>
|
#include <QTextStream>
|
||||||
#include <QFile>
|
#include <QFile>
|
||||||
|
#include <memory>
|
||||||
#include "dbus/instanceservice.h"
|
#include "dbus/instanceservice.h"
|
||||||
#include "global.h"
|
#include "global.h"
|
||||||
#include "desktopentry.h"
|
#include "desktopentry.h"
|
||||||
@ -47,6 +48,12 @@ public:
|
|||||||
Q_PROPERTY(QList<QDBusObjectPath> Instances READ instances)
|
Q_PROPERTY(QList<QDBusObjectPath> Instances READ instances)
|
||||||
[[nodiscard]] QList<QDBusObjectPath> instances() const noexcept;
|
[[nodiscard]] QList<QDBusObjectPath> instances() const noexcept;
|
||||||
|
|
||||||
|
Q_PROPERTY(QString IconName READ iconName CONSTANT)
|
||||||
|
[[nodiscard]] QString iconName() const noexcept;
|
||||||
|
|
||||||
|
Q_PROPERTY(QString DisplayName READ displayName CONSTANT)
|
||||||
|
[[nodiscard]] QString displayName() const noexcept;
|
||||||
|
|
||||||
[[nodiscard]] QDBusObjectPath findInstance(const QString &instanceId) const;
|
[[nodiscard]] QDBusObjectPath findInstance(const QString &instanceId) const;
|
||||||
|
|
||||||
[[nodiscard]] const QString &getLauncher() const noexcept { return m_launcher; }
|
[[nodiscard]] const QString &getLauncher() const noexcept { return m_launcher; }
|
||||||
@ -64,45 +71,13 @@ public Q_SLOTS:
|
|||||||
private:
|
private:
|
||||||
friend class ApplicationManager1Service;
|
friend class ApplicationManager1Service;
|
||||||
template <typename T>
|
template <typename T>
|
||||||
explicit ApplicationService(T &&source, ApplicationManager1Service *parent = nullptr)
|
friend QSharedPointer<ApplicationService> makeApplication(T &&source, ApplicationManager1Service *parent);
|
||||||
: m_parent(parent)
|
|
||||||
|
template <typename T>
|
||||||
|
explicit ApplicationService(T &&source)
|
||||||
|
: m_isPersistence(static_cast<bool>(std::is_same_v<T, DesktopFile>))
|
||||||
, m_desktopSource(std::forward<T>(source))
|
, m_desktopSource(std::forward<T>(source))
|
||||||
{
|
{
|
||||||
static_assert(std::is_same_v<T, DesktopFile> or std::is_same_v<T, QString>, "param type must be QString or DesktopFile.");
|
|
||||||
QString objectPath{DDEApplicationManager1ApplicationObjectPath};
|
|
||||||
QTextStream sourceStream;
|
|
||||||
QFile sourceFile;
|
|
||||||
auto dbusAppid = m_desktopSource.m_file.desktopId();
|
|
||||||
|
|
||||||
if constexpr (std::is_same_v<T, DesktopFile>) {
|
|
||||||
m_applicationPath =
|
|
||||||
#ifdef DEBUG_MODE
|
|
||||||
QDBusObjectPath{objectPath + escapeToObjectPath(dbusAppid)};
|
|
||||||
#else
|
|
||||||
QDBusObjectPath{objectPath + QUuid::createUuid().toString(QUuid::Id128)};
|
|
||||||
#endif
|
|
||||||
m_isPersistence = true;
|
|
||||||
sourceFile.setFileName(m_desktopSource.m_file.filePath());
|
|
||||||
if (!sourceFile.open(QFile::ExistingOnly | QFile::ReadOnly | QFile::Text)) {
|
|
||||||
#ifndef DEBUG_MODE
|
|
||||||
qCritical() << "desktop file can't open:" << m_desktopSource.m_file.filePath() << sourceFile.errorString();
|
|
||||||
#endif
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
sourceStream.setDevice(&sourceFile);
|
|
||||||
} else if (std::is_same_v<T, QString>) {
|
|
||||||
m_applicationPath = QDBusObjectPath{objectPath + QUuid::createUuid().toString(QUuid::Id128)};
|
|
||||||
m_isPersistence = false;
|
|
||||||
sourceStream.setString(&m_desktopSource.m_temp, QTextStream::ReadOnly | QTextStream::Text);
|
|
||||||
}
|
|
||||||
m_entry.reset(new DesktopEntry());
|
|
||||||
if (auto error = m_entry->parse(sourceStream); error != DesktopErrorCode::NoError) {
|
|
||||||
if (error != DesktopErrorCode::EntryKeyInvalid) {
|
|
||||||
m_entry.reset(nullptr);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
// TODO: icon lookup
|
|
||||||
}
|
}
|
||||||
|
|
||||||
bool m_AutoStart{false};
|
bool m_AutoStart{false};
|
||||||
@ -143,4 +118,58 @@ private:
|
|||||||
[[nodiscard]] LaunchTask unescapeExec(const QString &str, const QStringList &fields);
|
[[nodiscard]] LaunchTask unescapeExec(const QString &str, const QStringList &fields);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
template <typename T>
|
||||||
|
QSharedPointer<ApplicationService> makeApplication(T &&source, ApplicationManager1Service *parent)
|
||||||
|
{
|
||||||
|
static_assert(std::is_same_v<T, DesktopFile> or std::is_same_v<T, QString>, "param type must be QString or DesktopFile.");
|
||||||
|
QString objectPath;
|
||||||
|
QTextStream sourceStream;
|
||||||
|
QFile sourceFile;
|
||||||
|
QSharedPointer<ApplicationService> app{nullptr};
|
||||||
|
|
||||||
|
if constexpr (std::is_same_v<T, DesktopFile>) {
|
||||||
|
DesktopFile in{std::forward<T>(source)};
|
||||||
|
objectPath = QString{DDEApplicationManager1ObjectPath} + "/" + escapeToObjectPath(in.desktopId());
|
||||||
|
sourceFile.setFileName(in.filePath());
|
||||||
|
|
||||||
|
if (!sourceFile.open(QFile::ExistingOnly | QFile::ReadOnly | QFile::Text)) {
|
||||||
|
qCritical() << "desktop file can't open:" << in.filePath() << sourceFile.errorString();
|
||||||
|
return nullptr;
|
||||||
|
}
|
||||||
|
|
||||||
|
app.reset(new ApplicationService{std::move(in)});
|
||||||
|
sourceStream.setDevice(&sourceFile);
|
||||||
|
} else if (std::is_same_v<T, QString>) {
|
||||||
|
QString in{std::forward<T>(source)};
|
||||||
|
objectPath = QString{DDEApplicationManager1ObjectPath} + "/" + QUuid::createUuid().toString(QUuid::Id128);
|
||||||
|
|
||||||
|
app.reset(new ApplicationService{std::move(in)});
|
||||||
|
sourceStream.setString(&in, QTextStream::ReadOnly | QTextStream::Text);
|
||||||
|
}
|
||||||
|
|
||||||
|
std::unique_ptr<DesktopEntry> entry{std::make_unique<DesktopEntry>()};
|
||||||
|
auto error = entry->parse(sourceStream);
|
||||||
|
|
||||||
|
if (error != DesktopErrorCode::NoError) {
|
||||||
|
if (error != DesktopErrorCode::EntryKeyInvalid) {
|
||||||
|
return nullptr;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (auto val = entry->value(DesktopFileEntryKey, "Hidden"); val.has_value()) {
|
||||||
|
bool ok{false};
|
||||||
|
if (auto hidden = val.value().toBoolean(ok); ok and hidden) {
|
||||||
|
return nullptr;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
app->m_parent = parent;
|
||||||
|
app->m_entry.reset(entry.release());
|
||||||
|
app->m_applicationPath = QDBusObjectPath{std::move(objectPath)};
|
||||||
|
|
||||||
|
// TODO: icon lookup
|
||||||
|
|
||||||
|
return app;
|
||||||
|
}
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
@ -50,7 +50,8 @@ public:
|
|||||||
{
|
{
|
||||||
static_assert(std::is_invocable_v<F, QVariant>, "param type must be QVariant.");
|
static_assert(std::is_invocable_v<F, QVariant>, "param type must be QVariant.");
|
||||||
|
|
||||||
QString objectPath{DDEApplicationManager1JobObjectPath + QUuid::createUuid().toString(QUuid::Id128)};
|
QString objectPath =
|
||||||
|
QString{"%1/%2"}.arg(DDEApplicationManager1JobManagerObjectPath).arg(QUuid::createUuid().toString(QUuid::Id128));
|
||||||
QFuture<QVariantList> future = QtConcurrent::mappedReduced(std::move(args),
|
QFuture<QVariantList> future = QtConcurrent::mappedReduced(std::move(args),
|
||||||
func,
|
func,
|
||||||
qOverload<QVariantList::parameter_type>(&QVariantList::append),
|
qOverload<QVariantList::parameter_type>(&QVariantList::append),
|
||||||
|
@ -11,7 +11,7 @@ JobService::JobService(const QFuture<QVariantList> &job)
|
|||||||
|
|
||||||
JobService::~JobService() = default;
|
JobService::~JobService() = default;
|
||||||
|
|
||||||
QString JobService::status() const
|
QString JobService::status() const // FIXME: job status aren't mutually exclusive
|
||||||
{
|
{
|
||||||
if (m_job.isFinished()) {
|
if (m_job.isFinished()) {
|
||||||
return "finished";
|
return "finished";
|
||||||
|
@ -56,7 +56,9 @@ DesktopErrorCode DesktopEntry::parseEntry(const QString &str, decltype(m_entryMa
|
|||||||
re.optimize();
|
re.optimize();
|
||||||
auto matcher = re.match(keyStr);
|
auto matcher = re.match(keyStr);
|
||||||
if (!matcher.hasMatch()) {
|
if (!matcher.hasMatch()) {
|
||||||
|
#ifdef DEBUG_MODE
|
||||||
qWarning() << "invalid key: " << keyStr;
|
qWarning() << "invalid key: " << keyStr;
|
||||||
|
#endif
|
||||||
return DesktopErrorCode::EntryKeyInvalid;
|
return DesktopErrorCode::EntryKeyInvalid;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -205,7 +207,9 @@ DesktopErrorCode DesktopEntry::parse(QTextStream &stream) noexcept
|
|||||||
|
|
||||||
if (auto error = parseEntry(line, currentGroup); error != DesktopErrorCode::NoError) {
|
if (auto error = parseEntry(line, currentGroup); error != DesktopErrorCode::NoError) {
|
||||||
err = error;
|
err = error;
|
||||||
|
#ifdef DEBUG_MODE
|
||||||
qWarning() << "an error occurred,this line will be skipped:" << line;
|
qWarning() << "an error occurred,this line will be skipped:" << line;
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return err;
|
return err;
|
||||||
@ -223,13 +227,17 @@ std::optional<DesktopEntry::Value> DesktopEntry::value(const QString &groupKey,
|
|||||||
{
|
{
|
||||||
const auto &destGroup = group(groupKey);
|
const auto &destGroup = group(groupKey);
|
||||||
if (!destGroup) {
|
if (!destGroup) {
|
||||||
|
#ifdef DEBUG_MODE
|
||||||
qWarning() << "group " << groupKey << " can't be found.";
|
qWarning() << "group " << groupKey << " can't be found.";
|
||||||
|
#endif
|
||||||
return std::nullopt;
|
return std::nullopt;
|
||||||
}
|
}
|
||||||
|
|
||||||
auto it = destGroup->find(valueKey);
|
auto it = destGroup->find(valueKey);
|
||||||
if (it == destGroup->cend()) {
|
if (it == destGroup->cend()) {
|
||||||
|
#ifdef DEBUG_MODE
|
||||||
qWarning() << "value " << valueKey << " can't be found.";
|
qWarning() << "value " << valueKey << " can't be found.";
|
||||||
|
#endif
|
||||||
return std::nullopt;
|
return std::nullopt;
|
||||||
}
|
}
|
||||||
return *it;
|
return *it;
|
||||||
|
@ -44,23 +44,11 @@ public:
|
|||||||
static void TearDownTestCase() { m_am->deleteLater(); }
|
static void TearDownTestCase() { m_am->deleteLater(); }
|
||||||
|
|
||||||
static inline ApplicationManager1Service *m_am{nullptr};
|
static inline ApplicationManager1Service *m_am{nullptr};
|
||||||
const static inline QDBusObjectPath ApplicationPath{DDEApplicationManager1ApplicationObjectPath +
|
const static inline QDBusObjectPath ApplicationPath{QString{DDEApplicationManager1ObjectPath} + "/" +
|
||||||
QUuid::createUuid().toString(QUuid::Id128)};
|
QUuid::createUuid().toString(QUuid::Id128)};
|
||||||
const static inline QDBusObjectPath InstancePath{DDEApplicationManager1InstanceObjectPath +
|
const static inline QDBusObjectPath InstancePath{ApplicationPath.path() + "/" + QUuid::createUuid().toString(QUuid::Id128)};
|
||||||
QUuid::createUuid().toString(QUuid::Id128)};
|
|
||||||
};
|
};
|
||||||
|
|
||||||
TEST_F(TestApplicationManager, list)
|
|
||||||
{
|
|
||||||
auto lists = m_am->list();
|
|
||||||
EXPECT_EQ(lists.first(), ApplicationPath);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_F(TestApplicationManager, application)
|
|
||||||
{
|
|
||||||
EXPECT_EQ(m_am->Application("test-Application"), ApplicationPath);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_F(TestApplicationManager, identifyService)
|
TEST_F(TestApplicationManager, identifyService)
|
||||||
{
|
{
|
||||||
using namespace std::chrono_literals;
|
using namespace std::chrono_literals;
|
||||||
|
Loading…
Reference in New Issue
Block a user