diff options
author | Robert Newson <rnewson@apache.org> | 2018-07-04 17:27:10 +0100 |
---|---|---|
committer | Robert Newson <rnewson@apache.org> | 2018-07-10 15:30:14 +0100 |
commit | 38245dd55c830c7a436a1b6abad4e1d2d27f69d8 (patch) | |
tree | 25cacd085079859495a6b2ea998b150645bce6dd | |
parent | 2b63513f50a364a196e3e5ba9ceb8b325cfd4517 (diff) | |
download | couchdb-38245dd55c830c7a436a1b6abad4e1d2d27f69d8.tar.gz |
Extract side-effect free part of validate_args
validate_args/1 also modified the arguments. By separating the
validation from the update we are able to add updates that are not
idempotent.
-rw-r--r-- | src/chttpd/src/chttpd_db.erl | 4 | ||||
-rw-r--r-- | src/chttpd/src/chttpd_view.erl | 2 | ||||
-rw-r--r-- | src/couch_mrview/src/couch_mrview.erl | 2 | ||||
-rw-r--r-- | src/couch_mrview/src/couch_mrview_http.erl | 2 | ||||
-rw-r--r-- | src/couch_mrview/src/couch_mrview_util.erl | 25 | ||||
-rw-r--r-- | src/couch_mrview/test/couch_mrview_util_tests.erl | 2 | ||||
-rw-r--r-- | src/couch_replicator/src/couch_replicator_httpd.erl | 2 | ||||
-rw-r--r-- | src/fabric/src/fabric.erl | 2 |
8 files changed, 26 insertions, 15 deletions
diff --git a/src/chttpd/src/chttpd_db.erl b/src/chttpd/src/chttpd_db.erl index ed0adead9..bf1fe8c3b 100644 --- a/src/chttpd/src/chttpd_db.erl +++ b/src/chttpd/src/chttpd_db.erl @@ -663,7 +663,7 @@ multi_all_docs_view(Req, Db, OP, Queries) -> ArgQueries = lists:map(fun({Query}) -> QueryArg1 = couch_mrview_http:parse_params(Query, undefined, Args1, [decoded]), - QueryArgs2 = couch_mrview_util:validate_args(QueryArg1), + QueryArgs2 = couch_mrview_util:validate_and_update_args(QueryArg1), set_namespace(OP, QueryArgs2) end, Queries), Options = [{user_ctx, Req#httpd.user_ctx}], @@ -683,7 +683,7 @@ multi_all_docs_view(Req, Db, OP, Queries) -> all_docs_view(Req, Db, Keys, OP) -> Args0 = couch_mrview_http:parse_params(Req, Keys), Args1 = Args0#mrargs{view_type=map}, - Args2 = couch_mrview_util:validate_args(Args1), + Args2 = couch_mrview_util:validate_and_update_args(Args1), Args3 = set_namespace(OP, Args2), Options = [{user_ctx, Req#httpd.user_ctx}], Max = chttpd:chunked_response_buffer_size(), diff --git a/src/chttpd/src/chttpd_view.erl b/src/chttpd/src/chttpd_view.erl index 3c05c64ca..799df61b4 100644 --- a/src/chttpd/src/chttpd_view.erl +++ b/src/chttpd/src/chttpd_view.erl @@ -24,7 +24,7 @@ multi_query_view(Req, Db, DDoc, ViewName, Queries) -> QueryArg = couch_mrview_http:parse_params(Query, undefined, Args1, [decoded]), QueryArg1 = couch_mrview_util:set_view_type(QueryArg, ViewName, Views), - couch_mrview_util:validate_args(QueryArg1) + couch_mrview_util:validate_and_update_args(QueryArg1) end, Queries), Options = [{user_ctx, Req#httpd.user_ctx}], VAcc0 = #vacc{db=Db, req=Req, prepend="\r\n"}, diff --git a/src/couch_mrview/src/couch_mrview.erl b/src/couch_mrview/src/couch_mrview.erl index 82bbd7928..a9d5d0ad1 100644 --- a/src/couch_mrview/src/couch_mrview.erl +++ b/src/couch_mrview/src/couch_mrview.erl @@ -223,7 +223,7 @@ query_all_docs(Db, Args0, Callback, Acc) -> couch_index_util:hexsig(crypto:hash(md5, term_to_binary(Info))) end), Args1 = Args0#mrargs{view_type=map}, - Args2 = couch_mrview_util:validate_args(Args1), + Args2 = couch_mrview_util:validate_and_update_args(Args1), {ok, Acc1} = case Args2#mrargs.preflight_fun of PFFun when is_function(PFFun, 2) -> PFFun(Sig, Acc); _ -> {ok, Acc} diff --git a/src/couch_mrview/src/couch_mrview_http.erl b/src/couch_mrview/src/couch_mrview_http.erl index 004caef09..9dae1d86c 100644 --- a/src/couch_mrview/src/couch_mrview_http.erl +++ b/src/couch_mrview/src/couch_mrview_http.erl @@ -296,7 +296,7 @@ multi_query_view(Req, Db, DDoc, ViewName, Queries) -> {ok, _, _, Args1} = couch_mrview_util:get_view(Db, DDoc, ViewName, Args0), ArgQueries = lists:map(fun({Query}) -> QueryArg = parse_params(Query, undefined, Args1), - couch_mrview_util:validate_args(QueryArg) + couch_mrview_util:validate_and_update_args(QueryArg) end, Queries), {ok, Resp2} = couch_httpd:etag_maybe(Req, fun() -> Max = chttpd:chunked_response_buffer_size(), diff --git a/src/couch_mrview/src/couch_mrview_util.erl b/src/couch_mrview/src/couch_mrview_util.erl index eb461d017..086bf9bbf 100644 --- a/src/couch_mrview/src/couch_mrview_util.erl +++ b/src/couch_mrview/src/couch_mrview_util.erl @@ -24,7 +24,7 @@ -export([temp_view_to_ddoc/1]). -export([calculate_external_size/1]). -export([calculate_active_size/1]). --export([validate_args/1]). +-export([validate_and_update_args/1]). -export([maybe_load_doc/3, maybe_load_doc/4]). -export([maybe_update_index_file/1]). -export([extract_view/4, extract_view_reduce/1]). @@ -59,7 +59,7 @@ get_view(Db, DDoc, ViewName, Args0) -> get_view_index_pid(Db, DDoc, ViewName, Args0) -> ArgCheck = fun(InitState) -> Args1 = set_view_type(Args0, ViewName, InitState#mrst.views), - {ok, validate_args(Args1)} + {ok, validate_and_update_args(Args1)} end, couch_index_server:get_index(?MOD, Db, DDoc, ArgCheck). @@ -546,6 +546,17 @@ validate_args(Args) -> {red, _} -> mrverror(<<"`conflicts` is invalid for reduce views.">>) end, + case is_boolean(Args#mrargs.sorted) of + true -> ok; + _ -> mrverror(<<"Invalid value for `sorted`.">>) + end, + + true. + + +update_args(#mrargs{} = Args) -> + GroupLevel = determine_group_level(Args), + SKDocId = case {Args#mrargs.direction, Args#mrargs.start_key_docid} of {fwd, undefined} -> <<>>; {rev, undefined} -> <<255>>; @@ -558,11 +569,6 @@ validate_args(Args) -> {_, EKDocId1} -> EKDocId1 end, - case is_boolean(Args#mrargs.sorted) of - true -> ok; - _ -> mrverror(<<"Invalid value for `sorted`.">>) - end, - Args#mrargs{ start_key_docid=SKDocId, end_key_docid=EKDocId, @@ -570,6 +576,11 @@ validate_args(Args) -> }. +validate_and_update_args(#mrargs{} = Args) -> + true = validate_args(Args), + update_args(Args). + + determine_group_level(#mrargs{group=undefined, group_level=undefined}) -> 0; determine_group_level(#mrargs{group=false, group_level=undefined}) -> diff --git a/src/couch_mrview/test/couch_mrview_util_tests.erl b/src/couch_mrview/test/couch_mrview_util_tests.erl index 7046c9bb2..df50187fc 100644 --- a/src/couch_mrview/test/couch_mrview_util_tests.erl +++ b/src/couch_mrview/test/couch_mrview_util_tests.erl @@ -34,6 +34,6 @@ couch_mrview_util_test_() -> validate_group_level(Group, GroupLevel) -> Args0 = #mrargs{group=Group, group_level=GroupLevel, view_type=red}, - Args1 = couch_mrview_util:validate_args(Args0), + Args1 = couch_mrview_util:validate_and_update_args(Args0), Args1#mrargs.group_level. diff --git a/src/couch_replicator/src/couch_replicator_httpd.erl b/src/couch_replicator/src/couch_replicator_httpd.erl index abd9f7fd0..f37d4364d 100644 --- a/src/couch_replicator/src/couch_replicator_httpd.erl +++ b/src/couch_replicator/src/couch_replicator_httpd.erl @@ -124,7 +124,7 @@ handle_scheduler_docs(Db, Req) when is_binary(Db) -> reduce = false, extra = [{filter_states, States}] }, - VArgs2 = couch_mrview_util:validate_args(VArgs1), + VArgs2 = couch_mrview_util:validate_and_update_args(VArgs1), Opts = [{user_ctx, Req#httpd.user_ctx}], Max = chttpd:chunked_response_buffer_size(), Acc = couch_replicator_httpd_util:docs_acc_new(Req, Db, Max), diff --git a/src/fabric/src/fabric.erl b/src/fabric/src/fabric.erl index 4a0727131..1b761abf3 100644 --- a/src/fabric/src/fabric.erl +++ b/src/fabric/src/fabric.erl @@ -355,7 +355,7 @@ query_view(DbName, Options, DDoc, ViewName, Callback, Acc0, QueryArgs0) -> {ok, #mrst{views=Views, language=Lang}} = couch_mrview_util:ddoc_to_mrst(Db, DDoc), QueryArgs1 = couch_mrview_util:set_view_type(QueryArgs0, View, Views), - QueryArgs2 = couch_mrview_util:validate_args(QueryArgs1), + QueryArgs2 = couch_mrview_util:validate_and_update_args(QueryArgs1), VInfo = couch_mrview_util:extract_view(Lang, QueryArgs2, View, Views), case is_reduce_view(QueryArgs2) of true -> |