Implement reading/writing extra fields in layout and storing in json_value structure, fix bug reading arrays and objects (uninitialized json_value)
parent
2e01bfd30d
commit
95ced0973d
@ -0,0 +1,131 @@
|
||||
#include "../layout.h"
|
||||
|
||||
#include "json/json.h"
|
||||
#include "json/value.h"
|
||||
#include "collections/array.h"
|
||||
|
||||
#include <string.h>
|
||||
|
||||
//#define DEBUG
|
||||
|
||||
#ifdef DEBUG
|
||||
#define DEBUG_printf printf
|
||||
#define DEBUG_fflush fflush
|
||||
#else
|
||||
#define DEBUG_printf(...)
|
||||
#define DEBUG_fflush(...)
|
||||
#endif
|
||||
|
||||
static bool extra_reader( struct json_pull_parser* jpp, void* field_data, struct json_object_field* layout_field_data )
|
||||
{
|
||||
printf( "extra_reader key=%s\n", layout_field_data->key );
|
||||
|
||||
struct json_value* extra = field_data;
|
||||
struct json_object_pair pair = {
|
||||
.key = strdup(layout_field_data->key),
|
||||
.value = {
|
||||
.type = jvt_null
|
||||
},
|
||||
};
|
||||
|
||||
if( !json_pull_parser_read_value( jpp, &pair.value ) ) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if( extra->type != jvt_object ) {
|
||||
json_value_free_composite(extra);
|
||||
}
|
||||
|
||||
extra->type = jvt_object;
|
||||
array_append( &extra->o, sizeof(pair), &pair );
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool json_value_writer( struct json_writer* jw, const char* field_name, void* data, struct json_object_field* layout_field_data )
|
||||
{
|
||||
struct json_value* value = data;
|
||||
|
||||
// Discard layout data
|
||||
layout_field_data = NULL;
|
||||
|
||||
switch( value->type ) {
|
||||
case jvt_null:
|
||||
return false;
|
||||
case jvt_number:
|
||||
json_write_field_name( jw, field_name );
|
||||
fprintf( jw->f, "%g", value->n );
|
||||
return true;
|
||||
case jvt_string:
|
||||
json_write_field_name( jw, field_name );
|
||||
json_write_string( jw->f, value->s );
|
||||
return true;
|
||||
case jvt_array:
|
||||
json_write_field_name( jw, field_name );
|
||||
{
|
||||
fprintf( jw->f, "[" );
|
||||
for( int i = 0; i < value->a.count; ++i ) {
|
||||
if( i > 0 ) {
|
||||
fprintf( jw->f, "," );
|
||||
}
|
||||
|
||||
if( value->a.items[i].type == jvt_null ) {
|
||||
fprintf( jw->f, "null" );
|
||||
} else {
|
||||
json_value_writer( jw, NULL, &value->a.items[i], NULL );
|
||||
}
|
||||
}
|
||||
fprintf( jw->f, "]" );
|
||||
}
|
||||
return true;
|
||||
case jvt_object:
|
||||
json_write_field_name( jw, field_name );
|
||||
{
|
||||
fprintf( jw->f, "{" ); jw->indent += 1;
|
||||
for( int i = 0; i < value->o.count; ++i ) {
|
||||
if( i > 0 ) {
|
||||
fprintf( jw->f, ",\n" );
|
||||
}
|
||||
json_write_indention(jw);
|
||||
json_write_string( jw->f, value->o.items[i].key );
|
||||
fprintf( jw->f, ":" );
|
||||
if( value->o.items[i].value.type == jvt_null ) {
|
||||
fprintf( jw->f, "null" );
|
||||
} else {
|
||||
json_value_writer( jw, NULL, &value->o.items[i].value, NULL );
|
||||
}
|
||||
}
|
||||
fprintf( jw->f, "}" ); jw->indent -= 1;
|
||||
}
|
||||
return true;
|
||||
|
||||
};
|
||||
return false;
|
||||
}
|
||||
static bool extra_writer( struct json_writer* jw, const char* field_name, void* data, struct json_object_field* layout_field_data )
|
||||
{
|
||||
struct json_value* value = data;
|
||||
|
||||
if( value->type != jvt_object ) { return false; }
|
||||
|
||||
for( int i = 0; i < value->o.count; ++i ) {
|
||||
json_write_indention(jw);
|
||||
json_write_string( jw->f, value->o.items[i].key );
|
||||
fprintf( jw->f, ":" );
|
||||
if( value->o.items[i].value.type == jvt_null ) {
|
||||
fprintf( jw->f, "null" );
|
||||
} else {
|
||||
json_value_writer( jw, NULL, &value->o.items[i].value, NULL );
|
||||
}
|
||||
jw->need_comma = true;
|
||||
}
|
||||
jw->need_comma = true;
|
||||
|
||||
return value->o.count > 0;
|
||||
}
|
||||
|
||||
struct json_field_type json_field_extra = {
|
||||
.reader = extra_reader,
|
||||
.writer = extra_writer,
|
||||
};
|
||||
|
Loading…
Reference in new issue