Tweak FC enum reflection

Previously when enum values not defined in the original enum type were
used in serialized objects, FC threw exceptions when it encountered
these values. Now it just serializes unknown values to and from numbers
instead of names.

As an added benefit, the compiler now warns you if a value is defined in
the enum, but not reflected!
This commit is contained in:
Nathan Hourt 2014-10-31 16:30:18 -04:00
parent 95c2c461ac
commit 72088c548b
2 changed files with 17 additions and 13 deletions

View file

@ -114,6 +114,8 @@ void fc::reflector<TYPE>::visit( const Visitor& v ) { \
v.TEMPLATE operator()<enum_type::elem>(BOOST_PP_STRINGIZE(elem));
#define FC_REFLECT_ENUM_TO_STRING( r, enum_type, elem ) \
case enum_type::elem: return BOOST_PP_STRINGIZE(elem);
#define FC_REFLECT_ENUM_TO_FC_STRING( r, enum_type, elem ) \
case enum_type::elem: return fc::string(BOOST_PP_STRINGIZE(elem));
#define FC_REFLECT_ENUM_FROM_STRING( r, enum_type, elem ) \
if( strcmp( s, BOOST_PP_STRINGIZE(elem) ) == 0 ) return enum_type::elem;
@ -124,14 +126,6 @@ namespace fc { \
template<> struct reflector<ENUM> { \
typedef fc::true_type is_defined; \
typedef fc::true_type is_enum; \
static const char* to_string(int64_t i) { \
switch( ENUM(i) ) { \
BOOST_PP_SEQ_FOR_EACH( FC_REFLECT_ENUM_TO_STRING, ENUM, FIELDS ) \
default: \
fc::throw_bad_enum_cast( i, BOOST_PP_STRINGIZE(ENUM) ); \
}\
return nullptr; \
} \
static const char* to_string(ENUM elem) { \
switch( elem ) { \
BOOST_PP_SEQ_FOR_EACH( FC_REFLECT_ENUM_TO_STRING, ENUM, FIELDS ) \
@ -140,10 +134,21 @@ template<> struct reflector<ENUM> { \
}\
return nullptr; \
} \
static const char* to_string(int64_t i) { \
return to_string(ENUM(i)); \
} \
static fc::string to_fc_string(ENUM elem) { \
switch( elem ) { \
BOOST_PP_SEQ_FOR_EACH( FC_REFLECT_ENUM_TO_FC_STRING, ENUM, FIELDS ) \
} \
return fc::to_string(int64_t(elem)); \
} \
static fc::string to_fc_string(int64_t i) { \
return to_fc_string(ENUM(i)); \
} \
static ENUM from_string( const char* s ) { \
BOOST_PP_SEQ_FOR_EACH( FC_REFLECT_ENUM_FROM_STRING, ENUM, FIELDS ) \
fc::throw_bad_enum_cast( s, BOOST_PP_STRINGIZE(ENUM) ); \
return ENUM();\
return ENUM(atoi(s));\
} \
}; \
}

View file

@ -70,7 +70,7 @@ namespace fc
template<typename T>
static inline void to_variant( const T& o, fc::variant& v )
{
v = fc::reflector<T>::to_string(o);
v = fc::reflector<T>::to_fc_string(o);
}
template<typename T>
static inline void from_variant( const fc::variant& v, T& o )
@ -78,8 +78,7 @@ namespace fc
if( v.is_string() )
o = fc::reflector<T>::from_string( v.get_string().c_str() );
else
// throw if invalid int, by attempting to convert to string
fc::reflector<T>::to_string( o = static_cast<T>(v.as_int64()) );
o = static_cast<T>(v.as_int64());
}
};