% 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(chttpd_auth_cache).
-behaviour(gen_server).

-export([start_link/0, get_user_creds/2, update_user_creds/3]).
-export([init/1, handle_call/3, handle_cast/2, handle_info/2, terminate/2,
	 code_change/3]).
-export([listen_for_changes/1, changes_callback/2]).

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

-define(CACHE, chttpd_auth_cache_lru).

-record(state, {
    changes_pid,
    last_seq="0"
}).

%% public functions

start_link() ->
    gen_server:start_link({local, ?MODULE}, ?MODULE, [], []).

get_user_creds(Req, UserName) when is_list(UserName) ->
    get_user_creds(Req, ?l2b(UserName));
get_user_creds(_Req, UserName) when is_binary(UserName) ->
    Resp = case couch_auth_cache:get_admin(UserName) of
    nil ->
        get_from_cache(UserName);
    Props ->
        case get_from_cache(UserName) of
        nil ->
            Props;
        UserProps when is_list(UserProps) ->
            couch_auth_cache:add_roles(Props,
	        couch_util:get_value(<<"roles">>, UserProps))
        end
    end,
    maybe_validate_user_creds(Resp).

update_user_creds(_Req, UserDoc, _Ctx) ->
    {_, Ref} = spawn_monitor(fun() ->
        case fabric:update_doc(dbname(), UserDoc, []) of
            {ok, _} ->
                exit(ok);
            Else ->
                exit(Else)
        end
    end),
    receive
        {'DOWN', Ref, _, _, ok} ->
            ok;
        {'DOWN', Ref, _, _, Else} ->
            Else
    end.

get_from_cache(UserName) ->
    try ets_lru:lookup_d(?CACHE, UserName) of
        {ok, Props} ->
            couch_stats:increment_counter([couchdb, auth_cache_hits]),
            couch_log:debug("cache hit for ~s", [UserName]),
            Props;
        _ ->
            couch_stats:increment_counter([couchdb, auth_cache_misses]),
            couch_log:debug("cache miss for ~s", [UserName]),
            case load_user_from_db(UserName) of
                nil ->
                    nil;
                Props ->
                    ets_lru:insert(?CACHE, UserName, Props),
                    Props
            end
    catch
        error:badarg ->
            couch_stats:increment_counter([couchdb, auth_cache_misses]),
            couch_log:debug("cache miss for ~s", [UserName]),
            load_user_from_db(UserName)
    end.

%% gen_server callbacks

init([]) ->
    self() ! {start_listener, 0},
    {ok, #state{}}.

handle_call(_Call, _From, State) ->
    {noreply, State}.

handle_cast(_Msg, State) ->
    {noreply, State}.

handle_info({'DOWN', _, _, Pid, Reason}, #state{changes_pid=Pid} = State) ->
    Seq = case Reason of
        {seq, EndSeq} ->
            EndSeq;
        _ ->
            couch_log:notice("~p changes listener died ~r", [?MODULE, Reason]),
            0
    end,
    erlang:send_after(5000, self(), {start_listener, Seq}),
    {noreply, State#state{last_seq=Seq}};
handle_info({start_listener, Seq}, State) ->
    {noreply, State#state{changes_pid = spawn_changes(Seq)}};
handle_info(_Msg, State) ->
    {noreply, State}.

terminate(_Reason, #state{changes_pid = Pid}) when is_pid(Pid) ->
    exit(Pid, kill);
terminate(_Reason, _State) ->
    ok.

code_change(_OldVsn, #state{}=State, _Extra) ->
    {ok, State}.

%% private functions

spawn_changes(Since) ->
    {Pid, _} = spawn_monitor(?MODULE, listen_for_changes, [Since]),
    Pid.

listen_for_changes(Since) ->
    ensure_auth_ddoc_exists(dbname(), <<"_design/_auth">>),
    CBFun = fun ?MODULE:changes_callback/2,
    Args = #changes_args{
        feed = "continuous",
        since = Since,
        heartbeat = true,
        filter = {default, main_only}
    },
    fabric:changes(dbname(), CBFun, Since, Args).

changes_callback(waiting_for_updates, Acc) ->
    {ok, Acc};
changes_callback(start, Since) ->
    {ok, Since};
changes_callback({stop, EndSeq, _Pending}, _) ->
    exit({seq, EndSeq});
changes_callback({change, {Change}}, _) ->
    case couch_util:get_value(id, Change) of
        <<"_design/", _/binary>> ->
            ok;
        DocId ->
            UserName = username(DocId),
            couch_log:debug("Invalidating cached credentials for ~s", [UserName]),
            ets_lru:remove(?CACHE, UserName)
    end,
    {ok, couch_util:get_value(seq, Change)};
changes_callback(timeout, Acc) ->
    {ok, Acc};
changes_callback({error, _}, EndSeq) ->
    exit({seq, EndSeq}).

load_user_from_db(UserName) ->
    try fabric:open_doc(dbname(), docid(UserName), [?ADMIN_CTX, ejson_body, conflicts]) of
	{ok, Doc} ->
	    {Props} = couch_doc:to_json_obj(Doc, []),
	    Props;
	_Else ->
	    couch_log:debug("no record of user ~s", [UserName]),
	    nil
    catch error:database_does_not_exist ->
	    nil
    end.

dbname() ->
    config:get("chttpd_auth", "authentication_db", "_users").

docid(UserName) ->
    <<"org.couchdb.user:", UserName/binary>>.

username(<<"org.couchdb.user:", UserName/binary>>) ->
    UserName.

ensure_auth_ddoc_exists(DbName, DDocId) ->
    case fabric:open_doc(DbName, DDocId, [?ADMIN_CTX, ejson_body]) of
    {not_found, _Reason} ->
        {ok, AuthDesign} = couch_auth_cache:auth_design_doc(DDocId),
        update_doc_ignoring_conflict(DbName, AuthDesign, [?ADMIN_CTX]);
    {ok, Doc} ->
        {Props} = couch_doc:to_json_obj(Doc, []),
        case couch_util:get_value(<<"validate_doc_update">>, Props, []) of
            ?AUTH_DB_DOC_VALIDATE_FUNCTION ->
                ok;
            _ ->
                Props1 = lists:keyreplace(<<"validate_doc_update">>, 1, Props,
                    {<<"validate_doc_update">>,
                    ?AUTH_DB_DOC_VALIDATE_FUNCTION}),
                update_doc_ignoring_conflict(DbName, couch_doc:from_json_obj({Props1}), [?ADMIN_CTX])
        end;
    {error, Reason} ->
        couch_log:notice("Failed to ensure auth ddoc ~s/~s exists for reason: ~p", [DbName, DDocId, Reason]),
        ok
    end,
    ok.

update_doc_ignoring_conflict(DbName, Doc, Options) ->
    try
        fabric:update_doc(DbName, Doc, Options)
    catch
        throw:conflict ->
            ok
    end.

maybe_validate_user_creds(nil) ->
    nil;
% throws if UserCreds includes a _conflicts member
% returns UserCreds otherwise
maybe_validate_user_creds(UserCreds) ->
    AllowConflictedUserDocs = config:get_boolean("chttpd_auth", "allow_conflicted_user_docs", false),
    case {couch_util:get_value(<<"_conflicts">>, UserCreds), AllowConflictedUserDocs} of
        {undefined, _} ->
            {ok, UserCreds, nil};
        {_, true} ->
            {ok, UserCreds, nil};
        {_ConflictList, false} ->
            throw({unauthorized,
                <<"User document conflicts must be resolved before the document",
                  " is used for authentication purposes.">>
            })
    end.
