Framework: First pass at fixing searchdn/writedn support
authorBen Klang <ben@alkaloid.net>
Tue, 8 Jun 2010 17:38:54 +0000 (13:38 -0400)
committerBen Klang <ben@alkaloid.net>
Tue, 8 Jun 2010 19:36:54 +0000 (15:36 -0400)
framework/Auth/lib/Horde/Auth/Ldap.php
framework/Core/lib/Horde/Config.php
framework/Ldap/lib/Horde/Ldap.php
horde/config/conf.xml

index 0f20dcc..9798ccb 100644 (file)
@@ -59,7 +59,7 @@ class Horde_Auth_Ldap extends Horde_Auth_Base
      */
     public function __construct(array $params = array())
     {
-        foreach (array('basedn', 'filter', 'ldap', 'objectclass', 'uid') as $val) {
+        foreach (array('basedn', 'filter', 'ldap', 'uid') as $val) {
             if (!isset($params[$val])) {
                 throw new InvalidArgumentException(__CLASS__ . ': Missing ' . $val . ' parameter.');
             }
index 32131a9..214a200 100644 (file)
@@ -681,9 +681,9 @@ class Horde_Config
             'default' => $this->_default($ctx . '|port', null)
         );
 
-        $writedn = array(
+        $writeas = array(
             'desc' => 'Bind to LDAP as which user when performing writes?',
-            'default' => $this->_default($ctx . '|writedn', 'search'),
+            'default' => $this->_default($ctx . '|writeas', 'search'),
             'switch' => array(
                 'user' => array(
                     'desc' => 'Bind as the currently logged-in user',
@@ -696,7 +696,7 @@ class Horde_Config
                             '_type' => 'text',
                             'required' => true,
                             'desc' => 'DN used to bind to LDAP for writes',
-                            'default' => $this->_default($ctx . '|writedn', '')
+                            'default' => $this->_default($ctx . '|writeas', '')
                         ),
                         'bindpw' => array(
                             '_type' => 'text',
@@ -729,7 +729,7 @@ class Horde_Config
 
         $custom_fields = array(
             'required' => true,
-            'desc' => 'Use a LDAP backend?',
+            'desc' => 'Use an LDAP backend?',
             'default' => $this->_default($ctx . '|useldap', 'false'),
             'switch' => array(
                 'false' => array(
@@ -746,7 +746,7 @@ class Horde_Config
                         'searchdn' => $searchdn,
                         'searchpw' => $searchpw,
                         'basedn' => $basedn,
-                        'writedn' => $writedn,
+                        'writeas' => $writeas,
                         'ca' => $ca
                     )
                 )
index 6091759..7472009 100644 (file)
@@ -50,8 +50,8 @@ class Horde_Ldap
      * port     = the server port
      * version  = ldap version (defaults to v 3)
      * starttls = when set, ldap_start_tls() is run after connecting.
-     * bindpw   = no explanation needed
-     * binddn   = the DN to bind as.
+     * searchpw = password to use when searching LDAP
+     * seachdn  = the DN to bind as when searching
      * basedn   = ldap base
      * options  = hash of ldap options to set (opt => val)
      * filter   = default search filter
@@ -75,8 +75,11 @@ class Horde_Ldap
                                'port'            => 389,
                                'version'         => 3,
                                'starttls'        => false,
-                               'binddn'          => '',
-                               'bindpw'          => '',
+                               'searchdn'        => '',
+                               'searchpw'        => '',
+                               'writeas'         => 'search',
+                               'writedn'         => '',
+                               'writepw'         => '',
                                'basedn'          => '',
                                'options'         => array(),
                                'filter'          => '(objectClass=*)',
@@ -237,10 +240,10 @@ class Horde_Ldap
                 // map old (Net_Ldap) parms to new ones
                 switch($k) {
                 case "dn":
-                    $this->_config["binddn"] = $v;
+                    $this->_config["searchdn"] = $v;
                     break;
                 case "password":
-                    $this->_config["bindpw"] = $v;
+                    $this->_config["searchpw"] = $v;
                     break;
                 case "tls":
                     $this->_config["starttls"] = $v;
@@ -297,11 +300,11 @@ class Horde_Ldap
     public function bind($dn = null, $password = null)
     {
         // fetch current bind credentials
-        if (is_null($dn)) {
-            $dn = $this->_config["binddn"];
+        if (empty($dn)) {
+            $dn = $this->_config["searchdn"];
         }
-        if (is_null($password)) {
-            $password = $this->_config["bindpw"];
+        if (empty($password)) {
+            $password = $this->_config["searchpw"];
         }
 
         // Connect first, if we haven't so far.
@@ -309,20 +312,20 @@ class Horde_Ldap
         if ($this->_link === false) {
             // store old credentials so we can revert them later
             // then overwrite config with new bind credentials
-            $olddn = $this->_config["binddn"];
-            $oldpw = $this->_config["bindpw"];
+            $olddn = $this->_config["searchdn"];
+            $oldpw = $this->_config["searchpw"];
 
             // overwrite bind credentials in config
             // so performConnect() knows about them
-            $this->_config["binddn"] = $dn;
-            $this->_config["bindpw"] = $password;
+            $this->_config["searchdn"] = $dn;
+            $this->_config["searchpw"] = $password;
 
             // try to connect with provided credentials
             $msg = $this->performConnect();
 
             // reset to previous config
-            $this->_config["binddn"] = $olddn;
-            $this->_config["bindpw"] = $oldpw;
+            $this->_config["searchdn"] = $olddn;
+            $this->_config["searchpw"] = $oldpw;
         } else {
             // do the requested bind as we are
             // asked to bind manually
@@ -663,9 +666,13 @@ class Horde_Ldap
      */
     public function add(Horde_Ldap_Entry &$entry)
     {
+        // Rebind as the write DN
+        if (!empty($this->writedn)) {
+            $this->bind($this->writedn, $this->writepw);
+        }
+
         // Continue attempting the add operation in a loop until we
         // get a success, a definitive failure, or the world ends.
-        $foo = 0;
         while (true) {
             $link = $this->getLink();
 
@@ -732,6 +739,12 @@ class Horde_Ldap
         if (false === is_string($dn)) {
             throw new Horde_Ldap_Exception("Parameter is not a string nor an entry object!");
         }
+
+        // Re-bind as the write DN if not using searchdn credentials
+        if (!empty($this->writedn)) {
+            $this->bind($this->writedn, $this->writepw);
+        }
+
         // Recursive delete searches for children and calls delete for them
         if ($recursive) {
             $result = @ldap_list($this->_link, $dn, '(objectClass=*)', array(null), 0, 0);
@@ -831,6 +844,11 @@ class Horde_Ldap
      */
     public function modify($entry, $parms = array())
     {
+        // Re-bind as the write DN
+        if (!empty($this->writedn)) {
+            $this->bind($this->writedn, $this->writepw);
+        }
+
         if (is_string($entry)) {
             $entry = $this->getEntry($entry);
         }
index 3202d93..9abcc4a 100644 (file)
        cn,sn,userPassword attributes as well as the username search key">
        shadowAccount,inetOrgPerson</configlist>
 
-       <configswitch name="filter" desc="How to specify a filter for the
-       user lists">objectclass
-        <case name="objectclass" desc="One or more objectclass filters">
-         <configlist name="objectclass" desc="The objectclass filter used to
-         search for users. Can be a single objectclass or a list."/>
-        </case>
-        <case name="free" desc="A complete LDAP filter expression">
-         <configstring name="filter" desc="The LDAP RFC formatted filter used
-         to search for users."/>
-        </case>
-       </configswitch>
+       <configstring name="filter" desc="The LDAP RFC formatted filter used
+         to search for users.">(objectclass=*)
+       </configstring>
 
        <configswitch name="password_expiration" desc="Enable the creating of
        accounts with expiring passwords? (Note: New users should have the