Welcome to mirror list, hosted at ThFree Co, Russian Federation.

github.com/processone/ejabberd.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorAlexey Shchepin <alexey@process-one.net>2004-08-13 02:34:19 +0400
committerAlexey Shchepin <alexey@process-one.net>2004-08-13 02:34:19 +0400
commitd77a936b322220a67e703525ff585660ea8da670 (patch)
tree69c3cb1dfd199de6f78884f1e3db9a991958c42e /src
parent357554265e4c86c5cd0dc3b6ae2f69f20c85786b (diff)
* src/ejabberd_c2s.erl: Bugfix in resend_offline_messages/1
* src/mod_announce.erl: New module to manage announce messages (thanks to Sergei Golovan) * src/ejabberd_local.erl: Moved processing of announce messages to mod_announce (thanks to Sergei Golovan) * src/ejabberd_c2s.erl: Added several hooks * src/ejabberd_hooks.erl: Fixed run_fold (thanks to Sergei Golovan) * src/ejabberd.cfg.example: Updated (thanks to Sergei Golovan) * doc/guide.tex: Updated (thanks to Sergei Golovan) SVN Revision: 256
Diffstat (limited to 'src')
-rw-r--r--src/cyrsasl_digest.erl4
-rw-r--r--src/ejabberd.cfg.example1
-rw-r--r--src/ejabberd_c2s.erl48
-rw-r--r--src/ejabberd_hooks.erl2
-rw-r--r--src/ejabberd_local.erl33
-rw-r--r--src/mod_announce.erl178
6 files changed, 231 insertions, 35 deletions
diff --git a/src/cyrsasl_digest.erl b/src/cyrsasl_digest.erl
index ae94c181f..2e5e94e5a 100644
--- a/src/cyrsasl_digest.erl
+++ b/src/cyrsasl_digest.erl
@@ -51,7 +51,7 @@ mech_step(#state{step = 3, nonce = Nonce} = State, ClientIn) ->
AuthzId = xml:get_attr_s("authzid", KeyVals),
case ejabberd_auth:get_password(UserName) of
false ->
- {error, "no-user"};
+ {error, "not-authorized"};
Passwd ->
Response = response(KeyVals, UserName, Passwd,
Nonce, AuthzId, "AUTHENTICATE"),
@@ -66,7 +66,7 @@ mech_step(#state{step = 3, nonce = Nonce} = State, ClientIn) ->
username = UserName,
authzid = AuthzId}};
_ ->
- {error, "bad-auth"}
+ {error, "not-authorized"}
end
end
end;
diff --git a/src/ejabberd.cfg.example b/src/ejabberd.cfg.example
index 82e1cc43c..253752f53 100644
--- a/src/ejabberd.cfg.example
+++ b/src/ejabberd.cfg.example
@@ -121,6 +121,7 @@
{mod_stats, []},
{mod_vcard, []},
{mod_offline, []},
+ {mod_announce, [{access, announce}]},
{mod_echo, [{host, "echo.localhost"}]},
{mod_private, []},
{mod_irc, []},
diff --git a/src/ejabberd_c2s.erl b/src/ejabberd_c2s.erl
index 844e7bcfb..d8021606f 100644
--- a/src/ejabberd_c2s.erl
+++ b/src/ejabberd_c2s.erl
@@ -673,12 +673,17 @@ session_established({xmlstreamelement, El}, StateData) ->
process_privacy_iq(
FromJID, ToJID, IQ, StateData);
_ ->
+ ejabberd_hooks:run(
+ user_send_packet,
+ [FromJID, ToJID, NewEl]),
ejabberd_router:route(
FromJID, ToJID, NewEl),
StateData
end
end;
"message" ->
+ ejabberd_hooks:run(user_send_packet,
+ [FromJID, ToJID, NewEl]),
ejabberd_router:route(FromJID, ToJID, NewEl),
StateData;
_ ->
@@ -882,8 +887,11 @@ handle_info({route, From, To, Packet}, StateName, StateData) ->
Attrs2 = jlib:replace_from_to_attrs(jlib:jid_to_string(From),
jlib:jid_to_string(To),
NewAttrs),
- Text = xml:element_to_string({xmlelement, Name, Attrs2, Els}),
+ FixedPacket = {xmlelement, Name, Attrs2, Els},
+ Text = xml:element_to_string(FixedPacket),
send_text(StateData, Text),
+ ejabberd_hooks:run(user_receive_packet,
+ [StateData#state.jid, From, To, FixedPacket]),
{next_state, StateName, NewState};
true ->
{next_state, StateName, NewState}
@@ -1102,6 +1110,8 @@ presence_update(From, Packet, StateData) ->
NewState =
if
FromUnavail ->
+ ejabberd_hooks:run(user_available_hook,
+ [StateData#state.jid]),
resend_offline_messages(StateData),
presence_broadcast_first(
From, StateData#state{pres_last = Packet,
@@ -1385,17 +1395,37 @@ process_privacy_iq(From, To,
NewStateData.
-resend_offline_messages(StateData) ->
+resend_offline_messages(#state{user = User,
+ privacy_list = PrivList} = StateData) ->
case ejabberd_hooks:run_fold(resend_offline_messages_hook, [],
- [StateData#state.user]) of
+ [User]) of
Rs when list(Rs) ->
lists:foreach(
- fun({route, From, To, {xmlelement, Name, Attrs, Els}}) ->
- Attrs2 = jlib:replace_from_to_attrs(
- jlib:jid_to_string(From),
- jlib:jid_to_string(To),
- Attrs),
- send_element(StateData, {xmlelement, Name, Attrs2, Els})
+ fun({route,
+ From, To, {xmlelement, Name, Attrs, Els} = Packet}) ->
+ Pass = case catch mod_privacy:check_packet(
+ User,
+ PrivList,
+ {From, To, Packet},
+ in) of
+ {'EXIT', _Reason} ->
+ true;
+ allow ->
+ true;
+ deny ->
+ false
+ end,
+ if
+ Pass ->
+ Attrs2 = jlib:replace_from_to_attrs(
+ jlib:jid_to_string(From),
+ jlib:jid_to_string(To),
+ Attrs),
+ send_element(StateData,
+ {xmlelement, Name, Attrs2, Els});
+ true ->
+ ok
+ end
end, Rs)
end.
diff --git a/src/ejabberd_hooks.erl b/src/ejabberd_hooks.erl
index c00035b41..d316fae89 100644
--- a/src/ejabberd_hooks.erl
+++ b/src/ejabberd_hooks.erl
@@ -55,7 +55,7 @@ run_fold(Hook, Val, Args) ->
[{_, Ls}] ->
run_fold1(Ls, Hook, Val, Args);
[] ->
- ok
+ Val
end.
%%%----------------------------------------------------------------------
diff --git a/src/ejabberd_local.erl b/src/ejabberd_local.erl
index 446ec292b..5da4cfaa1 100644
--- a/src/ejabberd_local.erl
+++ b/src/ejabberd_local.erl
@@ -15,7 +15,8 @@
-export([register_iq_handler/3,
register_iq_handler/4,
unregister_iq_handler/1,
- refresh_iq_handlers/0
+ refresh_iq_handlers/0,
+ bounce_resource_packet/3
]).
-include("ejabberd.hrl").
@@ -32,6 +33,8 @@ init() ->
MyDomain = ?MYNAME,
ejabberd_router:register_route(MyDomain),
catch ets:new(local_iqtable, [named_table, public]),
+ ejabberd_hooks:add(local_send_to_resource_hook,
+ ?MODULE, bounce_resource_packet, 100),
loop(#state{mydomain = MyDomain,
iqtable = local_iqtable}).
@@ -104,14 +107,8 @@ do_route(State, From, To, Packet) ->
"error" -> ok;
"result" -> ok;
_ ->
- case {Res, Name} of
- {"announce/online", "message"} ->
- announce_online(From, To, Packet);
- _ ->
- Err = jlib:make_error_reply(
- Packet, ?ERR_ITEM_NOT_FOUND),
- ejabberd_router:route(To, From, Err)
- end
+ ejabberd_hooks:run(local_send_to_resource_hook,
+ [From, To, Packet])
end;
_ ->
ejabberd_sm ! {route, From, To, Packet}
@@ -159,17 +156,7 @@ unregister_iq_handler(XMLNS) ->
refresh_iq_handlers() ->
ejabberd_local ! refresh_iq_handlers.
-announce_online(From, To, Packet) ->
- case acl:match_rule(announce, From) of
- deny ->
- Err = jlib:make_error_reply(Packet, ?ERR_NOT_ALLOWED),
- ejabberd_router:route(To, From, Err);
- allow ->
- Local = jlib:make_jid("", ?MYNAME, ""),
- lists:foreach(
- fun({U, R}) ->
- Dest = jlib:make_jid(U, ?MYNAME, R),
- ejabberd_router:route(Local, Dest, Packet)
- end, ejabberd_sm:dirty_get_sessions_list())
- end.
-
+bounce_resource_packet(From, To, Packet) ->
+ Err = jlib:make_error_reply(Packet, ?ERR_ITEM_NOT_FOUND),
+ ejabberd_router:route(To, From, Err),
+ stop.
diff --git a/src/mod_announce.erl b/src/mod_announce.erl
new file mode 100644
index 000000000..29ac65e87
--- /dev/null
+++ b/src/mod_announce.erl
@@ -0,0 +1,178 @@
+%%%----------------------------------------------------------------------
+%%% File : mod_announce.erl
+%%% Author : Alexey Shchepin <alexey@sevcom.net>
+%%% Purpose : Manage announce messages
+%%% Created : 11 Aug 2003 by Alexey Shchepin <alexey@sevcom.net>
+%%% Id : $Id$
+%%%----------------------------------------------------------------------
+
+-module(mod_announce).
+-author('alexey@sevcom.net').
+
+-behaviour(gen_mod).
+
+-export([start/1,
+ init/0,
+ stop/0,
+ announce/3,
+ send_motd/1]).
+
+-include("ejabberd.hrl").
+-include("jlib.hrl").
+
+-record(motd, {id, packet}).
+-record(motd_users, {luser, dummy = []}).
+
+-define(PROCNAME, ejabberd_announce).
+
+start(_) ->
+ mnesia:create_table(motd, [{disc_copies, [node()]},
+ {attributes, record_info(fields, motd)}]),
+ mnesia:create_table(motd_users, [{disc_copies, [node()]},
+ {attributes, record_info(fields, motd_users)}]),
+ ejabberd_hooks:add(local_send_to_resource_hook,
+ ?MODULE, announce, 50),
+ ejabberd_hooks:add(user_available_hook,
+ ?MODULE, send_motd, 50),
+ register(?PROCNAME, proc_lib:spawn(?MODULE, init, [])).
+
+init() ->
+ loop().
+
+loop() ->
+ receive
+ {announce_online, From, To, Packet} ->
+ announce_online(From, To, Packet),
+ loop();
+ {announce_motd, From, To, Packet} ->
+ announce_motd(From, To, Packet),
+ loop();
+ {announce_motd_update, From, To, Packet} ->
+ announce_motd_update(From, To, Packet),
+ loop();
+ {announce_motd_delete, From, To, Packet} ->
+ announce_motd_delete(From, To, Packet),
+ loop();
+ _ ->
+ loop()
+ end.
+
+stop() ->
+ ejabberd_hooks:delete(local_send_to_resource_hook,
+ ?MODULE, announce, 50),
+ ejabberd_hooks:delete(sm_register_connection_hook,
+ ?MODULE, send_motd, 50),
+ exit(whereis(?PROCNAME), stop),
+ ok.
+
+announce(From, To, Packet) ->
+ case To of
+ #jid{luser = "", lresource = Res} ->
+ {xmlelement, Name, _Attrs, _Els} = Packet,
+ case {Res, Name} of
+ {"announce/online", "message"} ->
+ ?PROCNAME ! {announce_online, From, To, Packet},
+ stop;
+ {"announce/motd", "message"} ->
+ ?PROCNAME ! {announce_motd, From, To, Packet},
+ stop;
+ {"announce/motd/update", "message"} ->
+ ?PROCNAME ! {announce_motd_update, From, To, Packet},
+ stop;
+ {"announce/motd/delete", "message"} ->
+ ?PROCNAME ! {announce_motd_delete, From, To, Packet},
+ stop;
+ _ ->
+ ok
+ end;
+ _ ->
+ ok
+ end.
+
+announce_online(From, To, Packet) ->
+ Access = gen_mod:get_module_opt(?MODULE, access, none),
+ case acl:match_rule(Access, From) of
+ deny ->
+ Err = jlib:make_error_reply(Packet, ?ERR_NOT_ALLOWED),
+ ejabberd_router:route(To, From, Err);
+ allow ->
+ announce_online1(ejabberd_sm:dirty_get_sessions_list(), Packet)
+ end.
+
+announce_online1(Sessions, Packet) ->
+ Server = ?MYNAME,
+ Local = jlib:make_jid("", Server, ""),
+ lists:foreach(
+ fun({U, R}) ->
+ Dest = jlib:make_jid(U, Server, R),
+ ejabberd_router:route(Local, Dest, Packet)
+ end, Sessions).
+
+announce_motd(From, To, Packet) ->
+ Access = gen_mod:get_module_opt(?MODULE, access, none),
+ case acl:match_rule(Access, From) of
+ deny ->
+ Err = jlib:make_error_reply(Packet, ?ERR_NOT_ALLOWED),
+ ejabberd_router:route(To, From, Err);
+ allow ->
+ announce_motd_update(Packet),
+ Sessions = ejabberd_sm:dirty_get_sessions_list(),
+ announce_online1(Sessions, Packet),
+ F = fun() ->
+ lists:foreach(
+ fun({U, _R}) ->
+ mnesia:write(#motd_users{luser = U})
+ end, Sessions)
+ end,
+ mnesia:transaction(F)
+ end.
+
+announce_motd_update(From, To, Packet) ->
+ Access = gen_mod:get_module_opt(?MODULE, access, none),
+ case acl:match_rule(Access, From) of
+ deny ->
+ Err = jlib:make_error_reply(Packet, ?ERR_NOT_ALLOWED),
+ ejabberd_router:route(To, From, Err);
+ allow ->
+ announce_motd_update(Packet)
+ end.
+
+announce_motd_update(Packet) ->
+ announce_motd_delete(),
+ F = fun() ->
+ mnesia:write(#motd{id = motd, packet = Packet})
+ end,
+ mnesia:transaction(F).
+
+announce_motd_delete(From, To, Packet) ->
+ Access = gen_mod:get_module_opt(?MODULE, access, none),
+ case acl:match_rule(Access, From) of
+ deny ->
+ Err = jlib:make_error_reply(Packet, ?ERR_NOT_ALLOWED),
+ ejabberd_router:route(To, From, Err);
+ allow ->
+ announce_motd_delete()
+ end.
+
+announce_motd_delete() ->
+ mnesia:clear_table(motd),
+ mnesia:clear_table(motd_users).
+
+send_motd(#jid{luser = LUser} = JID) ->
+ case catch mnesia:dirty_read({motd, motd}) of
+ [#motd{packet = Packet}] ->
+ case catch mnesia:dirty_read({motd_users, LUser}) of
+ [#motd_users{}] ->
+ ok;
+ _ ->
+ Local = jlib:make_jid("", ?MYNAME, ""),
+ ejabberd_router:route(Local, JID, Packet),
+ F = fun() ->
+ mnesia:write(#motd_users{luser = LUser})
+ end,
+ mnesia:transaction(F)
+ end;
+ _ ->
+ ok
+ end.
+