Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

The second release of mod_mam #151

Merged
merged 39 commits into from
Jun 4, 2014
Merged
Show file tree
Hide file tree
Changes from 35 commits
Commits
Show all changes
39 commits
Select commit Hold shift + click to select a range
98c0dcb
Added a first version of Cassandra MAM backend.
arcusfelis Jan 10, 2014
1b34361
Added query_refs_count for mod_mam_muc_ca_arch.
arcusfelis Jan 10, 2014
4f52139
Added new book filter_local_packet. Fixed {badarg,[{ets,member,['ejab…
arcusfelis Jan 10, 2014
1f862da
Added a special version of mod_mam_cache_user for MUC.
arcusfelis Jan 21, 2014
5f57392
Added mod_mam_odbc_server_user: archive id assignor for multiple hosts.
arcusfelis Jan 22, 2014
7e9dcef
Added unique constraint for mam_user and mam_server_user tables.
arcusfelis Jan 22, 2014
96a6787
Deleted MAM_ARCHIVE_PRESENCE. Splited is_complete_message into severa…
arcusfelis Jan 22, 2014
a4963f8
Added seestar into release dependencies.
arcusfelis Jan 22, 2014
6fdb71c
Fixed wrong function name.
arcusfelis Jan 22, 2014
5277e01
Added prepare_user_id/1 for mod_mam_ca_arch.
arcusfelis Jan 23, 2014
8e95418
Added mod_mam_muc_ca_arch:select_worker/2.
arcusfelis Jan 24, 2014
c0b0197
Merge branch 'arc-mam-mods' into arc-mam-ca
arcusfelis Jan 24, 2014
a429296
Added mod_mam_muc_ca_arch:prepare_room_id/1.
arcusfelis Jan 24, 2014
d682fa3
Added servers config variable for mod_mam_muc_ca_arch.
arcusfelis Jan 24, 2014
cffc459
Select worker based on archive id in mod_mam_muc_ca_arch.
arcusfelis Jan 24, 2014
de799c0
Deleted prepare_room_id.
arcusfelis Jan 28, 2014
3ae3e19
Added mod_mam_con_ca_arch.
arcusfelis Jan 28, 2014
ccf9f3e
Added mam_con_user table. for tracking conversations.
arcusfelis Jan 28, 2014
ee5dfb4
Removing messages from mod_mam_con_ca_arch.
arcusfelis Jan 28, 2014
c87b188
Choosed a better strategy of cleaning conversation archives.
arcusfelis Jan 29, 2014
de38339
Deleted mod_mam:check_archive_id/2 to allow an archive id to be undef…
arcusfelis Jan 30, 2014
bd8d543
Added cassandra.cql.
arcusfelis Jan 30, 2014
fc27f26
Unreachable cassandra nodes do not crash MIM. Wait 10 seconds before …
arcusfelis Jan 30, 2014
0c1f48f
Added a helper function mod_mam_con_ca_arch:get_conversations_after/3.
arcusfelis Jan 30, 2014
568ba88
Allow filtering of the small result set on the server side.
arcusfelis Jan 31, 2014
8947831
Filter data inside mod_mam_con_ca_arch:get_conversations_after/3 in E…
arcusfelis Jan 31, 2014
e09d327
Added get_last_conversations/2.
arcusfelis Jan 31, 2014
1c22f7e
Replaced mam_ns_binary() with ?NS_MAM.
arcusfelis Feb 4, 2014
95ac562
Handle timeouts (show an error message and increase metric's value).
arcusfelis Feb 7, 2014
752eb4b
Catch exceptions inside backend modules.
arcusfelis Feb 7, 2014
d779e83
Deleted incompleted mod_mam_ca_arch.
arcusfelis Feb 10, 2014
32bf411
Added configuration examples for Cassandra back-ends.
arcusfelis Feb 10, 2014
a3265b3
Merge branch 'arc-mam-mods' into arc-mam-rel2
arcusfelis Feb 10, 2014
e36db07
Merge branch 'arc-mam-ca' into arc-mam-rel2
arcusfelis Feb 10, 2014
a52d940
Add process tags
arcusfelis Feb 10, 2014
e767045
Merge branch 'master' into arc-mam-rel2
arcusfelis May 29, 2014
08813f4
Encode MAM message ids in Base 32
arcusfelis May 29, 2014
9223cec
Fix a bug in elem_to_end_microseconds/1
arcusfelis May 29, 2014
44d919f
Add PgSQL schema for mam_server_user table (compare with mysql.sql)
arcusfelis May 29, 2014
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions apps/ejabberd/include/jlib.hrl
Original file line number Diff line number Diff line change
Expand Up @@ -69,6 +69,7 @@
-define(NS_BYTESTREAMS, <<"http://jabber.org/protocol/bytestreams">>).
-define(NS_ADMIN, <<"http://jabber.org/protocol/admin">>).
-define(NS_SERVERINFO, <<"http://jabber.org/network/serverinfo">>).
-define(NS_MAM, <<"urn:xmpp:mam:tmp">>).

-define(NS_RSM, <<"http://jabber.org/protocol/rsm">>).
-define(NS_EJABBERD_CONFIG,<<"ejabberd:config">>).
Expand Down
25 changes: 25 additions & 0 deletions apps/ejabberd/priv/cassandra.cql
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
CREATE KEYSPACE mam
WITH REPLICATION = {'class' : 'SimpleStrategy', 'replication_factor': 3};
USE mam;

CREATE TABLE mam_muc_message (
id bigint,
room_id int,
nick_name varchar,
message blob,
PRIMARY KEY (room_id, id));

CREATE TABLE mam_con_message(
id bigint,
lower_jid varchar,
upper_jid varchar,
is_from_lower boolean,
message blob,
PRIMARY KEY ((lower_jid, upper_jid), id));

CREATE TABLE mam_con_user(
local_jid varchar,
remote_jid varchar,
last_message_id bigint,
PRIMARY KEY (local_jid, remote_jid));

12 changes: 11 additions & 1 deletion apps/ejabberd/priv/mysql.sql
Original file line number Diff line number Diff line change
Expand Up @@ -266,10 +266,20 @@ CREATE INDEX i_mam_config USING HASH ON mam_config(user_id, remote_jid);
CREATE TABLE mam_user(
id INT UNSIGNED NOT NULL AUTO_INCREMENT,
user_name varchar(250) CHARACTER SET binary NOT NULL,
PRIMARY KEY(id) USING HASH
PRIMARY KEY(id) USING HASH,
CONSTRAINT uc_mam_user_name UNIQUE (user_name)
);
CREATE INDEX i_mam_user_name USING HASH ON mam_user(user_name);

CREATE TABLE mam_server_user(
id INT UNSIGNED NOT NULL AUTO_INCREMENT,
server varchar(250) CHARACTER SET binary NOT NULL,
user_name varchar(250) CHARACTER SET binary NOT NULL,
PRIMARY KEY(id) USING HASH,
CONSTRAINT uc_mam_server_user_name UNIQUE (server, user_name)
);
CREATE INDEX i_mam_server_user_name USING HASH ON mam_server_user(server, user_name);


CREATE TABLE mam_muc_message(
-- Message UID
Expand Down
4 changes: 4 additions & 0 deletions apps/ejabberd/src/ejabberd_odbc.erl
Original file line number Diff line number Diff line change
Expand Up @@ -210,6 +210,10 @@ to_bool(_) -> false.
%%% Callback functions from gen_fsm
%%%----------------------------------------------------------------------
init([Host, StartInterval, ParentPid, Dedicated]) ->
%% For debugging and introspection only.
put(mim_host, Host),
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why do we want process dictionary here? Can't this be in process state?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@arcusfelis could you answer this question?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It is used for getting information about running processes. To get information from state, you need to call process (hard, if its message queue is too big). But process dictionary can be asked directly.
Also, information from the process dictionary is shown in SASL crash messages.
I am using this kind of code to find MySQL connection and receiver processes for localhost:

IsMySQL = fun(Host, Pid) ->
    try
        {dictionary, PD} = erlang:process_info(Pid, dictionary),
        {mim_process_type, Type} = lists:keyfind(mim_process_type, 1, PD),
        case Type of
            mysql_recv ->
                true;
            mysql_conn ->
                true
        end
    catch _:_ ->
        false
    end
    end.

[Pid || Pid <- processes(), IsMySQL(<<"localhost">>, Pid)].

This functionality also can be used for something else :)

put(mim_process_type, odbc_worker),
put(mim_odbc_dedicated, Dedicated),
case ejabberd_config:get_local_option({odbc_keepalive_interval, Host}) of
KeepaliveInterval when is_integer(KeepaliveInterval) ->
timer:apply_interval(KeepaliveInterval*1000, ?MODULE,
Expand Down
26 changes: 20 additions & 6 deletions apps/ejabberd/src/ejabberd_router.erl
Original file line number Diff line number Diff line change
Expand Up @@ -222,6 +222,7 @@ code_change(_OldVsn, State, _Extra) ->
do_route(OrigFrom, OrigTo, OrigPacket) ->
?DEBUG("route~n\tfrom ~p~n\tto ~p~n\tpacket ~p~n",
[OrigFrom, OrigTo, OrigPacket]),
%% Filter globally
case ejabberd_hooks:run_fold(filter_packet,
{OrigFrom, OrigTo, OrigPacket}, []) of
{From, To, Packet} ->
Expand All @@ -230,12 +231,25 @@ do_route(OrigFrom, OrigTo, OrigPacket) ->
[] ->
ejabberd_s2s:route(From, To, Packet);
[#route{handler=Handler}] ->
case Handler of
{apply_fun, Fun} ->
Fun(From, To, Packet);
{apply, Module, Function} ->
Module:Function(From, To, Packet)
end
do_local_route(OrigFrom, OrigTo, OrigPacket, LDstDomain, Handler)
end;
drop ->
ejabberd_hooks:run(xmpp_stanza_dropped,
OrigFrom#jid.lserver,
[OrigFrom, OrigTo, OrigPacket]),
ok
end.

do_local_route(OrigFrom, OrigTo, OrigPacket, LDstDomain, Handler) ->
%% Filter locally
case ejabberd_hooks:run_fold(filter_local_packet, LDstDomain,
{OrigFrom, OrigTo, OrigPacket}, []) of
{From, To, Packet} ->
case Handler of
{apply_fun, Fun} ->
Fun(From, To, Packet);
{apply, Module, Function} ->
Module:Function(From, To, Packet)
end;
drop ->
ejabberd_hooks:run(xmpp_stanza_dropped,
Expand Down
115 changes: 68 additions & 47 deletions apps/ejabberd/src/mod_mam.erl
Original file line number Diff line number Diff line change
Expand Up @@ -114,10 +114,6 @@
%% ----------------------------------------------------------------------
%% Constants

mam_ns_string() -> "urn:xmpp:mam:tmp".

mam_ns_binary() -> <<"urn:xmpp:mam:tmp">>.

default_result_limit() -> 50.

max_result_limit() -> 50.
Expand Down Expand Up @@ -236,21 +232,21 @@ start(Host, Opts) ->
ejabberd_users:start(Host),
%% `parallel' is the only one recommended here.
IQDisc = gen_mod:get_opt(iqdisc, Opts, parallel), %% Type
mod_disco:register_feature(Host, mam_ns_binary()),
gen_iq_handler:add_iq_handler(ejabberd_sm, Host, mam_ns_binary(),
mod_disco:register_feature(Host, ?NS_MAM),
gen_iq_handler:add_iq_handler(ejabberd_sm, Host, ?NS_MAM,
?MODULE, process_mam_iq, IQDisc),
ejabberd_hooks:add(user_send_packet, Host, ?MODULE, user_send_packet, 90),
ejabberd_hooks:add(filter_packet, global, ?MODULE, filter_packet, 90),
ejabberd_hooks:add(filter_local_packet, Host, ?MODULE, filter_packet, 90),
ejabberd_hooks:add(remove_user, Host, ?MODULE, remove_user, 50),
ok.

stop(Host) ->
?DEBUG("mod_mam stopping", []),
ejabberd_hooks:delete(user_send_packet, Host, ?MODULE, user_send_packet, 90),
ejabberd_hooks:delete(filter_packet, global, ?MODULE, filter_packet, 90),
ejabberd_hooks:delete(filter_local_packet, Host, ?MODULE, filter_packet, 90),
ejabberd_hooks:delete(remove_user, Host, ?MODULE, remove_user, 50),
gen_iq_handler:remove_iq_handler(ejabberd_sm, Host, mam_ns_string()),
mod_disco:unregister_feature(Host, mam_ns_binary()),
gen_iq_handler:remove_iq_handler(ejabberd_sm, Host, ?NS_MAM),
mod_disco:unregister_feature(Host, ?NS_MAM),
ok.

%% ----------------------------------------------------------------------
Expand All @@ -271,14 +267,8 @@ process_mam_iq(From=#jid{lserver=Host}, To, IQ) ->
true ->
case wait_shaper(Host, Action, From) of
ok ->
try
handle_mam_iq(Action, From, To, IQ)
catch error:Reason ->
ejabberd_hooks:run(mam_drop_iq, Host,
[Host, To, IQ, Action, Reason]),
lager:error("Action ~p failed ~p", [Action, Reason]),
return_error_iq(IQ, Reason)
end;
handle_error_iq(Host, To, Action,
handle_mam_iq(Action, From, To, IQ));
{error, max_delay_reached} ->
ejabberd_hooks:run(mam_drop_iq, Host,
[Host, To, IQ, Action, max_delay_reached]),
Expand Down Expand Up @@ -399,19 +389,29 @@ handle_set_prefs(ArcJID=#jid{},
[DefaultMode, AlwaysJIDs, NeverJIDs]),
Host = server_host(ArcJID),
ArcID = archive_id_int(Host, ArcJID),
set_prefs(Host, ArcID, ArcJID, DefaultMode, AlwaysJIDs, NeverJIDs),
Res = set_prefs(Host, ArcID, ArcJID, DefaultMode, AlwaysJIDs, NeverJIDs),
handle_set_prefs_result(Res, DefaultMode, AlwaysJIDs, NeverJIDs, IQ).

handle_set_prefs_result(ok, DefaultMode, AlwaysJIDs, NeverJIDs, IQ) ->
ResultPrefsEl = result_prefs(DefaultMode, AlwaysJIDs, NeverJIDs),
IQ#iq{type = result, sub_el = [ResultPrefsEl]}.
IQ#iq{type = result, sub_el = [ResultPrefsEl]};
handle_set_prefs_result({error, Reason},
_DefaultMode, _AlwaysJIDs, _NeverJIDs, IQ) ->
return_error_iq(IQ, Reason).

handle_get_prefs(ArcJID=#jid{}, IQ=#iq{}) ->
Host = server_host(ArcJID),
ArcID = archive_id_int(Host, ArcJID),
{DefaultMode, AlwaysJIDs, NeverJIDs} =
get_prefs(Host, ArcID, ArcJID, always),
Res = get_prefs(Host, ArcID, ArcJID, always),
handle_get_prefs_result(Res, IQ).

handle_get_prefs_result({DefaultMode, AlwaysJIDs, NeverJIDs}, IQ) ->
?DEBUG("Extracted data~n\tDefaultMode ~p~n\tAlwaysJIDs ~p~n\tNeverJIDS ~p~n",
[DefaultMode, AlwaysJIDs, NeverJIDs]),
ResultPrefsEl = result_prefs(DefaultMode, AlwaysJIDs, NeverJIDs),
IQ#iq{type = result, sub_el = [ResultPrefsEl]}.
IQ#iq{type = result, sub_el = [ResultPrefsEl]};
handle_get_prefs_result({error, Reason}, IQ) ->
return_error_iq(IQ, Reason).

handle_lookup_messages(
From=#jid{},
Expand Down Expand Up @@ -442,6 +442,8 @@ handle_lookup_messages(
ErrorEl = ?STANZA_ERRORT(<<"">>, <<"modify">>, <<"policy-violation">>,
<<"en">>, <<"Too many results">>),
IQ#iq{type = error, sub_el = [ErrorEl]};
{error, Reason} ->
return_error_iq(IQ, Reason);
{ok, {TotalCount, Offset, MessageRows}} ->
{FirstMessID, LastMessID} =
case MessageRows of
Expand Down Expand Up @@ -473,8 +475,9 @@ handle_purge_multiple_messages(ArcJID=#jid{},
Borders = borders_decode(PurgeEl),
%% Filtering by contact.
With = elem_to_with_jid(PurgeEl),
purge_multiple_messages(Host, ArcID, ArcJID, Borders, Start, End, Now, With),
return_purge_success(IQ).
Res = purge_multiple_messages(Host, ArcID, ArcJID, Borders,
Start, End, Now, With),
return_purge_multiple_message_iq(IQ, Res).

handle_purge_single_message(ArcJID=#jid{},
IQ=#iq{sub_el = PurgeEl}) ->
Expand Down Expand Up @@ -550,9 +553,10 @@ set_prefs(Host, ArcID, ArcJID, DefaultMode, AlwaysJIDs, NeverJIDs) ->
ArcJID :: jid(),
DefaultMode :: archive_behaviour(),
GlobalDefaultMode :: archive_behaviour(),
Result :: {DefaultMode, AlwaysJIDs, NeverJIDs},
Result :: {DefaultMode, AlwaysJIDs, NeverJIDs} | {error, Reason},
AlwaysJIDs :: [literal_jid()],
NeverJIDs :: [literal_jid()].
NeverJIDs :: [literal_jid()],
Reason :: term().
get_prefs(Host, ArcID, ArcJID, GlobalDefaultMode) ->
ejabberd_hooks:run_fold(mam_get_prefs, Host,
{GlobalDefaultMode, [], []},
Expand All @@ -565,7 +569,9 @@ remove_archive(Host, ArcID, ArcJID=#jid{}) ->
-spec lookup_messages(Host, ArcID, ArcJID, RSM, Borders,
Start, End, Now, WithJID,
PageSize, LimitPassed, MaxResultLimit, IsSimple) ->
{ok, {TotalCount, Offset, MessageRows}} | {error, 'policy-violation'}
{ok, {TotalCount, Offset, MessageRows}}
| {error, 'policy-violation'}
| {error, Reason}
when
Host :: server_host(),
ArcID :: archive_id(),
Expand All @@ -582,7 +588,8 @@ remove_archive(Host, ArcID, ArcJID=#jid{}) ->
IsSimple :: boolean() | opt_count,
TotalCount :: non_neg_integer(),
Offset :: non_neg_integer(),
MessageRows :: list(tuple()).
MessageRows :: list(tuple()),
Reason :: term().
lookup_messages(Host, ArcID, ArcJID, RSM, Borders, Start, End, Now,
WithJID, PageSize, LimitPassed, MaxResultLimit, IsSimple) ->
ejabberd_hooks:run_fold(mam_lookup_messages, Host, {ok, {0, 0, []}},
Expand All @@ -604,20 +611,20 @@ archive_message(Host, MessID, ArcID, LocJID, RemJID, SrcJID, Dir, Packet) ->
ejabberd_hooks:run_fold(mam_archive_message, Host, ok,
[Host, MessID, ArcID, LocJID, RemJID, SrcJID, Dir, Packet]).


-spec purge_single_message(Host, MessID, ArcID, ArcJID, Now) ->
ok | {error, 'not-found'} when
ok | {error, 'not-found'} | {error, Reason} when
Host :: server_host(),
MessID :: message_id(),
ArcID :: archive_id(),
ArcJID :: jid(),
Now :: unix_timestamp().
Now :: unix_timestamp(),
Reason :: term().
purge_single_message(Host, MessID, ArcID, ArcJID, Now) ->
ejabberd_hooks:run_fold(mam_purge_single_message, Host, ok,
[Host, MessID, ArcID, ArcJID, Now]).

-spec purge_multiple_messages(Host, ArcID, ArcJID, Borders,
Start, End, Now, WithJID) -> ok
Start, End, Now, WithJID) -> ok | {error, Reason}
when
Host :: server_host(),
ArcID :: archive_id(),
Expand All @@ -626,7 +633,8 @@ purge_single_message(Host, MessID, ArcID, ArcJID, Now) ->
Start :: unix_timestamp() | undefined,
End :: unix_timestamp() | undefined,
Now :: unix_timestamp(),
WithJID :: jid() | undefined.
WithJID :: jid() | undefined,
Reason :: term().
purge_multiple_messages(Host, ArcID, ArcJID, Borders, Start, End, Now, WithJID) ->
ejabberd_hooks:run_fold(mam_purge_multiple_messages, Host, ok,
[Host, ArcID, ArcJID, Borders, Start, End, Now, WithJID]).
Expand Down Expand Up @@ -688,14 +696,38 @@ elem_to_limit(QueryEl) ->
[{elem, <<"set">>}, {elem, <<"limit">>}, cdata]
]).

return_purge_success(IQ) ->
IQ#iq{type = result, sub_el = []}.
handle_error_iq(Host, To, Action, IQ=#iq{type = {error, Reason}}) ->
ejabberd_hooks:run(mam_drop_iq, Host,
[Host, To, IQ, Action, Reason]),
IQ#iq{type = error};
handle_error_iq(_Host, _To, _Action, IQ) ->
IQ.

return_error_iq(IQ, timeout) ->
IQ#iq{type = {error, timeout}, sub_el = [?ERR_SERVICE_UNAVAILABLE]};
return_error_iq(IQ, Reason) ->
IQ#iq{type = {error, Reason}, sub_el = [?ERR_INTERNAL_SERVER_ERROR]}.

return_action_not_allowed_error_iq(IQ) ->
ErrorEl = ?STANZA_ERRORT(<<"">>, <<"cancel">>, <<"not-allowed">>,
<<"en">>, <<"The action is not allowed.">>),
IQ#iq{type = error, sub_el = [ErrorEl]}.

return_purge_multiple_message_iq(IQ, ok) ->
return_purge_success(IQ);
return_purge_multiple_message_iq(IQ, {error, Reason}) ->
return_error_iq(IQ, Reason).

return_purge_single_message_iq(IQ, ok) ->
return_purge_success(IQ);
return_purge_single_message_iq(IQ, {error, 'not-found'}) ->
return_purge_not_found_error_iq(IQ);
return_purge_single_message_iq(IQ, {error, Reason}) ->
return_error_iq(IQ, Reason).

return_purge_success(IQ) ->
IQ#iq{type = result, sub_el = []}.

return_purge_not_found_error_iq(IQ) ->
%% Message not found.
ErrorEl = ?STANZA_ERRORT(<<"">>, <<"cancel">>, <<"item-not-found">>,
Expand All @@ -707,14 +739,3 @@ return_max_delay_reached_error_iq(IQ) ->
ErrorEl = ?ERRT_RESOURCE_CONSTRAINT(
<<"en">>, <<"The action is cancelled because of flooding.">>),
IQ#iq{type = error, sub_el = [ErrorEl]}.

return_error_iq(IQ, timeout) ->
IQ#iq{type = error, sub_el = [?ERR_SERVICE_UNAVAILABLE]};
return_error_iq(IQ, _Reason) ->
IQ#iq{type = error, sub_el = [?ERR_INTERNAL_SERVER_ERROR]}.

return_purge_single_message_iq(IQ, ok) ->
return_purge_success(IQ);
return_purge_single_message_iq(IQ, {error, 'not-found'}) ->
return_purge_not_found_error_iq(IQ).

19 changes: 14 additions & 5 deletions apps/ejabberd/src/mod_mam_cache_user.erl
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,9 @@
%%% This module is a proxy for `mod_mam_odbc_user' (it should be started).
%%%
%%% There are 2 hooks for `mam_archive_id':
%%% `cache_archive_id/3' and `store_archive_id/3'.
%%% `cached_archive_id/3' and `store_archive_id/3'.
%%%
%%% This module supports several hosts.
%%%
%%% @end
%%%-------------------------------------------------------------------
Expand Down Expand Up @@ -53,7 +55,7 @@ su_key(#jid{lserver = LServer, luser = LUser}) ->
%% Starting and stopping functions for users' archives

start(Host, Opts) ->
supervisor:start_child(ejabberd_sup, writer_child_spec()),
start_server(Host),
case gen_mod:get_module_opt(Host, ?MODULE, pm, false) of
true ->
start_pm(Host, Opts);
Expand All @@ -68,6 +70,7 @@ start(Host, Opts) ->
end.

stop(Host) ->
stop_server(Host),
case gen_mod:get_module_opt(Host, ?MODULE, pm, false) of
true ->
stop_pm(Host);
Expand All @@ -82,12 +85,18 @@ stop(Host) ->
end.

writer_child_spec() ->
{mod_mam_cache_user,
{mod_mam_cache_user, start_link, []},
{?MODULE,
{?MODULE, start_link, []},
permanent,
5000,
worker,
[mod_mam_cache_user]}.
[?MODULE]}.

start_server(_Host) ->
supervisor:start_child(ejabberd_sup, writer_child_spec()).

stop_server(_Host) ->
ok.

%% ----------------------------------------------------------------------
%% Add hooks for mod_mam
Expand Down
Loading