mirror of
https://github.com/processone/ejabberd.git
synced 2024-11-22 16:20:52 +01:00
Fix core files
This commit is contained in:
parent
13fad04d14
commit
58bed2cbff
@ -98,7 +98,7 @@ register_mechanism(Mechanism, Module, RequirePlainPassword) ->
|
||||
% {error, "invalid-authzid"};
|
||||
% JID ->
|
||||
% LUser = jlib:nodeprep(xml:get_attr_s(username, Props)),
|
||||
% {U, S, R} = jlib:jid_tolower(JID),
|
||||
% {U, S, R} = jlib:short_prepd_jid(JID),
|
||||
% case R of
|
||||
% "" ->
|
||||
% {error, "invalid-authzid"};
|
||||
|
@ -296,8 +296,8 @@ send_service_message_all_mucs(Subject, AnnouncementText) ->
|
||||
Message = io_lib:format("~s~n~s", [Subject, AnnouncementText]),
|
||||
lists:foreach(
|
||||
fun(ServerHost) ->
|
||||
MUCHost = gen_mod:expand_host_name(
|
||||
ServerHost, mod_muc, "conference"),
|
||||
MUCHost = gen_mod:get_module_opt_host(
|
||||
ServerHost, mod_muc, "conference.@HOST@"),
|
||||
MUCHostB = list_to_binary(MUCHost),
|
||||
mod_muc:broadcast_service_message(MUCHostB, Message)
|
||||
end,
|
||||
|
@ -490,6 +490,15 @@ process_host_term(Term, Host, State) ->
|
||||
State;
|
||||
{odbc_server, ODBC_server} ->
|
||||
add_option({odbc_server, Host}, ODBC_server, State);
|
||||
{auth_method, Methods} ->
|
||||
{Methods2, StorageOption} = replace_storage_auth(Host, Methods),
|
||||
State2 = case StorageOption of
|
||||
{auth_storage, Storage} ->
|
||||
add_option({auth_storage, Host}, Storage, State);
|
||||
undefined ->
|
||||
State
|
||||
end,
|
||||
add_option({auth_method, Host}, Methods2, State2);
|
||||
{Opt, Val} ->
|
||||
add_option({Opt, Host}, Val, State)
|
||||
end.
|
||||
@ -720,3 +729,35 @@ mnesia_write_objects(List) when is_list(List) ->
|
||||
true = lists:all(fun (I) ->
|
||||
ok =:= mnesia:write(I)
|
||||
end, List).
|
||||
|
||||
%% Replace internal and odbc auth_methods with storage.
|
||||
%% Only one storage type can be used, either internal or odbc.
|
||||
replace_storage_auth(Host, Val) when not is_list(Val) ->
|
||||
replace_storage_auth(Host, [Val]);
|
||||
replace_storage_auth(Host, Val) ->
|
||||
replace_storage_auth(Host, Val, [], undefined).
|
||||
|
||||
replace_storage_auth(_Host, [], Val2, Storage) ->
|
||||
{lists:reverse(Val2), Storage};
|
||||
|
||||
replace_storage_auth(Host, [internal = Val | ValT], Val2, undefined) ->
|
||||
Storage = {auth_storage, mnesia},
|
||||
?WARNING_MSG("The auth method '~p' is deprecated.~nReplace it with 'storage'"
|
||||
" and also add this option: ~n~p.", [Val, Storage]),
|
||||
replace_storage_auth(Host, ValT, [storage | Val2], Storage);
|
||||
|
||||
replace_storage_auth(Host, [odbc = Val | ValT], Val2, undefined) ->
|
||||
Storage = {auth_storage, odbc},
|
||||
?WARNING_MSG("The auth method '~p' is deprecated.~nReplace it with 'storage'"
|
||||
" and also add this option: ~n~p.", [Val, Storage]),
|
||||
replace_storage_auth(Host, ValT, [storage | Val2], Storage);
|
||||
|
||||
replace_storage_auth(Host, [Val | ValT], Val2, Storage)
|
||||
when (Val /= internal) and (Val /= odbc) ->
|
||||
replace_storage_auth(Host, ValT, [Val | Val2], Storage);
|
||||
|
||||
replace_storage_auth(Host, [Val | _ValT], _Val2, Storage) ->
|
||||
?CRITICAL_MSG("The auth method '~p' conflicts with~n~p in the host \"~p\"."
|
||||
"~nOnly one of them can be used in each host.",
|
||||
[Val, Storage, Host]),
|
||||
throw({unacceptable_auth_conflict, Host, Val, Storage}).
|
||||
|
@ -327,7 +327,7 @@ run1([{_Seq, Module, Function} | Ls], Hook, Args) ->
|
||||
[Reason, {Hook, Args}]),
|
||||
run1(Ls, Hook, Args);
|
||||
stop ->
|
||||
ok;
|
||||
stop;
|
||||
_ ->
|
||||
run1(Ls, Hook, Args)
|
||||
end.
|
||||
|
@ -1,9 +1,22 @@
|
||||
%%%-------------------------------------------------------------------
|
||||
%%% File : ejabberd_hosts.erl
|
||||
%%% Author : Alexey Shchepin <alexey@process-one.net>
|
||||
%%% Description : Synchronises running VHosts with the hosts table in the database.
|
||||
%%% Description : Synchronises running VHosts with the hosts table in the Mnesia database.
|
||||
%%% Created : 16 Nov 2007 by Alexey Shchepin <alexey@process-one.net>
|
||||
%%%-------------------------------------------------------------------
|
||||
|
||||
%%% Database schema (version / storage / table)
|
||||
%%%
|
||||
%%% 3.0.0-alpha-x / mnesia / hosts
|
||||
%%% host = string()
|
||||
%%% clusterid = integer()
|
||||
%%% config = string()
|
||||
%%%
|
||||
%%% 3.0.0-alpha-x / odbc / hosts
|
||||
%%% host = varchar150
|
||||
%%% clusterid = integer
|
||||
%%% config = text
|
||||
|
||||
-module(ejabberd_hosts).
|
||||
|
||||
-behaviour(gen_server).
|
||||
@ -50,7 +63,9 @@
|
||||
-include_lib("stdlib/include/ms_transform.hrl").
|
||||
|
||||
-record(state, {state=wait_odbc,
|
||||
backend=mnesia,
|
||||
odbc_wait_time=120}).
|
||||
-record(hosts, {host, clusterid, config}).
|
||||
|
||||
-define(RELOAD_INTERVAL, timer:seconds(60)).
|
||||
-define(ODBC_STARTUP_TIME, 120). % 2minute limit for ODBC startup.
|
||||
@ -65,32 +80,25 @@ reload() ->
|
||||
%% Creates a vhost in the system.
|
||||
register(Host) when is_list(Host) -> ?MODULE:register(Host, "").
|
||||
register(Host, Config) when is_list(Host), is_list(Config) ->
|
||||
true = jlib:is_nodename(Host),
|
||||
ID = ejabberd_config:get_local_option(clusterid),
|
||||
case ejabberd_odbc:sql_query(?MYNAME,
|
||||
["INSERT INTO hosts (clusterid,host,config) VALUES (",
|
||||
integer_to_list(ID), ", '",Host,"','",Config,"')"]) of
|
||||
{updated, 1} ->
|
||||
reload(),
|
||||
ok;
|
||||
{error, E} -> {error, E}
|
||||
end.
|
||||
true = exmpp_stringprep:is_node(Host),
|
||||
ID = get_clusterid(),
|
||||
H = #hosts{host = Host, clusterid = ID, config = Config},
|
||||
ok = gen_storage:dirty_write(Host, H),
|
||||
reload(),
|
||||
ok.
|
||||
|
||||
%% Removes a vhost from the system,
|
||||
%% XXX deleting all ODBC data.
|
||||
remove(Host) when is_list(Host) ->
|
||||
true = jlib:is_nodename(Host),
|
||||
ID = ejabberd_config:get_local_option(clusterid),
|
||||
case ejabberd_odbc:sql_query(?MYNAME,
|
||||
["DELETE FROM hosts "
|
||||
"WHERE clusterid=",
|
||||
integer_to_list(ID), " AND host='",Host,"'"]) of
|
||||
{updated, 1} ->
|
||||
reload(),
|
||||
ok;
|
||||
{updated, 0} -> {error, no_such_host};
|
||||
{error, E} -> {error, E}
|
||||
end.
|
||||
true = exmpp_stringprep:is_node(Host),
|
||||
ID = get_clusterid(),
|
||||
gen_storage:dirty_delete_where(
|
||||
Host, hosts,
|
||||
[{'andalso',
|
||||
{'==', clusterid, ID},
|
||||
{'==', host, Host}}]),
|
||||
reload(),
|
||||
ok.
|
||||
|
||||
registered() ->
|
||||
mnesia:dirty_select(local_config,
|
||||
@ -136,9 +144,11 @@ start_link() ->
|
||||
%% Description: Initiates the server
|
||||
%%--------------------------------------------------------------------
|
||||
init([]) ->
|
||||
Backend = mnesia, %%+++ TODO: allow to configure this in ejabberd.cfg
|
||||
configure_static_hosts(),
|
||||
get_clusterid(), %% this is to report an error if the option wasn't configured
|
||||
%% Wait up to 120 seconds for odbc to start
|
||||
{ok, #state{state=wait_odbc,odbc_wait_time=?ODBC_STARTUP_TIME}, timer:seconds(1)}.
|
||||
{ok, #state{state=wait_odbc,backend=Backend,odbc_wait_time=?ODBC_STARTUP_TIME}, timer:seconds(1)}.
|
||||
|
||||
%%--------------------------------------------------------------------
|
||||
%% Function: %% handle_call(Request, From, State) -> {reply, Reply, State} |
|
||||
@ -169,10 +179,27 @@ handle_cast(_Msg, State) ->
|
||||
%% Description: Handling all non call/cast messages
|
||||
%%--------------------------------------------------------------------
|
||||
%% Wait for odbc to start.
|
||||
handle_info(timeout, State = #state{state=wait_odbc,odbc_wait_time=N}) when N > 0 ->
|
||||
case ejabberd_odbc:running(?MYNAME) of
|
||||
handle_info(timeout, State = #state{state=wait_odbc,backend=Backend,odbc_wait_time=N}) when N > 0 ->
|
||||
case (Backend /= odbc) orelse ejabberd_odbc:running(?MYNAME) of
|
||||
true ->
|
||||
?DEBUG("ejabberd_hosts: odbc now running.",[]),
|
||||
|
||||
%% The table 'hosts' is defined in gen_storage as being for the "localhost" vhost
|
||||
Host = ?MYNAME,
|
||||
HostB = list_to_binary(Host),
|
||||
gen_storage:create_table(Backend, HostB, hosts,
|
||||
[{disc_only_copies, [node()]},
|
||||
{odbc_host, Host},
|
||||
{attributes, record_info(fields, hosts)},
|
||||
{types, [{host, text},
|
||||
{clusterid, int},
|
||||
{config, text}]}]),
|
||||
|
||||
%% Now let's add the default vhost: "localhost"
|
||||
gen_storage:dirty_write(Host, #hosts{host = Host,
|
||||
clusterid = 1,
|
||||
config = ""}),
|
||||
|
||||
self() ! reload,
|
||||
timer:send_interval(?RELOAD_INTERVAL, reload),
|
||||
{noreply, State#state{state=running,odbc_wait_time=0}};
|
||||
@ -305,35 +332,29 @@ stop_host(Host) ->
|
||||
%% Get the current vhost list from a variety of sources (ODBC, internal)
|
||||
get_hosts(ejabberd) -> ?MYHOSTS;
|
||||
get_hosts(odbc) ->
|
||||
ClusterID = ejabberd_config:get_local_option(clusterid),
|
||||
case ejabberd_odbc:sql_query(
|
||||
?MYNAME,
|
||||
["select host from hosts where clusterid = ",
|
||||
integer_to_list(ClusterID)]) of
|
||||
{selected, ["host"], SHosts} ->
|
||||
lists:map(fun ({Host}) ->
|
||||
case jlib:nameprep(Host) of
|
||||
ClusterID = get_clusterid(),
|
||||
case gen_storage:dirty_select(?MYNAME, hosts, [{'=', clusterid, ClusterID}]) of
|
||||
Hosts when is_list(Hosts) ->
|
||||
lists:map(fun (#hosts{host = Host}) ->
|
||||
case exmpp_stringprep:nameprep(Host) of
|
||||
error ->
|
||||
erlang:error({bad_vhost_name, Host});
|
||||
Name ->
|
||||
Name
|
||||
end
|
||||
end, SHosts);
|
||||
E ->
|
||||
erlang:error({get_hosts_odbc_error, E})
|
||||
end, Hosts);
|
||||
E ->
|
||||
erlang:error({get_hosts_error, E})
|
||||
end.
|
||||
|
||||
%% Retreive the text format config for host Host from ODBC and covert
|
||||
%% it into a {host, Host, Config} tuple.
|
||||
get_host_config(odbc, Host) ->
|
||||
case ejabberd_odbc:sql_query(
|
||||
?MYNAME,
|
||||
["select config from hosts where host = '",
|
||||
Host, "'"]) of
|
||||
{selected, ["config"], [{Config}]} ->
|
||||
config_from_string(Host, Config);
|
||||
{selected, ["config"], []} ->
|
||||
case gen_storage:dirty_read(?MYNAME, hosts, Host) of
|
||||
[] ->
|
||||
erlang:error({no_such_host, Host});
|
||||
[H] ->
|
||||
config_from_string(Host, H#hosts.config);
|
||||
E ->
|
||||
erlang:error({host_config_error, E})
|
||||
end.
|
||||
@ -401,3 +422,12 @@ reconfigure_host_cert(Host) ->
|
||||
false ->
|
||||
no_cert
|
||||
end.
|
||||
|
||||
get_clusterid() ->
|
||||
case ejabberd_config:get_local_option(clusterid) of
|
||||
ID when is_integer(ID) ->
|
||||
ID;
|
||||
Other ->
|
||||
?ERROR_MSG("The option {clusterid, INTEGER}. was configured to: ~p", [Other]),
|
||||
1
|
||||
end.
|
||||
|
@ -44,7 +44,7 @@
|
||||
-include_lib("exmpp/include/exmpp_client.hrl").
|
||||
|
||||
%% Copied from mod_private.erl
|
||||
-record(private_storage, {usns, xml}).
|
||||
-record(private_storage, {user_host_ns, xml}).
|
||||
|
||||
%%-define(ERROR_MSG(M,Args),io:format(M,Args)).
|
||||
%%-define(INFO_MSG(M,Args),ok).
|
||||
@ -465,7 +465,7 @@ make_xinclude(Fn) ->
|
||||
%% @doc Extract user information and print it.
|
||||
export_user(Fd, Username, Host) ->
|
||||
try extract_user(Username, Host) of
|
||||
UserString ->
|
||||
UserString when is_list(UserString) ->
|
||||
print(Fd, UserString)
|
||||
catch
|
||||
E1:E2 ->
|
||||
@ -543,7 +543,7 @@ extract_user_info(vcard, Username, Host) ->
|
||||
%%%% Interface with ejabberd offline storage
|
||||
|
||||
%% Copied from mod_offline.erl and customized
|
||||
-record(offline_msg, {us, timestamp, expire, from, to, packet}).
|
||||
-record(offline_msg, {user_host, timestamp, expire, from, to, packet}).
|
||||
mnesia_pop_offline_messages(Ls, User, Server) ->
|
||||
try
|
||||
LUser = User,
|
||||
@ -556,31 +556,31 @@ mnesia_pop_offline_messages(Ls, User, Server) ->
|
||||
end,
|
||||
case mnesia:transaction(F) of
|
||||
{atomic, Rs} ->
|
||||
TS = now(),
|
||||
TS = make_timestamp(),
|
||||
Ls ++ lists:map(
|
||||
fun(R) ->
|
||||
Packet = R#offline_msg.packet,
|
||||
[Packet] = exmpp_xml:parse_document(R#offline_msg.packet, [names_as_atom]),
|
||||
FromString = exmpp_jid:prep_to_list(R#offline_msg.from),
|
||||
Packet2 = exmpp_xml:set_attribute(Packet, "from", FromString),
|
||||
Packet3 = Packet2#xmlel{ns = ?NS_JABBER_CLIENT},
|
||||
exmpp_xml:append_children(
|
||||
Packet3,
|
||||
[jlib:timestamp_to_xml(
|
||||
calendar:now_to_universal_time(
|
||||
calendar:gregorian_seconds_to_datetime(
|
||||
R#offline_msg.timestamp),
|
||||
utc,
|
||||
exmpp_jid:make("", Server, ""),
|
||||
"Offline Storage"),
|
||||
%% TODO: Delete the next three lines once XEP-0091 is Obsolete
|
||||
jlib:timestamp_to_xml(
|
||||
calendar:now_to_universal_time(
|
||||
calendar:gregorian_seconds_to_datetime(
|
||||
R#offline_msg.timestamp))]
|
||||
)
|
||||
end,
|
||||
lists:filter(
|
||||
fun(R) ->
|
||||
case R#offline_msg.expire of
|
||||
never ->
|
||||
0 ->
|
||||
true;
|
||||
TimeStamp ->
|
||||
TS < TimeStamp
|
||||
@ -595,15 +595,18 @@ mnesia_pop_offline_messages(Ls, User, Server) ->
|
||||
Ls
|
||||
end.
|
||||
|
||||
make_timestamp() ->
|
||||
{MegaSecs, Secs, _MicroSecs} = now(),
|
||||
MegaSecs * 1000000 + Secs.
|
||||
|
||||
%%%==================================
|
||||
%%%% Interface with ejabberd private storage
|
||||
|
||||
get_user_private_mnesia(Username, Host) ->
|
||||
ListNsEl = mnesia:dirty_select(private_storage,
|
||||
[{#private_storage{usns={?LTB(Username), ?LTB(Host), '$1'}, xml = '$2'},
|
||||
[{#private_storage{user_host_ns={?LTB(Username), ?LTB(Host), '$1'}, xml = '$2'},
|
||||
[], ['$$']}]),
|
||||
Els = [exmpp_xml:document_to_list(El) || [_Ns, El] <- ListNsEl],
|
||||
Els = [lists:flatten(exmpp_xml:document_to_list(El)) || [_Ns, El] <- ListNsEl],
|
||||
case lists:flatten(Els) of
|
||||
"" -> "";
|
||||
ElsString ->
|
||||
|
107
src/ejd2odbc.erl
107
src/ejd2odbc.erl
@ -30,6 +30,7 @@
|
||||
%% External exports
|
||||
-export([export_passwd/2,
|
||||
export_roster/2,
|
||||
export_roster_group/2,
|
||||
export_offline/2,
|
||||
export_last/2,
|
||||
export_vcard/2,
|
||||
@ -41,10 +42,10 @@
|
||||
-include("ejabberd.hrl").
|
||||
-include("mod_roster.hrl").
|
||||
|
||||
-record(offline_msg, {us, timestamp, expire, from, to, packet}).
|
||||
-record(last_activity, {us, timestamp, status}).
|
||||
-record(vcard, {us, vcard}).
|
||||
-record(vcard_search, {us,
|
||||
-record(offline_msg, {user_host, timestamp, expire, from, to, packet}).
|
||||
-record(last_activity, {user_host, timestamp, status}).
|
||||
-record(vcard, {user_host, vcard}).
|
||||
-record(vcard_search, {user_host,
|
||||
user, luser,
|
||||
fn, lfn,
|
||||
family, lfamily,
|
||||
@ -58,7 +59,7 @@
|
||||
orgname, lorgname,
|
||||
orgunit, lorgunit
|
||||
}).
|
||||
-record(private_storage, {usns, xml}).
|
||||
-record(private_storage, {user_host_ns, xml}).
|
||||
|
||||
-define(MAX_RECORDS_PER_TRANSACTION, 1000).
|
||||
|
||||
@ -79,9 +80,9 @@ export_passwd(Server, Output) ->
|
||||
when LServer == Host ->
|
||||
Username = ejabberd_odbc:escape(LUser),
|
||||
Pass = ejabberd_odbc:escape(Password),
|
||||
["delete from users where username='", Username ,"';"
|
||||
"insert into users(username, password) "
|
||||
"values ('", Username, "', '", Pass, "');"];
|
||||
["delete from users where host='", Server, "' and username='", Username ,"';\n"
|
||||
"insert into users(host, username, password) "
|
||||
"values ('", Server, "', '", Username, "', '", Pass, "');\n"];
|
||||
(_Host, _R) ->
|
||||
[]
|
||||
end).
|
||||
@ -89,28 +90,37 @@ export_passwd(Server, Output) ->
|
||||
export_roster(ServerS, Output) ->
|
||||
Server = list_to_binary(ServerS),
|
||||
export_common(
|
||||
Server, roster, Output,
|
||||
fun(Host, #roster{usj = {LUser, LServer, {N, D, Res} = _LJID}} = R)
|
||||
Server, rosteritem, Output,
|
||||
fun(Host, #rosteritem{user_host_jid = {LUser, LServer, {N, D, Res} = _LJID}} = R)
|
||||
when LServer == Host ->
|
||||
Username = ejabberd_odbc:escape(LUser),
|
||||
SJID = ejabberd_odbc:escape(exmpp_jid:to_list(N, D, Res)),
|
||||
ItemVals = record_to_string(R),
|
||||
ItemGroups = groups_to_string(R),
|
||||
ItemVals = record_to_string(R, ServerS),
|
||||
["delete from rosterusers "
|
||||
" where username='", Username, "' "
|
||||
" and jid='", SJID, "';"
|
||||
" and jid='", SJID, "';\n"
|
||||
"insert into rosterusers("
|
||||
" username, jid, nick, "
|
||||
" host, username, jid, nick, "
|
||||
" subscription, ask, askmessage, "
|
||||
" server, subscribe, type) "
|
||||
" values ", ItemVals, ";"
|
||||
"delete from rostergroups "
|
||||
" where username='", Username, "' "
|
||||
" and jid='", SJID, "';",
|
||||
[["insert into rostergroups("
|
||||
" username, jid, grp) "
|
||||
" values ", ItemGroup, ";"] ||
|
||||
ItemGroup <- ItemGroups]];
|
||||
" values ", ItemVals, ";\n"];
|
||||
(_Host, _R) ->
|
||||
[]
|
||||
end).
|
||||
|
||||
export_roster_group(ServerS, Output) ->
|
||||
Server = list_to_binary(ServerS),
|
||||
export_common(
|
||||
Server, rostergroup, Output,
|
||||
fun(Host, #rostergroup{user_host_jid = {_LUser, LServer, _LJID}} = R)
|
||||
when LServer == Host ->
|
||||
ItemGroup = group_to_string(R, ServerS),
|
||||
[%%"delete from rostergroups"
|
||||
%%" where username='", Username, "'"
|
||||
%%" and host='", ServerS, "'"
|
||||
%%" and jid='", SJID, "';"
|
||||
"insert into rostergroups(host, username, jid, grp)"
|
||||
" values ", ItemGroup, ";\n"];
|
||||
(_Host, _R) ->
|
||||
[]
|
||||
end).
|
||||
@ -118,33 +128,34 @@ export_roster(ServerS, Output) ->
|
||||
export_offline(Server, Output) ->
|
||||
export_common(
|
||||
Server, offline_msg, Output,
|
||||
fun(Host, #offline_msg{us = {LUser, LServer},
|
||||
fun(Host, #offline_msg{user_host = {LUser, LServer},
|
||||
timestamp = TimeStamp,
|
||||
from = From,
|
||||
to = To,
|
||||
packet = Packet})
|
||||
packet = PacketString})
|
||||
when LServer == Host ->
|
||||
Username = ejabberd_odbc:escape(LUser),
|
||||
[Packet] = exmpp_xml:parse_document(PacketString, [names_as_atom]),
|
||||
Packet0 = exmpp_stanza:set_jids(Packet,
|
||||
exmpp_jid:to_list(From),
|
||||
exmpp_jid:to_list(To)),
|
||||
Packet0b = exmpp_xml:append_child(Packet0,
|
||||
jlib:timestamp_to_xml(
|
||||
calendar:now_to_universal_time(TimeStamp),
|
||||
calendar:gregorian_seconds_to_datetime(TimeStamp),
|
||||
utc,
|
||||
exmpp_jid:make("", Server, ""),
|
||||
"Offline Storage")),
|
||||
%% TODO: Delete the next three lines once XEP-0091 is Obsolete
|
||||
Packet1 = exmpp_xml:append_child(Packet0b,
|
||||
jlib:timestamp_to_xml(
|
||||
calendar:now_to_universal_time(TimeStamp))),
|
||||
calendar:gregorian_seconds_to_datetime(TimeStamp))),
|
||||
XML =
|
||||
ejabberd_odbc:escape(
|
||||
exmpp_xml:document_to_list(Packet1)),
|
||||
["insert into spool(username, xml) "
|
||||
"values ('", Username, "', '",
|
||||
["insert into spool(host, username, xml) "
|
||||
"values ('", Server, "', '", Username, "', '",
|
||||
XML,
|
||||
"');"];
|
||||
"');\n"];
|
||||
(_Host, _R) ->
|
||||
[]
|
||||
end).
|
||||
@ -153,16 +164,16 @@ export_last(ServerS, Output) ->
|
||||
Server = list_to_binary(ServerS),
|
||||
export_common(
|
||||
Server, last_activity, Output,
|
||||
fun(Host, #last_activity{us = {LUser, LServer},
|
||||
fun(Host, #last_activity{user_host = {LUser, LServer},
|
||||
timestamp = TimeStamp,
|
||||
status = Status})
|
||||
when LServer == Host ->
|
||||
Username = ejabberd_odbc:escape(LUser),
|
||||
Seconds = ejabberd_odbc:escape(integer_to_list(TimeStamp)),
|
||||
State = ejabberd_odbc:escape(Status),
|
||||
["delete from last where username='", Username, "';"
|
||||
["delete from last where host='", ServerS, "' and username='", Username, "';\n"
|
||||
"insert into last(username, seconds, state) "
|
||||
"values ('", Username, "', '", Seconds, "', '", State, "');"];
|
||||
"values ('", Username, "', '", Seconds, "', '", State, "');\n"];
|
||||
(_Host, _R) ->
|
||||
[]
|
||||
end).
|
||||
@ -170,15 +181,15 @@ export_last(ServerS, Output) ->
|
||||
export_vcard(Server, Output) ->
|
||||
export_common(
|
||||
Server, vcard, Output,
|
||||
fun(Host, #vcard{us = {LUser, LServer},
|
||||
fun(Host, #vcard{user_host = {LUser, LServer},
|
||||
vcard = VCARD})
|
||||
when LServer == Host ->
|
||||
Username = ejabberd_odbc:escape(LUser),
|
||||
SVCARD = ejabberd_odbc:escape(
|
||||
exmpp_xml:document_to_list(VCARD)),
|
||||
["delete from vcard where username='", Username, "';"
|
||||
"insert into vcard(username, vcard) "
|
||||
"values ('", Username, "', '", SVCARD, "');"];
|
||||
["delete from vcard where host='", Server,"' and username='", Username, "';\n"
|
||||
"insert into vcard(host, username, vcard) "
|
||||
"values ('", Server, "', '", Username, "', '", SVCARD, "');\n"];
|
||||
(_Host, _R) ->
|
||||
[]
|
||||
end).
|
||||
@ -227,7 +238,7 @@ export_vcard_search(Server, Output) ->
|
||||
SOrgUnit = ejabberd_odbc:escape(OrgUnit),
|
||||
SLOrgUnit = ejabberd_odbc:escape(LOrgUnit),
|
||||
|
||||
["delete from vcard_search where lusername='", LUsername, "';"
|
||||
["delete from vcard_search where host='", Server, "' and lusername='", LUsername, "';\n"
|
||||
"insert into vcard_search("
|
||||
" username, lusername, fn, lfn, family, lfamily,"
|
||||
" given, lgiven, middle, lmiddle, nickname, lnickname,"
|
||||
@ -245,7 +256,7 @@ export_vcard_search(Server, Output) ->
|
||||
" '", SLocality, "', '", SLLocality, "',"
|
||||
" '", SEMail, "', '", SLEMail, "',"
|
||||
" '", SOrgName, "', '", SLOrgName, "',"
|
||||
" '", SOrgUnit, "', '", SLOrgUnit, "');"];
|
||||
" '", SOrgUnit, "', '", SLOrgUnit, "');\n"];
|
||||
(_Host, _R) ->
|
||||
[]
|
||||
end).
|
||||
@ -254,7 +265,7 @@ export_private_storage(ServerS, Output) ->
|
||||
Server = list_to_binary(ServerS),
|
||||
export_common(
|
||||
Server, private_storage, Output,
|
||||
fun(Host, #private_storage{usns = {LUser, LServer, XMLNS},
|
||||
fun(Host, #private_storage{user_host_ns = {LUser, LServer, XMLNS},
|
||||
xml = Data})
|
||||
when LServer == Host ->
|
||||
Username = ejabberd_odbc:escape(LUser),
|
||||
@ -295,7 +306,7 @@ export_common(Server, Table, Output, ConvertFun) ->
|
||||
true ->
|
||||
%% Execute full SQL transaction
|
||||
output(LServer, IO,
|
||||
["begin;",
|
||||
["begin;\n",
|
||||
lists:reverse([SQL | SQLs]),
|
||||
"commit"]),
|
||||
{0, []}
|
||||
@ -304,7 +315,7 @@ export_common(Server, Table, Output, ConvertFun) ->
|
||||
end, {0, []}, Table),
|
||||
%% Execute SQL transaction with remaining records
|
||||
output(LServer, IO,
|
||||
["begin;",
|
||||
["begin;\n",
|
||||
lists:reverse(SQLs),
|
||||
"commit"])
|
||||
end).
|
||||
@ -317,11 +328,11 @@ output(LServer, IO, SQL) ->
|
||||
file:write(IO, [SQL, $;, $\n])
|
||||
end.
|
||||
|
||||
record_to_string(#roster{usj = {User, _Server, {N, D, R} = _JID},
|
||||
record_to_string(#rosteritem{user_host_jid = {User, _Server, {N, D, R} = _JID},
|
||||
name = Name,
|
||||
subscription = Subscription,
|
||||
ask = Ask,
|
||||
askmessage = AskMessage}) ->
|
||||
askmessage = AskMessage}, ServerS) ->
|
||||
Username = ejabberd_odbc:escape(User),
|
||||
SJID = ejabberd_odbc:escape(exmpp_jid:to_list(N, D, R)),
|
||||
Nick = ejabberd_odbc:escape(Name),
|
||||
@ -348,6 +359,7 @@ record_to_string(#roster{usj = {User, _Server, {N, D, R} = _JID},
|
||||
SAM
|
||||
end,
|
||||
["("
|
||||
"'", ServerS, "',"
|
||||
"'", Username, "',"
|
||||
"'", SJID, "',"
|
||||
"'", Nick, "',"
|
||||
@ -356,11 +368,12 @@ record_to_string(#roster{usj = {User, _Server, {N, D, R} = _JID},
|
||||
"'", SAskMessage, "',"
|
||||
"'N', '', 'item')"].
|
||||
|
||||
groups_to_string(#roster{usj = {User, _Server, {N, D, R} = _JID},
|
||||
groups = Groups}) ->
|
||||
group_to_string(#rostergroup{user_host_jid = {User, _Server, {N, D, R} = _JID},
|
||||
grp = Group}, ServerS) ->
|
||||
Username = ejabberd_odbc:escape(User),
|
||||
SJID = ejabberd_odbc:escape(exmpp_jid:to_list(N, D, R)),
|
||||
[["("
|
||||
["("
|
||||
"'", ServerS, "',"
|
||||
"'", Username, "',"
|
||||
"'", SJID, "',"
|
||||
"'", ejabberd_odbc:escape(Group), "')"] || Group <- Groups].
|
||||
"'", ejabberd_odbc:escape(Group), "')"].
|
||||
|
@ -133,17 +133,19 @@ store_room(Host, Name, Opts) when is_binary(Host), is_binary(Name) ->
|
||||
{_, _} = A -> A;
|
||||
A when is_atom(A) -> {A, ""}
|
||||
end,
|
||||
{Username, Server, Resource} = JID,
|
||||
gen_storage:write(
|
||||
Host,
|
||||
#muc_room_affiliation{name_host = {Name, Host},
|
||||
jid = jlib:make_jid(JID),
|
||||
jid = exmpp_jid:make(Username, Server, Resource),
|
||||
affiliation = Affiliation,
|
||||
reason = Reason})
|
||||
end, Affiliations);
|
||||
({Opt, Val}) ->
|
||||
ValS = if
|
||||
is_integer(Val) -> integer_to_list(Val);
|
||||
is_list(Val);
|
||||
is_binary(Val) -> binary_to_list(Val);
|
||||
is_list(Val) -> Val;
|
||||
is_atom(Val) -> Val
|
||||
end,
|
||||
gen_storage:write(Host,
|
||||
@ -194,7 +196,7 @@ restore_room_internal(Host, Name) ->
|
||||
"" -> Affiliation;
|
||||
_ -> {Affiliation, Reason}
|
||||
end,
|
||||
{jlib:jid_tolower(JID), A}
|
||||
{jlib:short_prepd_jid(JID), A}
|
||||
end, RoomAffiliations),
|
||||
[{affiliations, Affiliations} | Opts].
|
||||
|
||||
@ -646,7 +648,7 @@ load_permanent_rooms(Host, ServerHost, Access, HistorySize, RoomShaper) ->
|
||||
start_new_room(Host, ServerHost, Access, Room,
|
||||
HistorySize, RoomShaper, From,
|
||||
Nick, DefRoomOpts) ->
|
||||
case gen_storage:read(Host, {muc_room_opt, {Room, Host}}) of
|
||||
case gen_storage:dirty_read(Host, {muc_room_opt, {Room, Host}}) of
|
||||
[] ->
|
||||
?DEBUG("MUC: open new room '~s'~n", [Room]),
|
||||
mod_muc_room:start(Host, ServerHost, Access,
|
||||
@ -711,7 +713,7 @@ iq_disco_items(Host, From, Lang, none) when is_binary(Host) ->
|
||||
flush(),
|
||||
{true,
|
||||
{xmlelement, "item",
|
||||
[{"jid", jlib:jid_to_string({Name, Host, ""})},
|
||||
[{"jid", exmpp_jid:to_list(Name, Host, "")},
|
||||
{"name", Desc}], []}};
|
||||
_ ->
|
||||
false
|
||||
@ -735,7 +737,7 @@ iq_disco_items(Host, From, Lang, Rsm) ->
|
||||
_ ->
|
||||
false
|
||||
end
|
||||
end, get_vh_rooms_all_nodes(Host)).
|
||||
end, Rooms) ++ RsmOut.
|
||||
|
||||
get_vh_rooms(Host, #rsm_in{max=M, direction=Direction, id=I, index=Index})->
|
||||
AllRooms = get_vh_rooms_all_nodes(Host),
|
||||
|
Loading…
Reference in New Issue
Block a user