refactor: use string_view in Property convenience classes

This commit is contained in:
Stanislav Angelovič
2024-04-16 18:16:40 +02:00
parent f15c260750
commit d41a176c2a
4 changed files with 69 additions and 118 deletions

View File

@@ -37,6 +37,7 @@
#include <future> #include <future>
#include <map> #include <map>
#include <string> #include <string>
#include <string_view>
#include <vector> #include <vector>
// Forward declarations // Forward declarations
@@ -133,8 +134,8 @@ namespace sdbus {
{ {
public: public:
SignalSubscriber(IProxy& proxy, const SignalName& signalName); SignalSubscriber(IProxy& proxy, const SignalName& signalName);
SignalSubscriber& onInterface(InterfaceName interfaceName); SignalSubscriber& onInterface(InterfaceName interfaceName); // TODO: This could be const char*
SignalSubscriber& onInterface(std::string interfaceName); SignalSubscriber& onInterface(std::string interfaceName); // TODO: This could be const char*
template <typename _Function> void call(_Function&& callback); template <typename _Function> void call(_Function&& callback);
template <typename _Function> [[nodiscard]] Slot call(_Function&& callback, return_slot_t); template <typename _Function> [[nodiscard]] Slot call(_Function&& callback, return_slot_t);
@@ -150,24 +151,22 @@ namespace sdbus {
class PropertyGetter class PropertyGetter
{ {
public: public:
PropertyGetter(IProxy& proxy, const PropertyName& propertyName); PropertyGetter(IProxy& proxy, std::string_view propertyName);
Variant onInterface(const InterfaceName& interfaceName); Variant onInterface(std::string_view interfaceName);
Variant onInterface(const std::string& interfaceName);
private: private:
static inline const InterfaceName DBUS_PROPERTIES_INTERFACE_NAME{"org.freedesktop.DBus.Properties"}; static inline const InterfaceName DBUS_PROPERTIES_INTERFACE_NAME{"org.freedesktop.DBus.Properties"};
private: private:
IProxy& proxy_; IProxy& proxy_;
const PropertyName& propertyName_; std::string_view propertyName_;
}; };
class AsyncPropertyGetter class AsyncPropertyGetter
{ {
public: public:
AsyncPropertyGetter(IProxy& proxy, const PropertyName& propertyName); AsyncPropertyGetter(IProxy& proxy, std::string_view propertyName);
AsyncPropertyGetter& onInterface(const InterfaceName& interfaceName); AsyncPropertyGetter& onInterface(std::string_view interfaceName);
AsyncPropertyGetter& onInterface(const std::string& interfaceName);
template <typename _Function> PendingAsyncCall uponReplyInvoke(_Function&& callback); template <typename _Function> PendingAsyncCall uponReplyInvoke(_Function&& callback);
std::future<Variant> getResultAsFuture(); std::future<Variant> getResultAsFuture();
@@ -176,16 +175,15 @@ namespace sdbus {
private: private:
IProxy& proxy_; IProxy& proxy_;
const PropertyName& propertyName_; std::string_view propertyName_;
const InterfaceName* interfaceName_{}; std::string_view interfaceName_;
}; };
class PropertySetter class PropertySetter
{ {
public: public:
PropertySetter(IProxy& proxy, const PropertyName& propertyName); PropertySetter(IProxy& proxy, std::string_view propertyName);
PropertySetter& onInterface(const InterfaceName& interfaceName); PropertySetter& onInterface(std::string_view interfaceName);
PropertySetter& onInterface(const std::string& interfaceName);
template <typename _Value> void toValue(const _Value& value); template <typename _Value> void toValue(const _Value& value);
template <typename _Value> void toValue(const _Value& value, dont_expect_reply_t); template <typename _Value> void toValue(const _Value& value, dont_expect_reply_t);
void toValue(const Variant& value); void toValue(const Variant& value);
@@ -196,16 +194,15 @@ namespace sdbus {
private: private:
IProxy& proxy_; IProxy& proxy_;
const PropertyName& propertyName_; std::string_view propertyName_;
const InterfaceName* interfaceName_{}; std::string_view interfaceName_;
}; };
class AsyncPropertySetter class AsyncPropertySetter
{ {
public: public:
AsyncPropertySetter(IProxy& proxy, const PropertyName& propertyName); AsyncPropertySetter(IProxy& proxy, std::string_view propertyName);
AsyncPropertySetter& onInterface(const InterfaceName& interfaceName); AsyncPropertySetter& onInterface(std::string_view interfaceName);
AsyncPropertySetter& onInterface(const std::string& interfaceName);
template <typename _Value> AsyncPropertySetter& toValue(_Value&& value); template <typename _Value> AsyncPropertySetter& toValue(_Value&& value);
AsyncPropertySetter& toValue(Variant value); AsyncPropertySetter& toValue(Variant value);
template <typename _Function> PendingAsyncCall uponReplyInvoke(_Function&& callback); template <typename _Function> PendingAsyncCall uponReplyInvoke(_Function&& callback);
@@ -216,8 +213,8 @@ namespace sdbus {
private: private:
IProxy& proxy_; IProxy& proxy_;
const PropertyName& propertyName_; std::string_view propertyName_;
const InterfaceName* interfaceName_{}; std::string_view interfaceName_;
Variant value_; Variant value_;
}; };
@@ -225,8 +222,7 @@ namespace sdbus {
{ {
public: public:
AllPropertiesGetter(IProxy& proxy); AllPropertiesGetter(IProxy& proxy);
std::map<PropertyName, Variant> onInterface(const InterfaceName& interfaceName); std::map<PropertyName, Variant> onInterface(std::string_view interfaceName);
std::map<PropertyName, Variant> onInterface(const std::string& interfaceName);
private: private:
static inline const InterfaceName DBUS_PROPERTIES_INTERFACE_NAME{"org.freedesktop.DBus.Properties"}; static inline const InterfaceName DBUS_PROPERTIES_INTERFACE_NAME{"org.freedesktop.DBus.Properties"};
@@ -239,17 +235,16 @@ namespace sdbus {
{ {
public: public:
AsyncAllPropertiesGetter(IProxy& proxy); AsyncAllPropertiesGetter(IProxy& proxy);
AsyncAllPropertiesGetter& onInterface(const InterfaceName& interfaceName); AsyncAllPropertiesGetter& onInterface(std::string_view interfaceName);
AsyncAllPropertiesGetter& onInterface(const std::string& interfaceName);
template <typename _Function> PendingAsyncCall uponReplyInvoke(_Function&& callback); template <typename _Function> PendingAsyncCall uponReplyInvoke(_Function&& callback);
std::future<std::map<PropertyName, Variant>> getResultAsFuture(); std::future<std::map<PropertyName, Variant>> getResultAsFuture();
private: private:
static inline const InterfaceName DBUS_PROPERTIES_INTERFACE_NAME{"org.freedesktop.DBus.Properties"}; static inline const InterfaceName DBUS_PROPERTIES_INTERFACE_NAME{"org.freedesktop.DBus.Properties"}; // TODO: Couldn't this be const char*?
private: private:
IProxy& proxy_; IProxy& proxy_;
const InterfaceName* interfaceName_{}; std::string_view interfaceName_;
}; };
} // namespace sdbus } // namespace sdbus

View File

@@ -404,13 +404,13 @@ namespace sdbus {
/*** PropertyGetter ***/ /*** PropertyGetter ***/
/*** -------------- ***/ /*** -------------- ***/
inline PropertyGetter::PropertyGetter(IProxy& proxy, const PropertyName& propertyName) inline PropertyGetter::PropertyGetter(IProxy& proxy, std::string_view propertyName)
: proxy_(proxy) : proxy_(proxy)
, propertyName_(propertyName) , propertyName_(std::move(propertyName))
{ {
} }
inline Variant PropertyGetter::onInterface(const InterfaceName& interfaceName) inline Variant PropertyGetter::onInterface(std::string_view interfaceName)
{ {
Variant var; Variant var;
proxy_.callMethod("Get") proxy_.callMethod("Get")
@@ -420,57 +420,43 @@ namespace sdbus {
return var; return var;
} }
inline Variant PropertyGetter::onInterface(const std::string& interfaceName)
{
// Down-cast through static cast for performance reasons (no extra copy and object construction needed)
static_assert(sizeof(interfaceName) == sizeof(InterfaceName));
return onInterface(static_cast<const InterfaceName&>(interfaceName));
}
/*** ------------------- ***/ /*** ------------------- ***/
/*** AsyncPropertyGetter ***/ /*** AsyncPropertyGetter ***/
/*** ------------------- ***/ /*** ------------------- ***/
inline AsyncPropertyGetter::AsyncPropertyGetter(IProxy& proxy, const PropertyName& propertyName) inline AsyncPropertyGetter::AsyncPropertyGetter(IProxy& proxy, std::string_view propertyName)
: proxy_(proxy) : proxy_(proxy)
, propertyName_(propertyName) , propertyName_(std::move(propertyName))
{ {
} }
inline AsyncPropertyGetter& AsyncPropertyGetter::onInterface(const InterfaceName& interfaceName) inline AsyncPropertyGetter& AsyncPropertyGetter::onInterface(std::string_view interfaceName)
{ {
interfaceName_ = &interfaceName; interfaceName_ = std::move(interfaceName);
return *this; return *this;
} }
inline AsyncPropertyGetter& AsyncPropertyGetter::onInterface(const std::string& interfaceName)
{
// Down-cast through static cast for performance reasons (no extra copy and object construction needed)
static_assert(sizeof(interfaceName) == sizeof(InterfaceName));
return onInterface(static_cast<const InterfaceName&>(interfaceName));
}
template <typename _Function> template <typename _Function>
PendingAsyncCall AsyncPropertyGetter::uponReplyInvoke(_Function&& callback) PendingAsyncCall AsyncPropertyGetter::uponReplyInvoke(_Function&& callback)
{ {
static_assert(std::is_invocable_r_v<void, _Function, std::optional<Error>, Variant>, "Property get callback function must accept std::optional<Error> and property value as Variant"); static_assert(std::is_invocable_r_v<void, _Function, std::optional<Error>, Variant>, "Property get callback function must accept std::optional<Error> and property value as Variant");
assert(interfaceName_ != nullptr); // onInterface() must be placed/called prior to this function assert(!interfaceName_.empty()); // onInterface() must be placed/called prior to this function
return proxy_.callMethodAsync("Get") return proxy_.callMethodAsync("Get")
.onInterface(DBUS_PROPERTIES_INTERFACE_NAME) .onInterface(DBUS_PROPERTIES_INTERFACE_NAME)
.withArguments(*interfaceName_, propertyName_) .withArguments(interfaceName_, propertyName_)
.uponReplyInvoke(std::forward<_Function>(callback)); .uponReplyInvoke(std::forward<_Function>(callback));
} }
inline std::future<Variant> AsyncPropertyGetter::getResultAsFuture() inline std::future<Variant> AsyncPropertyGetter::getResultAsFuture()
{ {
assert(interfaceName_ != nullptr); // onInterface() must be placed/called prior to this function assert(!interfaceName_.empty()); // onInterface() must be placed/called prior to this function
return proxy_.callMethodAsync("Get") return proxy_.callMethodAsync("Get")
.onInterface(DBUS_PROPERTIES_INTERFACE_NAME) .onInterface(DBUS_PROPERTIES_INTERFACE_NAME)
.withArguments(*interfaceName_, propertyName_) .withArguments(interfaceName_, propertyName_)
.getResultAsFuture<Variant>(); .getResultAsFuture<Variant>();
} }
@@ -478,26 +464,19 @@ namespace sdbus {
/*** PropertySetter ***/ /*** PropertySetter ***/
/*** -------------- ***/ /*** -------------- ***/
inline PropertySetter::PropertySetter(IProxy& proxy, const PropertyName& propertyName) inline PropertySetter::PropertySetter(IProxy& proxy, std::string_view propertyName)
: proxy_(proxy) : proxy_(proxy)
, propertyName_(propertyName) , propertyName_(std::move(propertyName))
{ {
} }
inline PropertySetter& PropertySetter::onInterface(const InterfaceName& interfaceName) inline PropertySetter& PropertySetter::onInterface(std::string_view interfaceName)
{ {
interfaceName_ = &interfaceName; interfaceName_ = std::move(interfaceName);
return *this; return *this;
} }
inline PropertySetter& PropertySetter::onInterface(const std::string& interfaceName)
{
// Down-cast through static cast for performance reasons (no extra copy and object construction needed)
static_assert(sizeof(interfaceName) == sizeof(InterfaceName));
return onInterface(static_cast<const InterfaceName&>(interfaceName));
}
template <typename _Value> template <typename _Value>
inline void PropertySetter::toValue(const _Value& value) inline void PropertySetter::toValue(const _Value& value)
{ {
@@ -512,20 +491,20 @@ namespace sdbus {
inline void PropertySetter::toValue(const Variant& value) inline void PropertySetter::toValue(const Variant& value)
{ {
assert(interfaceName_ != nullptr); // onInterface() must be placed/called prior to this function assert(!interfaceName_.empty()); // onInterface() must be placed/called prior to this function
proxy_.callMethod("Set") proxy_.callMethod("Set")
.onInterface(DBUS_PROPERTIES_INTERFACE_NAME) .onInterface(DBUS_PROPERTIES_INTERFACE_NAME)
.withArguments(*interfaceName_, propertyName_, value); .withArguments(interfaceName_, propertyName_, value);
} }
inline void PropertySetter::toValue(const Variant& value, dont_expect_reply_t) inline void PropertySetter::toValue(const Variant& value, dont_expect_reply_t)
{ {
assert(interfaceName_ != nullptr); // onInterface() must be placed/called prior to this function assert(!interfaceName_.empty()); // onInterface() must be placed/called prior to this function
proxy_.callMethod("Set") proxy_.callMethod("Set")
.onInterface(DBUS_PROPERTIES_INTERFACE_NAME) .onInterface(DBUS_PROPERTIES_INTERFACE_NAME)
.withArguments(*interfaceName_, propertyName_, value) .withArguments(interfaceName_, propertyName_, value)
.dontExpectReply(); .dontExpectReply();
} }
@@ -533,26 +512,19 @@ namespace sdbus {
/*** AsyncPropertySetter ***/ /*** AsyncPropertySetter ***/
/*** ------------------- ***/ /*** ------------------- ***/
inline AsyncPropertySetter::AsyncPropertySetter(IProxy& proxy, const PropertyName& propertyName) inline AsyncPropertySetter::AsyncPropertySetter(IProxy& proxy, std::string_view propertyName)
: proxy_(proxy) : proxy_(proxy)
, propertyName_(propertyName) , propertyName_(propertyName)
{ {
} }
inline AsyncPropertySetter& AsyncPropertySetter::onInterface(const InterfaceName& interfaceName) inline AsyncPropertySetter& AsyncPropertySetter::onInterface(std::string_view interfaceName)
{ {
interfaceName_ = &interfaceName; interfaceName_ = std::move(interfaceName);
return *this; return *this;
} }
inline AsyncPropertySetter& AsyncPropertySetter::onInterface(const std::string& interfaceName)
{
// Down-cast through static cast for performance reasons (no extra copy and object construction needed)
static_assert(sizeof(interfaceName) == sizeof(InterfaceName));
return onInterface(static_cast<const InterfaceName&>(interfaceName));
}
template <typename _Value> template <typename _Value>
inline AsyncPropertySetter& AsyncPropertySetter::toValue(_Value&& value) inline AsyncPropertySetter& AsyncPropertySetter::toValue(_Value&& value)
{ {
@@ -571,21 +543,21 @@ namespace sdbus {
{ {
static_assert(std::is_invocable_r_v<void, _Function, std::optional<Error>>, "Property set callback function must accept std::optional<Error> only"); static_assert(std::is_invocable_r_v<void, _Function, std::optional<Error>>, "Property set callback function must accept std::optional<Error> only");
assert(interfaceName_ != nullptr); // onInterface() must be placed/called prior to this function assert(!interfaceName_.empty()); // onInterface() must be placed/called prior to this function
return proxy_.callMethodAsync("Set") return proxy_.callMethodAsync("Set")
.onInterface(DBUS_PROPERTIES_INTERFACE_NAME) .onInterface(DBUS_PROPERTIES_INTERFACE_NAME)
.withArguments(*interfaceName_, propertyName_, std::move(value_)) .withArguments(interfaceName_, propertyName_, std::move(value_))
.uponReplyInvoke(std::forward<_Function>(callback)); .uponReplyInvoke(std::forward<_Function>(callback));
} }
inline std::future<void> AsyncPropertySetter::getResultAsFuture() inline std::future<void> AsyncPropertySetter::getResultAsFuture()
{ {
assert(interfaceName_ != nullptr); // onInterface() must be placed/called prior to this function assert(!interfaceName_.empty()); // onInterface() must be placed/called prior to this function
return proxy_.callMethodAsync("Set") return proxy_.callMethodAsync("Set")
.onInterface(DBUS_PROPERTIES_INTERFACE_NAME) .onInterface(DBUS_PROPERTIES_INTERFACE_NAME)
.withArguments(*interfaceName_, propertyName_, std::move(value_)) .withArguments(interfaceName_, propertyName_, std::move(value_))
.getResultAsFuture<>(); .getResultAsFuture<>();
} }
@@ -598,23 +570,16 @@ namespace sdbus {
{ {
} }
inline std::map<PropertyName, Variant> AllPropertiesGetter::onInterface(const InterfaceName& interfaceName) inline std::map<PropertyName, Variant> AllPropertiesGetter::onInterface(std::string_view interfaceName)
{ {
std::map<PropertyName, Variant> props; std::map<PropertyName, Variant> props;
proxy_.callMethod("GetAll") proxy_.callMethod("GetAll")
.onInterface(DBUS_PROPERTIES_INTERFACE_NAME) .onInterface(DBUS_PROPERTIES_INTERFACE_NAME)
.withArguments(interfaceName) .withArguments(std::move(interfaceName))
.storeResultsTo(props); .storeResultsTo(props);
return props; return props;
} }
inline std::map<PropertyName, Variant> AllPropertiesGetter::onInterface(const std::string& interfaceName)
{
// Down-cast through static cast for performance reasons (no extra copy and object construction needed)
static_assert(sizeof(interfaceName) == sizeof(InterfaceName));
return onInterface(static_cast<const InterfaceName&>(interfaceName));
}
/*** ------------------------ ***/ /*** ------------------------ ***/
/*** AsyncAllPropertiesGetter ***/ /*** AsyncAllPropertiesGetter ***/
/*** ------------------------ ***/ /*** ------------------------ ***/
@@ -624,41 +589,34 @@ namespace sdbus {
{ {
} }
inline AsyncAllPropertiesGetter& AsyncAllPropertiesGetter::onInterface(const InterfaceName& interfaceName) inline AsyncAllPropertiesGetter& AsyncAllPropertiesGetter::onInterface(std::string_view interfaceName)
{ {
interfaceName_ = &interfaceName; interfaceName_ = std::move(interfaceName);
return *this; return *this;
} }
inline AsyncAllPropertiesGetter& AsyncAllPropertiesGetter::onInterface(const std::string& interfaceName)
{
// Down-cast through static cast for performance reasons (no extra copy and object construction needed)
static_assert(sizeof(interfaceName) == sizeof(InterfaceName));
return onInterface(static_cast<const InterfaceName&>(interfaceName));
}
template <typename _Function> template <typename _Function>
PendingAsyncCall AsyncAllPropertiesGetter::uponReplyInvoke(_Function&& callback) PendingAsyncCall AsyncAllPropertiesGetter::uponReplyInvoke(_Function&& callback)
{ {
static_assert( std::is_invocable_r_v<void, _Function, std::optional<Error>, std::map<PropertyName, Variant>> static_assert( std::is_invocable_r_v<void, _Function, std::optional<Error>, std::map<PropertyName, Variant>>
, "All properties get callback function must accept std::optional<Error> and a map of property names to their values" ); , "All properties get callback function must accept std::optional<Error> and a map of property names to their values" );
assert(interfaceName_ != nullptr); // onInterface() must be placed/called prior to this function assert(!interfaceName_.empty()); // onInterface() must be placed/called prior to this function
return proxy_.callMethodAsync("GetAll") return proxy_.callMethodAsync("GetAll")
.onInterface(DBUS_PROPERTIES_INTERFACE_NAME) .onInterface(DBUS_PROPERTIES_INTERFACE_NAME)
.withArguments(*interfaceName_) .withArguments(interfaceName_)
.uponReplyInvoke(std::forward<_Function>(callback)); .uponReplyInvoke(std::forward<_Function>(callback));
} }
inline std::future<std::map<PropertyName, Variant>> AsyncAllPropertiesGetter::getResultAsFuture() inline std::future<std::map<PropertyName, Variant>> AsyncAllPropertiesGetter::getResultAsFuture()
{ {
assert(interfaceName_ != nullptr); // onInterface() must be placed/called prior to this function assert(!interfaceName_.empty()); // onInterface() must be placed/called prior to this function
return proxy_.callMethodAsync("GetAll") return proxy_.callMethodAsync("GetAll")
.onInterface(DBUS_PROPERTIES_INTERFACE_NAME) .onInterface(DBUS_PROPERTIES_INTERFACE_NAME)
.withArguments(*interfaceName_) .withArguments(interfaceName_)
.getResultAsFuture<std::map<PropertyName, Variant>>(); .getResultAsFuture<std::map<PropertyName, Variant>>();
} }

View File

@@ -35,6 +35,7 @@
#include <future> #include <future>
#include <memory> #include <memory>
#include <string> #include <string>
#include <string_view>
// Forward declarations // Forward declarations
namespace sdbus { namespace sdbus {
@@ -358,7 +359,7 @@ namespace sdbus {
/*! /*!
* @copydoc IProxy::getProperty(const PropertyName&) * @copydoc IProxy::getProperty(const PropertyName&)
*/ */
[[nodiscard]] PropertyGetter getProperty(const std::string& propertyName); [[nodiscard]] PropertyGetter getProperty(std::string_view propertyName);
/*! /*!
* @brief Gets value of a property of the D-Bus object asynchronously * @brief Gets value of a property of the D-Bus object asynchronously
@@ -610,11 +611,9 @@ namespace sdbus {
return PropertyGetter(*this, propertyName); return PropertyGetter(*this, propertyName);
} }
inline PropertyGetter IProxy::getProperty(const std::string& propertyName) inline PropertyGetter IProxy::getProperty(std::string_view propertyName)
{ {
// Down-cast through static cast for performance reasons (no extra copy and object construction needed) return PropertyGetter(*this, propertyName);
static_assert(sizeof(propertyName) == sizeof(PropertyName));
return getProperty(static_cast<const PropertyName&>(propertyName));
} }
inline AsyncPropertyGetter IProxy::getPropertyAsync(const PropertyName& propertyName) inline AsyncPropertyGetter IProxy::getPropertyAsync(const PropertyName& propertyName)

View File

@@ -150,8 +150,7 @@ namespace sdbus {
return proxy_->getProperty(propertyName).onInterface(interfaceName); return proxy_->getProperty(propertyName).onInterface(interfaceName);
} }
// TODO: Refactor from std::string to std::string_view before release/v2.0 !!! sdbus::Variant Get(const InterfaceName& interfaceName, std::string_view propertyName)
sdbus::Variant Get(const InterfaceName& interfaceName, const std::string& propertyName)
{ {
return proxy_->getProperty(propertyName).onInterface(interfaceName); return proxy_->getProperty(propertyName).onInterface(interfaceName);
} }