feature: json serialize parse to native object
diff --git a/src/dubbo_codec.erl b/src/dubbo_codec.erl
index f2a9301..49c0c38 100644
--- a/src/dubbo_codec.erl
+++ b/src/dubbo_codec.erl
@@ -47,85 +47,27 @@
     Header = << ?DUBBO_MEGIC:16,Header22:8,RequestState:8,RequestId:64,DataLen:32>>,
     Header.
 encode_request_data(?SERIALIZATION_FASTJSON,Request)->
-    dubbo_serializa_fastjson:encode_request_data(Request);
+    dubbo_serializa_json:encode_request_data(Request);
 
 encode_request_data(?SERIALIZATION_HESSIAN,Request)->
-    State=type_encoding:init(),
-    DataType =case Request#dubbo_request.is_event of
-                 true->
-                    dubbo_event;
-                 false->
-                    case Request#dubbo_request.data of
-                       #dubbo_rpc_invocation{} ->
-                           dubbo_rpc_invocation;
-                       _ ->
-                           unknow
-                    end
-             end,
-    {ok,Bin} = encode_request_data(DataType,Request,Request#dubbo_request.data,State),
-    {ok,Bin}.
+    dubbo_serializa_hessian:encode_request_data(Request).
 
-encode_request_data(dubbo_event,Request,Data,State) ->
-    Bin = cotton_hessian:encode(Data,State),
-    {ok,Bin};
-encode_request_data(dubbo_rpc_invocation,Request,Data,State) ->
-    METHOD_NAME = Data#dubbo_rpc_invocation.methodName,
-    METHOD_ARGS_TYPES = Data#dubbo_rpc_invocation.parameterDesc,
-    RequestList = [
-        cotton_hessian:encode(?DUBBO_VERSION, State), %% dubbo version
-        cotton_hessian:encode(Data#dubbo_rpc_invocation.className, State),
-        cotton_hessian:encode(Data#dubbo_rpc_invocation.classVersion, State),
-        cotton_hessian:encode(METHOD_NAME, State),
-        cotton_hessian:encode(METHOD_ARGS_TYPES, State)
-    ],
-    {ArgsBin,State2} = encode_arguments(Data,State),
-    AttachDict = dict:from_list(Data#dubbo_rpc_invocation.attachments),
-    AttachMaps = #map{dict = AttachDict },
-    {AttachBinay,_} = cotton_hessian:encode(AttachMaps, State2),
-    RequestData = erlang:iolist_to_binary(RequestList ++ [ArgsBin,AttachBinay]),
-    {ok,RequestData}.
 
 -spec encode_response(#dubbo_response{})-> {ok,term()}.
 encode_response(Response)->
-    {ok,ResponseData} = encode_response_data(Response),
+    {ok,ResponseData} = encode_response_data(Response#dubbo_response.serialize_type,Response),
     Size = byte_size(ResponseData),
     Header = encode_response_header(Response,Size,?RESPONSE_STATE_OK),
     ResponseContent = <<Header/binary,ResponseData/binary>>,
     {ok, ResponseContent}.
 
-encode_response_data(Response)->
-    State=type_encoding:init(),
-    DataType =case Response#dubbo_response.is_event of
-                  true->
-                      dubbo_event;
-                  false->
-                      case Response#dubbo_response.data of
-                          #dubbo_rpc_invocation{} ->
-                              dubbo_rpc_invocation;
-                          _ ->
-                              unknow
-                      end
-              end,
-    {ok,Bin} = encode_response_data(DataType,Response,Response#dubbo_response.data,State),
-    {ok,Bin}.
-encode_response_data(dubbo_event,Response,Data,State) ->
-    Bin = cotton_hessian:encode(Data,State),
+encode_response_data(?SERIALIZATION_FASTJSON,Response)->
+    {ok,Bin} = dubbo_serializa_json:encode_response_data(Response),
     {ok,Bin};
-encode_response_data(dubbo_rpc_invocation,Response,Data,State) ->
-    Result = case Data of
-        null ->
-            [
-                cotton_hessian:encode(?RESPONSE_NULL_VALUE, State)
-            ];
-        _ ->
-            {ArgsBin,_State2} = encode_arguments(Data,State),
-            [
-                cotton_hessian:encode(?RESPONSE_VALUE, State),
-                ArgsBin
-            ]
-    end,
-    ResponseData = erlang:iolist_to_binary(Result),
-    {ok,ResponseData}.
+encode_response_data(?SERIALIZATION_HESSIAN,Response)->
+
+    {ok,Bin} = dubbo_serializa_hessian:encode_response_data(Response),
+    {ok,Bin}.
 
 encode_response_header(Response,DataLen, ResponseState)->
     Header2= Response#dubbo_response.serialize_type,
@@ -140,20 +82,7 @@
     RequestId = Response#dubbo_response.mid,
     Header = << ?DUBBO_MEGIC:16,Header22:8, ResponseState:8,RequestId:64,DataLen:32>>,
     Header.
-encode_arguments(Data,State)->
-    {StateNew} = lists:foldl(fun(X,{StateTmp})->
-        StateTmpNew = type_encoding:enlist(X,StateTmp),
-        {StateTmpNew} end,
-        {State},Data#dubbo_rpc_invocation.parameterTypes),
-    {Bin,State2} = lists:foldl(fun(X,{BinTmp,StateTmp2})->
-        case cotton_hessian:encode(X, StateTmp2) of
-            {ArgsBin,StateTmpNew} ->
-                {<<BinTmp/binary,ArgsBin/binary>>, StateTmpNew};
-            ArgsBin2 ->
-                {<<BinTmp/binary,ArgsBin2/binary>>, StateTmp2}
-        end end,
-        {<<>>,StateNew},Data#dubbo_rpc_invocation.parameters),
-    {Bin,State2}.
+
 
 -spec decode_header(binary())-> {State::ok|error,Type::request|response,Data::#dubbo_response{}|#dubbo_request{}}.
 decode_header(Header)->
@@ -201,13 +130,13 @@
 decode_response(Res,Data)->
     case Res#dubbo_response.serialize_type of
         ?SERIALIZATION_FASTJSON ->
-            dubbo_serializa_fastjson:decode_response(Res,Data);
+            dubbo_serializa_json:decode_response(Res,Data);
         ?SERIALIZATION_HESSIAN ->
             dubbo_serializa_hessian:decode_response(Res,Data)
     end.
 
 %%decode_response(?SERIALIZATION_FASTJSON,dubbo_rpc_invocation,Res,Data)->
-%%    dubbo_serializa_fastjson:decode_response(dubbo_rpc_invocation,Res,Data);
+%%    dubbo_serializa_json:decode_response(dubbo_rpc_invocation,Res,Data);
 %%
 %%decode_response(?SERIALIZATION_HESSIAN,dubbo_rpc_invocation,Res,Data)->
 %%    {Rest,Type,State} = cotton_hessian:decode(Data,cotton_hessian:init()),
@@ -231,7 +160,7 @@
 decode_request(Req,Data)->
     case Req#dubbo_request.serialize_type of
         ?SERIALIZATION_FASTJSON ->
-            dubbo_serializa_fastjson:decode_request(Req,Data);
+            dubbo_serializa_json:decode_request(Req,Data);
         ?SERIALIZATION_HESSIAN ->
             dubbo_serializa_hessian:decode_request(Req,Data)
     end.
diff --git a/src/dubbo_provider_worker.erl b/src/dubbo_provider_worker.erl
index bf1d8a2..f857a91 100644
--- a/src/dubbo_provider_worker.erl
+++ b/src/dubbo_provider_worker.erl
@@ -184,13 +184,18 @@
                     ok;
                 #dubbo_rpc_invocation{}=ResultInvoca ->
                     #dubbo_request{mid = Mid} = Request,
-                    {ok,Content }= dubbo_codec:encode_response(#dubbo_response{mid=Mid,is_event = false,data= ResultInvoca}),
+                    {ok,Content }=
+                        dubbo_codec:encode_response(#dubbo_response{
+                            serialize_type = Request#dubbo_request.serialize_type,
+                            mid=Mid,
+                            is_event = false,
+                            data= ResultInvoca}),
                     {ok,Content};
                 ResultObj->
 %%                    Data = #databaseOperateResponse{databaseOperateRsp = "ha-ha"},
                     #dubbo_request{mid = Mid} = Request,
                     Data2 =#dubbo_rpc_invocation{parameters = [ResultObj]},
-                    {ok,Content }= dubbo_codec:encode_response(#dubbo_response{mid=Mid,is_event = false,data= Data2}),
+                    {ok,Content }= dubbo_codec:encode_response(#dubbo_response{serialize_type = Request#dubbo_request.serialize_type,mid=Mid,is_event = false,data= Data2}),
                     {ok,Content}
             end;
         {error,Reason}  ->
diff --git a/src/dubbo_serializa_hessian.erl b/src/dubbo_serializa_hessian.erl
index 13fc3fd..927bc82 100644
--- a/src/dubbo_serializa_hessian.erl
+++ b/src/dubbo_serializa_hessian.erl
@@ -14,12 +14,29 @@
 -export([decode_header/1]).
 -export([decode_response/2]).
 -export([decode_request/2]).
+-export([encode_request_data/1,encode_response_data/1]).
 
 
-encode_request_data(dubbo_event,Request,Data,State) ->
+encode_request_data(Request)->
+    State=type_encoding:init(),
+    DataType =case Request#dubbo_request.is_event of
+                  true->
+                      dubbo_event;
+                  false->
+                      case Request#dubbo_request.data of
+                          #dubbo_rpc_invocation{} ->
+                              dubbo_rpc_invocation;
+                          _ ->
+                              unknow
+                      end
+              end,
+    {ok,Bin} = encode_request_data(DataType,Request,Request#dubbo_request.data,State),
+    {ok,Bin}.
+
+encode_request_data(dubbo_event,_Request,Data,State) ->
     Bin = cotton_hessian:encode(Data,State),
     {ok,Bin};
-encode_request_data(dubbo_rpc_invocation,Request,Data,State) ->
+encode_request_data(dubbo_rpc_invocation,_Request,Data,State) ->
     METHOD_NAME = Data#dubbo_rpc_invocation.methodName,
     METHOD_ARGS_TYPES = Data#dubbo_rpc_invocation.parameterDesc,
     RequestList = [
@@ -36,13 +53,6 @@
     RequestData = erlang:iolist_to_binary(RequestList ++ [ArgsBin,AttachBinay]),
     {ok,RequestData}.
 
--spec encode_response(#dubbo_response{})-> {ok,term()}.
-encode_response(Response)->
-    {ok,ResponseData} = encode_response_data(Response),
-    Size = byte_size(ResponseData),
-    Header = encode_response_header(Response,Size,?RESPONSE_STATE_OK),
-    ResponseContent = <<Header/binary,ResponseData/binary>>,
-    {ok, ResponseContent}.
 
 encode_response_data(Response)->
     State=type_encoding:init(),
@@ -59,10 +69,11 @@
               end,
     {ok,Bin} = encode_response_data(DataType,Response,Response#dubbo_response.data,State),
     {ok,Bin}.
-encode_response_data(dubbo_event,Response,Data,State) ->
+
+encode_response_data(dubbo_event,_Response,Data,State) ->
     Bin = cotton_hessian:encode(Data,State),
     {ok,Bin};
-encode_response_data(dubbo_rpc_invocation,Response,Data,State) ->
+encode_response_data(dubbo_rpc_invocation,_Response,Data,State) ->
     Result = case Data of
                  null ->
                      [
@@ -78,19 +89,6 @@
     ResponseData = erlang:iolist_to_binary(Result),
     {ok,ResponseData}.
 
-encode_response_header(Response,DataLen, ResponseState)->
-    Header2= Response#dubbo_response.serialize_type,
-    Header21=case Response#dubbo_response.is_twoway of
-                 true -> Header2 bor 64;
-                 false-> Header2
-             end,
-    Header22=case Response#dubbo_response.is_event of
-                 true -> Header21 bor 32;
-                 false-> Header21
-             end,
-    RequestId = Response#dubbo_response.mid,
-    Header = << ?DUBBO_MEGIC:16,Header22:8, ResponseState:8,RequestId:64,DataLen:32>>,
-    Header.
 encode_arguments(Data,State)->
     {StateNew} = lists:foldl(fun(X,{StateTmp})->
         StateTmpNew = type_encoding:enlist(X,StateTmp),
diff --git a/src/dubbo_serializa_fastjson.erl b/src/dubbo_serializa_json.erl
similarity index 77%
rename from src/dubbo_serializa_fastjson.erl
rename to src/dubbo_serializa_json.erl
index 0c1ed57..fd8a211 100644
--- a/src/dubbo_serializa_fastjson.erl
+++ b/src/dubbo_serializa_json.erl
@@ -6,15 +6,14 @@
 %%% @end
 %%% Created : 11. May 2018 10:07 AM
 %%%-------------------------------------------------------------------
--module(dubbo_serializa_fastjson).
+-module(dubbo_serializa_json).
 -author("dlive").
 
 -include("dubbo.hrl").
 %% API
--export([encode_request_data/1,decode_response/2,decode_request/2]).
+-export([decode_response/2,decode_request/2,decode_header/1,decode_request/2]).
 
--export([decode_header/1]).
--export([decode_request/2]).
+-export([encode_request_data/1,encode_response_data/1]).
 
 encode_request_data(Request)->
     DataType =case Request#dubbo_request.is_event of
@@ -61,16 +60,8 @@
     {ok,Bin}.
 
 
--spec encode_response(#dubbo_response{})-> {ok,term()}.
-encode_response(Response)->
-    {ok,ResponseData} = encode_response_data(Response),
-    Size = byte_size(ResponseData),
-    Header = encode_response_header(Response,Size,?RESPONSE_STATE_OK),
-    ResponseContent = <<Header/binary,ResponseData/binary>>,
-    {ok, ResponseContent}.
-
 encode_response_data(Response)->
-    State=type_encoding:init(),
+    State=#{},
     DataType =case Response#dubbo_response.is_event of
                   true->
                       dubbo_event;
@@ -84,38 +75,27 @@
               end,
     {ok,Bin} = encode_response_data(DataType,Response,Response#dubbo_response.data,State),
     {ok,Bin}.
-encode_response_data(dubbo_event,Response,Data,State) ->
-    Bin = cotton_hessian:encode(Data,State),
+
+encode_response_data(dubbo_event,_Response,Data,State) ->
+    Bin = jiffy:encode(Data,[]),
     {ok,Bin};
-encode_response_data(dubbo_rpc_invocation,Response,Data,State) ->
+encode_response_data(dubbo_rpc_invocation,_Response,Data,State) ->
     Result = case Data of
                  null ->
                      [
-                         cotton_hessian:encode(?RESPONSE_NULL_VALUE, State)
+                         string_encode(?RESPONSE_NULL_VALUE)
                      ];
                  _ ->
                      {ArgsBin,_State2} = encode_arguments(Data,State),
                      [
-                         cotton_hessian:encode(?RESPONSE_VALUE, State),
+                         string_encode(?RESPONSE_VALUE),
+                         ?LINE_SEPERATOR,
                          ArgsBin
                      ]
              end,
     ResponseData = erlang:iolist_to_binary(Result),
     {ok,ResponseData}.
 
-encode_response_header(Response,DataLen, ResponseState)->
-    Header2= Response#dubbo_response.serialize_type,
-    Header21=case Response#dubbo_response.is_twoway of
-                 true -> Header2 bor 64;
-                 false-> Header2
-             end,
-    Header22=case Response#dubbo_response.is_event of
-                 true -> Header21 bor 32;
-                 false-> Header21
-             end,
-    RequestId = Response#dubbo_response.mid,
-    Header = << ?DUBBO_MEGIC:16,Header22:8, ResponseState:8,RequestId:64,DataLen:32>>,
-    Header.
 encode_arguments(Data,State)->
     {Bin} = lists:foldl(
         fun(X,{BinTmp})->
@@ -176,7 +156,7 @@
             decode_response(dubbo_rpc_invocation,Res,Data)
     end.
 decode_response(dubbo_rpc_invocation,Res,Data)->
-    DataList = binary:split(Data,<<"\n">>),
+    DataList = binary:split(Data,<<"\n">>,[global]),
     [TypeBin | DataList1] = DataList,
 %%    {Rest,Type,State} = cotton_hessian:decode(Data,cotton_hessian:init()),
     Type = jiffy:decode(TypeBin),
@@ -185,7 +165,7 @@
         ?RESPONSE_VALUE ->
 %%            {_,Object,DecodeState} = cotton_hessian:decode(Rest,State),
             [Value | _] = DataList1,
-            Object = jiffy:decode(Value),
+            Object = jiffy:decode(Value,[return_maps]),
             {ok,Res#dubbo_response{data = Object}};
         ?RESPONSE_NULL_VALUE ->
             {ok,Res#dubbo_response{data = null}};
@@ -212,9 +192,9 @@
     end.
 
 decode_request(dubbo_rpc_invocation,Req,Data)->
-    {ResultList,NewState,RestData} = decode_request_body(Data,cotton_hessian:init(),[dubbo,path,version,method_name,desc_and_args,attachments]),
+    {ResultList,NewState,RestData} = decode_request_body(Data,#{},[dubbo,path,version,method_name,desc_and_args,attachments]),
     [DubboVersion,Path,Version,MethodName,Desc,ArgsObj,Attachments]=ResultList,
-    RpcData = #dubbo_rpc_invocation{className = Path,classVersion = Version,methodName = MethodName,parameterDesc = Data,parameters = ArgsObj,attachments = Attachments},
+    RpcData = #dubbo_rpc_invocation{className = Path,classVersion = Version,methodName = MethodName,parameterDesc = Desc,parameters = ArgsObj,attachments = Attachments},
     Req2 = Req#dubbo_request{data = RpcData},
     {ok,Req2};
 
@@ -226,7 +206,8 @@
     {ok,Req#dubbo_request{data = Result}}.
 
 decode_request_body(Data,State,List)->
-    DataList = binary:split(Data,<<"\n">>),
+    logger:debug("decode_request_body origin data ~p",[Data]),
+    DataList = binary:split(Data,<<"\n">>,[global]),
     if
         length(DataList) <6 ->
             {error,request_data_error};
@@ -237,10 +218,10 @@
 
 
 
-decode_request_body([ParseType|List],[DataItem | Data],_,ResultList)
+decode_request_body([ParseType|List],[DataItem | Data],State,ResultList)
     when ParseType==dubbo;ParseType==path;ParseType==version;ParseType==method_name ->
-    DecodeData = jiffy:decode(DataItem,[]),
-    decode_request_body(List,Data,_, [DecodeData] ++ ResultList);
+    DecodeData = jiffy:decode(DataItem,[return_maps]),
+    decode_request_body(List,Data,State, [DecodeData] ++ ResultList);
 
 decode_request_body([desc_and_args| List],[DescBin|Data],State,ResultList)->
     ParameterDesc = jiffy:decode(DescBin,[]),
@@ -254,10 +235,10 @@
             {ArgsObjList,NewState,RestData} = decode_request_body_args(ParameterDescArray,Data,State,[]),
             decode_request_body(List,RestData,NewState, [ArgsObjList,ParameterDesc]++ ResultList)
     end;
-decode_request_body([attachments|List],Data,State,ResultList)->
-    {Rest,Attachments,State1 } = cotton_hessian:decode(Data,State),
-    AttachmentsList = dict:to_list(Attachments#map.dict),
-    decode_request_body(List,Rest,State1,[AttachmentsList] ++ ResultList);
+decode_request_body([attachments|List],[DataItem|Data],State,ResultList)->
+    Attachments = jiffy:decode(DataItem,[return_maps]),
+%%    AttachmentsList = dict:to_list(Attachments#map.dict),
+    decode_request_body(List,Data,State,[Attachments] ++ ResultList);
 decode_request_body([_Type1|List],Data,State,ResultList)->
     logger:warning("decode_request_body unknow type"),
     decode_request_body(List,Data,State, ResultList);
@@ -271,12 +252,29 @@
 decode_request_body_args([ArgsType|RestList],Data,State,ArgsObjList) when ArgsType== <<>> ->
     decode_request_body_args(RestList,Data,State,ArgsObjList);
 
-decode_request_body_args([_ArgsType|RestList],Data,State,ArgsObjList) ->
-    {Rest,ArgObj,NewState } = cotton_hessian:decode(Data,State),
-    ArgObj2 = dubbo_type_transfer:classobj_to_native(ArgObj,NewState),
-    decode_request_body_args(RestList,Rest,NewState,ArgsObjList++[ArgObj2]).
+decode_request_body_args([ArgsType|RestList],[DataItem |Data],State,ArgsObjList) ->
+    ArgObj = jiffy:decode(DataItem,[return_maps]),
+%%    {Rest,ArgObj,NewState } = cotton_hessian:decode(Data,State),
+    ArgObj2 = dubbo_type_transfer:jsonobj_to_native(ArgsType,ArgObj,State),
+    decode_request_body_args(RestList,Data,State,ArgsObjList++[ArgObj2]).
 
-string_encode(Data) when is_binary(Data)->
+string_encode(Data) when is_binary(Data) ->
     << <<"\"">>/binary,Data/binary,<<"\"">>/binary >>;
+string_encode(Data) when is_tuple(Data) ->
+    [Name |_] = tuple_to_list(Data),
+%%    Size = record_info(size, Name),
+%%    Fields = record_info(fields, Name),
+    case type_register:lookup_native_type(Name) of
+        undefined ->
+            <<"data encode error">>;
+        #type_def{fieldnames = Fields,foreign_type = _ForeignType} ->
+            logger:debug("string_encode lookup ~p ret ~p",[Name,Fields]),
+            MapValue = lists:foldl(
+                fun({I, E}, Acc) ->
+                    Acc#{E => element(I, Data)}
+                end, #{}, lists:zip(lists:seq(2, length(Fields)+1 ),Fields)),
+            jiffy:encode(MapValue)
+    end;
+
 string_encode(Data)->
     jiffy:encode(Data).