KCGroups

kapplicationscopelister.cpp
1 // SPDX-FileCopyrightText: 2020 Henri Chain <[email protected]>
2 // SPDX-FileCopyrightText: 2020 Kevin Ottens <[email protected]>
3 //
4 // SPDX-License-Identifier: LGPL-2.1-or-later
5 
6 #include "kapplicationscopelister.h"
7 #include "kapplicationscopelister_p.h"
8 #include "kcgroups_debug.h"
9 #include "managerinterface.h"
10 
11 KApplicationScopeLister::KApplicationScopeLister(QObject *parent)
12  : QObject(parent)
13  , d(new KApplicationScopeListerPrivate(this))
14 {
15 }
16 
17 KApplicationScopeLister::~KApplicationScopeLister()
18 {
19  delete d;
20 }
21 
23 {
24  return d->m_lastError;
25 }
26 
28 {
29  return d->m_appPaths;
30 }
31 
32 static const auto glob = QStringLiteral("app-*");
33 
34 KApplicationScopeListerPrivate::KApplicationScopeListerPrivate(KApplicationScopeLister *parent)
35  : m_lastError(KApplicationScopeLister::NoError)
36  , m_appPaths(QStringList())
37  , q(parent)
38 {
39  static const auto service = QStringLiteral("org.freedesktop.systemd1");
40  static const auto path = QStringLiteral("/org/freedesktop/systemd1");
41 
42  qDBusRegisterMetaType<ManagerDBusUnit>();
43  qDBusRegisterMetaType<ManagerDBusUnitList>();
44 
45  m_manager = new org::freedesktop::systemd1::Manager(service, path, QDBusConnection::sessionBus(), q);
46 
47  const auto *watcher = new QDBusPendingCallWatcher(m_manager->ListUnitsByPatterns({}, {glob}), q);
49  handleGetListCallFinished(watcher);
50  });
51 
52  const auto *subscribeWatcher = new QDBusPendingCallWatcher(m_manager->Subscribe(), q);
53  QObject::connect(subscribeWatcher, &QDBusPendingCallWatcher::finished, q, [this](QDBusPendingCallWatcher *watcher) {
54  handleSubscribeFinished(watcher);
55  });
56 
57  QObject::connect(m_manager,
58  &org::freedesktop::systemd1::Manager::UnitNew,
59  q,
60  [this](const QString &name, const QDBusObjectPath &path) { handleUnitNew(name, path); });
61  QObject::connect(m_manager,
62  &org::freedesktop::systemd1::Manager::UnitRemoved,
63  q,
64  [this](const QString &name, const QDBusObjectPath &path) { handleUnitRemoved(name, path); });
65 }
66 
67 void KApplicationScopeListerPrivate::handleGetListCallFinished(QDBusPendingCallWatcher *call)
68 {
70  if (reply.isError()) {
72  } else {
73  const auto unitList = reply.argumentAt<0>();
74  int changes = 0;
75  for (const auto &unit : unitList) {
76  qCDebug(KCGROUPS_LOG) << unit.activeState;
77  const auto path = unit.path.path();
78  if (!m_appPaths.contains(path)) {
79  m_appPaths.append(path);
80  emit q->pathAdded(path, unit.id);
81  changes++;
82  }
83  }
84  if (changes > 0) {
85  emit q->pathsChanged(m_appPaths);
86  }
87  }
88  call->deleteLater();
89 }
90 
91 void KApplicationScopeListerPrivate::handleSubscribeFinished(QDBusPendingCallWatcher *call)
92 {
93  QDBusPendingReply<> reply = *call;
94  if (reply.isError()) {
96  }
97  call->deleteLater();
98 }
99 
100 void KApplicationScopeListerPrivate::handleUnitNew(const QString &id, const QDBusObjectPath &path)
101 {
102  const auto pathStr = path.path();
103  qCDebug(KCGROUPS_LOG) << "handleUnitNew" << id << path.path();
105  if (regex.globalMatch(id).hasNext() && !m_appPaths.contains(pathStr)) {
106  m_appPaths.append(pathStr);
107  emit q->pathAdded(pathStr, id);
108  emit q->pathsChanged(m_appPaths);
109  }
110 }
111 
112 void KApplicationScopeListerPrivate::handleUnitRemoved(const QString &name, const QDBusObjectPath &path)
113 {
114  const auto pathStr = path.path();
115  qCDebug(KCGROUPS_LOG) << "handleUnitRemoved" << name << path.path();
116  if (m_appPaths.contains(pathStr)) {
117  m_appPaths.removeOne(pathStr);
118  emit q->pathRemoved(pathStr);
119  emit q->pathsChanged(m_appPaths);
120  }
121 }
122 
123 void KApplicationScopeListerPrivate::setError(KApplicationScopeLister::ErrorCode code, const QString &message)
124 {
125  m_lastError = code;
126  qCDebug(KCGROUPS_LOG) << "ERROR: " << message;
127  emit q->errorOccurred(m_lastError);
128 }
QStringList paths
list of dbus paths that corresponds to currently running applications @accessors paths() @notifySigna...
void finished(QDBusPendingCallWatcher *self)
QString wildcardToRegularExpression(const QString &pattern)
QString message() const const
@ CannotSubscribeError
Error while trying to subscribe to systemd manager signals.
bool isError() const const
QMetaObject::Connection connect(const QObject *sender, const char *signal, const QObject *receiver, const char *method, Qt::ConnectionType type)
void deleteLater()
QDBusConnection sessionBus()
Keeps an updated list of desktop application systemd scopes.
ErrorCode
The types of error that can occur.
QDBusError error() const const
QString path(const QString &relativePath)
@ CannotListError
Error while listing applications.
const char * name(StandardAction id)
QVariant argumentAt(int index) const const
ErrorCode lastError
code of the last error that occurred (NoError if none) @accessors lastError() @notifySignal errorOccu...
QString path
the dbus path of the application.
QString message
QString & append(QChar ch)
This file is part of the KDE documentation.
Documentation copyright © 1996-2023 The KDE developers.
Generated on Fri Dec 1 2023 04:13:56 by doxygen 1.8.17 written by Dimitri van Heesch, © 1997-2006

KDE's Doxygen guidelines are available online.