|
From: Dean M. B. <mik...@gm...> - 2010-08-20 10:03:35
|
I found one good hack to make the directives more generic and more
tied into the async-friendly messages. I've implemented it locally and
am in the process of gutting every directive we've ever written (I
really need to learn preprocessor metaprogramming at some point to
make this easier).
The basic pattern is this:
struct directive {
boost::variant<
string<tags::default_string>::type,
string<tags::default_wstring>::type,
boost::shared_future<string<tags::default_string>::type>,
boost::shared_future<string<tags::default_wstring>::type>
> value_;
directive(string<tags::default_string>::type const & value)
: value_(value) {}
directive(string<tags::default_wstring>::type const & value)
: value_(value) {}
directive(boost::shared_future<string<tags::default_string>::type>
const & value)
: value_(value) {}
directive(boost::shared_future<string<tags::default_wstring>::type>
const & value)
: value_(value) {}
template <class Tag>
struct value :
mpl::if_<
is_async<Tag>,
boost::shared_future<typename string<Tag>::type>,
typename mpl::if_<
is_sync<Tag>,
typename string<Tag>::type,
unsupported_tag<Tag>
>::type
>
{};
template <class Tag, class Message>
struct value_visitor : boost::static_visitor<> {
Message const & message_;
value_visitor(Message const & message)
: message_(message) {}
void operator() (typename value<Tag>::type const & value) const {
message_.value(value);
}
template <class T> void operator() (T const &) const {
// FIXME -- fail here somehow at compile time
}
};
template <class Message>
Message & operator() (Message const & message) const {
apply_visitor(value_visitor<typename Message::tag,
Message>(message), value_);
return message;
}
};
So yeah, the idea is metaprogramming technically saves the day... :)
Expect a few changes (well, technically a lot of changes ;) ) to come
into the branch.
Have a good one guys, and it's good to be programming C++ again. :D
--
Dean Michael Berris
deanberris.com
|