From 9e8361e10a740d038665a6d4f05fd74ae22fdc69 Mon Sep 17 00:00:00 2001 From: alisdair sullivan Date: Wed, 31 Aug 2011 19:35:09 -0700 Subject: [PATCH] incremental test, fixed revealed bug in incomlete implementation --- include/jsx_scanner.hrl | 7 ++++--- src/jsx.erl | 32 +++++++++++++++++++------------- 2 files changed, 23 insertions(+), 16 deletions(-) diff --git a/include/jsx_scanner.hrl b/include/jsx_scanner.hrl index fed4b97..dd48b19 100644 --- a/include/jsx_scanner.hrl +++ b/include/jsx_scanner.hrl @@ -85,13 +85,13 @@ -ifndef(incomplete). -define(incomplete(State, Rest, T, Stack, Opts), {ok, lists:reverse(T), fun(Stream) when is_binary(Stream) -> - State(<>, [], Stack, Opts) + State(<>, [], Stack, Opts) end } ). -define(incomplete(State, Rest, T, Stack, Opts, Acc), - {ok, T, fun(Stream) when is_binary(Stream) -> - State(<>, [], Stack, Opts, Acc) + {ok, lists:reverse(T), fun(Stream) when is_binary(Stream) -> + State(<>, [], Stack, Opts, Acc) end } ). @@ -244,6 +244,7 @@ partial_utf(<>) when X >= 16#f0, X =< 16#f4 -> end; partial_utf(_) -> false. + string(<>, T, [key|_] = Stack, Opts, Acc) -> ?event([{key, lists:reverse(Acc)}], colon, Rest, T, Stack, Opts); string(<>, T, Stack, Opts, Acc) -> diff --git a/src/jsx.erl b/src/jsx.erl index eed0705..d500fe5 100644 --- a/src/jsx.erl +++ b/src/jsx.erl @@ -82,7 +82,12 @@ jsx_decoder_gen([Test|Rest]) -> JSX = proplists:get_value(jsx, Test), Flags = proplists:get_value(jsx_flags, Test, []), {generator, fun() -> - [{Name, ?_assertEqual(decode(JSON, Flags), JSX)} | jsx_decoder_gen(Rest)] + [{Name, ?_assertEqual(decode(JSON, Flags), JSX)}, + {Name ++ " (incremental)", + ?_assertEqual(incremental_decode(JSON, Flags), JSX) + } + | jsx_decoder_gen(Rest) + ] end}. @@ -133,19 +138,20 @@ decode(JSON, Flags) -> incremental_decode(<>, Flags) -> - P = jsx:scanner([iterate] ++ Flags), - incremental_decode_loop(P(C), Rest, []). + P = jsx:scanner(Flags), + try incremental_decode_loop(P(C), Rest, []) + catch error:badarg -> io:format("~p~n", [erlang:get_stacktrace()]), {error, badjson} + end. -incremental_decode_loop({jsx, incomplete, Next}, <<>>, Acc) -> - incremental_decode_loop(Next(end_stream), <<>>, Acc); -incremental_decode_loop({jsx, incomplete, Next}, <>, Acc) -> - incremental_decode_loop(Next(C), Rest, Acc); -incremental_decode_loop({jsx, end_json, _Next}, _Rest, Acc) -> - lists:reverse([end_json] ++ Acc); -incremental_decode_loop({jsx, Event, Next}, Rest, Acc) -> - incremental_decode_loop(Next(), Rest, [Event] ++ Acc); -incremental_decode_loop({error, {badjson, _Error}}, _Rest, _Acc) -> - {error, badjson}. +incremental_decode_loop({ok, X, More}, <<>>, Acc) -> + {ok, Y, _} = More(<<" ">>), %% clear any naked numbers + V = Acc ++ X ++ Y, + case lists:reverse(V) of + [end_json|_] -> V + ; _ -> {error, badjson} + end; +incremental_decode_loop({ok, T, More}, <>, Acc) -> + incremental_decode_loop(More(C), Rest, Acc ++ T). -endif. \ No newline at end of file