Document property_types.hpp

Summary: Resolves T16534

Reviewers: korina

Reviewed By: korina

Subscribers: ivica, miljen

Maniphest Tasks: T16534

Differential Revision: https://repo.mireo.local/D34028
This commit is contained in:
Bruno Iljazovic
2025-03-03 17:09:34 +01:00
parent 1fe10dd6a3
commit 7f4cfc2145
20 changed files with 105 additions and 35 deletions

View File

@ -522,10 +522,10 @@ public:
}
/**
* \brief Send a \__SUBSCRIBE\__ packet to Broker to create a subscription
* \brief Send a \__SUBSCRIBE\__ packet to Broker to create a Subscription
* to one or more Topics of interest.
*
* \details After the subscription has been established, the Broker will send
* \details After the Subscription has been established, the Broker will send
* PUBLISH packets to the Client to forward Application Messages that were published
* to Topics that the Client subscribed to. The Application Messages can be received
* with \ref mqtt_client::async_receive function.
@ -543,7 +543,7 @@ public:
* void (
* __ERROR_CODE__, // Result of operation.
* std::vector<__REASON_CODE__>, // Vector of Reason Codes indicating
* // the subscription result for each Topic
* // the Subscription result for each Topic
* // in the SUBSCRIBE packet.
* __SUBACK_PROPS__, // Properties received in the SUBACK packet.
* )
@ -595,10 +595,10 @@ public:
}
/**
* \brief Send a \__SUBSCRIBE\__ packet to Broker to create a subscription
* \brief Send a \__SUBSCRIBE\__ packet to Broker to create a Subscription
* to one Topic of interest.
*
* \details After the subscription has been established, the Broker will send
* \details After the Subscription has been established, the Broker will send
* \__PUBLISH\__ packets to the Client to forward Application Messages that were published
* to Topics that the Client subscribed to. The Application Messages can be received
* with \ref mqtt_client::async_receive function.
@ -616,7 +616,7 @@ public:
* void (
* __ERROR_CODE__, // Result of operation.
* std::vector<__REASON_CODE__>, // Vector of Reason Codes containing the
* // single subscription result for the Topic
* // single Subscription result for the Topic
* // in the SUBSCRIBE packet.
* __SUBACK_PROPS__, // Properties received in the SUBACK packet.
* )
@ -808,7 +808,7 @@ public:
* from internal storage.
*
* \note It is only recommended to call this function if you have established
* a successful subscription to a Topic using the \ref async_subscribe function.
* a successful Subscription to a Topic using the \ref async_subscribe function.
*
* \param token Completion token that will be used to produce a
* completion handler. The handler will be invoked when the operation completes.

View File

@ -21,6 +21,7 @@
namespace boost::mqtt5::prop {
/// \cond internal
enum property_type : uint8_t {
payload_format_indicator_t = 0x01,
message_expiry_interval_t = 0x02,
@ -50,7 +51,16 @@ enum property_type : uint8_t {
subscription_identifier_available_t = 0x29,
shared_subscription_available_t = 0x2a
};
/// \endcond
/**
* \brief A class holding any number of Subscription Identifiers.
*
* \details Subscription Identifier is an integer that can be set in \__SUBSCRIBE_PROPS\__ when subscribing to a Topic.
* Broker will store the mapping between that Subscription and the Subscription Identifier.
* When an incoming \__PUBLISH\__ message matches one or more Subscriptions, respective Subscription
* Identifiers will be forwarded in the \__PUBLISH_PROPS\__ of the received message.
*/
class alignas(8) subscription_identifiers :
public boost::container::small_vector<int32_t, 1>
{
@ -58,8 +68,11 @@ class alignas(8) subscription_identifiers :
public:
using base_type::base_type;
/// Constructs Subscription Identifiers with given parameters.
subscription_identifiers(int32_t val) : base_type { val } {}
/// \{ Checks whether there are any Subscription Identifiers.
bool has_value() const noexcept {
return !empty();
}
@ -67,7 +80,9 @@ public:
explicit operator bool() const noexcept {
return !empty();
}
/// \}
/// \{ Accesses the (first) Subscription Identifier.
int32_t& operator*() noexcept {
return front();
}
@ -75,19 +90,24 @@ public:
int32_t operator*() const noexcept {
return front();
}
/// \}
/// Sets or replaces the (first) Subscription Identifier.
void emplace(int32_t val = 0) {
*this = val;
}
/// Returns the first Subscription Identifier.
int32_t value() const {
return front();
}
/// Returns the first Subscription Identifier if it exists, otherwise returns \p default_val
int32_t value_or(int32_t default_val) const noexcept {
return empty() ? default_val : front();
}
/// Clears the Subscription Identifiers.
void reset() noexcept {
clear();
}
@ -142,6 +162,10 @@ using value_type_t = typename property_traits<p>::type;
template <property_type p>
constexpr std::string_view name_v = property_traits<p>::name;
/**
* \brief Base class for different Property classes that contains common access
and modification functions.
*/
template <property_type ...Ps>
class properties {
@ -155,18 +179,21 @@ class properties {
public:
/// \brief Accesses the value of a Property by its compile-time constant ID.
template <property_type v>
constexpr auto& operator[](std::integral_constant<property_type, v>)
noexcept {
return std::get<property<v>>(_props).value;
}
/// \copydoc operator[]
template <property_type v>
constexpr const auto& operator[](std::integral_constant<property_type, v>)
const noexcept {
return std::get<property<v>>(_props).value;
}
/// \cond internal
template <typename Func>
using is_apply_on = std::conjunction<
std::is_invocable<Func, value_type_t<Ps>&>...
@ -176,7 +203,18 @@ public:
using is_nothrow_apply_on = std::conjunction<
std::is_nothrow_invocable<Func, value_type_t<Ps>&>...
>;
/// \endcond
/**
* \brief Applies a function to a Property identified by its ID.
*
* This function iterates over all Properties and invokes the provided function
* on the value of the Property that matches the given property ID.
*
* \param property_id The ID of the Property to apply the function on.
* \param func The function to invoke on the Property value.
* \return `true` if the function was applied to a Property and `false` otherwise.
*/
template <
typename Func,
std::enable_if_t<is_apply_on<Func>::value, bool> = true
@ -190,14 +228,15 @@ public:
constexpr typename ptype::key prop;
if (prop.value == property_id)
std::invoke(func, px.value);
return prop.value != property_id;
return prop.value == property_id;
};
return (pc(ptype) && ...);
return (pc(ptype) || ...);
},
_props
);
}
/// \cond internal
template <typename Func>
using is_visitor = std::conjunction<
std::is_invocable_r<bool, Func, decltype(Ps), value_type_t<Ps>&>...
@ -207,7 +246,20 @@ public:
using is_nothrow_visitor = std::conjunction<
std::is_nothrow_invocable<Func, decltype(Ps), value_type_t<Ps>&>...
>;
/// \endcond
/**
* \brief Invokes a visitor function on each Property.
*
* This function iterates over Properties and invokes the provided function
* on each Property, passing both the compile-time constant Property ID and its value.
* The visitor function should return a boolean value that determines whether iteration continues.
*
* @param func The visitor function to invoke. It must accept two arguments:
* a Property ID and the corresponding Property value.
* @return `true` if the visitor function returns `true` for all Properties,
* `false` otherwise.
*/
template <
typename Func,
std::enable_if_t<is_visitor<Func>::value, bool> = true
@ -221,12 +273,13 @@ public:
constexpr typename ptype::key prop;
return std::invoke(func, prop, px.value);
};
return (pc(props) &&...);
return (pc(props) && ...);
},
_props
);
}
/// \copydoc visit
template <
typename Func,
std::enable_if_t<is_visitor<Func>::value, bool> = true

View File

@ -48,7 +48,7 @@ class reason_code {
uint8_t _code;
reason_codes::category _category { reason_codes::category::none };
public:
/// \cond INTERNAL
/// \cond internal
constexpr reason_code() : _code(0xff) {}
constexpr reason_code(uint8_t code, reason_codes::category cat) :

View File

@ -111,7 +111,7 @@ enum class no_local_e : std::uint8_t {
* \brief Representation of the Retain As Published Subscribe Option.
*
* \details A Subscribe Option indicating whether or not Application Messages forwarded
* using this subscription keep the \__RETAIN\__ flag they were published with.
* using this Subscription keep the \__RETAIN\__ flag they were published with.
*/
enum class retain_as_published_e : std::uint8_t {
/** \brief Application Messages have the \__RETAIN\__ flag set to 0. */
@ -125,13 +125,13 @@ enum class retain_as_published_e : std::uint8_t {
* \brief Representation of the Retain Handling Subscribe Option.
*
* \details A Subscribe Option specifying whether retained messages are sent
* when the subscription is established.
* when the Subscription is established.
*/
enum class retain_handling_e : std::uint8_t {
/** \brief Send retained messages at the time of subscribe. */
send = 0b00,
/** \brief Send retained message only if the subscription does not currently exist. */
/** \brief Send retained message only if the Subscription does not currently exist. */
new_subscription_only = 0b01,
/** \brief Do not send retained messages at the time of subscribe. */
@ -153,7 +153,7 @@ struct subscribe_options {
retain_as_published_e retain_as_published = retain_as_published_e::retain;
/** \brief Option determining if retained messages are sent
when the subscription is established. */
when the Subscription is established. */
retain_handling_e retain_handling = retain_handling_e::new_subscription_only;
};
@ -165,11 +165,11 @@ struct subscribe_topic {
/** \brief An UTF-8 Encoded String indicating the Topics to which the Client wants to subscribe. */
std::string topic_filter;
/** \brief The \ref subscribe_options associated with the subscription. */
/** \brief The \ref subscribe_options associated with the Subscription. */
subscribe_options sub_opts;
};
/// \cond
/// \cond internal
class connect_props : public prop::properties<
prop::session_expiry_interval_t,