% Licensed under the Apache License, Version 2.0 (the "License"); you may not
% use this file except in compliance with the License. You may obtain a copy of
% the License at
%
%   http://www.apache.org/licenses/LICENSE-2.0
%
% Unless required by applicable law or agreed to in writing, software
% distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
% WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
% License for the specific language governing permissions and limitations under
% the License.

-module(couchdb_mrview_tests).

-include_lib("couch/include/couch_eunit.hrl").
-include_lib("couch/include/couch_db.hrl").



-define(DDOC, {[
    {<<"_id">>, <<"_design/foo">>},
    {<<"shows">>, {[
        {<<"bar">>, <<"function(doc, req) {return '<h1>wosh</h1>';}">>}
    ]}},
    {<<"updates">>, {[
        {<<"report">>, <<"function(doc, req) {"
            "var data = JSON.parse(req.body); "
            "return ['test', data];"
        "}">>}
    ]}},
    {<<"views">>, {[
        {<<"view1">>, {[
            {<<"map">>, <<"function(doc){emit(doc._id, doc._rev)}">>}
        ]}}
    ]}}
]}).

-define(USER, "admin").
-define(PASS, "pass").
-define(AUTH, {basic_auth, {?USER, ?PASS}}).


start() ->
    Ctx = test_util:start_couch([chttpd]),
    ok = config:set("admins", ?USER, ?PASS, _Persist=false),
    Ctx.

setup(PortType) ->
    ok = meck:new(mochiweb_socket, [passthrough]),
    ok = meck:expect(mochiweb_socket, recv, fun mochiweb_socket_recv/3),

    DbName = ?tempdb(),
    ok = create_db(PortType, DbName),

    Host = host_url(PortType),
    upload_ddoc(Host, ?b2l(DbName)),
    {Host, ?b2l(DbName)}.

teardown(Ctx) ->
    ok = config:delete("admins", ?USER, _Persist=false),
    test_util:stop_couch(Ctx).

teardown(PortType, {_Host, DbName}) ->
    (catch meck:unload(mochiweb_socket)),
    delete_db(PortType, ?l2b(DbName)),
    ok.

mrview_show_test_() ->
    {
        "Check show functionality",
        {
            setup,
            fun start/0, fun teardown/1,
            [
                make_test_case(clustered, [fun should_return_invalid_request_body/2]),
                make_test_case(backdoor, [fun should_return_invalid_request_body/2])
            ]
        }
    }.

mrview_query_test_() ->
    {
        "Check view query functionality",
        {
            setup,
            fun start/0, fun teardown/1,
            [
                make_test_case(clustered, [fun should_return_400_for_wrong_order_of_keys/2]),
                make_test_case(backdoor, [fun should_return_400_for_wrong_order_of_keys/2])
            ]
        }
    }.

make_test_case(Mod, Funs) ->
    {
        lists:flatten(io_lib:format("~s", [Mod])),
        {foreachx, fun setup/1, fun teardown/2, [{Mod, Fun} || Fun <- Funs]}
    }.

should_return_invalid_request_body(PortType, {Host, DbName}) ->
    ?_test(begin
         ok = create_doc(PortType, ?l2b(DbName), <<"doc_id">>, {[]}),
         ReqUrl = Host ++ "/" ++ DbName ++ "/_design/foo/_update/report/doc_id",
         {ok, Status, _Headers, Body} =
              test_request:post(ReqUrl, [?AUTH], <<"{truncated}">>),
         {Props} = jiffy:decode(Body),
         ?assertEqual(
            <<"bad_request">>, couch_util:get_value(<<"error">>, Props)),
         ?assertEqual(
            <<"Invalid request body">>, couch_util:get_value(<<"reason">>, Props)),
         ?assertEqual(400, Status),
         ok
    end).

should_return_400_for_wrong_order_of_keys(_PortType, {Host, DbName}) ->
    Args = [{start_key, "\"bbb\""}, {end_key, "\"aaa\""}],
    ?_test(begin
         ReqUrl = Host ++ "/" ++ DbName
              ++ "/_design/foo/_view/view1?" ++ mochiweb_util:urlencode(Args),
         {ok, Status, _Headers, Body} = test_request:get(ReqUrl, [?AUTH]),
         {Props} = jiffy:decode(Body),
         ?assertEqual(
            <<"query_parse_error">>, couch_util:get_value(<<"error">>, Props)),
         ?assertEqual(
            <<"No rows can match your key range, reverse your start_key and end_key or set descending=true">>,
            couch_util:get_value(<<"reason">>, Props)),
         ?assertEqual(400, Status),
         ok
    end).

create_doc(backdoor, DbName, Id, Body) ->
    JsonDoc = couch_util:json_apply_field({<<"_id">>, Id}, Body),
    Doc = couch_doc:from_json_obj(JsonDoc),
    {ok, Db} = couch_db:open(DbName, [?ADMIN_CTX]),
    {ok, _} = couch_db:update_docs(Db, [Doc]),
    couch_db:ensure_full_commit(Db),
    couch_db:close(Db);
create_doc(clustered, DbName, Id, Body) ->
    JsonDoc = couch_util:json_apply_field({<<"_id">>, Id}, Body),
    Doc = couch_doc:from_json_obj(JsonDoc),
    {ok, _} = fabric:update_docs(DbName, [Doc], [?ADMIN_CTX]),
    ok.

create_db(backdoor, DbName) ->
    {ok, Db} = couch_db:create(DbName, [?ADMIN_CTX]),
    couch_db:close(Db);
create_db(clustered, DbName) ->
    {ok, Status, _, _} = test_request:put(db_url(DbName), [?AUTH], ""),
    assert_success(create_db, Status),
    ok.

delete_db(backdoor, DbName) ->
    couch_server:delete(DbName, [?ADMIN_CTX]);
delete_db(clustered, DbName) ->
    {ok, Status, _, _} = test_request:delete(db_url(DbName), [?AUTH]),
    assert_success(delete_db, Status),
    ok.

assert_success(create_db, Status) ->
    ?assert(lists:member(Status, [201, 202]));
assert_success(delete_db, Status) ->
    ?assert(lists:member(Status, [200, 202])).


host_url(PortType) ->
    "http://" ++ bind_address(PortType) ++ ":" ++ port(PortType).

bind_address(PortType) ->
    config:get(section(PortType), "bind_address", "127.0.0.1").

section(backdoor) -> "http";
section(clustered) -> "chttpd".

db_url(DbName) when is_binary(DbName) ->
    db_url(binary_to_list(DbName));
db_url(DbName) when is_list(DbName) ->
    host_url(clustered) ++ "/" ++ DbName.

port(clustered) ->
    integer_to_list(mochiweb_socket_server:get(chttpd, port));
port(backdoor) ->
    integer_to_list(mochiweb_socket_server:get(couch_httpd, port)).


upload_ddoc(Host, DbName) ->
    Url = Host ++ "/" ++ DbName ++ "/_design/foo",
    Body = couch_util:json_encode(?DDOC),
    {ok, 201, _Resp, _Body} = test_request:put(Url, [?AUTH], Body),
    ok.

mochiweb_socket_recv(Sock, Len, Timeout) ->
    case meck:passthrough([Sock, Len, Timeout]) of
        {ok, <<"{truncated}">>} ->
            {error, closed};
        {ok, Data} ->
            {ok, Data};
        Else ->
            Else
    end.
