Repository navigation
Replies: 6 comments
|
The binding with getters and setters is implemented, and generally working, however I'm not quite sure this is the right solution to your problem. I'm assuming that "bind an object with an enum type" refers to an object with a member variable of enum type? Using getters and setters is to provide access to member variables that are not public, or when there are other reasons (e.g. class invariants) that go beyond directly accessing a public member variable. The translation from strings to enum values should be performed in the traits for the enum type, then you don't need any special tricks with the binding, and you don't need to write additional getters and setters for every instance of such an enum because once the traits know about your enum type it will work in every context. That is why I would advise against doing the conversions in getters and setters, even though that is possible, and put them into the traits where they rightfully belong (according to our current understanding of our current design...), and only use getters and setters to resolve issues of accessing a value. Does this make sense? Do you need any help with implementing the traits for your enum? Unfortunately using |
|
thanks for your feedback. I thought it would make more sense to expose the enum to json. A quick pointer on how to do this would be highly appreciated. I have a structure similar to: enum Type{
A,
B
};
struct Foo{
Type type;
}
|
|
The first step is to add traits for #include <iostream>
#include <tao/json.hpp>
enum Type
{
A,
B
};
struct Foo
{
Type type;
};
template< typename T > struct traits
: tao::json::traits< T >
{};
template<> struct traits< Type >
{
template< template< typename... > class Traits, typename Consumer >
static void produce( Consumer& c, const Type t )
{
switch( t ) {
case Type::A:
c.string( "A" );
return;
case Type::B:
c.string( "B" );
return;
}
assert( false );
}
template< template< typename... > class Traits, typename Producer >
static Type consume( Producer& p )
{
const std::string s = p.string();
if( s == "A" ) {
return Type::A;
}
if( s == "B" ) {
return Type::B;
}
p.throw_parse_error( "incorrect value for Type: " + s );
assert( false );
}
// Also implement assign(), and as() or to(), to enable conversion
// between tao::basic_value< traits > and Type.
};
template<> struct traits< Foo >
: tao::json::binding::object< TAO_JSON_BIND_REQUIRED( "type", &Foo::type ) >
{};
using json_value = tao::json::basic_value< traits >;
int main( int, char** )
{
// Use consume, consume_string or consume_file to build a Foo:
const Foo foo = tao::json::consume_string< Foo, traits >( "{ \"type\" : \"B\" }" );
assert( foo.type == Type::B );
// Use one of the produce functions to serialise back to JSON:
tao::json::produce::to_stream< traits >( std::cout, foo, 3 ); // 3 is indend for pretty-printing
std::cout << std::endl;
// Alternatively convert to json_value via producing Events:
const json_value value = tao::json::produce::to_value< traits >( foo );
tao::json::to_stream( std::cout, value, 3 ); // Will output the same as above.
std::cout << std::endl;
return 0;
} |
|
I should add that in the example |
|
thank you! would be great to have some more "real world" code recipes in the docs. |
Definitely coming for 1.0, in the docs and/or in |
Uh oh!
There was an error while loading. Please reload this page.
The docs mention binding traits with getters and setters. https://github.com/taocpp/json/blob/master/doc/Binding-Traits.md#indirect
Is that already implemented but not documented or is this feature missing?
I have this use case where i try bind an object with an enum type. I'd like to be able to write the type name as a string in the json file, but then translate it to the correct enum value on the object. would this be the way to go?
All reactions