]> CyberLeo.Net >> Repos - SourceForge/phpwiki.git/blob - lib/plugin/LdapSearch.php
function run: @return mixed
[SourceForge/phpwiki.git] / lib / plugin / LdapSearch.php
1 <?php
2 /**
3  * Copyright 2004 John Lines
4  * Copyright 2007 $ThePhpWikiProgrammingTeam
5  *
6  * This file is part of PhpWiki.
7  *
8  * PhpWiki is free software; you can redistribute it and/or modify
9  * it under the terms of the GNU General Public License as published by
10  * the Free Software Foundation; either version 2 of the License, or
11  * (at your option) any later version.
12  *
13  * PhpWiki is distributed in the hope that it will be useful,
14  * but WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16  * GNU General Public License for more details.
17  *
18  * You should have received a copy of the GNU General Public License along
19  * with PhpWiki; if not, write to the Free Software Foundation, Inc.,
20  * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
21  */
22
23 /**
24  * WikiPlugin which searches an LDAP directory.
25  *
26  * Uses the config.ini constants as defaults.
27  * See http://phpwiki.fr/LdapSearchPlugin
28  * TODO: Return a pagelist on certain attributes
29  *
30  * Usage Samples:
31 <<LdapSearch>>
32 <<LdapSearch
33 host="localhost"
34 port=389
35 basedn=""
36 filter="(cn=*)"
37 attributes=""
38 >>
39 <<LdapSearch host=ldap.example.com filter="(ou=web-team)"
40 attributes="sn cn telephonenumber" >>
41 <<LdapSearch host="ldap.itd.umich.edu" basedn="" filter="(sn=jensen)" attributes="cn drink" >>
42 <<LdapSearch host=ldap.example.com attributes="cn sn telephonenumber" >>
43 <<LdapSearch host=bugs.debian.org port=10101 basedn="dc=current,dc=bugs,dc=debian,dc=org"
44 filter="(debbugsPackage=phpwiki)"
45 attributes="debbugsSeverity debbugsState debbugsTitle" >>
46  * @author John Lines
47  */
48
49 class WikiPlugin_LdapSearch
50     extends WikiPlugin
51 {
52     function getDescription()
53     {
54         return _("Search an LDAP directory.");
55     }
56
57     function getDefaultArguments()
58     {
59         return array('host' => "", // default: LDAP_AUTH_HOST
60             'port' => 389, // ignored if host = full uri
61             'basedn' => "", // LDAP_BASE_DN
62             'filter' => "(cn=*)",
63             'attributes' => "",
64             'user' => '',
65             'password' => '',
66             'options' => "",
67         );
68     }
69
70     /**
71      * @param WikiDB $dbi
72      * @param string $argstr
73      * @param WikiRequest $request
74      * @param string $basepage
75      * @return mixed
76      */
77     function run($dbi, $argstr, &$request, $basepage)
78     {
79         $args = $this->getArgs($argstr, $request);
80         extract($args);
81         //include_once("lib/WikiUser/LDAP.php");
82         if (!$host) {
83             if (defined('LDAP_AUTH_HOST')) {
84                 $host = LDAP_AUTH_HOST;
85                 if (strstr(LDAP_AUTH_HOST, '://'))
86                     $port = null;
87             } else {
88                 $host = 'localhost';
89             }
90         } else {
91             if (strstr($host, '://'))
92                 $port = null;
93         }
94         $html = HTML();
95         if (is_null($port))
96             $connect = ldap_connect($host);
97         else
98             $connect = ldap_connect($host, $port);
99         if (!$connect)
100             return $this->error(_("Failed to connect to LDAP host"));
101         if (!$options and defined('LDAP_AUTH_HOST') and $args['host'] == LDAP_AUTH_HOST) {
102             if (!empty($GLOBALS['LDAP_SET_OPTION'])) {
103                 $options = $GLOBALS['LDAP_SET_OPTION'];
104             }
105         }
106         if ($options) {
107             foreach ($options as $key => $value) {
108                 if (!ldap_set_option($connect, $key, $value))
109                     $this->error(_("Failed to set LDAP $key $value"));
110             }
111         }
112
113         // special convenience: if host = LDAP_AUTH_HOST
114         // then take user and password from config.ini also
115         if ($user) {
116             if ($password)
117                 // required for Windows Active Directory Server
118                 $bind = ldap_bind($connect, $user, $password);
119             else
120                 $bind = ldap_bind($connect, $user);
121         } elseif (defined('LDAP_AUTH_HOST') and $args['host'] == LDAP_AUTH_HOST) {
122             if (LDAP_AUTH_USER)
123                 if (LDAP_AUTH_PASSWORD)
124                     // Windows Active Directory Server is strict
125                     $r = ldap_bind($connect, LDAP_AUTH_USER, LDAP_AUTH_PASSWORD);
126                 else
127                     $r = ldap_bind($connect, LDAP_AUTH_USER);
128             else // anonymous bind
129                 $bind = ldap_bind($connect);
130         } else { // other anonymous bind
131             $bind = ldap_bind($connect);
132         }
133         if (!$bind) return $this->error(_("Failed to bind LDAP host"));
134         if (!$basedn) $basedn = LDAP_BASE_DN;
135         $attr_array = array("");
136         if (!$attributes) {
137             $res = ldap_search($connect, $basedn, $filter);
138         } else {
139             $attr_array = explode(" ", $attributes);
140             $res = ldap_search($connect, $basedn, $filter, $attr_array);
141         }
142         $entries = ldap_get_entries($connect, $res);
143
144         // If we were given attributes then we return them in the order given
145         // else take all
146         if (!$attributes) {
147             $attr_array = array();
148             for ($ii = 0; $ii < $entries[0]["count"]; $ii++) {
149                 $data = $entries[0][$ii];
150                 $attr_array[] = $data;
151             }
152         }
153         for ($i = 0; $i < count($attr_array); $i++) {
154             $attrcols[$i] = 0;
155         }
156         // Work out how many columns we need for each attribute. objectclass has more
157         for ($i = 0; $i < $entries[0]["count"]; $i++) {
158             $data = $entries[0][$i];
159             $datalen = $entries[0][$data]["count"];
160             if ($attrcols[$i] < $datalen) {
161                 $attrcols[$i] = $datalen;
162             }
163         }
164         // Print the headers
165         $row = HTML::tr();
166         for ($i = 0; $i < count($attr_array); $i++) {
167             // span subcolumns, like objectclass
168             if ($attrcols[$i] > 1)
169                 $row->pushContent(HTML::th(array('colspan' => $attrcols[$i]), $attr_array[$i]));
170             else
171                 $row->pushContent(HTML::th(array(), $attr_array[$i]));
172         }
173         $html->pushContent($row);
174
175         // Print the data rows
176         for ($currow = 0; $currow < $entries["count"]; $currow++) {
177             $row = HTML::tr();
178             $nc = 0;
179             // columns
180             for ($i = 0; $i < count($attr_array); $i++) {
181                 $colname = $attr_array[$i];
182                 $data = @$entries[$currow][$colname];
183                 if ($data and $data["count"] > 0) {
184                     // subcolumns, e.g. for objectclass
185                     for ($iii = 0; $iii < $data["count"]; $iii++) {
186                         $row->pushContent(HTML::td($data[$iii]));
187                         $nc++;
188                     }
189                 } else {
190                     $row->pushContent(HTML::td(""));
191                     $nc++;
192                 }
193                 // Make up some blank cells if required to pad this row
194                 /*for ( $j=0 ; $j < ($attrcols[$ii] - $nc); $j++ ) {
195                     $row->pushContent(HTML::td(""));
196                 }*/
197             }
198             $html->pushContent($row);
199         }
200         return HTML::table(array('class' => 'bordered'), $html);
201     }
202 }
203
204 // Local Variables:
205 // mode: php
206 // tab-width: 8
207 // c-basic-offset: 4
208 // c-hanging-comment-ender-p: nil
209 // indent-tabs-mode: nil
210 // End: