1 |
%%%---------------------------------------------------------------------- |
2 |
%%% File : ejabberd_auth_ad.erl |
3 |
%%% Author : Alexey Shchepin <alexey@sevcom.net> |
4 |
%%% Author : Alex Gorbachenko <agent_007@immo.ru> |
5 |
%%% Author : Stanislav Bogatyrev <realloc@realloc.spb.ru> |
6 |
%%% Purpose : Authentification via Active Directory |
7 |
%%% Created : 12 Dec 2004 by Alexey Shchepin <alexey@sevcom.net> |
8 |
%%% Id : $Id: ejabberd_auth_ad.erl 386 2005-12-20 10:06:37Z agent_007 $ |
9 |
%%%---------------------------------------------------------------------- |
10 |
|
11 |
-module(ejabberd_auth_ad). |
12 |
-author('alexey@sevcom.net'). |
13 |
-author('agent_007@immo.ru'). |
14 |
-author('realloc@realloc.spb.ru'). |
15 |
-vsn('$Revision: 386 $ '). |
16 |
|
17 |
%% External exports |
18 |
-export([start/1, |
19 |
set_password/3, |
20 |
check_password/3, |
21 |
check_password/5, |
22 |
try_register/3, |
23 |
dirty_get_registered_users/0, |
24 |
get_vh_registered_users/1, |
25 |
get_password/2, |
26 |
get_password_s/2, |
27 |
is_user_exists/2, |
28 |
remove_user/2, |
29 |
remove_user/3, |
30 |
plain_password_required/0 |
31 |
]). |
32 |
|
33 |
-include("ejabberd.hrl"). |
34 |
-include("eldap/eldap.hrl"). |
35 |
|
36 |
%%%---------------------------------------------------------------------- |
37 |
%%% API |
38 |
%%%---------------------------------------------------------------------- |
39 |
start(Host) -> |
40 |
LDAPServers = ejabberd_config:get_local_option({ad_servers, Host}), |
41 |
RootDN = ejabberd_config:get_local_option({ad_rootdn, Host}), |
42 |
Password = ejabberd_config:get_local_option({ad_password, Host}), |
43 |
eldap:start_link(get_eldap_id(Host, ejabberd), |
44 |
LDAPServers, 389, RootDN, Password), |
45 |
eldap:start_link(get_eldap_id(Host, ejabberd_bind), |
46 |
LDAPServers, 389, RootDN, Password), |
47 |
ok. |
48 |
|
49 |
plain_password_required() -> |
50 |
true. |
51 |
|
52 |
check_password(User, Server, Password) -> |
53 |
case find_user_dn(User, Server) of |
54 |
false -> |
55 |
false; |
56 |
DN -> |
57 |
LServer = jlib:nameprep(Server), |
58 |
case eldap:bind(get_eldap_id(LServer, ejabberd_bind), |
59 |
DN, Password) of |
60 |
ok -> |
61 |
true; |
62 |
_ -> |
63 |
false |
64 |
end |
65 |
end. |
66 |
|
67 |
check_password(User, Server, Password, _StreamID, _Digest) -> |
68 |
check_password(User, Server, Password). |
69 |
|
70 |
set_password(_User, _Server, _Password) -> |
71 |
{error, not_allowed}. |
72 |
|
73 |
try_register(_User, _Server, _Password) -> |
74 |
{error, not_allowed}. |
75 |
|
76 |
dirty_get_registered_users() -> |
77 |
get_vh_registered_users(?MYNAME). |
78 |
|
79 |
get_vh_registered_users(Server) -> |
80 |
LServer = jlib:nameprep(Server), |
81 |
Attr = ejabberd_config:get_local_option({ad_uidattr, LServer}), |
82 |
% AdGroup = ejabberd_config:get_local_option({ad_group, LServer}), |
83 |
FilterPerson = eldap:equalityMatch("objectCategory", "person"), |
84 |
FilterComp = eldap:equalityMatch("objectClass", "computer"), |
85 |
FilterHidden = eldap:equalityMatch("description", "hidden"), |
86 |
% FilterGroup = eldap:equalityMatch("memberOf", AdGroup), |
87 |
FilterLive = eldap:equalityMatch("userAccountControl", "66050"), |
88 |
FilterDef = eldap:present(Attr), |
89 |
Filter = eldap:'and'([ |
90 |
FilterDef, |
91 |
FilterPerson, |
92 |
% FilterGroup, |
93 |
eldap:'not'(FilterComp), |
94 |
eldap:'not'(FilterHidden), |
95 |
eldap:'not'(FilterLive)]), |
96 |
Base = ejabberd_config:get_local_option({ad_base, LServer}), |
97 |
case eldap:search(get_eldap_id(LServer, ejabberd), |
98 |
[{base, Base}, |
99 |
{filter, Filter}, |
100 |
{attributes, [Attr]}]) of |
101 |
#eldap_search_result{entries = Es} -> |
102 |
lists:flatmap( |
103 |
fun(E) -> |
104 |
case lists:keysearch(Attr, 1, E#eldap_entry.attributes) of |
105 |
{value, {_, [U]}} -> |
106 |
case jlib:nodeprep(U) of |
107 |
error -> |
108 |
[]; |
109 |
LU -> |
110 |
[{LU, LServer}] |
111 |
end; |
112 |
_ -> |
113 |
[] |
114 |
end |
115 |
end, Es); |
116 |
_ -> |
117 |
[] |
118 |
end. |
119 |
|
120 |
get_password(_User, _Server) -> |
121 |
false. |
122 |
|
123 |
get_password_s(_User, _Server) -> |
124 |
"". |
125 |
|
126 |
is_user_exists(User, Server) -> |
127 |
case find_user_dn(User, Server) of |
128 |
false -> |
129 |
false; |
130 |
_DN -> |
131 |
true |
132 |
end. |
133 |
|
134 |
remove_user(_User, _Server) -> |
135 |
{error, not_allowed}. |
136 |
|
137 |
remove_user(_User, _Server, _Password) -> |
138 |
not_allowed. |
139 |
|
140 |
|
141 |
%%%---------------------------------------------------------------------- |
142 |
%%% Internal functions |
143 |
%%%---------------------------------------------------------------------- |
144 |
|
145 |
find_user_dn(User, Server) -> |
146 |
LServer = jlib:nameprep(Server), |
147 |
AdGroup = ejabberd_config:get_local_option({ad_group, LServer}), |
148 |
Attr = ejabberd_config:get_local_option({ad_uidattr, LServer}), |
149 |
FilterAttr = eldap:equalityMatch(Attr, User), |
150 |
FilterGroup = eldap:equalityMatch("memberOf", AdGroup), |
151 |
Filter = eldap:'and'([ |
152 |
FilterAttr, |
153 |
FilterGroup |
154 |
]), |
155 |
Base = ejabberd_config:get_local_option({ad_base, LServer}), |
156 |
case eldap:search(get_eldap_id(LServer, ejabberd), |
157 |
[{base, Base}, |
158 |
{filter, Filter}, |
159 |
{attributes, []}]) of |
160 |
#eldap_search_result{entries = [E | _]} -> |
161 |
E#eldap_entry.object_name; |
162 |
_ -> |
163 |
false |
164 |
end. |
165 |
|
166 |
get_eldap_id(Host, Name) -> |
167 |
atom_to_list(gen_mod:get_module_proc(Host, Name)). |