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
diff options
context:
space:
mode:
authorBadlop <badlop@process-one.net>2011-08-17 21:33:08 +0400
committerBadlop <badlop@process-one.net>2011-08-17 21:44:56 +0400
commitfef8c3a1f301b65b2a011efc254af1256b6c2c63 (patch)
treef1defb6b65494a984cb827b5508b95f73df05025 /src/ejabberd_c2s.erl
parent7355e810a8871be18089822c5d92f32892737387 (diff)
New option resource_conflict defines server action (thanks to Lee Boynton)(EJAB-650)
Diffstat (limited to 'src/ejabberd_c2s.erl')
-rw-r--r--src/ejabberd_c2s.erl37
1 files changed, 33 insertions, 4 deletions
diff --git a/src/ejabberd_c2s.erl b/src/ejabberd_c2s.erl
index 7c2872e65..d4df773c2 100644
--- a/src/ejabberd_c2s.erl
+++ b/src/ejabberd_c2s.erl
@@ -907,6 +907,29 @@ wait_for_sasl_response(closed, StateData) ->
{stop, normal, StateData}.
+resource_conflict_action(U, S, R) ->
+ OptionRaw = case ejabberd_sm:is_existing_resource(U, S, R) of
+ true ->
+ ejabberd_config:get_local_option({resource_conflict,binary_to_list(S)});
+ false ->
+ acceptnew
+ end,
+ Option = case OptionRaw of
+ setresource -> setresource;
+ closeold -> acceptnew; %% ejabberd_sm will close old session
+ closenew -> closenew;
+ acceptnew -> acceptnew;
+ _ -> acceptnew %% default ejabberd behavior
+ end,
+ case Option of
+ acceptnew ->
+ {accept_resource, R};
+ closenew ->
+ closenew;
+ setresource ->
+ Rnew = lists:concat([randoms:get_string() | tuple_to_list(now())]),
+ {accept_resource, Rnew}
+ end.
wait_for_bind({xmlstreamelement, El}, StateData) ->
try
@@ -923,11 +946,17 @@ wait_for_bind({xmlstreamelement, El}, StateData) ->
%%send_element(StateData,
%% exmpp_stream:features([exmpp_server_session:feature()
%% | RosterVersioningFeature])),
- JID = exmpp_jid:make(StateData#state.user, StateData#state.server, R),
- Res = exmpp_server_binding:bind(El, JID),
- send_element(StateData, Res),
- fsm_next_state(wait_for_session,
+ case resource_conflict_action(StateData#state.user, StateData#state.server, list_to_binary(R)) of
+ closenew ->
+ send_element(StateData, ?SERRT_CONFLICT), %% (Lang, "Replaced by new connection")),
+ fsm_next_state(wait_for_bind, StateData);
+ {accept_resource, R2} ->
+ JID = exmpp_jid:make(StateData#state.user, StateData#state.server, R2),
+ Res = exmpp_server_binding:bind(El, JID),
+ send_element(StateData, Res),
+ fsm_next_state(wait_for_session,
StateData#state{resource = exmpp_jid:resource(JID), jid = JID})
+ end
catch
throw:{stringprep, resourceprep, _, _} ->
Err = exmpp_server_binding:error(El, 'bad-request'),