3 commits - lib/api lib/Auth lib/Auth.php

Aleksander Machniak machniak at kolabsys.com
Mon Mar 26 10:46:07 CEST 2012


 lib/Auth.php                       |    9 
 lib/Auth/LDAP.php                  |  652 +++++++++++++++++--------------------
 lib/api/kolab_api_service_user.php |   15 
 3 files changed, 312 insertions(+), 364 deletions(-)

New commits:
commit dc6628c308868b1091439b1e16ec1c45548c64ed
Author: Aleksander Machniak <machniak at kolabsys.com>
Date:   Mon Mar 26 10:45:27 2012 +0200

    Limit ldap_search() calls by fetching all extra user attributes in one call

diff --git a/lib/Auth.php b/lib/Auth.php
index aae59e7..a9f11c0 100644
--- a/lib/Auth.php
+++ b/lib/Auth.php
@@ -268,9 +268,9 @@ class Auth {
         return $this->_auth[$_SESSION['user']->get_domain()]->user_find_by_attribute($attribute);
     }
 
-    public function user_get_attribute($user, $attribute)
+    public function user_attributes($user, $attributes)
     {
-        return $this->_auth[$_SESSION['user']->get_domain()]->user_get_attribute($user, $attribute);
+        return $this->_auth[$_SESSION['user']->get_domain()]->user_attributes($user, $attributes);
     }
 
     public function user_info($userdata)
diff --git a/lib/Auth/LDAP.php b/lib/Auth/LDAP.php
index bd9cfc8..b5a94bf 100644
--- a/lib/Auth/LDAP.php
+++ b/lib/Auth/LDAP.php
@@ -437,16 +437,22 @@ class LDAP
         }
     }
 
-    public function user_get_attribute($user_dn, $attribute)
+    /**
+     * User attributes
+     *
+     *
+     */
+    public function user_attributes($user_dn, $attributes)
     {
-        $result = $this->search($user_dn, '(objectclass=*)', array($attribute));
+        $result = $this->search($user_dn, '(objectclass=*)', $attributes);
         $result = self::normalize_result($result);
 
-        if (!empty($result) && array_key_exists($attribute, $result[$user_dn])) {
-            return $result[$user_dn][$attribute];
-        } else {
-            return FALSE;
+        if (!empty($result)) {
+            $result = array_pop($result);
+            return $result;
         }
+
+        return false;
     }
 
     public function user_info($user)
diff --git a/lib/api/kolab_api_service_user.php b/lib/api/kolab_api_service_user.php
index 61cd7ce..8c60d33 100644
--- a/lib/api/kolab_api_service_user.php
+++ b/lib/api/kolab_api_service_user.php
@@ -159,18 +159,23 @@ class kolab_api_service_user extends kolab_api_service
         // Search for attributes associated with the type_id that are not part
         // of the results returned earlier. Example: nsrole / nsroledn / aci, etc.
         if ($result['user_type_id']) {
-            $uta = $this->user_type_attributes($result['user_type_id']);
+            $uta   = $this->user_type_attributes($result['user_type_id']);
+            $attrs = array();
 
             foreach ($uta as $field_type => $attributes) {
                 foreach ($attributes as $attribute => $data) {
                     if (!array_key_exists($attribute, $result)) {
-                        $attribute_value = $auth->user_get_attribute($result['entrydn'], $attribute);
-                        if ($attribute_value) {
-                            $result[$attribute] = $attribute_value;
-                        }
+                        $attrs[] = $attribute;
                     }
                 }
             }
+
+            if (!empty($attrs)) {
+                $attrs = $auth->user_attributes($result['entrydn'], $attrs);
+                if (!empty($attrs)) {
+                    $result = array_merge($result, $attrs);
+                }
+            }
         }
 
         if ($result) {


commit 4faca4946e79246feaa8939a3906981dca368ad6
Author: Aleksander Machniak <machniak at kolabsys.com>
Date:   Mon Mar 26 10:33:58 2012 +0200

    Limit ldap_bind() calls

diff --git a/lib/Auth/LDAP.php b/lib/Auth/LDAP.php
index 0bda119..bd9cfc8 100644
--- a/lib/Auth/LDAP.php
+++ b/lib/Auth/LDAP.php
@@ -30,13 +30,11 @@ class LDAP
 {
     public $_name = "LDAP";
 
-    // Needs to be protected and not just private
-    protected $_connection = NULL;
+    private $conn;
+    private $bind_dn;
+    private $bind_pw;
 
-    protected $user_bind_dn;
-    protected $user_bind_pw;
-
-    protected $attribute_level_rights_map = array(
+    private $attribute_level_rights_map = array(
             "r" => "read",
             "s" => "search",
             "w" => "write",
@@ -46,7 +44,7 @@ class LDAP
             "O" => "delete"
         );
 
-    protected $entry_level_rights_map = array(
+    private $entry_level_rights_map = array(
             "a" => "add",
             "d" => "delete",
             "n" => "modrdn",
@@ -62,7 +60,7 @@ class LDAP
     /**
      * Class constructor
      */
-    public function __construct($domain = NULL)
+    public function __construct($domain = null)
     {
         $this->conf = Conf::get_instance();
 
@@ -165,11 +163,6 @@ class LDAP
         }
     }
 
-    public function domain_exists($domain)
-    {
-        return $this->_ldap->domain_exists($domain);
-    }
-
     /*
         Translate a domain name into it's corresponding root dn.
     */
@@ -193,13 +186,13 @@ class LDAP
         }
 
         // TODO: Get domain_attr from config
-        if (($results = ldap_search($this->_connection, $conf->get('domain_base_dn'), '(associatedDomain=' . $domain . ')')) == false) {
+        if (($results = ldap_search($this->conn, $conf->get('domain_base_dn'), '(associatedDomain=' . $domain . ')')) == false) {
             error_log("No results?");
             return false;
         }
 
-        $domain = ldap_first_entry($this->_connection, $results);
-        $domain_info = ldap_get_attributes($this->_connection, $domain);
+        $domain = ldap_first_entry($this->conn, $results);
+        $domain_info = ldap_get_attributes($this->conn, $domain);
 
 //        echo "<pre>"; print_r($domain_info); echo "</pre>";
 
@@ -364,9 +357,9 @@ class LDAP
         return $roles;
     }
 
-    public function user_add($attrs, $type = NULL)
+    public function user_add($attrs, $type = null)
     {
-        if ($type == NULL) {
+        if ($type == null) {
             $type_str = 'user';
         }
         else {
@@ -695,11 +688,6 @@ class LDAP
         return strcmp(mb_strtoupper($str1), mb_strtoupper($str2));
     }
 
-    public function setup()
-    {
-        return $this->_ldap->setup();
-    }
-
     /**
      * Qualify a username.
      *
@@ -771,21 +759,6 @@ class LDAP
     }
 
     /*
-        Private functions
-     */
-
-    private function _domain_add_alias($domain, $domain_alias)
-    {
-        $this->_ldap->_domain_add_alias($domain, $domain_alias);
-    }
-
-    private function _domain_add_new($domain, $populatedomain)
-    {
-        $this->connect();
-        $this->_ldap->_domain_add_new($domain, $populatedomain);
-    }
-
-    /*
 
         Shortcut functions
 
@@ -801,7 +774,7 @@ class LDAP
         $this->_connect();
         $this->_bind($_SESSION['user']->user_bind_dn, $_SESSION['user']->user_bind_pw);
 
-        if (($add_result = ldap_add($this->_connection, $entry_dn, $attributes)) == false) {
+        if (($add_result = ldap_add($this->conn, $entry_dn, $attributes)) == false) {
             // Issue warning
             return false;
         }
@@ -816,21 +789,27 @@ class LDAP
     {
         $this->_connect();
 
+        if (!$this->conn || !$dn || !$pw) {
+            return false;
+        }
+
+        if ($dn == $this->bind_dn && $pw == $this->bind_pw) {
+            return true;
+        }
+
         // TODO: Debug logging
         error_log("->_bind() Binding with $dn");
 
-        if (!$dn || !$pw) {
-            return false;
-        }
+        $this->bind_dn = $dn;
+        $this->bind_pw = $pw;
 
-        if (($bind_ok = ldap_bind($this->_connection, $dn, $pw)) == false) {
+        if (($bind_ok = ldap_bind($this->conn, $dn, $pw)) == false) {
             error_log("LDAP Error: " . $this->_errstr());
             // Issue error message
             return false;
         }
-        else {
-            return true;
-        }
+
+        return true;
     }
 
     /**
@@ -838,26 +817,23 @@ class LDAP
      */
     private function _connect()
     {
-        if ($this->_connection == false) {
+        if (!$this->conn) {
             // TODO: Debug logging
             error_log("Connecting to " . $this->_ldap_server . " on port " . $this->_ldap_port);
             $connection = ldap_connect($this->_ldap_server, $this->_ldap_port);
 
             if ($connection == false) {
-                $this->_connection = false;
+                $this->conn = null;
                 // TODO: Debug logging
                 error_log("Not connected: " . ldap_err2str() .  "(no.) " . ldap_errno());
             }
             else {
-                $this->_connection = $connection;
+                $this->conn = $connection;
             }
 
             // TODO: Debug logging
             error_log("Connected!");
         }
-        else {
-            error_log("Already connected");
-        }
     }
 
     /**
@@ -869,7 +845,7 @@ class LDAP
         // Always bind with the session credentials
         $this->_bind($_SESSION['user']->user_bind_dn, $_SESSION['user']->user_bind_pw);
 
-        if (($delete_result = ldap_delete($this->_connection, $entry_dn)) == false) {
+        if (($delete_result = ldap_delete($this->conn, $entry_dn)) == false) {
             // Issue warning
             return false;
         }
@@ -883,18 +859,18 @@ class LDAP
      */
     private function _disconnect()
     {
-        if ($this->_connection == false) {
+        if (!$this->conn) {
             return true;
         }
 
-        if (($result = ldap_close($this->_connection)) == true) {
-            $this->_connection = false;
+        if (($result = ldap_close($this->conn)) == true) {
+            $this->conn = null;
+            $this->bind_dn = null;
+            $this->bind_pw = null;
+
             return true;
         }
 
-        // Issue a warning
-        $this->_connection = false;
-        $this->_ldap = false;
         return false;
     }
 
@@ -903,14 +879,14 @@ class LDAP
      */
     private function _errstr()
     {
-        if ($errno = @ldap_errno($this->_connection)) {
+        if ($errno = @ldap_errno($this->conn)) {
             if ($err2str = @ldap_err2str($errno)) {
                 return $err2str;
             }
         }
 
         // Issue warning
-        return NULL;
+        return null;
     }
 
     /**
@@ -923,11 +899,11 @@ class LDAP
     {
         $ldap_entries = array( "count" => 0 );
 
-        if (($ldap_list = @ldap_list($this->_connection, $base_dn, $filter)) == false) {
+        if (($ldap_list = @ldap_list($this->conn, $base_dn, $filter)) == false) {
             //message("LDAP Error: Could not search " . $base_dn . ": " . $this->_errstr() );
         }
         else {
-            if (($ldap_entries = @ldap_get_entries($this->_connection, $ldap_list)) == false) {
+            if (($ldap_entries = @ldap_get_entries($this->conn, $ldap_list)) == false) {
                 //message("LDAP Error: No entries for " . $filter . " in " . $base_dn . ": " . $this->_errstr());
             }
         }
@@ -943,12 +919,12 @@ class LDAP
         error_log("Searching with user " . $_SESSION['user']->user_bind_dn);
         $this->_bind($_SESSION['user']->user_bind_dn, $_SESSION['user']->user_bind_pw);
 
-        if (($search_results = @ldap_search($this->_connection, $base_dn, $search_filter, $attributes)) == false) {
+        if (($search_results = @ldap_search($this->conn, $base_dn, $search_filter, $attributes)) == false) {
             //message("Could not search in " . __METHOD__ . " in " . __FILE__ . " on line " . __LINE__ . ": " . $this->_errstr());
             return false;
         }
 
-        if (($entries = ldap_get_entries($this->_connection, $search_results)) == false) {
+        if (($entries = ldap_get_entries($this->conn, $search_results)) == false) {
             //message("Could not get the results of the search: " . $this->_errstr());
             return false;
         }
@@ -1006,8 +982,11 @@ class LDAP
     private function _unbind($yes = false, $really = false)
     {
         if ($yes && $really) {
-            ldap_unbind($this->_connection);
-            $this->_connection = false;
+            ldap_unbind($this->conn);
+
+            $this->conn    = null;
+            $this->bind_dn = null;
+            $this->bind_pw = null;
         }
         else {
             // What?
@@ -1035,26 +1014,26 @@ class LDAP
     private function _probe_root_dn($entry_root_dn)
     {
         error_log("Running for entry root dn: " . $entry_root_dn);
-        if (($tmp_connection = ldap_connect($this->_ldap_server)) == false) {
+        if (($tmpconn = ldap_connect($this->_ldap_server)) == false) {
             //message("LDAP Error: " . $this->_errstr());
             return false;
         }
 
         error_log("User DN: " . $_SESSION['user']->user_bind_dn);
 
-        if (($bind_success = ldap_bind($tmp_connection, $_SESSION['user']->user_bind_dn, $_SESSION['user']->user_bind_pw)) == false) {
+        if (($bind_success = ldap_bind($tmpconn, $_SESSION['user']->user_bind_dn, $_SESSION['user']->user_bind_pw)) == false) {
             //message("LDAP Error: " . $this->_errstr());
             return false;
         }
 
-        if (($list_success = ldap_list($tmp_connection, $entry_root_dn, '(objectClass=*)', array('*', 'aci'))) == false) {
+        if (($list_success = ldap_list($tmpconn, $entry_root_dn, '(objectClass=*)', array('*', 'aci'))) == false) {
             //message("LDAP Error: " . $this->_errstr());
             return false;
         }
 
-//        print_r(ldap_get_entries($tmp_connection, $list_success));
+//        print_r(ldap_get_entries($tmpconn, $list_success));
 /*
-        if (ldap_count_entries($tmp_connection, $list_success) == 0) {
+        if (ldap_count_entries($tmpconn, $list_success) == 0) {
             echo "<li>Listed things, but got no results";
             return false;
         }
@@ -1103,17 +1082,17 @@ class LDAP
             $this->_bind($this->conf->get('manager_bind_dn'), $this->conf->get('manager_bind_pw'));
         }
 
-        $search_results = ldap_search($this->_connection, $root_dn, $search_filter);
+        $search_results = ldap_search($this->conn, $root_dn, $search_filter);
 
-        if (ldap_count_entries($this->_connection, $search_results) == 0) {
+        if (ldap_count_entries($this->conn, $search_results) == 0) {
             return false;
         }
 
-        if (($first_entry = ldap_first_entry($this->_connection, $search_results)) == false) {
+        if (($first_entry = ldap_first_entry($this->conn, $search_results)) == false) {
             return false;
         }
 
-        $group_dn = ldap_get_dn($this->_connection, $first_entry);
+        $group_dn = ldap_get_dn($this->conn, $first_entry);
         return $group_dn;
     }
 
@@ -1128,18 +1107,18 @@ class LDAP
             $this->_bind($this->conf->get('manager_bind_dn'), $this->conf->get('manager_bind_pw'));
         }
 
-        $search_results = ldap_search($this->_connection, $root_dn, $search_filter);
+        $search_results = ldap_search($this->conn, $root_dn, $search_filter);
 
-        if (ldap_count_entries($this->_connection, $search_results) == 0) {
+        if (ldap_count_entries($this->conn, $search_results) == 0) {
             //message("No entries found for the user dn in " . __METHOD__);
             return false;
         }
 
-        if (($first_entry = ldap_first_entry($this->_connection, $search_results)) == false) {
+        if (($first_entry = ldap_first_entry($this->conn, $search_results)) == false) {
             return false;
         }
 
-        $user_dn = ldap_get_dn($this->_connection, $first_entry);
+        $user_dn = ldap_get_dn($this->conn, $first_entry);
         return $user_dn;
     }
 
@@ -1194,13 +1173,13 @@ class LDAP
         // Use the member attributes to return an array of member ldap objects
         // NOTE that the member attribute is supposed to contain a DN
         foreach ($entry['member'] as $member) {
-            $result = @ldap_read($this->_connection, $member, '(objectclass=*)');
+            $result = @ldap_read($this->conn, $member, '(objectclass=*)');
 
             if (!$result) {
                 continue;
             }
 
-            $member_entry = self::normalize_result(@ldap_get_entries($this->_connection, $result));
+            $member_entry = self::normalize_result(@ldap_get_entries($this->conn, $result));
             $group_members[$member] = array_pop($member_entry);
 
             // Nested groups
@@ -1225,13 +1204,13 @@ class LDAP
         }
 
         foreach ($entry['uniquemember'] as $member) {
-            $result = @ldap_read($this->_connection, $member, '(objectclass=*)');
+            $result = @ldap_read($this->conn, $member, '(objectclass=*)');
 
             if (!$result) {
                 continue;
             }
 
-            $member_entry = self::normalize_result(@ldap_get_entries($this->_connection, $result));
+            $member_entry = self::normalize_result(@ldap_get_entries($this->conn, $result));
             $group_members[$member] = array_pop($member_entry);
 
             // Nested groups


commit 8fdf2421cc4d8f76f9736e86127278334a776779
Author: Aleksander Machniak <machniak at kolabsys.com>
Date:   Mon Mar 26 10:11:39 2012 +0200

    Code cleanup and some fixes

diff --git a/lib/Auth.php b/lib/Auth.php
index de29e7f..aae59e7 100644
--- a/lib/Auth.php
+++ b/lib/Auth.php
@@ -253,11 +253,6 @@ class Auth {
         }
     }
 
-    public function search($attributes)
-    {
-        return $this->_auth[$_SESSION['user']->get_domain()]->search();
-    }
-
     public function user_add($attributes, $type=NULL)
     {
         return $this->_auth[$_SESSION['user']->get_domain()]->user_add($attributes, $type);
diff --git a/lib/Auth/LDAP.php b/lib/Auth/LDAP.php
index 315bfe4..0bda119 100644
--- a/lib/Auth/LDAP.php
+++ b/lib/Auth/LDAP.php
@@ -36,7 +36,7 @@ class LDAP
     protected $user_bind_dn;
     protected $user_bind_pw;
 
-    protected $attribute_level_rights_map = Array(
+    protected $attribute_level_rights_map = array(
             "r" => "read",
             "s" => "search",
             "w" => "write",
@@ -46,7 +46,7 @@ class LDAP
             "O" => "delete"
         );
 
-    protected $entry_level_rights_map = Array(
+    protected $entry_level_rights_map = array(
             "a" => "add",
             "d" => "delete",
             "n" => "modrdn",
@@ -59,6 +59,9 @@ class LDAP
 
     private $conf;
 
+    /**
+     * Class constructor
+     */
     public function __construct($domain = NULL)
     {
         $this->conf = Conf::get_instance();
@@ -98,14 +101,10 @@ class LDAP
         // )
     }
 
-    /*
-         Public functions
-     */
 
-    public function add($dn, $attributes)
-    {
-        return $this->_add($dn, $attributes);
-    }
+    /**********************************************************
+     ***********          Public methods           ************
+     **********************************************************/
 
     public function authenticate($username, $password)
     {
@@ -149,23 +148,12 @@ class LDAP
         }
     }
 
-    public function bind($bind_dn, $bind_pw)
-    {
-        // Apply some routines for access control to this function here.
-        return $this->_bind($bind_dn, $bind_pw);
-    }
-
     public function connect()
     {
         // Apply some routines for access control to this function here.
         return $this->_connect();
     }
 
-    public function delete($dn)
-    {
-        return $this->_delete($dn);
-    }
-
     public function domain_add($domain, $domain_alias = false, $prepopulate = true)
     {
         // Apply some routines for access control to this function here.
@@ -182,15 +170,9 @@ class LDAP
         return $this->_ldap->domain_exists($domain);
     }
 
-    public function domain_list($rev_sort = false)
-    {
-        return $this->_ldap->domain_list($rev_sort);
-    }
-
     /*
         Translate a domain name into it's corresponding root dn.
     */
-
     public function domain_root_dn($domain = '')
     {
         $conf = Conf::get_instance();
@@ -210,7 +192,7 @@ class LDAP
             $this->_bind($conf->manager_bind_dn, $conf->manager_bind_pw);
         }
 
-        # TODO: Get domain_attr from config
+        // TODO: Get domain_attr from config
         if (($results = ldap_search($this->_connection, $conf->get('domain_base_dn'), '(associatedDomain=' . $domain . ')')) == false) {
             error_log("No results?");
             return false;
@@ -236,31 +218,22 @@ class LDAP
         return $domain_rootdn;
     }
 
-    public function domains_list()
-    {
-        $section = $this->conf->get('kolab', 'auth_mechanism');
-        $base_dn = $this->conf->get($section, 'domain_base_dn');
-        $filter  = $this->conf->get($section, 'kolab_domain_filter');
-
-        return $this->search($base_dn, $filter);
-    }
-
     public function effective_rights($subject_dn)
     {
-        $attributes = Array();
-        $output = Array();
+        $attributes = array();
+        $output = array();
 
         $conf = Conf::get_instance();
 
-        $command = Array(
-                # TODO: Very 64-bit specific
+        $command = array(
+                // TODO: Very 64-bit specific
                 '/usr/lib64/mozldap/ldapsearch',
                 '-x',
                 '-h',
-                # TODO: Get from conf
+                // TODO: Get from conf
                 'ldap.klab.cc',
                 '-b',
-                # TODO: Get from conf
+                // TODO: Get from conf
                 'dc=klab,dc=cc',
                 '-D',
                 '"' . $_SESSION['user']->user_bind_dn . '"',
@@ -269,10 +242,10 @@ class LDAP
                 '-J',
                 '"' . implode(
                         ':',
-                        Array(
-                                '1.3.6.1.4.1.42.2.27.9.5.2',            # OID
-                                'true',                                 # Criticality
-                                'dn:' . $_SESSION['user']->user_bind_dn # User DN
+                        array(
+                                '1.3.6.1.4.1.42.2.27.9.5.2',            // OID
+                                'true',                                 // Criticality
+                                'dn:' . $_SESSION['user']->user_bind_dn // User DN
                             )
                     ) . '"',
                 '"(entrydn=' . $subject_dn . ')"'
@@ -281,7 +254,7 @@ class LDAP
 
         exec(implode(' ', $command), $output);
 
-        $lines = Array();
+        $lines = array();
         foreach ($output as $line_num => $line) {
             if (substr($line, 0, 1) == " ") {
                 $lines[count($lines)-1] .= trim($line);
@@ -314,97 +287,10 @@ class LDAP
         return $attributes;
     }
 
-    public function find_user_groups($member_dn)
-    {
-        error_log(__FILE__ . "(" . __LINE__ . "): " .  $member_dn);
-
-        $groups = array();
-
-        $root_dn = $this->domain_root_dn($this->domain);
-
-        # TODO: Do not query for both, it's either one or the other
-        $entries = $this->search($root_dn, "(|" .
-                "(&(objectclass=groupofnames)(member=$member_dn))" .
-                "(&(objectclass=groupofuniquenames)(uniquemember=$member_dn))" .
-            ")");
-
-        $entries = $this->normalize_result($entries);
-
-        foreach ($entries as $entry_dn => $entry_attributes) {
-            $groups[] = $entry_dn;
-        }
-
-        return $groups;
-    }
-
-    public function group_info($group)
-    {
-        $is_dn = ldap_explode_dn($group, 1);
-        if (!$is_dn) {
-            $root_dn = $this->domain_root_dn($this->domain);
-            $group_dn = $this->_get_group_dn($root_dn, '(mail=' . $group . ')');
-        }
-        else {
-            $group_dn = $group;
-        }
-
-        if (!$group_dn) {
-            return false;
-        }
-
-        return $this->normalize_result($this->search($group_dn));
-    }
-
-    public function group_members_list($group)
-    {
-        $is_dn = ldap_explode_dn($group, 1);
-        if (!$is_dn) {
-            $root_dn = $this->domain_root_dn($this->domain);
-            $group_dn = $this->_get_group_dn($root_dn, '(mail=' . $group . ')');
-        }
-        else {
-            $group_dn = $group;
-        }
-
-        if (!$group_dn) {
-            return false;
-        }
-
-        return $this->_list_group_members($group_dn);
-    }
-
-    public function groups_list($attributes = array(), $search = array())
-    {
-        # TODO: From config
-        $base_dn = "ou=Groups,dc=klab,dc=cc";
-        # TODO: From config
-        $filter  = "(|"
-            ."(objectClass=kolabgroupofnames)"
-            ."(objectclass=kolabgroupofuniquenames)"
-            ."(objectclass=kolabgroupofurls)"
-            .")";
-
-        if (empty($attributes) || !is_array($attributes)) {
-            $attributes = array('*');
-        }
-
-        if ($s_filter = $this->_search_filter($search)) {
-            // join search filter with objectClass filter
-            $filter = '(&' . $filter . $s_filter . ')';
-        }
-
-        return $this->search($base_dn, $filter, $attributes);
-    }
-
-    public function llist($base_dn, $filter)
-    {
-        return $this->_list($base_dn, $filter);
-    }
-
     public function list_domains()
     {
         $domains = $this->domains_list();
-        $domains = $this->normalize_result($domains);
+        $domains = self::normalize_result($domains);
 
         return $domains;
     }
@@ -418,7 +304,7 @@ class LDAP
         }
 
         $groups = $this->groups_list($attributes, $search);
-        $groups = $this->normalize_result($groups);
+        $groups = self::normalize_result($groups);
 
         if (!empty($params['sort_by'])) {
             $this->sort_result_key = $params['sort_by'];
@@ -441,7 +327,7 @@ class LDAP
         }
 
         $users = $this->users_list($attributes, $search);
-        $users = $this->normalize_result($users);
+        $users = self::normalize_result($users);
 
         if (!empty($params['sort_by'])) {
             $this->sort_result_key = $params['sort_by'];
@@ -464,7 +350,7 @@ class LDAP
         }
 
         $roles = $this->roles_list($attributes, $search);
-        $roles = $this->normalize_result($roles);
+        $roles = self::normalize_result($roles);
 
         if (!empty($params['sort_by'])) {
             $this->sort_result_key = $params['sort_by'];
@@ -478,87 +364,8 @@ class LDAP
         return $roles;
     }
 
-    static function normalize_result($__result)
-    {
-        $conf = Conf::get_instance();
-
-        $result = array();
-
-        for ($x = 0; $x < $__result["count"]; $x++) {
-            $dn = $__result[$x]['dn'];
-            $result[$dn] = array();
-            for ($y = 0; $y < $__result[$x]["count"]; $y++) {
-                $attr = $__result[$x][$y];
-                if ($__result[$x][$attr]["count"] == 1) {
-                    $result[$dn][$attr] = $__result[$x][$attr][0];
-                }
-                else {
-                    $result[$dn][$attr] = array();
-                    for ($z = 0; $z < $__result[$x][$attr]["count"]; $z++) {
-                        if ($z == 0 && $attr == $conf->get($conf->get('kolab', 'auth_mechanism'), 'domain_name_attribute')) {
-                            $result[$dn]['primary_domain'] = $__result[$x][$attr][$z];
-                        }
-
-                        $result[$dn][$attr][] = $__result[$x][$attr][$z];
-                    }
-                }
-            }
-        }
-
-        return $result;
-    }
-
-    private function parse_attribute_level_rights($attribute_value) {
-        $attribute_value = str_replace(", ", ",", $attribute_value);
-        $attribute_values = explode(",", $attribute_value);
-
-        $attribute_value = Array();
-
-        foreach ($attribute_values as $access_right) {
-            $access_right_components = explode(":", $access_right);
-            $access_attribute = array_shift($access_right_components);
-            $access_value = array_shift($access_right_components);
-
-            $attribute_value[$access_attribute] = Array();
-
-            for ($i = 0; $i < strlen($access_value); $i++) {
-                $method = $this->attribute_level_rights_map[substr($access_value, $i, 1)];
-
-                if (!in_array($method, $attribute_value[$access_attribute])) {
-                    $attribute_value[$access_attribute][] = $method;
-                }
-            }
-        }
-
-        return $attribute_value;
-    }
-
-    private function parse_entry_level_rights($attribute_value) {
-        $_attribute_value = Array();
-
-        for ($i = 0; $i < strlen($attribute_value); $i++) {
-            $method = $this->entry_level_rights_map[substr($attribute_value, $i, 1)];
-
-            if (!in_array($method, $_attribute_value)) {
-                $_attribute_value[] = $method;
-            }
-        }
-
-        return $_attribute_value;
-    }
-
-    /**
-     * Result sorting callback for uasort()
-     */
-    public function sort_result($a, $b)
+    public function user_add($attrs, $type = NULL)
     {
-        $str1 = $a[$this->sort_result_key];
-        $str2 = $b[$this->sort_result_key];
-
-        return strcmp(mb_strtoupper($str1), mb_strtoupper($str2));
-    }
-
-    public function user_add($attrs, $type = NULL) {
         if ($type == NULL) {
             $type_str = 'user';
         }
@@ -583,7 +390,7 @@ class LDAP
         // Use [$type_str . "_"]user_rdn_attr
         $dn = "uid=" . $attrs['uid'] . "," . $base_dn;
 
-        return $this->add($dn, $attrs);
+        return $this->_add($dn, $attrs);
     }
 
     public function user_delete($user)
@@ -602,7 +409,7 @@ class LDAP
             return false;
         }
 
-        return $this->delete($user_dn);
+        return $this->_delete($user_dn);
     }
 
     public function user_find_by_attribute($attribute)
@@ -625,7 +432,7 @@ class LDAP
 
         $base_dn = $this->domain_root_dn($this->domain);
 
-        $result = $this->normalize_result($this->search($base_dn, $filter, array_keys($attribute)));
+        $result = self::normalize_result($this->search($base_dn, $filter, array_keys($attribute)));
 
         if (count($result) > 0) {
             error_log("Results found: " . implode(', ', array_keys($result)));
@@ -639,9 +446,10 @@ class LDAP
 
     public function user_get_attribute($user_dn, $attribute)
     {
-        $result = $this->normalize_result($this->search($user_dn, '(objectclass=*)', array($attribute)));
+        $result = $this->search($user_dn, '(objectclass=*)', array($attribute));
+        $result = self::normalize_result($result);
 
-        if (array_key_exists($attribute, $result[$user_dn])) {
+        if (!empty($result) && array_key_exists($attribute, $result[$user_dn])) {
             return $result[$user_dn][$attribute];
         } else {
             return FALSE;
@@ -664,10 +472,84 @@ class LDAP
             return false;
         }
 
-        return $this->normalize_result($this->search($user_dn));
+        return self::normalize_result($this->search($user_dn));
+    }
+
+    public function find_user_groups($member_dn)
+    {
+        error_log(__FILE__ . "(" . __LINE__ . "): " .  $member_dn);
+
+        $groups = array();
+
+        $root_dn = $this->domain_root_dn($this->domain);
+
+        // TODO: Do not query for both, it's either one or the other
+        $entries = $this->search($root_dn, "(|" .
+                "(&(objectclass=groupofnames)(member=$member_dn))" .
+                "(&(objectclass=groupofuniquenames)(uniquemember=$member_dn))" .
+            ")");
+
+        $entries = self::normalize_result($entries);
+
+        foreach ($entries as $entry_dn => $entry_attributes) {
+            $groups[] = $entry_dn;
+        }
+
+        return $groups;
+    }
+
+    public function group_info($group)
+    {
+        $is_dn = ldap_explode_dn($group, 1);
+        if (!$is_dn) {
+            $root_dn = $this->domain_root_dn($this->domain);
+            $group_dn = $this->_get_group_dn($root_dn, '(mail=' . $group . ')');
+        }
+        else {
+            $group_dn = $group;
+        }
+
+        if (!$group_dn) {
+            return false;
+        }
+
+        return self::normalize_result($this->search($group_dn));
     }
 
-    public function users_list($attributes = array(), $search = array())
+    public function group_members_list($group)
+    {
+        $is_dn = ldap_explode_dn($group, 1);
+        if (!$is_dn) {
+            $root_dn = $this->domain_root_dn($this->domain);
+            $group_dn = $this->_get_group_dn($root_dn, '(mail=' . $group . ')');
+        }
+        else {
+            $group_dn = $group;
+        }
+
+        if (!$group_dn) {
+            return false;
+        }
+
+        return $this->_list_group_members($group_dn);
+    }
+
+    private function search($base_dn, $search_filter = '(objectClass=*)', $attributes = array('*'))
+    {
+        error_log("Searching $base_dn with filter '$search_filter'");
+        return $this->_search($base_dn, $search_filter, $attributes);
+    }
+
+    private function domains_list()
+    {
+        $section = $this->conf->get('kolab', 'auth_mechanism');
+        $base_dn = $this->conf->get($section, 'domain_base_dn');
+        $filter  = $this->conf->get($section, 'kolab_domain_filter');
+
+        return $this->search($base_dn, $filter);
+    }
+
+    private function users_list($attributes = array(), $search = array())
     {
         $conf = Conf::get_instance();
 
@@ -686,7 +568,7 @@ class LDAP
         return $this->search($base_dn, $filter, $attributes);
     }
 
-    public function roles_list($attributes = array(), $search = array())
+    private function roles_list($attributes = array(), $search = array())
     {
         $conf = Conf::get_instance();
 
@@ -707,27 +589,126 @@ class LDAP
         return $this->search($base_dn, $filter, $attributes);
     }
 
-    public function search($base_dn, $search_filter = '(objectClass=*)', $attributes = array('*'))
+    private function groups_list($attributes = array(), $search = array())
     {
-        error_log("Searching $base_dn with filter '$search_filter'");
-        return $this->_search($base_dn, $search_filter, $attributes);
+        // TODO: From config
+        $base_dn = "ou=Groups,dc=klab,dc=cc";
+        // TODO: From config
+        $filter  = "(|"
+            ."(objectClass=kolabgroupofnames)"
+            ."(objectclass=kolabgroupofuniquenames)"
+            ."(objectclass=kolabgroupofurls)"
+            .")";
+
+        if (empty($attributes) || !is_array($attributes)) {
+            $attributes = array('*');
+        }
+
+        if ($s_filter = $this->_search_filter($search)) {
+            // join search filter with objectClass filter
+            $filter = '(&' . $filter . $s_filter . ')';
+        }
+
+        return $this->search($base_dn, $filter, $attributes);
     }
 
-    public function setup()
+    public static function normalize_result($__result)
     {
-        return $this->_ldap->setup();
+        $conf = Conf::get_instance();
+
+        $dn_attr = $conf->get($conf->get('kolab', 'auth_mechanism'), 'domain_name_attribute');
+        $result = array();
+
+        for ($x = 0; $x < $__result["count"]; $x++) {
+            $dn = $__result[$x]['dn'];
+            $result[$dn] = array();
+            for ($y = 0; $y < $__result[$x]["count"]; $y++) {
+                $attr = $__result[$x][$y];
+                if ($__result[$x][$attr]["count"] == 1) {
+                    $result[$dn][$attr] = $__result[$x][$attr][0];
+                }
+                else {
+                    $result[$dn][$attr] = array();
+                    for ($z = 0; $z < $__result[$x][$attr]["count"]; $z++) {
+                        if ($z == 0 && $attr == $dn_attr) {
+                            $result[$dn]['primary_domain'] = $__result[$x][$attr][$z];
+                        }
+
+                        $result[$dn][$attr][] = $__result[$x][$attr][$z];
+                    }
+                }
+            }
+        }
+
+        return $result;
     }
 
-    /*
-        Qualify a username.
+    private function parse_attribute_level_rights($attribute_value)
+    {
+        $attribute_value = str_replace(", ", ",", $attribute_value);
+        $attribute_values = explode(",", $attribute_value);
 
-        Where username is 'kanarip at kanarip.com', the function will return an
-        array containing 'kanarip' and 'kanarip.com'. However, where the
-        username is 'kanarip', the domain name is to be assumed the
-        management domain name.
-    */
+        $attribute_value = array();
+
+        foreach ($attribute_values as $access_right) {
+            $access_right_components = explode(":", $access_right);
+            $access_attribute = array_shift($access_right_components);
+            $access_value = array_shift($access_right_components);
+
+            $attribute_value[$access_attribute] = array();
+
+            for ($i = 0; $i < strlen($access_value); $i++) {
+                $method = $this->attribute_level_rights_map[substr($access_value, $i, 1)];
+
+                if (!in_array($method, $attribute_value[$access_attribute])) {
+                    $attribute_value[$access_attribute][] = $method;
+                }
+            }
+        }
+
+        return $attribute_value;
+    }
+
+    private function parse_entry_level_rights($attribute_value)
+    {
+        $_attribute_value = array();
+
+        for ($i = 0; $i < strlen($attribute_value); $i++) {
+            $method = $this->entry_level_rights_map[substr($attribute_value, $i, 1)];
+
+            if (!in_array($method, $_attribute_value)) {
+                $_attribute_value[] = $method;
+            }
+        }
+
+        return $_attribute_value;
+    }
+
+    /**
+     * Result sorting callback for uasort()
+     */
+    public function sort_result($a, $b)
+    {
+        $str1 = $a[$this->sort_result_key];
+        $str2 = $b[$this->sort_result_key];
+
+        return strcmp(mb_strtoupper($str1), mb_strtoupper($str2));
+    }
+
+    public function setup()
+    {
+        return $this->_ldap->setup();
+    }
 
-    public function _qualify_id($username)
+    /**
+     * Qualify a username.
+     *
+     * Where username is 'kanarip at kanarip.com', the function will return an
+     * array containing 'kanarip' and 'kanarip.com'. However, where the
+     * username is 'kanarip', the domain name is to be assumed the
+     * management domain name.
+     */
+    private function _qualify_id($username)
     {
         $conf = Conf::get_instance();
 
@@ -818,7 +799,7 @@ class LDAP
     {
         // Always bind with the session credentials
         $this->_connect();
-        $this->bind($_SESSION['user']->user_bind_dn, $_SESSION['user']->user_bind_pw);
+        $this->_bind($_SESSION['user']->user_bind_dn, $_SESSION['user']->user_bind_pw);
 
         if (($add_result = ldap_add($this->_connection, $entry_dn, $attributes)) == false) {
             // Issue warning
@@ -963,12 +944,12 @@ class LDAP
         $this->_bind($_SESSION['user']->user_bind_dn, $_SESSION['user']->user_bind_pw);
 
         if (($search_results = @ldap_search($this->_connection, $base_dn, $search_filter, $attributes)) == false) {
-            #message("Could not search in " . __METHOD__ . " in " . __FILE__ . " on line " . __LINE__ . ": " . $this->_errstr());
+            //message("Could not search in " . __METHOD__ . " in " . __FILE__ . " on line " . __LINE__ . ": " . $this->_errstr());
             return false;
         }
 
         if (($entries = ldap_get_entries($this->_connection, $search_results)) == false) {
-            #message("Could not get the results of the search: " . $this->_errstr());
+            //message("Could not get the results of the search: " . $this->_errstr());
             return false;
         }
 
@@ -1067,11 +1048,11 @@ class LDAP
         }
 
         if (($list_success = ldap_list($tmp_connection, $entry_root_dn, '(objectClass=*)', array('*', 'aci'))) == false) {
-            #message("LDAP Error: " . $this->_errstr());
+            //message("LDAP Error: " . $this->_errstr());
             return false;
         }
 
-#        print_r(ldap_get_entries($tmp_connection, $list_success));
+//        print_r(ldap_get_entries($tmp_connection, $list_success));
 /*
         if (ldap_count_entries($tmp_connection, $list_success) == 0) {
             echo "<li>Listed things, but got no results";
@@ -1112,32 +1093,7 @@ class LDAP
         return "dc=" . implode(',dc=', explode('.', $relevant_associatedDomain));
     }
 
-################################################################################
-################################################################################
-################################################################################
-################################################################################
-################################################################################
-################################################################################
-################################################################################
-################################################################################
-################################################################################
-################################################################################
-################################################################################
-################################################################################
-################################################################################
-################################################################################
-################################################################################
-################################################################################
-################################################################################
-################################################################################
-################################################################################
-################################################################################
-################################################################################
-################################################################################
-################################################################################
-################################################################################
-
-    public function _get_group_dn($root_dn, $search_filter)
+    private function _get_group_dn($root_dn, $search_filter)
     {
         error_log("Searching for a group dn in $root_dn, with search filter: $search_filter");
 
@@ -1161,7 +1117,7 @@ class LDAP
         return $group_dn;
     }
 
-    public function _get_user_dn($root_dn, $search_filter)
+    private function _get_user_dn($root_dn, $search_filter)
     {
         error_log("Searching for a user dn in $root_dn, with search filter: $search_filter");
 
@@ -1201,7 +1157,7 @@ class LDAP
             }
         }
 
-        $entries = $this->normalize_result($this->search($dn));
+        $entries = self::normalize_result($this->search($dn));
 
         foreach ($entries as $entry_dn => $entry) {
             if (!isset($entry['objectclass'])) {
@@ -1244,7 +1200,7 @@ class LDAP
                 continue;
             }
 
-            $member_entry = $this->normalize_result(@ldap_get_entries($this->_connection, $result));
+            $member_entry = self::normalize_result(@ldap_get_entries($this->_connection, $result));
             $group_members[$member] = array_pop($member_entry);
 
             // Nested groups
@@ -1275,7 +1231,7 @@ class LDAP
                 continue;
             }
 
-            $member_entry = $this->normalize_result(@ldap_get_entries($this->_connection, $result));
+            $member_entry = self::normalize_result(@ldap_get_entries($this->_connection, $result));
             $group_members[$member] = array_pop($member_entry);
 
             // Nested groups
@@ -1299,7 +1255,7 @@ class LDAP
 
         foreach ((array)$entry['memberurl'] as $url) {
             $ldap_uri_components = $this->_parse_memberurl($url);
-            $entries = $this->normalize_result($this->search($ldap_uri_components[3], $ldap_uri_components[6]));
+            $entries = self::normalize_result($this->search($ldap_uri_components[3], $ldap_uri_components[6]));
             foreach ($entries as $entry_dn => $_entry) {
                 $group_members[$entry_dn] = $_entry;
                 error_log("Found " . $entry_dn);
@@ -1314,6 +1270,13 @@ class LDAP
         return array_filter($group_members);
     }
 
+    /**
+     * memberUrl attribute parser
+     *
+     * @param string $url URL string
+     *
+     * @return array URL elements
+     */
     private function _parse_memberurl($url)
     {
         error_log("Parsing URL: " . $url);
diff --git a/lib/api/kolab_api_service_user.php b/lib/api/kolab_api_service_user.php
index b13f40f..61cd7ce 100644
--- a/lib/api/kolab_api_service_user.php
+++ b/lib/api/kolab_api_service_user.php
@@ -164,7 +164,7 @@ class kolab_api_service_user extends kolab_api_service
             foreach ($uta as $field_type => $attributes) {
                 foreach ($attributes as $attribute => $data) {
                     if (!array_key_exists($attribute, $result)) {
-                        $attribute_value = $auth->user_get_attribute($user, $attribute);
+                        $attribute_value = $auth->user_get_attribute($result['entrydn'], $attribute);
                         if ($attribute_value) {
                             $result[$attribute] = $attribute_value;
                         }





More information about the commits mailing list