forked from Kistler-Group/sdbus-cpp
Add support for ObjectManager and other standard D-Bus interfaces (#55)
Fixes #50
This commit is contained in:
@@ -130,6 +130,30 @@ namespace sdbus {
|
||||
getObject().unregister();
|
||||
}
|
||||
|
||||
/*!
|
||||
* @brief Adds an ObjectManager interface at the path of this D-Bus object
|
||||
*
|
||||
* Creates an ObjectManager interface at the specified object path on
|
||||
* the connection. This is a convenient way to interrogate a connection
|
||||
* to see what objects it has.
|
||||
*
|
||||
* @throws sdbus::Error in case of failure
|
||||
*/
|
||||
void addObjectManager()
|
||||
{
|
||||
getObject().addObjectManager();
|
||||
}
|
||||
|
||||
/*!
|
||||
* @brief Removes an ObjectManager interface from the path of this D-Bus object
|
||||
*
|
||||
* @throws sdbus::Error in case of failure
|
||||
*/
|
||||
void removeObjectManager()
|
||||
{
|
||||
getObject().removeObjectManager();
|
||||
}
|
||||
|
||||
protected:
|
||||
using base_type = AdaptorInterfaces;
|
||||
};
|
||||
|
||||
@@ -220,6 +220,7 @@ namespace sdbus {
|
||||
PropertySetter(IProxy& proxy, const std::string& propertyName);
|
||||
PropertySetter& onInterface(const std::string& interfaceName);
|
||||
template <typename _Value> void toValue(const _Value& value);
|
||||
void toValue(const sdbus::Variant& value);
|
||||
|
||||
private:
|
||||
IProxy& proxy_;
|
||||
|
||||
@@ -596,13 +596,18 @@ namespace sdbus {
|
||||
|
||||
template <typename _Value>
|
||||
inline void PropertySetter::toValue(const _Value& value)
|
||||
{
|
||||
PropertySetter::toValue(sdbus::Variant{value});
|
||||
}
|
||||
|
||||
inline void PropertySetter::toValue(const sdbus::Variant& value)
|
||||
{
|
||||
SDBUS_THROW_ERROR_IF(interfaceName_.empty(), "DBus interface not specified when setting a property", EINVAL);
|
||||
|
||||
proxy_
|
||||
.callMethod("Set")
|
||||
.onInterface("org.freedesktop.DBus.Properties")
|
||||
.withArguments(interfaceName_, propertyName_, sdbus::Variant{value});
|
||||
.withArguments(interfaceName_, propertyName_, value);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -45,6 +45,8 @@ namespace sdbus {
|
||||
class IConnection
|
||||
{
|
||||
public:
|
||||
virtual ~IConnection() = default;
|
||||
|
||||
/*!
|
||||
* @brief Requests D-Bus name on the connection
|
||||
*
|
||||
@@ -91,7 +93,7 @@ namespace sdbus {
|
||||
virtual void leaveProcessingLoop() = 0;
|
||||
|
||||
/*!
|
||||
* @brief Add an ObjectManager at the specified D-Bus object path
|
||||
* @brief Adds an ObjectManager at the specified D-Bus object path
|
||||
*
|
||||
* Creates an ObjectManager interface at the specified object path on
|
||||
* the connection. This is a convenient way to interrogate a connection
|
||||
@@ -99,13 +101,9 @@ namespace sdbus {
|
||||
*
|
||||
* @throws sdbus::Error in case of failure
|
||||
*/
|
||||
virtual void addObjectManager( const std::string& objectPath ) = 0;
|
||||
|
||||
inline virtual ~IConnection() = 0;
|
||||
virtual void addObjectManager(const std::string& objectPath) = 0;
|
||||
};
|
||||
|
||||
IConnection::~IConnection() {}
|
||||
|
||||
/*!
|
||||
* @brief Creates/opens D-Bus system connection
|
||||
*
|
||||
|
||||
@@ -57,6 +57,8 @@ namespace sdbus {
|
||||
class IObject
|
||||
{
|
||||
public:
|
||||
virtual ~IObject() = default;
|
||||
|
||||
/*!
|
||||
* @brief Registers method that the object will provide on D-Bus
|
||||
*
|
||||
@@ -192,6 +194,30 @@ namespace sdbus {
|
||||
*/
|
||||
virtual sdbus::IConnection& getConnection() const = 0;
|
||||
|
||||
/*!
|
||||
* @brief Adds an ObjectManager interface at the path of this D-Bus object
|
||||
*
|
||||
* Creates an ObjectManager interface at the specified object path on
|
||||
* the connection. This is a convenient way to interrogate a connection
|
||||
* to see what objects it has.
|
||||
*
|
||||
* @throws sdbus::Error in case of failure
|
||||
*/
|
||||
virtual void addObjectManager() = 0;
|
||||
|
||||
/*!
|
||||
* @brief Removes an ObjectManager interface from the path of this D-Bus object
|
||||
*
|
||||
* @throws sdbus::Error in case of failure
|
||||
*/
|
||||
virtual void removeObjectManager() = 0;
|
||||
|
||||
/*!
|
||||
* @brief Tests whether ObjectManager interface is added at the path of this D-Bus object
|
||||
* @return True if ObjectManager interface is there, false otherwise
|
||||
*/
|
||||
virtual bool hasObjectManager() const = 0;
|
||||
|
||||
/*!
|
||||
* @brief Registers method that the object will provide on D-Bus
|
||||
*
|
||||
@@ -287,8 +313,6 @@ namespace sdbus {
|
||||
* @throws sdbus::Error in case of failure
|
||||
*/
|
||||
SignalEmitter emitSignal(const std::string& signalName);
|
||||
|
||||
virtual ~IObject() = 0;
|
||||
};
|
||||
|
||||
inline MethodRegistrator IObject::registerMethod(const std::string& methodName)
|
||||
@@ -316,8 +340,6 @@ namespace sdbus {
|
||||
return SignalEmitter(*this, signalName);
|
||||
}
|
||||
|
||||
inline IObject::~IObject() {}
|
||||
|
||||
/*!
|
||||
* @brief Creates instance representing a D-Bus object
|
||||
*
|
||||
|
||||
@@ -58,6 +58,8 @@ namespace sdbus {
|
||||
class IProxy
|
||||
{
|
||||
public:
|
||||
virtual ~IProxy() = default;
|
||||
|
||||
/*!
|
||||
* @brief Creates a method call message
|
||||
*
|
||||
@@ -259,8 +261,6 @@ namespace sdbus {
|
||||
* @throws sdbus::Error in case of failure
|
||||
*/
|
||||
PropertySetter setProperty(const std::string& propertyName);
|
||||
|
||||
virtual ~IProxy() = default;
|
||||
};
|
||||
|
||||
inline MethodInvoker IProxy::callMethod(const std::string& methodName)
|
||||
|
||||
@@ -1,84 +0,0 @@
|
||||
/**
|
||||
* (C) 2017 KISTLER INSTRUMENTE AG, Winterthur, Switzerland
|
||||
*
|
||||
* @file Introspection.h
|
||||
*
|
||||
* Created on: Dec 13, 2016
|
||||
* Project: sdbus-c++
|
||||
* Description: High-level D-Bus IPC C++ library based on sd-bus
|
||||
*
|
||||
* This file is part of sdbus-c++.
|
||||
*
|
||||
* sdbus-c++ is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU Lesser General Public License as published by
|
||||
* the Free Software Foundation, either version 2.1 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* sdbus-c++ is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with sdbus-c++. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef SDBUS_CXX_INTROSPECTION_H_
|
||||
#define SDBUS_CXX_INTROSPECTION_H_
|
||||
|
||||
#include <sdbus-c++/IObject.h>
|
||||
#include <sdbus-c++/IProxy.h>
|
||||
#include <string>
|
||||
|
||||
namespace sdbus {
|
||||
|
||||
// Proxy for introspection
|
||||
class introspectable_proxy
|
||||
{
|
||||
static constexpr const char* interfaceName = "org.freedesktop.DBus.Introspectable";
|
||||
|
||||
protected:
|
||||
introspectable_proxy(sdbus::IProxy& object)
|
||||
: object_(object)
|
||||
{
|
||||
}
|
||||
|
||||
public:
|
||||
std::string Introspect()
|
||||
{
|
||||
std::string xml;
|
||||
object_.callMethod("Introspect").onInterface(interfaceName).storeResultsTo(xml);
|
||||
return xml;
|
||||
}
|
||||
|
||||
private:
|
||||
sdbus::IProxy& object_;
|
||||
};
|
||||
|
||||
// Adaptor is not necessary if we want to rely on sdbus-provided introspection
|
||||
// class introspectable_adaptor
|
||||
// {
|
||||
// static constexpr const char* interfaceName = "org.freedesktop.DBus.Introspectable";
|
||||
//
|
||||
// protected:
|
||||
// introspectable_adaptor(sdbus::IObject& object)
|
||||
// : object_(object)
|
||||
// {
|
||||
// object_.registerMethod("Introspect").onInterface(interfaceName).implementedAs([this](){ return object_.introspect(); });
|
||||
// }
|
||||
//
|
||||
// public:
|
||||
// std::string introspect()
|
||||
// {
|
||||
// std::string xml;
|
||||
// object_.callMethod("Introspect").onInterface(interfaceName).storeResultsTo(xml);
|
||||
// return xml;
|
||||
// }
|
||||
//
|
||||
// private:
|
||||
// sdbus::IObject& object_;
|
||||
// };
|
||||
|
||||
}
|
||||
|
||||
#endif /* SDBUS_CXX_INTROSPECTION_H_ */
|
||||
@@ -0,0 +1,185 @@
|
||||
/**
|
||||
* (C) 2017 KISTLER INSTRUMENTE AG, Winterthur, Switzerland
|
||||
*
|
||||
* @file StandardInterfaces.h
|
||||
*
|
||||
* Created on: Dec 13, 2016
|
||||
* Project: sdbus-c++
|
||||
* Description: High-level D-Bus IPC C++ library based on sd-bus
|
||||
*
|
||||
* This file is part of sdbus-c++.
|
||||
*
|
||||
* sdbus-c++ is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU Lesser General Public License as published by
|
||||
* the Free Software Foundation, either version 2.1 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* sdbus-c++ is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with sdbus-c++. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef SDBUS_CXX_STANDARDINTERFACES_H_
|
||||
#define SDBUS_CXX_STANDARDINTERFACES_H_
|
||||
|
||||
#include <sdbus-c++/IObject.h>
|
||||
#include <sdbus-c++/IProxy.h>
|
||||
#include <sdbus-c++/Types.h>
|
||||
#include <string>
|
||||
#include <map>
|
||||
#include <vector>
|
||||
|
||||
namespace sdbus {
|
||||
|
||||
// Proxy for peer
|
||||
class Peer_proxy
|
||||
{
|
||||
static constexpr const char* INTERFACE_NAME = "org.freedesktop.DBus.Peer";
|
||||
|
||||
protected:
|
||||
Peer_proxy(sdbus::IProxy& proxy)
|
||||
: proxy_(proxy)
|
||||
{
|
||||
}
|
||||
|
||||
public:
|
||||
void Ping()
|
||||
{
|
||||
proxy_.callMethod("Ping").onInterface(INTERFACE_NAME);
|
||||
}
|
||||
|
||||
std::string GetMachineId()
|
||||
{
|
||||
std::string machineUUID;
|
||||
proxy_.callMethod("GetMachineId").onInterface(INTERFACE_NAME).storeResultsTo(machineUUID);
|
||||
return machineUUID;
|
||||
}
|
||||
|
||||
private:
|
||||
sdbus::IProxy& proxy_;
|
||||
};
|
||||
|
||||
// Proxy for introspection
|
||||
class Introspectable_proxy
|
||||
{
|
||||
static constexpr const char* INTERFACE_NAME = "org.freedesktop.DBus.Introspectable";
|
||||
|
||||
protected:
|
||||
Introspectable_proxy(sdbus::IProxy& proxy)
|
||||
: proxy_(proxy)
|
||||
{
|
||||
}
|
||||
|
||||
public:
|
||||
std::string Introspect()
|
||||
{
|
||||
std::string xml;
|
||||
proxy_.callMethod("Introspect").onInterface(INTERFACE_NAME).storeResultsTo(xml);
|
||||
return xml;
|
||||
}
|
||||
|
||||
private:
|
||||
sdbus::IProxy& proxy_;
|
||||
};
|
||||
|
||||
// Proxy for properties
|
||||
class Properties_proxy
|
||||
{
|
||||
static constexpr const char* INTERFACE_NAME = "org.freedesktop.DBus.Properties";
|
||||
|
||||
protected:
|
||||
Properties_proxy(sdbus::IProxy& proxy)
|
||||
: proxy_(proxy)
|
||||
{
|
||||
proxy_
|
||||
.uponSignal("PropertiesChanged")
|
||||
.onInterface(INTERFACE_NAME)
|
||||
.call([this]( const std::string& interfaceName
|
||||
, const std::map<std::string, sdbus::Variant>& changedProperties
|
||||
, const std::vector<std::string>& invalidatedProperties )
|
||||
{
|
||||
this->onPropertiesChanged(interfaceName, changedProperties, invalidatedProperties);
|
||||
});
|
||||
}
|
||||
|
||||
virtual void onPropertiesChanged( const std::string& interfaceName
|
||||
, const std::map<std::string, sdbus::Variant>& changedProperties
|
||||
, const std::vector<std::string>& invalidatedProperties ) = 0;
|
||||
|
||||
public:
|
||||
sdbus::Variant Get(const std::string& interfaceName, const std::string& propertyName)
|
||||
{
|
||||
return proxy_.getProperty(propertyName).onInterface(interfaceName);
|
||||
}
|
||||
|
||||
void Set(const std::string& interfaceName, const std::string& propertyName, const sdbus::Variant& value)
|
||||
{
|
||||
proxy_.setProperty(propertyName).onInterface(interfaceName).toValue(value);
|
||||
}
|
||||
|
||||
std::map<std::string, sdbus::Variant> GetAll(const std::string& interfaceName)
|
||||
{
|
||||
std::map<std::string, sdbus::Variant> props;
|
||||
proxy_.callMethod("GetAll").onInterface(INTERFACE_NAME).withArguments(interfaceName).storeResultsTo(props);
|
||||
return props;
|
||||
}
|
||||
|
||||
private:
|
||||
sdbus::IProxy& proxy_;
|
||||
};
|
||||
|
||||
// Proxy for object manager
|
||||
class ObjectManager_proxy
|
||||
{
|
||||
static constexpr const char* INTERFACE_NAME = "org.freedesktop.DBus.ObjectManager";
|
||||
|
||||
protected:
|
||||
ObjectManager_proxy(sdbus::IProxy& proxy)
|
||||
: proxy_(proxy)
|
||||
{
|
||||
proxy_
|
||||
.uponSignal("InterfacesAdded")
|
||||
.onInterface(INTERFACE_NAME)
|
||||
.call([this]( const sdbus::ObjectPath& objectPath
|
||||
, const std::map<std::string, std::map<std::string, sdbus::Variant>>& interfacesAndProperties )
|
||||
{
|
||||
this->onInterfacesAdded(objectPath, interfacesAndProperties);
|
||||
});
|
||||
|
||||
proxy_
|
||||
.uponSignal("InterfacesRemoved")
|
||||
.onInterface(INTERFACE_NAME)
|
||||
.call([this]( const sdbus::ObjectPath& objectPath
|
||||
, const std::vector<std::string>& interfaces )
|
||||
{
|
||||
this->onInterfacesRemoved(objectPath, interfaces);
|
||||
});
|
||||
}
|
||||
|
||||
virtual void onInterfacesAdded( const sdbus::ObjectPath& objectPath
|
||||
, const std::map<std::string, std::map<std::string, sdbus::Variant>>& interfacesAndProperties) = 0;
|
||||
virtual void onInterfacesRemoved( const sdbus::ObjectPath& objectPath
|
||||
, const std::vector<std::string>& interfaces) = 0;
|
||||
|
||||
public:
|
||||
std::map<sdbus::ObjectPath, std::map<std::string, std::map<std::string, sdbus::Variant>>> GetManagedObjects()
|
||||
{
|
||||
std::map<sdbus::ObjectPath, std::map<std::string, std::map<std::string, sdbus::Variant>>> objectsInterfacesAndProperties;
|
||||
proxy_.callMethod("GetManagedObjects").onInterface(INTERFACE_NAME).storeResultsTo(objectsInterfacesAndProperties);
|
||||
return objectsInterfacesAndProperties;
|
||||
}
|
||||
|
||||
private:
|
||||
sdbus::IProxy& proxy_;
|
||||
};
|
||||
|
||||
// Adaptors for the above-listed standard D-Bus interfaces are not necessary because the functionality
|
||||
// is provided automatically for each D-Bus object by underlying libsystemd (with the exception of
|
||||
// object manager which is provided but needs to be added explicitly, see IObject::addObjectManager).
|
||||
}
|
||||
|
||||
#endif /* SDBUS_CXX_STANDARDINTERFACES_H_ */
|
||||
@@ -28,9 +28,10 @@
|
||||
#include <sdbus-c++/IProxy.h>
|
||||
#include <sdbus-c++/AdaptorInterfaces.h>
|
||||
#include <sdbus-c++/ProxyInterfaces.h>
|
||||
#include <sdbus-c++/StandardInterfaces.h>
|
||||
#include <sdbus-c++/Message.h>
|
||||
#include <sdbus-c++/MethodResult.h>
|
||||
#include <sdbus-c++/Types.h>
|
||||
#include <sdbus-c++/TypeTraits.h>
|
||||
#include <sdbus-c++/Introspection.h>
|
||||
#include <sdbus-c++/Error.h>
|
||||
#include <sdbus-c++/Flags.h>
|
||||
|
||||
Reference in New Issue
Block a user