/src/jsonerl.hrl
Erlang | 72 lines | 56 code | 4 blank | 12 comment | 1 complexity | f1f23ac649e60f716a4b36ce3ccf50db MD5 | raw file
1-define(record_to_struct(RecordName, Record), 2 % we are zipping record's field names and corresponding values together 3 % then we turn it into tuple resulting in *struct* - erlang's equivalent of json's *object* 4 list_to_tuple( 5 lists:zip( 6 lists:map(fun(F) -> list_to_binary(atom_to_list(F)) end, record_info(fields, RecordName)), 7 lists:map( 8 %% convention record's *undefined* value is represented as json's *null* 9 fun(undefined) -> null; 10 (E) -> E 11 end, 12 %% we are turning the record into list chopping its head (record name) off 13 tl(tuple_to_list(Record)) 14 ) 15 ) 16 ) 17). 18 19-define(struct_to_record(RecordName, Struct), 20 % I use fun here in order to avoid possible variable collison by shaddowing them 21 fun(ValuesByFieldsDict) -> 22 % construct the tuple being the proper record from the struct 23 list_to_tuple( 24 %% first element in the tuple is record name 25 [RecordName] ++ 26 lists:map( 27 %% convention: json's *null* represents record's *undefined* value 28 fun(Field) -> 29 case dict:find(Field, ValuesByFieldsDict) of 30 {ok, Value} -> Value; 31 error -> undefined 32 end 33 end, 34 % getting the record field names in the order the tuple representing the record instance has its values 35 record_info(fields, RecordName) 36 ) 37 ) 38 end( 39 % create quickly accessible maping of struct values by its keys turned to atoms, as it is in records. 40 lists:foldl( 41 fun({K, V}, Dict) -> 42 dict:store(jsonerl:to_ex_a(K), V, Dict) 43 end, 44 dict:new(), 45 tuple_to_list(Struct) 46 ) 47 ) 48). 49 50-define(record_to_json(RecordName, Record), 51 % serialize erlang struct into json string 52 jsonerl:encode(?record_to_struct(RecordName, Record)) 53). 54 55-define(list_records_to_json(RecordName, List), 56 L___ = length(List), 57 Zipped___ = lists:zip(lists:seq(1,L___),List), 58 Quotes___ = lists:map( 59 fun({N___,X___}) -> 60 case L___ == N___ of 61 false -> 62 Json___ = jsonerl:encode(?record_to_struct(RecordName,X___)), 63 Json___ ++ ","; 64 true -> jsonerl:encode(?record_to_struct(RecordName,X___)) 65 end 66 end, Zipped___), 67 lists:flatten(io_lib:format("~s",["["++Quotes___++"]"]))). 68 69-define(json_to_record(RecordName, Json), 70 % decode json text to erlang struct 71 ?struct_to_record(RecordName, jsonerl:decode(Json)) 72).