...
This commit is contained in:
139
net/adc_netmsg.h
139
net/adc_netmsg.h
@@ -43,91 +43,17 @@ void convertToBytes(ByteStorageT& res, const T& v, const Ts&... vs)
|
||||
} // namespace utils
|
||||
|
||||
|
||||
namespace traits
|
||||
{
|
||||
|
||||
template <typename T, typename IT>
|
||||
concept adc_netmessage_c = requires(const T t) { // const methods
|
||||
requires std::same_as<std::iter_value_t<IT>, char>;
|
||||
{ t.empty() } -> std::convertible_to<bool>;
|
||||
{ t.byteSize() } -> std::convertible_to<size_t>;
|
||||
{ t.bytes() } -> adc_output_char_range;
|
||||
{ t.byteView() } -> adc_range_of_view_char_range;
|
||||
{ t.setFromBytes(std::input_iterator<IT>) } -> std::same_as<void>;
|
||||
};
|
||||
|
||||
} // namespace traits
|
||||
|
||||
|
||||
/*
|
||||
Trivial message interface:
|
||||
byte storage: just a char-range
|
||||
*/
|
||||
*/
|
||||
template <traits::adc_output_char_range ByteStorageT = std::string, traits::adc_char_view ByteViewT = std::string_view>
|
||||
class AdcNetMessageTrivialInterface
|
||||
class AdcNetMessageInterface
|
||||
{
|
||||
public:
|
||||
virtual ~AdcNetMessageTrivialInterface() = default;
|
||||
typedef ByteStorageT byte_storage_t;
|
||||
typedef ByteViewT byte_view_t;
|
||||
|
||||
bool empty() const { return std::ranges::distance(_bytes.begin(), _bytes.end()) == 0; }
|
||||
|
||||
size_t byteSize() const
|
||||
{
|
||||
//
|
||||
return std::ranges::distance(_bytes.begin(), _bytes.end());
|
||||
}
|
||||
|
||||
// get a copy of message bytes
|
||||
template <traits::adc_output_char_range R>
|
||||
R bytes() const
|
||||
{
|
||||
R r;
|
||||
std::ranges::copy(_bytes, std::back_inserter(r));
|
||||
|
||||
return r;
|
||||
}
|
||||
|
||||
|
||||
virtual ByteStorageT bytes() const
|
||||
{
|
||||
//
|
||||
return bytes<ByteStorageT>();
|
||||
}
|
||||
|
||||
// get a view of message bytes
|
||||
template <traits::adc_range_of_view_char_range R>
|
||||
R bytesView() const
|
||||
{
|
||||
R r;
|
||||
|
||||
r.emplace_back(_bytes.begin(), _bytes.end());
|
||||
|
||||
return r;
|
||||
}
|
||||
|
||||
std::vector<ByteViewT> bytesView() const
|
||||
{
|
||||
//
|
||||
return bytesView<std::vector<ByteViewT>>();
|
||||
}
|
||||
|
||||
protected:
|
||||
ByteStorageT _bytes;
|
||||
|
||||
AdcNetMessageTrivialInterface() = default;
|
||||
};
|
||||
|
||||
|
||||
|
||||
/*
|
||||
interface for more complex messages:
|
||||
byte storage: std::vector of char-range (sequence of buffers)
|
||||
*/
|
||||
template <traits::adc_output_char_range ByteStorageT = std::string, traits::adc_char_view ByteViewT = std::string_view>
|
||||
class AdcNetMessageSeqInterface
|
||||
{
|
||||
public:
|
||||
virtual ~AdcNetMessageSeqInterface() = default;
|
||||
virtual ~AdcNetMessageInterface() = default;
|
||||
|
||||
bool empty() const
|
||||
{
|
||||
@@ -201,11 +127,11 @@ public:
|
||||
}
|
||||
|
||||
protected:
|
||||
std::vector<ByteStorageT> _bytes;
|
||||
std::vector<ByteStorageT> _bytes; // sequence of byte buffers
|
||||
size_t _reservedNum;
|
||||
|
||||
|
||||
AdcNetMessageSeqInterface(size_t reserved = 0) : _reservedNum(reserved), _bytes()
|
||||
AdcNetMessageInterface(size_t reserved = 0) : _reservedNum(reserved), _bytes()
|
||||
{
|
||||
// reserve the "_reservedNum" first elements
|
||||
_bytes.resize(_reservedNum);
|
||||
@@ -220,16 +146,24 @@ protected:
|
||||
|
||||
// Generic message class
|
||||
template <traits::adc_output_char_range ByteStorageT = std::string, traits::adc_char_view ByteViewT = std::string_view>
|
||||
class AdcGenericNetMessage : public AdcNetMessageTrivialInterface<ByteStorageT, ByteViewT>
|
||||
class AdcGenericNetMessage : public AdcNetMessageInterface<ByteStorageT, ByteViewT>
|
||||
{
|
||||
using base_t = AdcNetMessageTrivialInterface<ByteStorageT, ByteViewT>;
|
||||
using base_t = AdcNetMessageInterface<ByteStorageT, ByteViewT>;
|
||||
|
||||
public:
|
||||
using typename base_t::byte_storage_t;
|
||||
using typename base_t::byte_view_t;
|
||||
|
||||
using base_t::base_t;
|
||||
using base_t::bytes;
|
||||
using base_t::bytesView;
|
||||
using base_t::empty;
|
||||
|
||||
AdcGenericNetMessage() : base_t()
|
||||
{
|
||||
// just the single buffer
|
||||
this->_bytes.resize(1);
|
||||
}
|
||||
|
||||
template <typename T, typename... Ts>
|
||||
AdcGenericNetMessage(const T& v, const Ts&... vs) : AdcGenericNetMessage()
|
||||
@@ -241,13 +175,13 @@ public:
|
||||
template <typename T, typename... Ts>
|
||||
void appendBytes(const T& v, const Ts&... vs)
|
||||
{
|
||||
utils::convertToBytes(this->_bytes, v, vs...);
|
||||
utils::convertToBytes(this->_bytes[0], v, vs...);
|
||||
}
|
||||
|
||||
template <typename T, typename... Ts>
|
||||
void setBytes(const T& v, const Ts&... vs)
|
||||
{
|
||||
this->_bytes = ByteStorageT();
|
||||
this->_bytes[0] = ByteStorageT();
|
||||
|
||||
appendBytes(v, vs...);
|
||||
}
|
||||
@@ -257,7 +191,7 @@ public:
|
||||
void appendFromBytes(IT begin, IT end)
|
||||
requires std::same_as<std::iter_value_t<IT>, char>
|
||||
{
|
||||
std::copy(begin, end, std::back_inserter(this->_bytes));
|
||||
std::copy(begin, end, std::back_inserter(this->_bytes[0]));
|
||||
}
|
||||
|
||||
|
||||
@@ -265,7 +199,7 @@ public:
|
||||
void setFromBytes(IT begin, IT end)
|
||||
requires std::same_as<std::iter_value_t<IT>, char>
|
||||
{
|
||||
this->_bytes = ByteStorageT();
|
||||
this->_bytes[0] = ByteStorageT();
|
||||
|
||||
appendFromBytes(begin, end);
|
||||
}
|
||||
@@ -283,10 +217,10 @@ static constexpr char ADC_DEFAULT_KEY_TOKEN_DELIMITER[] = " ";
|
||||
template <const char* TOKEN_DELIM = constants::ADC_DEFAULT_TOKEN_DELIMITER,
|
||||
traits::adc_output_char_range ByteStorageT = std::string,
|
||||
traits::adc_char_view ByteViewT = std::string_view>
|
||||
class AdcTokenNetMessage : public AdcNetMessageSeqInterface<ByteStorageT, ByteViewT>
|
||||
class AdcTokenNetMessage : public AdcNetMessageInterface<ByteStorageT, ByteViewT>
|
||||
{
|
||||
// AdcNetMessageSeqInterface<ByteStorageT, ByteViewT>::_bytes - tokens
|
||||
using base_t = AdcNetMessageSeqInterface<ByteStorageT, ByteViewT>;
|
||||
using base_t = AdcNetMessageInterface<ByteStorageT, ByteViewT>;
|
||||
|
||||
public:
|
||||
static constexpr std::string_view tokenDelimiter{TOKEN_DELIM};
|
||||
@@ -457,7 +391,7 @@ public:
|
||||
using base_t::tokens;
|
||||
|
||||
|
||||
AdcKeyTokenNetMessage()
|
||||
AdcKeyTokenNetMessage() : base_t()
|
||||
{
|
||||
this->_reservedNum = 1; // reserve the first element for keyword
|
||||
this->_bytes.resize(this->_reservedNum);
|
||||
@@ -599,4 +533,29 @@ public:
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
|
||||
namespace traits
|
||||
{
|
||||
|
||||
template <typename T>
|
||||
concept adc_netmessage_c = requires {
|
||||
typename T::byte_storage_t;
|
||||
typename T::byte_view_t;
|
||||
std::derived_from<T, AdcNetMessageInterface<typename T::byte_storage_t, typename T::byte_view_t>>;
|
||||
};
|
||||
// template <typename T, typename IT>
|
||||
// concept adc_netmessage_c = requires(const T t) { // const methods
|
||||
// requires std::same_as<std::iter_value_t<IT>, char>;
|
||||
// { t.empty() } -> std::convertible_to<bool>;
|
||||
// { t.byteSize() } -> std::convertible_to<size_t>;
|
||||
// { t.bytes() } -> adc_output_char_range;
|
||||
// { t.byteView() } -> adc_range_of_view_char_range;
|
||||
// { t.setFromBytes(std::input_iterator<IT>) } -> std::same_as<void>;
|
||||
// };
|
||||
|
||||
} // namespace traits
|
||||
|
||||
|
||||
|
||||
} // namespace adc
|
||||
|
||||
Reference in New Issue
Block a user