From: Gunnar Wrobel Date: Mon, 30 Mar 2009 04:38:34 +0000 (+0000) Subject: Upcase server class names. X-Git-Url: https://git.internetallee.de/?a=commitdiff_plain;h=22712abe04abdf7da54ab21f9eb38aeed1a51e16;p=horde.git Upcase server class names. --- diff --git a/framework/Kolab_Server/lib/Horde/Kolab/Server.php b/framework/Kolab_Server/lib/Horde/Kolab/Server.php index 5cbb1ebb3..a8091ad73 100644 --- a/framework/Kolab_Server/lib/Horde/Kolab/Server.php +++ b/framework/Kolab_Server/lib/Horde/Kolab/Server.php @@ -90,7 +90,7 @@ abstract class Horde_Kolab_Server */ static public function &factory($driver, $params = array()) { - $class = 'Horde_Kolab_Server_' . basename($driver); + $class = 'Horde_Kolab_Server_' . ucfirst(basename($driver)); if (class_exists($class)) { $db = new $class($params); return $db; diff --git a/framework/Kolab_Server/lib/Horde/Kolab/Server/File.php b/framework/Kolab_Server/lib/Horde/Kolab/Server/File.php new file mode 100644 index 000000000..6a32d5a7f --- /dev/null +++ b/framework/Kolab_Server/lib/Horde/Kolab/Server/File.php @@ -0,0 +1,115 @@ + + * @license http://www.fsf.org/copyleft/lgpl.html LGPL + * @link http://pear.horde.org/index.php?package=Kolab_Server + */ + +/** + * This class provides a persistant class for testing the Kolab Server DB. + * + * Copyright 2008-2009 The Horde Project (http://www.horde.org/) + * + * See the enclosed file COPYING for license information (LGPL). If you + * did not receive this file, see http://www.fsf.org/copyleft/lgpl.html. + * + * @category Kolab + * @package Kolab_Server + * @author Gunnar Wrobel + * @license http://www.fsf.org/copyleft/lgpl.html LGPL + * @link http://pear.horde.org/index.php?package=Kolab_Server + */ +class Horde_Kolab_Server_File extends Horde_Kolab_Server_Test +{ + + /** + * The file for storing the database data. + * + * @var string + */ + private $_file; + + /** + * Construct a new Horde_Kolab_Server object. + * + * @param array $params Parameter array. + */ + public function __construct($params = array()) + { + if (isset($params['file'])) { + $this->_file = $params['file']; + } else { + $this->_file = Horde::getTempFile('Horde_Kolab_Server', false); + } + parent::__construct($params); + } + + + /** + * Load the current state of the database. + * + * @return NULL + */ + protected function load() + { + $raw_data = file_get_contents($this->_file); + if (!$raw_data === false) { + $data = @unserialize($raw_data); + if ($data !== false) { + $this->data = $data; + } else { + $error = error_get_last(); + Horde::logMessage(sprintf('Horde_Kolab_Server_file failed to read the database from %s. Error was: %s', + $this->_file, $error['message']), __FILE__, + __LINE__, PEAR_LOG_WARNING); + $this->data = array(); + } + } + } + + /** + * Store the current state of the database. + * + * @return NULL + */ + protected function store() + { + $raw_data = serialize($this->data); + $result = @file_put_contents($this->_file, $raw_data); + if ($result === false) { + $error = error_get_last(); + Horde::logMessage(sprintf('Horde_Kolab_Server_file failed to store the database in %s. Error was: %s', + $this->_file, $error['message']), __FILE__, + __LINE__, PEAR_LOG_WARNING); + } + } + + /** + * Cleans the current state of the database. + * + * @return NULL + */ + public function clean() + { + unlink($this->_file); + $this->data = array(); + $this->store(); + } + + /** + * Returns the path to the storage location of the database. + * + * @return string The path to the database. + */ + public function getStoragePAth() + { + return $this->_file; + } +} diff --git a/framework/Kolab_Server/lib/Horde/Kolab/Server/Ldap.php b/framework/Kolab_Server/lib/Horde/Kolab/Server/Ldap.php new file mode 100644 index 000000000..becf7c383 --- /dev/null +++ b/framework/Kolab_Server/lib/Horde/Kolab/Server/Ldap.php @@ -0,0 +1,937 @@ + + * @license http://www.fsf.org/copyleft/lgpl.html LGPL + * @link http://pear.horde.org/index.php?package=Kolab_Server + */ + +/** + * This class provides methods to deal with Kolab objects stored in + * the standard Kolab LDAP db. + * + * Copyright 2008-2009 The Horde Project (http://www.horde.org/) + * + * See the enclosed file COPYING for license information (LGPL). If you + * did not receive this file, see http://www.fsf.org/copyleft/lgpl.html. + * + * @category Kolab + * @package Kolab_Server + * @author Gunnar Wrobel + * @license http://www.fsf.org/copyleft/lgpl.html LGPL + * @link http://pear.horde.org/index.php?package=Kolab_Server + */ +class Horde_Kolab_Server_Ldap extends Horde_Kolab_Server +{ + + /** + * The object types supported by this server type. + */ + const USER = 'kolabInetOrgPerson'; + const GROUP = 'kolabGroupOfNames'; + + /** + * LDAP connection handle. + * + * @var Net_LDAP2 + */ + private $_ldap; + + /** + * Base DN of the LDAP server. + * + * @var string + */ + private $_base_dn; + + /** + * Construct a new Horde_Kolab_Server_ldap object. + * + * @param array $params Parameter array. + */ + public function __construct($params = array()) + { + if (!isset($params['charset'])) { + $params['charset'] = 'UTF-8'; + } + + $base_config = array('host' => 'localhost', + 'port' => 389, + 'version' => 3, + 'starttls' => false, + 'uid' => '', + 'pass' => '', + 'basedn' => '', + 'charset' => '', + 'options' => array(), + 'auto_reconnect' => true); + + + $config = array_merge($base_config, $params); + + $this->_base_dn = $config['basedn']; + + $config['binddn'] = $config['uid']; + $config['bindpw'] = $config['pass']; + + $this->connect(); + + parent::__construct($params); + } + + + /** + * Connect to the LDAP server. + * + * @return NULL. + * + * @throws Horde_Kolab_Server_Exception If the connection failed. + */ + protected function connect() + { + $this->_ldap = Net_LDAP2::connect($config); + if (is_a($this->_ldap, 'PEAR_Error')) { + throw new Horde_Kolab_Server_Exception($this->_ldap); + } + } + + /** + * Read object data. + * + * @param string $dn The object to retrieve. + * @param string $attrs Restrict to these attributes. + * + * @return array|boolean An array of attributes or false if the specified + * object was not found. + * + * @throws Horde_Kolab_Server_Exception If the search operation retrieved a + * problematic result. + */ + public function read($dn, $attrs = null) + { + $params = array('scope' => 'base'); + if (!empty($attrs)) { + $params['attributes'] = $attrs; + } + + $data = $this->search(null, $params, $dn); + if (empty($data)) { + throw new Horde_Kolab_Server_Exception(_("Empty result!")); + } + + if (!isset($data[$dn])) { + throw new Horde_Kolab_Server_Exception(sprintf(_("No result found for %s"), + $dn)); + } + if (is_a($data[$dn], 'PEAR_Error')) { + throw new Horde_Kolab_Server_Exception($data[$dn]); + } + return $data[$dn]; + } + + /** + * Determine the type of a Kolab object. + * + * @param string $dn The DN of the object to examine. + * + * @return int The corresponding Kolab object type. + * + * @throws Horde_Kolab_Server_Exception If the object type is unknown. + */ + public function determineType($dn) + { + $oc = $this->getObjectClasses($dn); + // Not a user type? + if (!in_array('kolabinetorgperson', $oc)) { + // Is it a group? + if (in_array('kolabgroupofnames', $oc)) { + return 'Horde_Kolab_Server_Object_group'; + } + // Is it a shared Folder? + if (in_array('kolabsharedfolder', $oc)) { + return 'Horde_Kolab_Server_Object_sharedfolder'; + } + throw new Horde_Kolab_Server_Exception(sprintf(_("Unkown Kolab object type for DN %s."), + $dn)); + } + + $groups = $this->getGroups($dn); + if (!empty($groups)) { + if (in_array('cn=admin,cn=internal,' . $this->_base_dn, $groups)) { + return 'Horde_Kolab_Server_Object_administrator'; + } + if (in_array('cn=maintainer,cn=internal,' . $this->_base_dn, + $groups)) { + return 'Horde_Kolab_Server_Object_maintainer'; + } + if (in_array('cn=domain-maintainer,cn=internal,' . $this->_base_dn, + $groups)) { + return 'Horde_Kolab_Server_Object_domainmaintainer'; + } + } + + if (strpos($dn, 'cn=external') !== false) { + return 'Horde_Kolab_Server_Object_address'; + } + + return 'Horde_Kolab_Server_Object_user'; + } + + /** + * List all objects of a specific type + * + * @param string $type The type of the objects to be listed + * @param array $params Additional parameters. + * + * @return array An array of Kolab objects. + * + * @throws Horde_Kolab_Server_Exception + * + * @todo Sorting + */ + public function listObjects($type, $params = null) + { + if (empty($params['base_dn'])) { + $base = $this->_base_dn; + } else { + $base = $params['base_dn']; + } + + $result = Horde_Kolab_Server_Object::loadClass($type); + $vars = get_class_vars($type); + $filter = call_user_func(array($type, 'getFilter')); + $sort = $vars['sort_by']; + + if (isset($params['sort'])) { + $sort = $params['sort']; + } + + $options = array('scope' => 'sub'); + if (isset($params['attributes'])) { + $options['attributes'] = $params['attributes']; + } else { + $options['attributes'] = $vars['_supported_attributes']; + } + + $result = $this->search($filter, $options, $base); + if (empty($result)) { + return array(); + } + + if ($sort) { + /* FIXME */ + /*$this->sort($result, $sort); */ + } + + if (isset($params['from'])) { + $from = $params['from']; + } else { + $from = -1; + } + + if (isset($params['to'])) { + $sort = $params['to']; + } else { + $to = -1; + } + + $entries = array(); + foreach ($result as $entry) { + $entries[] = $entry['dn']; + } + + if (!empty($vars['required_group'])) { + $required_group = $this->fetch($vars['required_group'], + 'Horde_Kolab_Server_Object_group'); + } + + $objects = array(); + foreach ($entries as $dn) { + if (!empty($vars['required_group']) && $required_group->isMember($dn)) { + continue; + } + $result = $this->fetch($dn, $type); + $objects[$dn] = $result; + } + return $objects; + } + + /** + * Generates a UID for the given information. + * + * @param string $type The type of the object to create. + * @param string $id The id of the object. + * @param array $info Any additional information about the object to create. + * + * @return string The DN. + * + * @throws Horde_Kolab_Server_Exception If the given type is unknown. + */ + public function generateServerUid($type, $id, $info) + { + switch ($type) { + case 'Horde_Kolab_Server_Object_user': + if (!isset($info['user_type']) || $info['user_type'] == 0) { + return sprintf('cn=%s,%s', $id, $this->_base_dn); + } else if ($info['user_type'] == Horde_Kolab_Server_Object_user::USERTYPE_INTERNAL) { + return sprintf('cn=%s,cn=internal,%s', $id, $this->_base_dn); + } else if ($info['user_type'] == Horde_Kolab_Server_Object_user::USERTYPE_GROUP) { + return sprintf('cn=%s,cn=groups,%s', $id, $this->_base_dn); + } else if ($info['user_type'] == Horde_Kolab_Server_Object_user::USERTYPE_RESOURCE) { + return sprintf('cn=%s,cn=resources,%s', $id, $this->_base_dn); + } else { + return sprintf('cn=%s,%s', $id, $this->_base_dn); + } + case 'Horde_Kolab_Server_Object_address': + return sprintf('cn=%s,cn=external,%s', $id, $this->_base_dn); + case 'Horde_Kolab_Server_Object_sharedfolder': + case 'Horde_Kolab_Server_Object_administrator': + case 'Horde_Kolab_Server_Object_maintainer': + case 'Horde_Kolab_Server_Object_domainmaintainer': + return sprintf('cn=%s,%s', $id, $this->_base_dn); + case 'Horde_Kolab_Server_Object_group': + case 'Horde_Kolab_Server_Object_distlist': + if (!isset($info['visible']) || !empty($info['visible'])) { + return sprintf('cn=%s,%s', $id, $this->_base_dn); + } else { + return sprintf('cn=%s,cn=internal,%s', $id, $this->_base_dn); + } + default: + throw new Horde_Kolab_Server_Exception(_("Not implemented!")); + } + } + + /** + * Return the root of the UID values on this server. + * + * @return string The base UID on this server (base DN on ldap). + */ + public function getBaseUid() + { + return $this->_base_dn; + } + + /** + * Save an object. + * + * @param string $dn The DN of the object. + * @param array $data The data for the object. + * + * @return boolean True if successfull. + * + * @throws Horde_Kolab_Server_Exception If the given type is unknown. + */ + function save($dn, $data) + { + $result = $this->_add($dn, $data); + if (!$result && $this->_errno()) { + throw new Horde_Kolab_Server_Exception(sprintf(_("Failed saving object. Error was: %s"), + $this->_error())); + } + } + + /** + * Identify the UID for the first object found using the specified + * search criteria. + * + * @param array $criteria The search parameters as array. + * @param int $restrict A Horde_Kolab_Server::RESULT_* result restriction. + * + * @return boolean|string|array The UID(s) or false if there was no result. + * + * @throws Horde_Kolab_Server_Exception + */ + public function uidForSearch($criteria, + $restrict = Horde_Kolab_Server::RESULT_SINGLE) + { + $users = array('field' => 'objectClass', + 'op' => '=', + 'test' => self::USER); + if (!empty($criteria)) { + $criteria = array('AND' => array($users, $criteria)); + } else { + $criteria = array('AND' => array($users)); + } + + $filter = $this->searchQuery($criteria); + return $this->dnForFilter($filter, $restrict); + } + + /** + * Identify the GID for the first group found using the specified + * search criteria + * + * @param array $criteria The search parameters as array. + * @param int $restrict A Horde_Kolab_Server::RESULT_* result restriction. + * + * @return boolean|string|array The GID(s) or false if there was no result. + * + * @throws Horde_Kolab_Server_Exception + */ + public function gidForSearch($criteria, + $restrict = Horde_Kolab_Server::RESULT_SINGLE) + { + $groups = array('field' => 'objectClass', + 'op' => '=', + 'test' => self::GROUP); + if (!empty($criteria)) { + $criteria = array('AND' => array($groups, $criteria)); + } else { + $criteria = array('AND' => array($groups)); + } + + $filter = $this->searchQuery($criteria); + return $this->dnForFilter($filter, $restrict); + } + + /** + * Identify attributes for the objects found using a filter. + * + * @param array $criteria The search parameters as array. + * @param array $attrs The attributes to retrieve. + * @param int $restrict A Horde_Kolab_Server::RESULT_* result restriction. + * + * @return array The results. + * + * @throws Horde_Kolab_Server_Exception + */ + public function attrsForSearch($criteria, $attrs, + $restrict = Horde_Kolab_Server::RESULT_SINGLE) + { + $params = array('attributes' => $attrs); + $filter = $this->searchQuery($criteria); + $result = $this->search($filter, $params, $this->_base_dn); + return $this->attrsFromResult($result, $attrs, $restrict); + } + + /** + * Search for object data. + * + * @param string $filter The LDAP search filter. + * @param string $params Additional search parameters. + * @param string $base The search base + * + * @return array The result array. + * + * @throws Horde_Kolab_Server_Exception If the search operation encountered + * a problem. + */ + public function search($filter = null, $params = array(), $base = null) + { + if (!isset($base)) { + $base = $this->_base_dn; + } + $result = $this->_ldap->search($base, $filter, $params); + if (is_a($result, 'PEAR_Error')) { + throw new Horde_Kolab_Server_Exception($result->getMessage()); + } + return $result->as_struct(); + } + + /** + * Get the LDAP object classes for the given DN. + * + * @param string $dn DN of the object. + * + * @return array An array of object classes. + * + * @throws Horde_Kolab_Server_Exception If the object has no + * object classes. + */ + public function getObjectClasses($dn) + { + $object = $this->read($dn, array('objectClass')); + if (!isset($object['objectClass'])) { + throw new Horde_Kolab_Server_Exception(sprintf(_("The object %s has no object classes!"), + $dn)); + } + $result = array_map('strtolower', $object['objectClass']); + return $result; + } + + /** + * Build a search query. + * + * Taken from the Turba LDAP driver. + * + * @param array $criteria The array of criteria. + * + * @return string An LDAP query filter. + */ + protected function searchQuery($criteria) + { + /* Build the LDAP filter. */ + $filter = ''; + if (count($criteria)) { + foreach ($criteria as $key => $vals) { + if ($key == 'OR') { + $filter .= '(|' . $this->buildSearchQuery($vals) . ')'; + } elseif ($key == 'AND') { + $filter .= '(&' . $this->buildSearchQuery($vals) . ')'; + } + } + } else { + /* Accept everything. */ + $filter = '(objectclass=*)'; + } + + /* Add source-wide filters, which are _always_ AND-ed. */ + if (!empty($this->params['filter'])) { + $filter = '(&' . '(' . $this->params['filter'] . ')' . $filter . ')'; + } + return $filter; + } + + /** + * Build a piece of a search query. + * + * Taken from the Turba LDAP driver. + * + * @param array $criteria The array of criteria. + * + * @return string An LDAP query fragment. + */ + protected function buildSearchQuery($criteria) + { + $clause = ''; + foreach ($criteria as $key => $vals) { + if (!empty($vals['OR'])) { + $clause .= '(|' . $this->buildSearchQuery($vals) . ')'; + } elseif (!empty($vals['AND'])) { + $clause .= '(&' . $this->buildSearchQuery($vals) . ')'; + } else { + if (isset($vals['field'])) { + require_once 'Horde/String.php'; + require_once 'Horde/NLS.php'; + $rhs = String::convertCharset($vals['test'], NLS::getCharset(), $this->params['charset']); + $clause .= Horde_LDAP::buildClause($vals['field'], $vals['op'], $rhs, array('begin' => !empty($vals['begin']))); + } else { + foreach ($vals as $test) { + if (!empty($test['OR'])) { + $clause .= '(|' . $this->buildSearchQuery($test) . ')'; + } elseif (!empty($test['AND'])) { + $clause .= '(&' . $this->buildSearchQuery($test) . ')'; + } else { + $rhs = String::convertCharset($test['test'], NLS::getCharset(), $this->params['charset']); + $clause .= Horde_LDAP::buildClause($test['field'], $test['op'], $rhs, array('begin' => !empty($vals['begin']))); + } + } + } + } + } + + return $clause; + } + + /** + * Identify the DN of the first result entry. + * + * @param array $result The LDAP search result. + * @param int $restrict A Horde_Kolab_Server::RESULT_* result restriction. + * + * @return boolean|string|array The DN(s) or false if there was no result. + * + * @throws Horde_Kolab_Server_Exception If the number of results did not + * meet the expectations. + */ + protected function dnFromResult($result, + $restrict = Horde_Kolab_Server::RESULT_SINGLE) + { + if (empty($result)) { + return false; + } + $dns = array_keys($result); + + switch ($restrict) { + case self::RESULT_STRICT: + if (count($dns) > 1) { + throw new Horde_Kolab_Server_Exception(sprintf(_("Found %s results when expecting only one!"), + $count)); + } + case self::RESULT_SINGLE: + return $dns[0]; + case self::RESULT_MANY: + return $dns; + } + } + + /** + * Get the attributes of the first result entry. + * + * @param array $result The LDAP search result. + * @param array $attrs The attributes to retrieve. + * @param int $restrict A Horde_Kolab_Server::RESULT_* result restriction. + * + * @return array The DN. + * + * @throws Horde_Kolab_Server_Exception If the number of results did not + * meet the expectations. + */ + protected function attrsFromResult($result, $attrs, + $restrict = Horde_Kolab_Server::RESULT_SINGLE) + { + switch ($restrict) { + case self::RESULT_STRICT: + if (count($result) > 1) { + throw new Horde_Kolab_Server_Exception(sprintf(_("Found %s results when expecting only one!"), + $count)); + } + case self::RESULT_SINGLE: + if (count($result) > 0) { + return $result[0]; + } + return array(); + case self::RESULT_MANY: + return $result; + } + return array(); + } + + + /** + * Identify the DN for the first object found using a filter. + * + * @param string $filter The LDAP filter to use. + * @param int $restrict A Horde_Kolab_Server::RESULT_* result restriction. + * + * @return boolean|string|array The DN(s) or false if there was no result. + * + * @throws Horde_Kolab_Server_Exception + */ + protected function dnForFilter($filter, + $restrict = Horde_Kolab_Server::RESULT_SINGLE) + { + $params = array('attributes' => 'dn'); + $result = $this->search($filter, $params, $this->_base_dn); + return $this->dnFromResult($result, $restrict); + } + + /** + * Identify the UID for the first object found with the given ID. + * + * @param string $id Search for objects with this ID. + * @param int $restrict A Horde_Kolab_Server::RESULT_* result restriction. + * + * @return mixed The UID or false if there was no result. + * + * @throws Horde_Kolab_Server_Exception + */ + public function uidForId($id, + $restrict = Horde_Kolab_Server::RESULT_SINGLE) + { + $criteria = array('AND' => array(array('field' => 'uid', + 'op' => '=', + 'test' => $id), + ), + ); + return $this->uidForSearch($criteria, $restrict); + } + + /** + * Identify the UID for the first user found with the given mail. + * + * @param string $mail Search for users with this mail address. + * @param int $restrict A Horde_Kolab_Server::RESULT_* result restriction. + * + * @return mixed The UID or false if there was no result. + * + * @throws Horde_Kolab_Server_Exception + */ + public function uidForMail($mail, + $restrict = Horde_Kolab_Server::RESULT_SINGLE) + { + $criteria = array('AND' => array(array('field' => 'mail', + 'op' => '=', + 'test' => $mail), + ), + ); + return $this->uidForSearch($criteria, $restrict); + } + + /** + * Identify the UID for the first object found with the given alias. + * + * @param string $mail Search for objects with this mail alias. + * @param int $restrict A Horde_Kolab_Server::RESULT_* result restriction. + * + * @return mixed The UID or false if there was no result. + * + * @throws Horde_Kolab_Server_Exception + */ + public function uidForAlias($mail, + $restrict = Horde_Kolab_Server::RESULT_SINGLE) + { + $criteria = array('AND' => array(array('field' => 'alias', + 'op' => '=', + 'test' => $mail), + ), + ); + return $this->uidForSearch($criteria, $restrict); + } + + /** + * Identify the UID for the first object found with the given ID or mail. + * + * @param string $id Search for objects with this uid/mail. + * + * @return string|boolean The UID or false if there was no result. + * + * @throws Horde_Kolab_Server_Exception + */ + public function uidForIdOrMail($id) + { + $criteria = array('OR' => + array( + array('field' => 'uid', + 'op' => '=', + 'test' => $id), + array('field' => 'mail', + 'op' => '=', + 'test' => $id), + ), + ); + return $this->uidForSearch($criteria); + } + + /** + * Identify the UID for the first object found with the given mail + * address or alias. + * + * @param string $mail Search for objects with this mail address + * or alias. + * + * @return string|boolean The UID or false if there was no result. + * + * @throws Horde_Kolab_Server_Exception + */ + public function uidForMailOrAlias($mail) + { + $criteria = array('OR' => + array( + array('field' => 'alias', + 'op' => '=', + 'test' => $mail), + array('field' => 'mail', + 'op' => '=', + 'test' => $mail), + ) + ); + return $this->uidForSearch($criteria); + } + + /** + * Identify the UID for the first object found with the given ID, + * mail or alias. + * + * @param string $id Search for objects with this ID/mail/alias. + * + * @return string|boolean The UID or false if there was no result. + * + * @throws Horde_Kolab_Server_Exception + */ + public function uidForIdOrMailOrAlias($id) + { + $criteria = array('OR' => + array( + array('field' => 'alias', + 'op' => '=', + 'test' => $id), + array('field' => 'mail', + 'op' => '=', + 'test' => $id), + array('field' => 'uid', + 'op' => '=', + 'test' => $id), + ), + ); + return $this->uidForSearch($criteria); + } + + /** + * Identify the primary mail attribute for the first object found + * with the given ID or mail. + * + * @param string $id Search for objects with this ID/mail. + * + * @return mixed The mail address or false if there was no result. + * + * @throws Horde_Kolab_Server_Exception + */ + public function mailForIdOrMail($id) + { + $criteria = array('AND' => + array( + array('field' => 'objectClass', + 'op' => '=', + 'test' => self::USER), + array('OR' => + array( + array('field' => 'uid', + 'op' => '=', + 'test' => $id), + array('field' => 'mail', + 'op' => '=', + 'test' => $id), + ), + ), + ), + ); + + $data = $this->attrsForSearch($criteria, array('mail'), + self::RESULT_STRICT); + if (!empty($data)) { + return $data['mail'][0]; + } else { + return false; + } + } + + /** + * Returns a list of allowed email addresses for the given user. + * + * @param string $id Search for objects with this ID/mail. + * + * @return array An array of allowed mail addresses. + * + * @throws Horde_Kolab_Server_Exception + */ + public function addrsForIdOrMail($id) + { + $criteria = array('AND' => + array( + array('field' => 'objectClass', + 'op' => '=', + 'test' => self::USER), + array('OR' => + array( + array('field' => 'uid', + 'op' => '=', + 'test' => $id), + array('field' => 'mail', + 'op' => '=', + 'test' => $id), + ), + ), + ), + ); + + $result = $this->attrsForSearch($criteria, array('mail', 'alias'), + self::RESULT_STRICT); + if (isset($result['alias'])) { + $addrs = array_merge((array) $result['mail'], (array) $result['alias']); + } else { + $addrs = $result['mail']; + } + + if (empty($result)) { + return array(); + } + $criteria = array('AND' => + array( + array('field' => 'objectClass', + 'op' => '=', + 'test' => self::USER), + array('field' => 'kolabDelegate', + 'op' => '=', + 'test' => $result['mail'][0]), + ), + ); + + $result = $this->attrsForSearch($criteria, array('mail', 'alias'), + self::RESULT_MANY); + if (!empty($result)) { + foreach ($result as $adr) { + if (isset($adr['mail'])) { + $addrs = array_merge((array) $addrs, (array) $adr['mail']); + } + if (isset($adr['alias'])) { + $addrs = array_merge((array) $addrs, (array) $adr['alias']); + } + } + } + + $addrs = array_map('strtolower', $addrs); + + return $addrs; + } + + /** + * Identify the GID for the first group found with the given mail. + * + * @param string $mail Search for groups with this mail address. + * @param int $restrict A Horde_Kolab_Server::RESULT_* result restriction. + * + * @return mixed The GID or false if there was no result. + * + * @throws Horde_Kolab_Server_Exception + */ + public function gidForMail($mail, + $restrict = Horde_Kolab_Server::RESULT_SINGLE) + { + $criteria = array('AND' => array(array('field' => 'mail', + 'op' => '=', + 'test' => $mail), + ), + ); + return $this->gidForSearch($criteria, $restrict); + } + + /** + * Is the given UID member of the group with the given mail address? + * + * @param string $uid UID of the user. + * @param string $mail Search the group with this mail address. + * + * @return boolean True in case the user is in the group, false otherwise. + * + * @throws Horde_Kolab_Server_Exception + */ + public function memberOfGroupAddress($uid, $mail) + { + $criteria = array('AND' => + array( + array('field' => 'mail', + 'op' => '=', + 'test' => $mail), + array('field' => 'member', + 'op' => '=', + 'test' => $uid), + ), + ); + + $result = $this->gidForSearch($criteria, + self::RESULT_SINGLE); + return !empty($result); + } + + /** + * Get the groups for this object. + * + * @param string $uid The UID of the object to fetch. + * + * @return array An array of group ids. + * + * @throws Horde_Kolab_Server_Exception + */ + public function getGroups($uid) + { + $criteria = array('AND' => + array( + array('field' => 'member', + 'op' => '=', + 'test' => $uid), + ), + ); + + $result = $this->gidForSearch($criteria, self::RESULT_MANY); + if (empty($result)) { + return array(); + } + return $result; + } +} diff --git a/framework/Kolab_Server/lib/Horde/Kolab/Server/Test.php b/framework/Kolab_Server/lib/Horde/Kolab/Server/Test.php new file mode 100644 index 000000000..8f907b844 --- /dev/null +++ b/framework/Kolab_Server/lib/Horde/Kolab/Server/Test.php @@ -0,0 +1,715 @@ + + * @license http://www.fsf.org/copyleft/lgpl.html LGPL + * @link http://pear.horde.org/index.php?package=Kolab_Server + */ + +/** + * This class provides a class for testing the Kolab Server DB. + * + * Copyright 2008-2009 The Horde Project (http://www.horde.org/) + * + * See the enclosed file COPYING for license information (LGPL). If you + * did not receive this file, see http://www.fsf.org/copyleft/lgpl.html. + * + * @category Kolab + * @package Kolab_Server + * @author Gunnar Wrobel + * @license http://www.fsf.org/copyleft/lgpl.html LGPL + * @link http://pear.horde.org/index.php?package=Kolab_Server + */ +class Horde_Kolab_Server_Test extends Horde_Kolab_Server_Ldap +{ + + /** + * The current database data. + * + * @var array + */ + protected $data; + + /** + * Indicates if we are bound. + * + * @var array + */ + protected $bound; + + /** + * Array holding the current result set. + * + * @var array + */ + private $_result; + + /** + * Buffer for error numbers. + * + * @var int + */ + private $_errno = 0; + + /** + * Buffer for error descriptions. + * + * @var int + */ + private $_error = ''; + + /** + * Attribute used for sorting. + * + * @var string + */ + private $_sort_by; + + /** + * A result cache for iterating over the result. + * + * @var array + */ + private $_current_result; + + /** + * An index into the current result for iterating. + * + * @var int + */ + private $_current_index; + + /** + * Construct a new Horde_Kolab_Server object. + * + * @param array $params Parameter array. + */ + public function __construct($params = array()) + { + $this->load(); + if (isset($params['data'])) { + $this->data = $params['data']; + } else { + if (!isset($this->data)) { + $this->data = array(); + } + } + + parent::__construct($params); + + if (isset($this->params['adminuser']) + && isset($this->params['adminpass'])) { + $base_dn = isset($this->params['basedn']) ? ',' . $this->params['basedn'] : ''; + $dn = 'cn=' . $this->params['adminuser'] . ',cn=internal' . $base_dn; + if (!isset($this->data[$dn])) { + $ldap_data = array( + 'cn' => array('manager'), + 'sn' => array('n/a'), + 'uid' => array('manager'), + 'userPassword' => array($this->params['adminpass']), + 'objectClass' => array('top','inetOrgPerson','kolabInetOrgPerson') + ); + $this->data[$dn] = array( + 'dn' => $dn, + 'data' => $ldap_data + ); + } + } + + $this->store(); + } + + /** + * Connect to the server. + * + * @return NULL. + * + * @throws Horde_Kolab_Server_Exception If the connection failed. + */ + protected function connect() + { + } + + /** + * Load the current state of the database. + * + * @return NULL + */ + protected function load() + { + if (isset($GLOBALS['KOLAB_SERVER_TEST_DATA'])) { + $this->data = $GLOBALS['KOLAB_SERVER_TEST_DATA']; + } else { + $this->data = array(); + } + } + + /** + * Store the current state of the database. + * + * @return NULL + */ + protected function store() + { + $GLOBALS['KOLAB_SERVER_TEST_DATA'] = $this->data; + } + + /** + * Cleans the current state of the database. + * + * @return NULL + */ + public function clean() + { + $this->unbind(); + + $GLOBALS['KOLAB_SERVER_TEST_DATA'] = array(); + + $this->data = array(); + } + + /** + * Binds the LDAP connection with a specific user and pass. + * + * @param string $dn DN to bind with + * @param string $pw Password associated to this DN. + * + * @return boolean Whether or not the binding succeeded. + * + * @throws Horde_Kolab_Server_Exception If the user does not exit, he has no + * password, provided an incorrect + * password or anonymous binding is not + * allowed. + */ + protected function bind($dn = false, $pw = '') + { + if (!$dn) { + if (isset($this->params['uid'])) { + $dn = $this->params['uid']; + } else { + $dn = ''; + } + } + if (!$pw) { + if (isset($this->params['pass'])) { + $pw = $this->params['pass']; + } + } + + if (!empty($dn)) { + if (!isset($this->data[$dn])) { + throw new Horde_Kolab_Server_Exception('User does not exist!'); + } + + $this->bound = true; + + try { + $data = $this->read($dn, array('userPassword')); + } catch (Horde_Kolab_Server_Exception $e) { + $this->bound = false; + throw $e; + } + if (!isset($data['userPassword'])) { + $this->bound = false; + throw new Horde_Kolab_Server_Exception('User has no password entry!'); + } + $this->bound = $data['userPassword'][0] == $pw; + if (!$this->bound) { + throw new Horde_Kolab_Server_Exception('Incorrect password!'); + } + } else if (!empty($this->params['no_anonymous_bind'])) { + $this->bound = false; + throw new Horde_Kolab_Server_Exception('Anonymous bind is not allowed!'); + } else { + $this->bound = true; + } + return $this->bound; + } + + /** + * Disconnect from LDAP. + * + * @return NULL + */ + public function unbind() + { + $this->bound = false; + } + + /** + * Parse LDAP filter. + * Partially derived from Net_LDAP_Filter. + * + * @param string $filter The filter string. + * + * @return array An array of the parsed filter. + * + * @throws Horde_Kolab_Server_Exception If parsing the filter expression + * fails. + */ + public function parse($filter) + { + $result = array(); + if (preg_match('/^\((.+?)\)$/', $filter, $matches)) { + if (in_array(substr($matches[1], 0, 1), array('!', '|', '&'))) { + $result['op'] = substr($matches[1], 0, 1); + $result['sub'] = $this->parseSub(substr($matches[1], 1)); + return $result; + } else { + if (stristr($matches[1], ')(')) { + throw new Horde_Kolab_Server_Exception('Filter parsing error: invalid filter syntax - multiple leaf components detected!'); + } else { + $filter_parts = preg_split('/(?|<|>=|<=)/', + $matches[1], 2, + PREG_SPLIT_DELIM_CAPTURE); + if (count($filter_parts) != 3) { + throw new Horde_Kolab_Server_Exception('Filter parsing error: invalid filter syntax - unknown matching rule used'); + } else { + $result['att'] = $filter_parts[0]; + $result['log'] = $filter_parts[1]; + $result['val'] = $filter_parts[2]; + return $result; + } + } + } + } else { + throw new Horde_Kolab_Server_Exception(sprintf("Filter parsing error: %s - filter components must be enclosed in round brackets", + $filter)); + } + } + + /** + * Parse a LDAP subfilter. + * + * @param string $filter The subfilter string. + * + * @return array An array of the parsed subfilter. + * + * @throws Horde_Kolab_Server_Exception + */ + public function parseSub($filter) + { + $result = array(); + $level = 0; + $collect = ''; + while (preg_match('/^(\(.+?\))(.*)/', $filter, $matches)) { + if (in_array(substr($matches[1], 0, 2), array('(!', '(|', '(&'))) { + $level++; + } + if ($level) { + $collect .= $matches[1]; + if (substr($matches[2], 0, 1) == ')') { + $collect .= ')'; + $matches[2] = substr($matches[2], 1); + $level--; + if (!$level) { + $result[] = $this->parse($collect); + } + } + } else { + $result[] = $this->parse($matches[1]); + } + $filter = $matches[2]; + } + return $result; + } + + /** + * Search for object data. + * + * @param string $filter The LDAP search filter. + * @param string $params Additional search parameters. + * @param string $base The search base + * + * @return array The result array. + * + * @throws Horde_Kolab_Server_Exception If the search operation encountered + * a problem. + */ + public function search($filter = null, $params = array(), $base = null) + { + if (!$this->bound) { + $result = $this->bind(); + } + + $filter = $this->parse($filter); + if (isset($params['attributes'])) { + $attributes = $params['attributes']; + if (!is_array($attributes)) { + $attributes = array($attributes); + } + } else { + $attributes = array(); + } + $result = $this->doSearch($filter, $attributes); + if (empty($result)) { + return null; + } + if ($base) { + $subtree = array(); + foreach ($result as $entry) { + if (strpos($entry['dn'], $base)) { + $subtree[] = $entry; + } + } + $result = $subtree; + } + return $this->getEntries($result); + } + + /** + * Perform the search. + * + * @param array $filter Filter criteria- + * @param array $attributes Restrict the search result to + * these attributes. + * + * @return array A LDAP serach result. + * + * @throws Horde_Kolab_Server_Exception If the search operation is not + * available. + */ + protected function doSearch($filter, $attributes = null) + { + if (isset($filter['log'])) { + $result = array(); + foreach ($this->data as $element) { + if (isset($element['data'][$filter['att']])) { + switch ($filter['log']) { + case '=': + $value = $element['data'][$filter['att']]; + if (($filter['val'] == '*' && !empty($value)) + || $value == $filter['val'] + || (is_array($value) + && in_array($filter['val'], $value))) { + if (empty($attributes)) { + $result[] = $element; + } else { + $selection = $element; + foreach ($element['data'] as $attr => $value) { + if (!in_array($attr, $attributes)) { + unset($selection['data'][$attr]); + } + } + $result[] = $selection; + } + } + break; + default: + throw new Horde_Kolab_Server_Exception(_("Not implemented!")); + } + } + } + return $result; + } else { + $subresult = array(); + $filtercount = count($filter['sub']); + foreach ($filter['sub'] as $subfilter) { + $subresult = array_merge($subresult, + $this->doSearch($subfilter, + $attributes)); + } + $result = array(); + $dns = array(); + foreach ($subresult as $element) { + $dns[] = $element['dn']; + + $result[$element['dn']] = $element; + } + switch ($filter['op']) { + case '&': + $count = array_count_values($dns); + $selection = array(); + foreach ($count as $dn => $value) { + if ($value == $filtercount) { + $selection[] = $result[$dn]; + } + } + return $selection; + case '|': + return array_values($result); + case '!': + $dns = array(); + foreach ($result as $entry) { + if (!in_array($entry['dn'], $dns) ) { + $dns[] = $entry['dn']; + } + } + $all_dns = array_keys($this->data); + $diff = array_diff($all_dns, $dns); + + $result = array(); + foreach ($diff as $dn) { + if (empty($attributes)) { + $result[] = $this->data[$dn]; + } else { + $selection = $this->data[$dn]; + foreach ($this->data[$dn]['data'] + as $attr => $value) { + if (!in_array($attr, $attributes)) { + unset($selection['data'][$attr]); + } + } + $result[] = $selection; + } + } + return $result; + default: + throw new Horde_Kolab_Server_Exception(_("Not implemented!")); + } + } + } + + /** + * Read object data. + * + * @param string $dn The object to retrieve. + * @param string $attrs Restrict to these attributes + * + * @return array An array of attributes. + * + * @throws Horde_Kolab_Server_Exception If the object does not exist. + */ + public function read($dn, $attrs = null) + { + if (!$this->bound) { + $result = $this->bind(); + } + + if (!isset($this->data[$dn])) { + throw new Horde_Kolab_Server_MissingObjectException(sprintf("No such object: %s", + $dn)); + } + if (empty($attrs)) { + return $this->data[$dn]['data']; + } else { + $result = array(); + $data = $this->data[$dn]['data']; + + foreach ($attrs as $attr) { + if (isset($data[$attr])) { + $result[$attr] = $data[$attr]; + array_push($result, $attr); + } + } + return $result; + } + } + + /** + * Add a new object + * + * @param string $dn The DN of the object to be added. + * @param array $data The attributes of the object to be added. + * + * @return boolean True if adding succeeded. + */ + public function save($dn, $data) + { + if (!$this->bound) { + $result = $this->bind(); + } + + $ldap_data = array(); + foreach ($data as $key => $val) { + if (!is_array($val)) { + $val = array($val); + } + $ldap_data[$key] = $val; + } + + $this->data[$dn] = array( + 'dn' => $dn, + 'data' => $ldap_data + ); + $this->store(); + } + + /** + * Return the attributes of an entry. + * + * @param array $entry The LDAP entry. + * + * @return array The attributes of the entry. + */ + protected function getAttributes($entry) + { + if (is_array($entry)) { + return $entry; + } + return false; + } + + /** + * Return the current entry of a result. + * + * @return mixe The current entry of the result or false. + */ + protected function fetchEntry() + { + if (is_array($this->_current_result) + && $this->_current_index < count($this->_current_result)) { + + $data = array_keys($this->_current_result[$this->_current_index]['data']); + + $data['dn'] = array($this->_current_result[$this->_current_index]['dn']); + + foreach ($this->_current_result[$this->_current_index]['data'] + as $attr => $value) { + if (!is_array($value)) { + $value = array($value); + } + $data[$attr] = $value; + } + $this->_current_index++; + return $data; + } + return false; + } + + /** + * Return the first entry of a result. + * + * @param array $result The LDAP search result. + * + * @return mixed The first entry of the result or false. + */ + protected function firstEntry($result) + { + $this->_current_result = $result; + $this->_current_index = 0; + return $this->fetchEntry(); + } + + /** + * Return the next entry of a result. + * + * @param resource $entry The current LDAP entry. + * + * @return resource The next entry of the result. + */ + protected function nextEntry($entry) + { + return $this->fetchEntry(); + } + + /** + * Return the entries of a result. + * + * @param array $result The LDAP search result. + * + * @return mixed The entries of the result or false. + */ + protected function getEntries($result) + { + if (is_array($result)) { + $data = array(); + foreach ($result as $entry) { + $t = $entry['data']; + $t['dn'] = $entry['dn']; + $data[] = $t; + } + return $data; + } + return false; + } + + /** + * Sort the entries of a result. + * + * @param resource &$result The LDAP search result. + * @param string $attribute The attribute used for sorting. + * + * @return boolean True if sorting succeeded. + */ + public function sort(&$result, $attribute) + { + if (empty($result)) { + return $result; + } + + $this->_sort_by = $attribute; + usort($result, array($this, 'resultSort')); + return false; + } + + /** + * Sort two entries. + * + * @param array $a First entry. + * @param array $b Second entry. + * + * @return int Comparison result. + */ + protected function resultSort($a, $b) + { + $x = isset($a['data'][$this->_sort_by][0])?$a['data'][$this->_sort_by][0]:''; + $y = isset($b['data'][$this->_sort_by][0])?$b['data'][$this->_sort_by][0]:''; + return strcasecmp($x, $y); + } + + + /** + * Return the current LDAP error number. + * + * @return int The current LDAP error number. + */ + protected function errno() + { + return $this->_errno; + } + + /** + * Return the current LDAP error description. + * + * @return string The current LDAP error description. + */ + protected function error() + { + return $this->_error; + } + + /** + * Identify the DN of the first result entry. + * + * @todo Check if this could be reintegrated with the code in the LDAP handler + * again. + * + * @param array $result The LDAP search result. + * @param int $restrict A Horde_Kolab_Server::RESULT_* result restriction. + * + * @return boolean|string|array The DN(s) or false if there was no result. + * + * @throws Horde_Kolab_Server_Exception If the number of results did not + * meet the expectations. + */ + protected function dnFromResult($result, + $restrict = Horde_Kolab_Server::RESULT_SINGLE) + { + if (empty($result)) { + return false; + } + $dns = array(); + foreach ($result as $entry) { + $dns[] = $entry['dn']; + } + + switch ($restrict) { + case self::RESULT_STRICT: + if (count($dns) > 1) { + throw new Horde_Kolab_Server_Exception(sprintf(_("Found %s results when expecting only one!"), + $count)); + } + case self::RESULT_SINGLE: + return $dns[0]; + case self::RESULT_MANY: + return $dns; + } + } + +} diff --git a/framework/Kolab_Server/lib/Horde/Kolab/Server/file.php b/framework/Kolab_Server/lib/Horde/Kolab/Server/file.php deleted file mode 100644 index 6d087ff14..000000000 --- a/framework/Kolab_Server/lib/Horde/Kolab/Server/file.php +++ /dev/null @@ -1,115 +0,0 @@ - - * @license http://www.fsf.org/copyleft/lgpl.html LGPL - * @link http://pear.horde.org/index.php?package=Kolab_Server - */ - -/** - * This class provides a persistant class for testing the Kolab Server DB. - * - * Copyright 2008-2009 The Horde Project (http://www.horde.org/) - * - * See the enclosed file COPYING for license information (LGPL). If you - * did not receive this file, see http://www.fsf.org/copyleft/lgpl.html. - * - * @category Kolab - * @package Kolab_Server - * @author Gunnar Wrobel - * @license http://www.fsf.org/copyleft/lgpl.html LGPL - * @link http://pear.horde.org/index.php?package=Kolab_Server - */ -class Horde_Kolab_Server_file extends Horde_Kolab_Server_test -{ - - /** - * The file for storing the database data. - * - * @var string - */ - private $_file; - - /** - * Construct a new Horde_Kolab_Server object. - * - * @param array $params Parameter array. - */ - public function __construct($params = array()) - { - if (isset($params['file'])) { - $this->_file = $params['file']; - } else { - $this->_file = Horde::getTempFile('Horde_Kolab_Server', false); - } - parent::__construct($params); - } - - - /** - * Load the current state of the database. - * - * @return NULL - */ - protected function load() - { - $raw_data = file_get_contents($this->_file); - if (!$raw_data === false) { - $data = @unserialize($raw_data); - if ($data !== false) { - $this->data = $data; - } else { - $error = error_get_last(); - Horde::logMessage(sprintf('Horde_Kolab_Server_file failed to read the database from %s. Error was: %s', - $this->_file, $error['message']), __FILE__, - __LINE__, PEAR_LOG_WARNING); - $this->data = array(); - } - } - } - - /** - * Store the current state of the database. - * - * @return NULL - */ - protected function store() - { - $raw_data = serialize($this->data); - $result = @file_put_contents($this->_file, $raw_data); - if ($result === false) { - $error = error_get_last(); - Horde::logMessage(sprintf('Horde_Kolab_Server_file failed to store the database in %s. Error was: %s', - $this->_file, $error['message']), __FILE__, - __LINE__, PEAR_LOG_WARNING); - } - } - - /** - * Cleans the current state of the database. - * - * @return NULL - */ - public function clean() - { - unlink($this->_file); - $this->data = array(); - $this->store(); - } - - /** - * Returns the path to the storage location of the database. - * - * @return string The path to the database. - */ - public function getStoragePAth() - { - return $this->_file; - } -} diff --git a/framework/Kolab_Server/lib/Horde/Kolab/Server/ldap.php b/framework/Kolab_Server/lib/Horde/Kolab/Server/ldap.php deleted file mode 100644 index e261cbef5..000000000 --- a/framework/Kolab_Server/lib/Horde/Kolab/Server/ldap.php +++ /dev/null @@ -1,937 +0,0 @@ - - * @license http://www.fsf.org/copyleft/lgpl.html LGPL - * @link http://pear.horde.org/index.php?package=Kolab_Server - */ - -/** - * This class provides methods to deal with Kolab objects stored in - * the standard Kolab LDAP db. - * - * Copyright 2008-2009 The Horde Project (http://www.horde.org/) - * - * See the enclosed file COPYING for license information (LGPL). If you - * did not receive this file, see http://www.fsf.org/copyleft/lgpl.html. - * - * @category Kolab - * @package Kolab_Server - * @author Gunnar Wrobel - * @license http://www.fsf.org/copyleft/lgpl.html LGPL - * @link http://pear.horde.org/index.php?package=Kolab_Server - */ -class Horde_Kolab_Server_ldap extends Horde_Kolab_Server -{ - - /** - * The object types supported by this server type. - */ - const USER = 'kolabInetOrgPerson'; - const GROUP = 'kolabGroupOfNames'; - - /** - * LDAP connection handle. - * - * @var Net_LDAP2 - */ - private $_ldap; - - /** - * Base DN of the LDAP server. - * - * @var string - */ - private $_base_dn; - - /** - * Construct a new Horde_Kolab_Server_ldap object. - * - * @param array $params Parameter array. - */ - public function __construct($params = array()) - { - if (!isset($params['charset'])) { - $params['charset'] = 'UTF-8'; - } - - $base_config = array('host' => 'localhost', - 'port' => 389, - 'version' => 3, - 'starttls' => false, - 'uid' => '', - 'pass' => '', - 'basedn' => '', - 'charset' => '', - 'options' => array(), - 'auto_reconnect' => true); - - - $config = array_merge($base_config, $params); - - $this->_base_dn = $config['basedn']; - - $config['binddn'] = $config['uid']; - $config['bindpw'] = $config['pass']; - - $this->connect(); - - parent::__construct($params); - } - - - /** - * Connect to the LDAP server. - * - * @return NULL. - * - * @throws Horde_Kolab_Server_Exception If the connection failed. - */ - protected function connect() - { - $this->_ldap = Net_LDAP2::connect($config); - if (is_a($this->_ldap, 'PEAR_Error')) { - throw new Horde_Kolab_Server_Exception($this->_ldap); - } - } - - /** - * Read object data. - * - * @param string $dn The object to retrieve. - * @param string $attrs Restrict to these attributes. - * - * @return array|boolean An array of attributes or false if the specified - * object was not found. - * - * @throws Horde_Kolab_Server_Exception If the search operation retrieved a - * problematic result. - */ - public function read($dn, $attrs = null) - { - $params = array('scope' => 'base'); - if (!empty($attrs)) { - $params['attributes'] = $attrs; - } - - $data = $this->search(null, $params, $dn); - if (empty($data)) { - throw new Horde_Kolab_Server_Exception(_("Empty result!")); - } - - if (!isset($data[$dn])) { - throw new Horde_Kolab_Server_Exception(sprintf(_("No result found for %s"), - $dn)); - } - if (is_a($data[$dn], 'PEAR_Error')) { - throw new Horde_Kolab_Server_Exception($data[$dn]); - } - return $data[$dn]; - } - - /** - * Determine the type of a Kolab object. - * - * @param string $dn The DN of the object to examine. - * - * @return int The corresponding Kolab object type. - * - * @throws Horde_Kolab_Server_Exception If the object type is unknown. - */ - public function determineType($dn) - { - $oc = $this->getObjectClasses($dn); - // Not a user type? - if (!in_array('kolabinetorgperson', $oc)) { - // Is it a group? - if (in_array('kolabgroupofnames', $oc)) { - return 'Horde_Kolab_Server_Object_group'; - } - // Is it a shared Folder? - if (in_array('kolabsharedfolder', $oc)) { - return 'Horde_Kolab_Server_Object_sharedfolder'; - } - throw new Horde_Kolab_Server_Exception(sprintf(_("Unkown Kolab object type for DN %s."), - $dn)); - } - - $groups = $this->getGroups($dn); - if (!empty($groups)) { - if (in_array('cn=admin,cn=internal,' . $this->_base_dn, $groups)) { - return 'Horde_Kolab_Server_Object_administrator'; - } - if (in_array('cn=maintainer,cn=internal,' . $this->_base_dn, - $groups)) { - return 'Horde_Kolab_Server_Object_maintainer'; - } - if (in_array('cn=domain-maintainer,cn=internal,' . $this->_base_dn, - $groups)) { - return 'Horde_Kolab_Server_Object_domainmaintainer'; - } - } - - if (strpos($dn, 'cn=external') !== false) { - return 'Horde_Kolab_Server_Object_address'; - } - - return 'Horde_Kolab_Server_Object_user'; - } - - /** - * List all objects of a specific type - * - * @param string $type The type of the objects to be listed - * @param array $params Additional parameters. - * - * @return array An array of Kolab objects. - * - * @throws Horde_Kolab_Server_Exception - * - * @todo Sorting - */ - public function listObjects($type, $params = null) - { - if (empty($params['base_dn'])) { - $base = $this->_base_dn; - } else { - $base = $params['base_dn']; - } - - $result = Horde_Kolab_Server_Object::loadClass($type); - $vars = get_class_vars($type); - $filter = call_user_func(array($type, 'getFilter')); - $sort = $vars['sort_by']; - - if (isset($params['sort'])) { - $sort = $params['sort']; - } - - $options = array('scope' => 'sub'); - if (isset($params['attributes'])) { - $options['attributes'] = $params['attributes']; - } else { - $options['attributes'] = $vars['_supported_attributes']; - } - - $result = $this->search($filter, $options, $base); - if (empty($result)) { - return array(); - } - - if ($sort) { - /* FIXME */ - /*$this->sort($result, $sort); */ - } - - if (isset($params['from'])) { - $from = $params['from']; - } else { - $from = -1; - } - - if (isset($params['to'])) { - $sort = $params['to']; - } else { - $to = -1; - } - - $entries = array(); - foreach ($result as $entry) { - $entries[] = $entry['dn']; - } - - if (!empty($vars['required_group'])) { - $required_group = $this->fetch($vars['required_group'], - 'Horde_Kolab_Server_Object_group'); - } - - $objects = array(); - foreach ($entries as $dn) { - if (!empty($vars['required_group']) && $required_group->isMember($dn)) { - continue; - } - $result = $this->fetch($dn, $type); - $objects[$dn] = $result; - } - return $objects; - } - - /** - * Generates a UID for the given information. - * - * @param string $type The type of the object to create. - * @param string $id The id of the object. - * @param array $info Any additional information about the object to create. - * - * @return string The DN. - * - * @throws Horde_Kolab_Server_Exception If the given type is unknown. - */ - public function generateServerUid($type, $id, $info) - { - switch ($type) { - case 'Horde_Kolab_Server_Object_user': - if (!isset($info['user_type']) || $info['user_type'] == 0) { - return sprintf('cn=%s,%s', $id, $this->_base_dn); - } else if ($info['user_type'] == Horde_Kolab_Server_Object_user::USERTYPE_INTERNAL) { - return sprintf('cn=%s,cn=internal,%s', $id, $this->_base_dn); - } else if ($info['user_type'] == Horde_Kolab_Server_Object_user::USERTYPE_GROUP) { - return sprintf('cn=%s,cn=groups,%s', $id, $this->_base_dn); - } else if ($info['user_type'] == Horde_Kolab_Server_Object_user::USERTYPE_RESOURCE) { - return sprintf('cn=%s,cn=resources,%s', $id, $this->_base_dn); - } else { - return sprintf('cn=%s,%s', $id, $this->_base_dn); - } - case 'Horde_Kolab_Server_Object_address': - return sprintf('cn=%s,cn=external,%s', $id, $this->_base_dn); - case 'Horde_Kolab_Server_Object_sharedfolder': - case 'Horde_Kolab_Server_Object_administrator': - case 'Horde_Kolab_Server_Object_maintainer': - case 'Horde_Kolab_Server_Object_domainmaintainer': - return sprintf('cn=%s,%s', $id, $this->_base_dn); - case 'Horde_Kolab_Server_Object_group': - case 'Horde_Kolab_Server_Object_distlist': - if (!isset($info['visible']) || !empty($info['visible'])) { - return sprintf('cn=%s,%s', $id, $this->_base_dn); - } else { - return sprintf('cn=%s,cn=internal,%s', $id, $this->_base_dn); - } - default: - throw new Horde_Kolab_Server_Exception(_("Not implemented!")); - } - } - - /** - * Return the root of the UID values on this server. - * - * @return string The base UID on this server (base DN on ldap). - */ - public function getBaseUid() - { - return $this->_base_dn; - } - - /** - * Save an object. - * - * @param string $dn The DN of the object. - * @param array $data The data for the object. - * - * @return boolean True if successfull. - * - * @throws Horde_Kolab_Server_Exception If the given type is unknown. - */ - function save($dn, $data) - { - $result = $this->_add($dn, $data); - if (!$result && $this->_errno()) { - throw new Horde_Kolab_Server_Exception(sprintf(_("Failed saving object. Error was: %s"), - $this->_error())); - } - } - - /** - * Identify the UID for the first object found using the specified - * search criteria. - * - * @param array $criteria The search parameters as array. - * @param int $restrict A Horde_Kolab_Server::RESULT_* result restriction. - * - * @return boolean|string|array The UID(s) or false if there was no result. - * - * @throws Horde_Kolab_Server_Exception - */ - public function uidForSearch($criteria, - $restrict = Horde_Kolab_Server::RESULT_SINGLE) - { - $users = array('field' => 'objectClass', - 'op' => '=', - 'test' => self::USER); - if (!empty($criteria)) { - $criteria = array('AND' => array($users, $criteria)); - } else { - $criteria = array('AND' => array($users)); - } - - $filter = $this->searchQuery($criteria); - return $this->dnForFilter($filter, $restrict); - } - - /** - * Identify the GID for the first group found using the specified - * search criteria - * - * @param array $criteria The search parameters as array. - * @param int $restrict A Horde_Kolab_Server::RESULT_* result restriction. - * - * @return boolean|string|array The GID(s) or false if there was no result. - * - * @throws Horde_Kolab_Server_Exception - */ - public function gidForSearch($criteria, - $restrict = Horde_Kolab_Server::RESULT_SINGLE) - { - $groups = array('field' => 'objectClass', - 'op' => '=', - 'test' => self::GROUP); - if (!empty($criteria)) { - $criteria = array('AND' => array($groups, $criteria)); - } else { - $criteria = array('AND' => array($groups)); - } - - $filter = $this->searchQuery($criteria); - return $this->dnForFilter($filter, $restrict); - } - - /** - * Identify attributes for the objects found using a filter. - * - * @param array $criteria The search parameters as array. - * @param array $attrs The attributes to retrieve. - * @param int $restrict A Horde_Kolab_Server::RESULT_* result restriction. - * - * @return array The results. - * - * @throws Horde_Kolab_Server_Exception - */ - public function attrsForSearch($criteria, $attrs, - $restrict = Horde_Kolab_Server::RESULT_SINGLE) - { - $params = array('attributes' => $attrs); - $filter = $this->searchQuery($criteria); - $result = $this->search($filter, $params, $this->_base_dn); - return $this->attrsFromResult($result, $attrs, $restrict); - } - - /** - * Search for object data. - * - * @param string $filter The LDAP search filter. - * @param string $params Additional search parameters. - * @param string $base The search base - * - * @return array The result array. - * - * @throws Horde_Kolab_Server_Exception If the search operation encountered - * a problem. - */ - public function search($filter = null, $params = array(), $base = null) - { - if (!isset($base)) { - $base = $this->_base_dn; - } - $result = $this->_ldap->search($base, $filter, $params); - if (is_a($result, 'PEAR_Error')) { - throw new Horde_Kolab_Server_Exception($result->getMessage()); - } - return $result->as_struct(); - } - - /** - * Get the LDAP object classes for the given DN. - * - * @param string $dn DN of the object. - * - * @return array An array of object classes. - * - * @throws Horde_Kolab_Server_Exception If the object has no - * object classes. - */ - public function getObjectClasses($dn) - { - $object = $this->read($dn, array('objectClass')); - if (!isset($object['objectClass'])) { - throw new Horde_Kolab_Server_Exception(sprintf(_("The object %s has no object classes!"), - $dn)); - } - $result = array_map('strtolower', $object['objectClass']); - return $result; - } - - /** - * Build a search query. - * - * Taken from the Turba LDAP driver. - * - * @param array $criteria The array of criteria. - * - * @return string An LDAP query filter. - */ - protected function searchQuery($criteria) - { - /* Build the LDAP filter. */ - $filter = ''; - if (count($criteria)) { - foreach ($criteria as $key => $vals) { - if ($key == 'OR') { - $filter .= '(|' . $this->buildSearchQuery($vals) . ')'; - } elseif ($key == 'AND') { - $filter .= '(&' . $this->buildSearchQuery($vals) . ')'; - } - } - } else { - /* Accept everything. */ - $filter = '(objectclass=*)'; - } - - /* Add source-wide filters, which are _always_ AND-ed. */ - if (!empty($this->params['filter'])) { - $filter = '(&' . '(' . $this->params['filter'] . ')' . $filter . ')'; - } - return $filter; - } - - /** - * Build a piece of a search query. - * - * Taken from the Turba LDAP driver. - * - * @param array $criteria The array of criteria. - * - * @return string An LDAP query fragment. - */ - protected function buildSearchQuery($criteria) - { - $clause = ''; - foreach ($criteria as $key => $vals) { - if (!empty($vals['OR'])) { - $clause .= '(|' . $this->buildSearchQuery($vals) . ')'; - } elseif (!empty($vals['AND'])) { - $clause .= '(&' . $this->buildSearchQuery($vals) . ')'; - } else { - if (isset($vals['field'])) { - require_once 'Horde/String.php'; - require_once 'Horde/NLS.php'; - $rhs = String::convertCharset($vals['test'], NLS::getCharset(), $this->params['charset']); - $clause .= Horde_LDAP::buildClause($vals['field'], $vals['op'], $rhs, array('begin' => !empty($vals['begin']))); - } else { - foreach ($vals as $test) { - if (!empty($test['OR'])) { - $clause .= '(|' . $this->buildSearchQuery($test) . ')'; - } elseif (!empty($test['AND'])) { - $clause .= '(&' . $this->buildSearchQuery($test) . ')'; - } else { - $rhs = String::convertCharset($test['test'], NLS::getCharset(), $this->params['charset']); - $clause .= Horde_LDAP::buildClause($test['field'], $test['op'], $rhs, array('begin' => !empty($vals['begin']))); - } - } - } - } - } - - return $clause; - } - - /** - * Identify the DN of the first result entry. - * - * @param array $result The LDAP search result. - * @param int $restrict A Horde_Kolab_Server::RESULT_* result restriction. - * - * @return boolean|string|array The DN(s) or false if there was no result. - * - * @throws Horde_Kolab_Server_Exception If the number of results did not - * meet the expectations. - */ - protected function dnFromResult($result, - $restrict = Horde_Kolab_Server::RESULT_SINGLE) - { - if (empty($result)) { - return false; - } - $dns = array_keys($result); - - switch ($restrict) { - case self::RESULT_STRICT: - if (count($dns) > 1) { - throw new Horde_Kolab_Server_Exception(sprintf(_("Found %s results when expecting only one!"), - $count)); - } - case self::RESULT_SINGLE: - return $dns[0]; - case self::RESULT_MANY: - return $dns; - } - } - - /** - * Get the attributes of the first result entry. - * - * @param array $result The LDAP search result. - * @param array $attrs The attributes to retrieve. - * @param int $restrict A Horde_Kolab_Server::RESULT_* result restriction. - * - * @return array The DN. - * - * @throws Horde_Kolab_Server_Exception If the number of results did not - * meet the expectations. - */ - protected function attrsFromResult($result, $attrs, - $restrict = Horde_Kolab_Server::RESULT_SINGLE) - { - switch ($restrict) { - case self::RESULT_STRICT: - if (count($result) > 1) { - throw new Horde_Kolab_Server_Exception(sprintf(_("Found %s results when expecting only one!"), - $count)); - } - case self::RESULT_SINGLE: - if (count($result) > 0) { - return $result[0]; - } - return array(); - case self::RESULT_MANY: - return $result; - } - return array(); - } - - - /** - * Identify the DN for the first object found using a filter. - * - * @param string $filter The LDAP filter to use. - * @param int $restrict A Horde_Kolab_Server::RESULT_* result restriction. - * - * @return boolean|string|array The DN(s) or false if there was no result. - * - * @throws Horde_Kolab_Server_Exception - */ - protected function dnForFilter($filter, - $restrict = Horde_Kolab_Server::RESULT_SINGLE) - { - $params = array('attributes' => 'dn'); - $result = $this->search($filter, $params, $this->_base_dn); - return $this->dnFromResult($result, $restrict); - } - - /** - * Identify the UID for the first object found with the given ID. - * - * @param string $id Search for objects with this ID. - * @param int $restrict A Horde_Kolab_Server::RESULT_* result restriction. - * - * @return mixed The UID or false if there was no result. - * - * @throws Horde_Kolab_Server_Exception - */ - public function uidForId($id, - $restrict = Horde_Kolab_Server::RESULT_SINGLE) - { - $criteria = array('AND' => array(array('field' => 'uid', - 'op' => '=', - 'test' => $id), - ), - ); - return $this->uidForSearch($criteria, $restrict); - } - - /** - * Identify the UID for the first user found with the given mail. - * - * @param string $mail Search for users with this mail address. - * @param int $restrict A Horde_Kolab_Server::RESULT_* result restriction. - * - * @return mixed The UID or false if there was no result. - * - * @throws Horde_Kolab_Server_Exception - */ - public function uidForMail($mail, - $restrict = Horde_Kolab_Server::RESULT_SINGLE) - { - $criteria = array('AND' => array(array('field' => 'mail', - 'op' => '=', - 'test' => $mail), - ), - ); - return $this->uidForSearch($criteria, $restrict); - } - - /** - * Identify the UID for the first object found with the given alias. - * - * @param string $mail Search for objects with this mail alias. - * @param int $restrict A Horde_Kolab_Server::RESULT_* result restriction. - * - * @return mixed The UID or false if there was no result. - * - * @throws Horde_Kolab_Server_Exception - */ - public function uidForAlias($mail, - $restrict = Horde_Kolab_Server::RESULT_SINGLE) - { - $criteria = array('AND' => array(array('field' => 'alias', - 'op' => '=', - 'test' => $mail), - ), - ); - return $this->uidForSearch($criteria, $restrict); - } - - /** - * Identify the UID for the first object found with the given ID or mail. - * - * @param string $id Search for objects with this uid/mail. - * - * @return string|boolean The UID or false if there was no result. - * - * @throws Horde_Kolab_Server_Exception - */ - public function uidForIdOrMail($id) - { - $criteria = array('OR' => - array( - array('field' => 'uid', - 'op' => '=', - 'test' => $id), - array('field' => 'mail', - 'op' => '=', - 'test' => $id), - ), - ); - return $this->uidForSearch($criteria); - } - - /** - * Identify the UID for the first object found with the given mail - * address or alias. - * - * @param string $mail Search for objects with this mail address - * or alias. - * - * @return string|boolean The UID or false if there was no result. - * - * @throws Horde_Kolab_Server_Exception - */ - public function uidForMailOrAlias($mail) - { - $criteria = array('OR' => - array( - array('field' => 'alias', - 'op' => '=', - 'test' => $mail), - array('field' => 'mail', - 'op' => '=', - 'test' => $mail), - ) - ); - return $this->uidForSearch($criteria); - } - - /** - * Identify the UID for the first object found with the given ID, - * mail or alias. - * - * @param string $id Search for objects with this ID/mail/alias. - * - * @return string|boolean The UID or false if there was no result. - * - * @throws Horde_Kolab_Server_Exception - */ - public function uidForIdOrMailOrAlias($id) - { - $criteria = array('OR' => - array( - array('field' => 'alias', - 'op' => '=', - 'test' => $id), - array('field' => 'mail', - 'op' => '=', - 'test' => $id), - array('field' => 'uid', - 'op' => '=', - 'test' => $id), - ), - ); - return $this->uidForSearch($criteria); - } - - /** - * Identify the primary mail attribute for the first object found - * with the given ID or mail. - * - * @param string $id Search for objects with this ID/mail. - * - * @return mixed The mail address or false if there was no result. - * - * @throws Horde_Kolab_Server_Exception - */ - public function mailForIdOrMail($id) - { - $criteria = array('AND' => - array( - array('field' => 'objectClass', - 'op' => '=', - 'test' => self::USER), - array('OR' => - array( - array('field' => 'uid', - 'op' => '=', - 'test' => $id), - array('field' => 'mail', - 'op' => '=', - 'test' => $id), - ), - ), - ), - ); - - $data = $this->attrsForSearch($criteria, array('mail'), - self::RESULT_STRICT); - if (!empty($data)) { - return $data['mail'][0]; - } else { - return false; - } - } - - /** - * Returns a list of allowed email addresses for the given user. - * - * @param string $id Search for objects with this ID/mail. - * - * @return array An array of allowed mail addresses. - * - * @throws Horde_Kolab_Server_Exception - */ - public function addrsForIdOrMail($id) - { - $criteria = array('AND' => - array( - array('field' => 'objectClass', - 'op' => '=', - 'test' => self::USER), - array('OR' => - array( - array('field' => 'uid', - 'op' => '=', - 'test' => $id), - array('field' => 'mail', - 'op' => '=', - 'test' => $id), - ), - ), - ), - ); - - $result = $this->attrsForSearch($criteria, array('mail', 'alias'), - self::RESULT_STRICT); - if (isset($result['alias'])) { - $addrs = array_merge((array) $result['mail'], (array) $result['alias']); - } else { - $addrs = $result['mail']; - } - - if (empty($result)) { - return array(); - } - $criteria = array('AND' => - array( - array('field' => 'objectClass', - 'op' => '=', - 'test' => self::USER), - array('field' => 'kolabDelegate', - 'op' => '=', - 'test' => $result['mail'][0]), - ), - ); - - $result = $this->attrsForSearch($criteria, array('mail', 'alias'), - self::RESULT_MANY); - if (!empty($result)) { - foreach ($result as $adr) { - if (isset($adr['mail'])) { - $addrs = array_merge((array) $addrs, (array) $adr['mail']); - } - if (isset($adr['alias'])) { - $addrs = array_merge((array) $addrs, (array) $adr['alias']); - } - } - } - - $addrs = array_map('strtolower', $addrs); - - return $addrs; - } - - /** - * Identify the GID for the first group found with the given mail. - * - * @param string $mail Search for groups with this mail address. - * @param int $restrict A Horde_Kolab_Server::RESULT_* result restriction. - * - * @return mixed The GID or false if there was no result. - * - * @throws Horde_Kolab_Server_Exception - */ - public function gidForMail($mail, - $restrict = Horde_Kolab_Server::RESULT_SINGLE) - { - $criteria = array('AND' => array(array('field' => 'mail', - 'op' => '=', - 'test' => $mail), - ), - ); - return $this->gidForSearch($criteria, $restrict); - } - - /** - * Is the given UID member of the group with the given mail address? - * - * @param string $uid UID of the user. - * @param string $mail Search the group with this mail address. - * - * @return boolean True in case the user is in the group, false otherwise. - * - * @throws Horde_Kolab_Server_Exception - */ - public function memberOfGroupAddress($uid, $mail) - { - $criteria = array('AND' => - array( - array('field' => 'mail', - 'op' => '=', - 'test' => $mail), - array('field' => 'member', - 'op' => '=', - 'test' => $uid), - ), - ); - - $result = $this->gidForSearch($criteria, - self::RESULT_SINGLE); - return !empty($result); - } - - /** - * Get the groups for this object. - * - * @param string $uid The UID of the object to fetch. - * - * @return array An array of group ids. - * - * @throws Horde_Kolab_Server_Exception - */ - public function getGroups($uid) - { - $criteria = array('AND' => - array( - array('field' => 'member', - 'op' => '=', - 'test' => $uid), - ), - ); - - $result = $this->gidForSearch($criteria, self::RESULT_MANY); - if (empty($result)) { - return array(); - } - return $result; - } -} diff --git a/framework/Kolab_Server/lib/Horde/Kolab/Server/test.php b/framework/Kolab_Server/lib/Horde/Kolab/Server/test.php deleted file mode 100644 index daa908651..000000000 --- a/framework/Kolab_Server/lib/Horde/Kolab/Server/test.php +++ /dev/null @@ -1,715 +0,0 @@ - - * @license http://www.fsf.org/copyleft/lgpl.html LGPL - * @link http://pear.horde.org/index.php?package=Kolab_Server - */ - -/** - * This class provides a class for testing the Kolab Server DB. - * - * Copyright 2008-2009 The Horde Project (http://www.horde.org/) - * - * See the enclosed file COPYING for license information (LGPL). If you - * did not receive this file, see http://www.fsf.org/copyleft/lgpl.html. - * - * @category Kolab - * @package Kolab_Server - * @author Gunnar Wrobel - * @license http://www.fsf.org/copyleft/lgpl.html LGPL - * @link http://pear.horde.org/index.php?package=Kolab_Server - */ -class Horde_Kolab_Server_test extends Horde_Kolab_Server_ldap -{ - - /** - * The current database data. - * - * @var array - */ - protected $data; - - /** - * Indicates if we are bound. - * - * @var array - */ - protected $bound; - - /** - * Array holding the current result set. - * - * @var array - */ - private $_result; - - /** - * Buffer for error numbers. - * - * @var int - */ - private $_errno = 0; - - /** - * Buffer for error descriptions. - * - * @var int - */ - private $_error = ''; - - /** - * Attribute used for sorting. - * - * @var string - */ - private $_sort_by; - - /** - * A result cache for iterating over the result. - * - * @var array - */ - private $_current_result; - - /** - * An index into the current result for iterating. - * - * @var int - */ - private $_current_index; - - /** - * Construct a new Horde_Kolab_Server object. - * - * @param array $params Parameter array. - */ - public function __construct($params = array()) - { - $this->load(); - if (isset($params['data'])) { - $this->data = $params['data']; - } else { - if (!isset($this->data)) { - $this->data = array(); - } - } - - parent::__construct($params); - - if (isset($this->params['adminuser']) - && isset($this->params['adminpass'])) { - $base_dn = isset($this->params['basedn']) ? ',' . $this->params['basedn'] : ''; - $dn = 'cn=' . $this->params['adminuser'] . ',cn=internal' . $base_dn; - if (!isset($this->data[$dn])) { - $ldap_data = array( - 'cn' => array('manager'), - 'sn' => array('n/a'), - 'uid' => array('manager'), - 'userPassword' => array($this->params['adminpass']), - 'objectClass' => array('top','inetOrgPerson','kolabInetOrgPerson') - ); - $this->data[$dn] = array( - 'dn' => $dn, - 'data' => $ldap_data - ); - } - } - - $this->store(); - } - - /** - * Connect to the server. - * - * @return NULL. - * - * @throws Horde_Kolab_Server_Exception If the connection failed. - */ - protected function connect() - { - } - - /** - * Load the current state of the database. - * - * @return NULL - */ - protected function load() - { - if (isset($GLOBALS['KOLAB_SERVER_TEST_DATA'])) { - $this->data = $GLOBALS['KOLAB_SERVER_TEST_DATA']; - } else { - $this->data = array(); - } - } - - /** - * Store the current state of the database. - * - * @return NULL - */ - protected function store() - { - $GLOBALS['KOLAB_SERVER_TEST_DATA'] = $this->data; - } - - /** - * Cleans the current state of the database. - * - * @return NULL - */ - public function clean() - { - $this->unbind(); - - $GLOBALS['KOLAB_SERVER_TEST_DATA'] = array(); - - $this->data = array(); - } - - /** - * Binds the LDAP connection with a specific user and pass. - * - * @param string $dn DN to bind with - * @param string $pw Password associated to this DN. - * - * @return boolean Whether or not the binding succeeded. - * - * @throws Horde_Kolab_Server_Exception If the user does not exit, he has no - * password, provided an incorrect - * password or anonymous binding is not - * allowed. - */ - protected function bind($dn = false, $pw = '') - { - if (!$dn) { - if (isset($this->params['uid'])) { - $dn = $this->params['uid']; - } else { - $dn = ''; - } - } - if (!$pw) { - if (isset($this->params['pass'])) { - $pw = $this->params['pass']; - } - } - - if (!empty($dn)) { - if (!isset($this->data[$dn])) { - throw new Horde_Kolab_Server_Exception('User does not exist!'); - } - - $this->bound = true; - - try { - $data = $this->read($dn, array('userPassword')); - } catch (Horde_Kolab_Server_Exception $e) { - $this->bound = false; - throw $e; - } - if (!isset($data['userPassword'])) { - $this->bound = false; - throw new Horde_Kolab_Server_Exception('User has no password entry!'); - } - $this->bound = $data['userPassword'][0] == $pw; - if (!$this->bound) { - throw new Horde_Kolab_Server_Exception('Incorrect password!'); - } - } else if (!empty($this->params['no_anonymous_bind'])) { - $this->bound = false; - throw new Horde_Kolab_Server_Exception('Anonymous bind is not allowed!'); - } else { - $this->bound = true; - } - return $this->bound; - } - - /** - * Disconnect from LDAP. - * - * @return NULL - */ - public function unbind() - { - $this->bound = false; - } - - /** - * Parse LDAP filter. - * Partially derived from Net_LDAP_Filter. - * - * @param string $filter The filter string. - * - * @return array An array of the parsed filter. - * - * @throws Horde_Kolab_Server_Exception If parsing the filter expression - * fails. - */ - public function parse($filter) - { - $result = array(); - if (preg_match('/^\((.+?)\)$/', $filter, $matches)) { - if (in_array(substr($matches[1], 0, 1), array('!', '|', '&'))) { - $result['op'] = substr($matches[1], 0, 1); - $result['sub'] = $this->parseSub(substr($matches[1], 1)); - return $result; - } else { - if (stristr($matches[1], ')(')) { - throw new Horde_Kolab_Server_Exception('Filter parsing error: invalid filter syntax - multiple leaf components detected!'); - } else { - $filter_parts = preg_split('/(?|<|>=|<=)/', - $matches[1], 2, - PREG_SPLIT_DELIM_CAPTURE); - if (count($filter_parts) != 3) { - throw new Horde_Kolab_Server_Exception('Filter parsing error: invalid filter syntax - unknown matching rule used'); - } else { - $result['att'] = $filter_parts[0]; - $result['log'] = $filter_parts[1]; - $result['val'] = $filter_parts[2]; - return $result; - } - } - } - } else { - throw new Horde_Kolab_Server_Exception(sprintf("Filter parsing error: %s - filter components must be enclosed in round brackets", - $filter)); - } - } - - /** - * Parse a LDAP subfilter. - * - * @param string $filter The subfilter string. - * - * @return array An array of the parsed subfilter. - * - * @throws Horde_Kolab_Server_Exception - */ - public function parseSub($filter) - { - $result = array(); - $level = 0; - $collect = ''; - while (preg_match('/^(\(.+?\))(.*)/', $filter, $matches)) { - if (in_array(substr($matches[1], 0, 2), array('(!', '(|', '(&'))) { - $level++; - } - if ($level) { - $collect .= $matches[1]; - if (substr($matches[2], 0, 1) == ')') { - $collect .= ')'; - $matches[2] = substr($matches[2], 1); - $level--; - if (!$level) { - $result[] = $this->parse($collect); - } - } - } else { - $result[] = $this->parse($matches[1]); - } - $filter = $matches[2]; - } - return $result; - } - - /** - * Search for object data. - * - * @param string $filter The LDAP search filter. - * @param string $params Additional search parameters. - * @param string $base The search base - * - * @return array The result array. - * - * @throws Horde_Kolab_Server_Exception If the search operation encountered - * a problem. - */ - public function search($filter = null, $params = array(), $base = null) - { - if (!$this->bound) { - $result = $this->bind(); - } - - $filter = $this->parse($filter); - if (isset($params['attributes'])) { - $attributes = $params['attributes']; - if (!is_array($attributes)) { - $attributes = array($attributes); - } - } else { - $attributes = array(); - } - $result = $this->doSearch($filter, $attributes); - if (empty($result)) { - return null; - } - if ($base) { - $subtree = array(); - foreach ($result as $entry) { - if (strpos($entry['dn'], $base)) { - $subtree[] = $entry; - } - } - $result = $subtree; - } - return $this->getEntries($result); - } - - /** - * Perform the search. - * - * @param array $filter Filter criteria- - * @param array $attributes Restrict the search result to - * these attributes. - * - * @return array A LDAP serach result. - * - * @throws Horde_Kolab_Server_Exception If the search operation is not - * available. - */ - protected function doSearch($filter, $attributes = null) - { - if (isset($filter['log'])) { - $result = array(); - foreach ($this->data as $element) { - if (isset($element['data'][$filter['att']])) { - switch ($filter['log']) { - case '=': - $value = $element['data'][$filter['att']]; - if (($filter['val'] == '*' && !empty($value)) - || $value == $filter['val'] - || (is_array($value) - && in_array($filter['val'], $value))) { - if (empty($attributes)) { - $result[] = $element; - } else { - $selection = $element; - foreach ($element['data'] as $attr => $value) { - if (!in_array($attr, $attributes)) { - unset($selection['data'][$attr]); - } - } - $result[] = $selection; - } - } - break; - default: - throw new Horde_Kolab_Server_Exception(_("Not implemented!")); - } - } - } - return $result; - } else { - $subresult = array(); - $filtercount = count($filter['sub']); - foreach ($filter['sub'] as $subfilter) { - $subresult = array_merge($subresult, - $this->doSearch($subfilter, - $attributes)); - } - $result = array(); - $dns = array(); - foreach ($subresult as $element) { - $dns[] = $element['dn']; - - $result[$element['dn']] = $element; - } - switch ($filter['op']) { - case '&': - $count = array_count_values($dns); - $selection = array(); - foreach ($count as $dn => $value) { - if ($value == $filtercount) { - $selection[] = $result[$dn]; - } - } - return $selection; - case '|': - return array_values($result); - case '!': - $dns = array(); - foreach ($result as $entry) { - if (!in_array($entry['dn'], $dns) ) { - $dns[] = $entry['dn']; - } - } - $all_dns = array_keys($this->data); - $diff = array_diff($all_dns, $dns); - - $result = array(); - foreach ($diff as $dn) { - if (empty($attributes)) { - $result[] = $this->data[$dn]; - } else { - $selection = $this->data[$dn]; - foreach ($this->data[$dn]['data'] - as $attr => $value) { - if (!in_array($attr, $attributes)) { - unset($selection['data'][$attr]); - } - } - $result[] = $selection; - } - } - return $result; - default: - throw new Horde_Kolab_Server_Exception(_("Not implemented!")); - } - } - } - - /** - * Read object data. - * - * @param string $dn The object to retrieve. - * @param string $attrs Restrict to these attributes - * - * @return array An array of attributes. - * - * @throws Horde_Kolab_Server_Exception If the object does not exist. - */ - public function read($dn, $attrs = null) - { - if (!$this->bound) { - $result = $this->bind(); - } - - if (!isset($this->data[$dn])) { - throw new Horde_Kolab_Server_MissingObjectException(sprintf("No such object: %s", - $dn)); - } - if (empty($attrs)) { - return $this->data[$dn]['data']; - } else { - $result = array(); - $data = $this->data[$dn]['data']; - - foreach ($attrs as $attr) { - if (isset($data[$attr])) { - $result[$attr] = $data[$attr]; - array_push($result, $attr); - } - } - return $result; - } - } - - /** - * Add a new object - * - * @param string $dn The DN of the object to be added. - * @param array $data The attributes of the object to be added. - * - * @return boolean True if adding succeeded. - */ - public function save($dn, $data) - { - if (!$this->bound) { - $result = $this->bind(); - } - - $ldap_data = array(); - foreach ($data as $key => $val) { - if (!is_array($val)) { - $val = array($val); - } - $ldap_data[$key] = $val; - } - - $this->data[$dn] = array( - 'dn' => $dn, - 'data' => $ldap_data - ); - $this->store(); - } - - /** - * Return the attributes of an entry. - * - * @param array $entry The LDAP entry. - * - * @return array The attributes of the entry. - */ - protected function getAttributes($entry) - { - if (is_array($entry)) { - return $entry; - } - return false; - } - - /** - * Return the current entry of a result. - * - * @return mixe The current entry of the result or false. - */ - protected function fetchEntry() - { - if (is_array($this->_current_result) - && $this->_current_index < count($this->_current_result)) { - - $data = array_keys($this->_current_result[$this->_current_index]['data']); - - $data['dn'] = array($this->_current_result[$this->_current_index]['dn']); - - foreach ($this->_current_result[$this->_current_index]['data'] - as $attr => $value) { - if (!is_array($value)) { - $value = array($value); - } - $data[$attr] = $value; - } - $this->_current_index++; - return $data; - } - return false; - } - - /** - * Return the first entry of a result. - * - * @param array $result The LDAP search result. - * - * @return mixed The first entry of the result or false. - */ - protected function firstEntry($result) - { - $this->_current_result = $result; - $this->_current_index = 0; - return $this->fetchEntry(); - } - - /** - * Return the next entry of a result. - * - * @param resource $entry The current LDAP entry. - * - * @return resource The next entry of the result. - */ - protected function nextEntry($entry) - { - return $this->fetchEntry(); - } - - /** - * Return the entries of a result. - * - * @param array $result The LDAP search result. - * - * @return mixed The entries of the result or false. - */ - protected function getEntries($result) - { - if (is_array($result)) { - $data = array(); - foreach ($result as $entry) { - $t = $entry['data']; - $t['dn'] = $entry['dn']; - $data[] = $t; - } - return $data; - } - return false; - } - - /** - * Sort the entries of a result. - * - * @param resource &$result The LDAP search result. - * @param string $attribute The attribute used for sorting. - * - * @return boolean True if sorting succeeded. - */ - public function sort(&$result, $attribute) - { - if (empty($result)) { - return $result; - } - - $this->_sort_by = $attribute; - usort($result, array($this, 'resultSort')); - return false; - } - - /** - * Sort two entries. - * - * @param array $a First entry. - * @param array $b Second entry. - * - * @return int Comparison result. - */ - protected function resultSort($a, $b) - { - $x = isset($a['data'][$this->_sort_by][0])?$a['data'][$this->_sort_by][0]:''; - $y = isset($b['data'][$this->_sort_by][0])?$b['data'][$this->_sort_by][0]:''; - return strcasecmp($x, $y); - } - - - /** - * Return the current LDAP error number. - * - * @return int The current LDAP error number. - */ - protected function errno() - { - return $this->_errno; - } - - /** - * Return the current LDAP error description. - * - * @return string The current LDAP error description. - */ - protected function error() - { - return $this->_error; - } - - /** - * Identify the DN of the first result entry. - * - * @todo Check if this could be reintegrated with the code in the LDAP handler - * again. - * - * @param array $result The LDAP search result. - * @param int $restrict A Horde_Kolab_Server::RESULT_* result restriction. - * - * @return boolean|string|array The DN(s) or false if there was no result. - * - * @throws Horde_Kolab_Server_Exception If the number of results did not - * meet the expectations. - */ - protected function dnFromResult($result, - $restrict = Horde_Kolab_Server::RESULT_SINGLE) - { - if (empty($result)) { - return false; - } - $dns = array(); - foreach ($result as $entry) { - $dns[] = $entry['dn']; - } - - switch ($restrict) { - case self::RESULT_STRICT: - if (count($dns) > 1) { - throw new Horde_Kolab_Server_Exception(sprintf(_("Found %s results when expecting only one!"), - $count)); - } - case self::RESULT_SINGLE: - return $dns[0]; - case self::RESULT_MANY: - return $dns; - } - } - -} diff --git a/framework/Kolab_Server/package.xml b/framework/Kolab_Server/package.xml index aae96b098..cfb2ba4ca 100644 --- a/framework/Kolab_Server/package.xml +++ b/framework/Kolab_Server/package.xml @@ -49,11 +49,11 @@ http://pear.php.net/dtd/package-2.0.xsd"> - - + + - + @@ -84,10 +84,10 @@ http://pear.php.net/dtd/package-2.0.xsd"> - + - + @@ -132,10 +132,10 @@ http://pear.php.net/dtd/package-2.0.xsd"> - - + + - + diff --git a/framework/Kolab_Server/test/Horde/Kolab/Server/LdapTest.php b/framework/Kolab_Server/test/Horde/Kolab/Server/LdapTest.php new file mode 100644 index 000000000..086e3b1ba --- /dev/null +++ b/framework/Kolab_Server/test/Horde/Kolab/Server/LdapTest.php @@ -0,0 +1,229 @@ + + * @license http://www.fsf.org/copyleft/lgpl.html LGPL + * @link http://pear.horde.org/index.php?package=Kolab_Server + */ + +/** + * The Autoloader allows us to omit "require/include" statements. + */ +require_once 'Horde/Autoloader.php'; + +/** + * Test the LDAP backend. + * + * Copyright 2008-2009 The Horde Project (http://www.horde.org/) + * + * See the enclosed file COPYING for license information (LGPL). If you + * did not receive this file, see http://www.fsf.org/copyleft/lgpl.html. + * + * @category Kolab + * @package Kolab_Server + * @author Gunnar Wrobel + * @license http://www.fsf.org/copyleft/lgpl.html LGPL + * @link http://pear.horde.org/index.php?package=Kolab_Server + */ +class Horde_Kolab_Server_ldapTest extends PHPUnit_Framework_TestCase +{ + + /** + * Test handling of object classes. + * + * @return NULL + */ + public function testGetObjectClasses() + { +/* $ldap = $this->getMock('Horde_Kolab_Server_ldap', array('read')); */ +/* $ldap->expects($this->any()) */ +/* ->method('read') */ +/* ->will($this->returnValue(array ( */ +/* 'objectClass' => */ +/* array ( */ +/* 'count' => 4, */ +/* 0 => 'top', */ +/* 1 => 'inetOrgPerson', */ +/* 2 => 'kolabInetOrgPerson', */ +/* 3 => 'hordePerson', */ +/* ), */ +/* 0 => 'objectClass', */ +/* 'count' => 1))); */ + +/* $classes = $ldap->getObjectClasses('cn=Gunnar Wrobel,dc=example,dc=org'); */ +/* if ($classes instanceOf PEAR_Error) { */ +/* $this->assertEquals('', $classes->getMessage()); */ +/* } */ +/* $this->assertContains('top', $classes); */ +/* $this->assertContains('kolabinetorgperson', $classes); */ +/* $this->assertContains('hordeperson', $classes); */ + +/* $ldap = $this->getMock('Horde_Kolab_Server_ldap', array('read')); */ +/* $ldap->expects($this->any()) */ +/* ->method('read') */ +/* ->will($this->returnValue(PEAR::raiseError('LDAP Error: No such object: cn=DOES NOT EXIST,dc=example,dc=org: No such object'))); */ + +/* $classes = $ldap->getObjectClasses('cn=DOES NOT EXIST,dc=example,dc=org'); */ +/* $this->assertEquals('LDAP Error: No such object: cn=DOES NOT EXIST,dc=example,dc=org: No such object', */ +/* $classes->message); */ + } + + /** + * Test retrieving a primary mail for a mail or uid. + * + * @return NULL + */ +/* public function testMailForUidOrMail() */ +/* { */ +/* $ldap = $this->getMock('Horde_Kolab_Server_ldap', array('getAttributes', */ +/* 'search', 'count', */ +/* 'firstEntry')); */ +/* $ldap->expects($this->any()) */ +/* ->method('_getAttributes') */ +/* ->will($this->returnValue(array ( */ +/* 'mail' => */ +/* array ( */ +/* 'count' => 1, */ +/* 0 => 'wrobel@example.org', */ +/* ), */ +/* 0 => 'mail', */ +/* 'count' => 1))); */ +/* $ldap->expects($this->any()) */ +/* ->method('_search') */ +/* ->will($this->returnValue('cn=Gunnar Wrobel,dc=example,dc=org')); */ +/* $ldap->expects($this->any()) */ +/* ->method('_count') */ +/* ->will($this->returnValue(1)); */ +/* $ldap->expects($this->any()) */ +/* ->method('_firstEntry') */ +/* ->will($this->returnValue(1)); */ + +/* $mail = $ldap->mailForIdOrMail('wrobel'); */ +/* $this->assertEquals('wrobel@example.org', $mail); */ + +/* $ldap = $this->getMock('Horde_Kolab_Server_ldap', array('_getAttributes', */ +/* '_search', */ +/* '_count', */ +/* '_firstEntry', */ +/* '_errno', */ +/* '_error')); */ +/* $ldap->expects($this->any()) */ +/* ->method('_getAttributes') */ +/* ->will($this->returnValue(false)); */ +/* $ldap->expects($this->any()) */ +/* ->method('_search') */ +/* ->will($this->returnValue('cn=Gunnar Wrobel,dc=example,dc=org')); */ +/* $ldap->expects($this->any()) */ +/* ->method('_count') */ +/* ->will($this->returnValue(1)); */ +/* $ldap->expects($this->any()) */ +/* ->method('_firstEntry') */ +/* ->will($this->returnValue(1)); */ +/* $ldap->expects($this->any()) */ +/* ->method('_errno') */ +/* ->will($this->returnValue(1)); */ +/* $ldap->expects($this->any()) */ +/* ->method('_error') */ +/* ->will($this->returnValue('cn=DOES NOT EXIST,dc=example,dc=org: No such object')); */ + +/* $mail = $ldap->mailForIdOrMail('wrobel'); */ +/* $this->assertEquals('Retrieving attributes failed. Error was: cn=DOES NOT EXIST,dc=example,dc=org: No such object', */ +/* $mail->message); */ + +/* $ldap = $this->getMock('Horde_Kolab_Server_ldap', array('_getAttributes', */ +/* '_search', */ +/* '_count')); */ +/* $ldap->expects($this->any()) */ +/* ->method('_getAttributes') */ +/* ->will($this->returnValue(false)); */ +/* $ldap->expects($this->any()) */ +/* ->method('_search') */ +/* ->will($this->returnValue('cn=Gunnar Wrobel,dc=example,dc=org')); */ +/* $ldap->expects($this->any()) */ +/* ->method('_count') */ +/* ->will($this->returnValue(4)); */ + +/* $mail = $ldap->mailForIdOrMail('wrobel'); */ +/* $this->assertEquals('Found 4 results when expecting only one!', */ +/* $mail->message); */ +/* } */ + +/* /\** */ +/* * Test retrieving a DN for a mail or uid. */ +/* * */ +/* * @return NULL */ +/* *\/ */ +/* public function testDnForUidOrMail() */ +/* { */ +/* $ldap = $this->getMock('Horde_Kolab_Server_ldap', array('_getDn', */ +/* '_search', '_count', */ +/* '_firstEntry')); */ +/* $ldap->expects($this->any()) */ +/* ->method('_getDn') */ +/* ->will($this->returnValue('cn=Gunnar Wrobel,dc=example,dc=org')); */ +/* $ldap->expects($this->any()) */ +/* ->method('_search') */ +/* ->will($this->returnValue('cn=Gunnar Wrobel,dc=example,dc=org')); */ +/* $ldap->expects($this->any()) */ +/* ->method('_count') */ +/* ->will($this->returnValue(1)); */ +/* $ldap->expects($this->any()) */ +/* ->method('_firstEntry') */ +/* ->will($this->returnValue(1)); */ + +/* $dn = $ldap->uidForIdOrMail('wrobel'); */ +/* $this->assertEquals('cn=Gunnar Wrobel,dc=example,dc=org', $dn); */ + +/* $ldap = $this->getMock('Horde_Kolab_Server_ldap', array('_getDn', */ +/* '_search', */ +/* '_count', */ +/* '_firstEntry', */ +/* '_errno', */ +/* '_error')); */ +/* $ldap->expects($this->any()) */ +/* ->method('_getDn') */ +/* ->will($this->returnValue(false)); */ +/* $ldap->expects($this->any()) */ +/* ->method('_search') */ +/* ->will($this->returnValue('cn=Gunnar Wrobel,dc=example,dc=org')); */ +/* $ldap->expects($this->any()) */ +/* ->method('_count') */ +/* ->will($this->returnValue(1)); */ +/* $ldap->expects($this->any()) */ +/* ->method('_firstEntry') */ +/* ->will($this->returnValue(1)); */ +/* $ldap->expects($this->any()) */ +/* ->method('_errno') */ +/* ->will($this->returnValue(1)); */ +/* $ldap->expects($this->any()) */ +/* ->method('_error') */ +/* ->will($this->returnValue('cn=DOES NOT EXIST,dc=example,dc=org: No such object')); */ + +/* $dn = $ldap->uidForIdOrMail('wrobel'); */ +/* $this->assertEquals('Retrieving DN failed. Error was: cn=DOES NOT EXIST,dc=example,dc=org: No such object', */ +/* $dn->message); */ + +/* $ldap = $this->getMock('Horde_Kolab_Server_ldap', array('_getDn', */ +/* '_search', */ +/* '_count')); */ +/* $ldap->expects($this->any()) */ +/* ->method('_getDn') */ +/* ->will($this->returnValue(false)); */ +/* $ldap->expects($this->any()) */ +/* ->method('_search') */ +/* ->will($this->returnValue('cn=Gunnar Wrobel,dc=example,dc=org')); */ +/* $ldap->expects($this->any()) */ +/* ->method('_count') */ +/* ->will($this->returnValue(4)); */ + +/* $dn = $ldap->uidForIdOrMail('wrobel'); */ +/* $this->assertEquals('Found 4 results when expecting only one!', */ +/* $dn->message); */ +/* } */ + +} diff --git a/framework/Kolab_Server/test/Horde/Kolab/Server/ServerTest.php b/framework/Kolab_Server/test/Horde/Kolab/Server/ServerTest.php index 266af3392..6a532d235 100644 --- a/framework/Kolab_Server/test/Horde/Kolab/Server/ServerTest.php +++ b/framework/Kolab_Server/test/Horde/Kolab/Server/ServerTest.php @@ -56,7 +56,7 @@ class Horde_Kolab_Server_ServerTest extends PHPUnit_Framework_TestCase $this->assertFail('No error!'); } catch (Horde_Kolab_Server_Exception $e) { $this->assertEquals($e->getMessage(), - 'Server type definition "Horde_Kolab_Server_dummy" missing.'); + 'Server type definition "Horde_Kolab_Server_Dummy" missing.'); } } @@ -110,7 +110,7 @@ class Horde_Kolab_Server_ServerTest extends PHPUnit_Framework_TestCase * @license http://www.fsf.org/copyleft/lgpl.html LGPL * @link http://pear.horde.org/index.php?package=Kolab_Server */ -class Horde_Kolab_Server_none extends Horde_Kolab_Server +class Horde_Kolab_Server_None extends Horde_Kolab_Server { /** * Stub for reading object data. diff --git a/framework/Kolab_Server/test/Horde/Kolab/Server/TestTest.php b/framework/Kolab_Server/test/Horde/Kolab/Server/TestTest.php new file mode 100644 index 000000000..f28321f98 --- /dev/null +++ b/framework/Kolab_Server/test/Horde/Kolab/Server/TestTest.php @@ -0,0 +1,656 @@ + + * @license http://www.fsf.org/copyleft/lgpl.html LGPL + * @link http://pear.horde.org/index.php?package=Kolab_Server + */ + +/** + * The Autoloader allows us to omit "require/include" statements. + */ +require_once 'Horde/Autoloader.php'; + +/** + * Test the test backend. + * + * Copyright 2008-2009 The Horde Project (http://www.horde.org/) + * + * See the enclosed file COPYING for license information (LGPL). If you + * did not receive this file, see http://www.fsf.org/copyleft/lgpl.html. + * + * @category Kolab + * @package Kolab_Server + * @author Gunnar Wrobel + * @license http://www.fsf.org/copyleft/lgpl.html LGPL + * @link http://pear.horde.org/index.php?package=Kolab_Server + */ +class Horde_Kolab_Server_testTest extends Horde_Kolab_Test_Server +{ + + /** + * Test search base. + * + * @dataProvider provideServerTypes + * + * @return NULL + */ + public function testSearchBase($type) + { + $server = &$this->prepareBasicServer($type); + + $result = $server->search('(objectClass=top)', array('objectClass')); + $this->assertEquals(13, count($result)); + + $result = $server->search('(objectClass=top)', + array('objectClass'), + 'cn=internal,dc=example,dc=org'); + $this->assertNoError($result); + $this->assertEquals(4, count($result)); + } + + /** + * Test sorting. + * + * @dataProvider provideServerTypes + * + * @return NULL + */ + public function testSorting($type) + { + $server = &$this->prepareBasicServer($type); + +/* $result = $server->search('(mail=*)', array('mail')); */ +/* $this->assertNoError($result); */ +/* $this->assertEquals(5, count($result)); */ +/* $server->sort($result, 'mail'); */ +/* foreach ($result as $object) { */ +/* if (isset($object['data']['dn'])) { */ +/* switch ($object['data']['dn']) { */ +/* case 'cn=Test Address,cn=external,dc=example,dc=org': */ +/* $this->assertContains('address@example.org', $object['data']['mail']); */ +/* break; */ +/* case '': */ +/* $this->assertContains('address@example.org', $object['data']['mail']); */ +/* break; */ +/* } */ +/* } */ +/* } */ + } + + /** + * Test listing objects. + * + * @dataProvider provideServerTypes + * + * @return NULL + */ + public function testListObjects($type) + { + $server = &$this->prepareBasicServer($type); + + $filter = '(&(objectClass=kolabInetOrgPerson)(uid=*)(mail=*)(sn=*))'; + $attributes = array( + Horde_Kolab_Server_Object_base::ATTRIBUTE_SN, + Horde_Kolab_Server_Object_base::ATTRIBUTE_CN, + Horde_Kolab_Server_Object::ATTRIBUTE_UID, + Horde_Kolab_Server_Object_base::ATTRIBUTE_MAIL, + Horde_Kolab_Server_Object_base::ATTRIBUTE_DELETED, + ); + + $sort = Horde_Kolab_Server_Object_base::ATTRIBUTE_SN; + $result = $server->search($filter); + $this->assertNoError($result); + $this->assertEquals(2, count($result)); + + $result = $server->listObjects('Horde_Kolab_Server_Object_user'); + $this->assertNoError($result); + $this->assertEquals(2, count($result)); + $this->assertEquals('Horde_Kolab_Server_Object_user', get_class(array_shift($result))); + + $result = $server->listObjects('Horde_Kolab_Server_Object_sharedfolder'); + $this->assertNoError($result); + $this->assertEquals(1, count($result)); + $this->assertEquals('Horde_Kolab_Server_Object_sharedfolder', get_class(array_shift($result))); + } + + /** + * Test handling of object classes. + * + * @dataProvider provideServerTypes + * + * @return NULL + */ + public function testGetObjectClasses($type) + { + $server = &$this->prepareBasicServer($type); + + $classes = $server->getObjectClasses('cn=Gunnar Wrobel,dc=example,dc=org'); + $this->assertNoError($classes); + $this->assertContains('top', $classes); + $this->assertContains('kolabinetorgperson', $classes); + $this->assertContains('hordeperson', $classes); + + try { + $classes = $server->getObjectClasses('cn=DOES NOT EXIST,dc=example,dc=org'); + } catch (Horde_Kolab_Server_Exception $classes) { + } + $this->assertError($classes, + 'No such object: cn=DOES NOT EXIST,dc=example,dc=org'); + + $classes = $server->getObjectClasses('cn=The Administrator,dc=example,dc=org'); + $this->assertNoError($classes); + $this->assertContains('kolabinetorgperson', $classes); + } + + /** + * Test handling of object types. + * + * @dataProvider provideServerTypes + * + * @return NULL + */ + public function testDetermineType($type) + { + $server = &$this->prepareBasicServer($type); + + $type = $server->determineType('cn=empty.group@example.org,dc=example,dc=org'); + $this->assertNoError($type); + $this->assertEquals('Horde_Kolab_Server_Object_group', $type); + + $type = $server->determineType('cn=shared@example.org,dc=example,dc=org'); + $this->assertNoError($type); + $this->assertEquals('Horde_Kolab_Server_Object_sharedfolder', $type); + + $type = $server->determineType('cn=The Administrator,dc=example,dc=org'); + $this->assertNoError($type); + $this->assertEquals('Horde_Kolab_Server_Object_administrator', $type); + + $type = $server->determineType('cn=Main Tainer,dc=example,dc=org'); + $this->assertNoError($type); + $this->assertEquals('Horde_Kolab_Server_Object_maintainer', $type); + + $type = $server->determineType('cn=Domain Maintainer,dc=example,dc=org'); + $this->assertNoError($type); + $this->assertEquals('Horde_Kolab_Server_Object_domainmaintainer', $type); + + $type = $server->determineType('cn=Test Address,cn=external,dc=example,dc=org'); + $this->assertNoError($type); + $this->assertEquals('Horde_Kolab_Server_Object_address', $type); + + $type = $server->determineType('cn=Gunnar Wrobel,dc=example,dc=org'); + $this->assertNoError($type); + $this->assertEquals('Horde_Kolab_Server_Object_user', $type); + } + + /** + * Test retrieving a primary mail for a mail or id. + * + * @dataProvider provideServerTypes + * + * @return NULL + */ + public function testMailForIdOrMail($type) + { + $server = &$this->prepareBasicServer($type); + + $mail = $server->mailForIdOrMail('wrobel'); + $this->assertEquals('wrobel@example.org', $mail); + + $mail = $server->mailForIdOrMail('wrobel@example.org'); + $this->assertNoError($mail); + $this->assertEquals('wrobel@example.org', $mail); + + $mail = $server->mailForIdOrMail('DOES NOT EXIST'); + $this->assertNoError($mail); + $this->assertSame(false, $mail); + } + + /** + * Test retrieving a UID for a mail or id. + * + * @dataProvider provideServerTypes + * + * @return NULL + */ + public function testUidForIdOrMail($type) + { + $server = &$this->prepareBasicServer($type); + + $uid = $server->uidForIdOrMail('wrobel'); + $this->assertNoError($uid); + $this->assertEquals('cn=Gunnar Wrobel,dc=example,dc=org', $uid); + + $uid = $server->uidForIdOrMail('wrobel@example.org'); + $this->assertNoError($uid); + $this->assertEquals('cn=Gunnar Wrobel,dc=example,dc=org', $uid); + + $uid = $server->uidForIdOrMail('DOES NOT EXIST'); + $this->assertNoError($uid); + $this->assertSame(false, $uid); + } + + /** + * Test retrieving a UID for a mail or id. + * + * @dataProvider provideServerTypes + * + * @return NULL + */ + public function testUidForMailOrIdOrAlias($type) + { + $server = &$this->prepareBasicServer($type); + + $uid = $server->uidForIdOrMailOrAlias('g.wrobel@example.org'); + $this->assertNoError($uid); + $this->assertEquals('cn=Gunnar Wrobel,dc=example,dc=org', $uid); + + $uid = $server->uidForIdOrMailOrAlias('wrobel@example.org'); + $this->assertNoError($uid); + $this->assertEquals('cn=Gunnar Wrobel,dc=example,dc=org', $uid); + + $uid = $server->uidForIdOrMailOrAlias('wrobel'); + $this->assertNoError($uid); + $this->assertEquals('cn=Gunnar Wrobel,dc=example,dc=org', $uid); + + $uid = $server->uidForIdOrMailOrAlias('DOES NOT EXIST'); + $this->assertNoError($uid); + $this->assertSame(false, $uid); + } + + /** + * Test retrieving all addresses for a mail or id. + * + * @dataProvider provideServerTypes + * + * @return NULL + */ + public function testAddrsForIdOrMail($type) + { + $server = &$this->prepareBasicServer($type); + + $addrs = $server->addrsForIdOrMail('wrobel'); + + $testuser = $server->fetch('cn=Test Test,dc=example,dc=org'); + $this->assertNoError($testuser); + $this->assertContains('wrobel@example.org', + $testuser->get(Horde_Kolab_Server_Object_base::ATTRIBUTE_DELEGATE, false)); + + $this->assertNoError($addrs); + $this->assertContains('wrobel@example.org', $addrs); + $this->assertContains('test@example.org', $addrs); + $this->assertContains('t.test@example.org', $addrs); + $this->assertContains('g.wrobel@example.org', $addrs); + $this->assertContains('gunnar@example.org', $addrs); + + $addrs = $server->addrsForIdOrMail('test@example.org'); + $this->assertNoError($addrs); + $this->assertContains('test@example.org', $addrs); + $this->assertContains('t.test@example.org', $addrs); + } + + /** + * Test retrieving a UID for a primary mail. + * + * @dataProvider provideServerTypes + * + * @return NULL + */ + public function testUidForMailAddress($type) + { + $server = &$this->prepareBasicServer($type); + + $uid = $server->uidForIdOrMailOrAlias('wrobel@example.org'); + $this->assertNoError($uid); + $this->assertEquals('cn=Gunnar Wrobel,dc=example,dc=org', $uid); + + $uid = $server->uidForIdOrMailOrAlias('test@example.org'); + $this->assertNoError($uid); + $this->assertEquals('cn=Test Test,dc=example,dc=org', $uid); + + $uid = $server->uidForIdOrMailOrAlias('gunnar@example.org'); + $this->assertNoError($uid); + $this->assertEquals('cn=Gunnar Wrobel,dc=example,dc=org', $uid); + + $uid = $server->uidForIdOrMailOrAlias('wrobel'); + $this->assertNoError($uid); + $this->assertEquals('cn=Gunnar Wrobel,dc=example,dc=org', $uid); + } + + /** + * Test retrieving a UID for an attribute. + * + * @dataProvider provideServerTypes + * + * @return NULL + */ + public function testUidForAttr($type) + { + $server = &$this->prepareBasicServer($type); + + $uid = $server->uidForSearch(array('AND' => array(array('field' => 'alias', + 'op' => '=', + 'test' => 'g.wrobel@example.org')))); + $this->assertNoError($uid); + $this->assertEquals('cn=Gunnar Wrobel,dc=example,dc=org', $uid); + } + + /** + * Test group membership testing. + * + * @dataProvider provideServerTypes + * + * @return NULL + */ + public function testMemberOfGroupAddress($type) + { + $server = &$this->prepareBasicServer($type); + + $uid = $server->uidForIdOrMailOrAlias('g.wrobel@example.org'); + $this->assertNoError($uid); + $member = $server->memberOfGroupAddress($uid, 'group@example.org'); + $this->assertNoError($member); + $this->assertTrue($member); + + $member = $server->memberOfGroupAddress( + $server->uidForIdOrMailOrAlias('test@example.org'), + 'group@example.org'); + $this->assertNoError($member); + $this->assertTrue($member); + + $member = $server->memberOfGroupAddress( + $server->uidForIdOrMailOrAlias('somebody@example.org'), + 'group@example.org'); + $this->assertNoError($member); + $this->assertFalse($member); + } + + /** + * Test group fetching. + * + * @dataProvider provideServerTypes + * + * @return NULL + */ + public function testGetGroups($type) + { + $server = &$this->prepareBasicServer($type); + + $filter = '(&(objectClass=kolabGroupOfNames)(member=' + . Horde_LDAP::quote('cn=The Administrator,dc=example,dc=org') . '))'; + $result = $server->search($filter, array()); + $this->assertNoError($result); + $this->assertTrue(!empty($result)); + +/* $entry = $server->_firstEntry($result); */ +/* $this->assertNoError($entry); */ +/* $this->assertTrue(!empty($entry)); */ + +/* $uid = $server->_getDn($entry); */ +/* $this->assertNoError($uid); */ +/* $this->assertTrue(!empty($uid)); */ + +/* $entry = $server->_nextEntry($entry); */ +/* $this->assertNoError($entry); */ +/* $this->assertTrue(empty($entry)); */ + +/* $entries = $server->_getDns($result); */ +/* $this->assertNoError($entries); */ +/* $this->assertTrue(!empty($entries)); */ + + $groups = $server->getGroups('cn=The Administrator,dc=example,dc=org'); + $this->assertNoError($groups); + $this->assertTrue(!empty($groups)); + + $groups = $server->getGroups($server->uidForIdOrMailOrAlias('g.wrobel@example.org')); + $this->assertNoError($groups); + $this->assertContains('cn=group@example.org,dc=example,dc=org', $groups); + + $groups = $server->getGroups($server->uidForIdOrMailOrAlias('test@example.org')); + $this->assertNoError($groups); + $this->assertContains('cn=group@example.org,dc=example,dc=org', $groups); + + $groups = $server->getGroups('nobody'); + $this->assertNoError($groups); + $this->assertTrue(empty($groups)); + + } + + /** + * Test parsing of LDAP filters. + * + * @return NULL + */ + public function testFilterParse() + { + $db = &Horde_Kolab_Server::factory('test', array()); + + $a = $db->parse('(a=b)'); + $this->assertNoError($a); + $this->assertEquals(array('att' => 'a', 'log' => '=', 'val' => 'b'), + $a); + + $a = $db->parse('(&(a=b)(c=d))'); + $this->assertNoError($a); + $this->assertEquals(array('op' => '&', 'sub' => array( + array('att' => 'a', 'log' => '=', 'val' => 'b'), + array('att' => 'c', 'log' => '=', 'val' => 'd'), + )), $a); + + $a = $db->parse('(&(a=1)(|(b=2)(c=3)))'); + $this->assertNoError($a); + $this->assertEquals(array('op' => '&', 'sub' => array( + array('att' => 'a', 'log' => '=', 'val' => '1'), + array('op' => '|', 'sub' => + array( + array('att' => 'b', 'log' => '=', 'val' => '2'), + array('att' => 'c', 'log' => '=', 'val' => '3'), + )))), $a); + + $a = $db->parseSub('(!(x=2))(b=1)'); + $this->assertNoError($a); + $this->assertEquals(array(array('op' => '!', 'sub' => + array( + array('att' => 'x', 'log' => '=', 'val' => '2'), + ) + ), + array('att' => 'b', 'log' => '=', 'val' => '1'), + ), $a); + + $a = $db->parse('(&(!(x=2))(b=1))'); + $this->assertNoError($a); + $this->assertEquals(array('op' => '&', 'sub' => array( + array('op' => '!', 'sub' => + array( + array('att' => 'x', 'log' => '=', 'val' => '2'), + ) + ), + array('att' => 'b', 'log' => '=', 'val' => '1'), + )), $a); + + } + + /** + * Test searching in the simulated LDAP data. + * + * @return NULL + */ + public function testSearch() + { +/* $db = &Horde_Kolab_Server::factory('test', */ +/* array('data' => */ +/* array( */ +/* 'cn=a' => array( */ +/* 'dn' => 'cn=a', */ +/* 'data' => array( */ +/* 'a' => '1', */ +/* 'b' => '1', */ +/* 'c' => '1', */ +/* ) */ +/* ), */ +/* 'cn=b' => array( */ +/* 'dn' => 'cn=b', */ +/* 'data' => array( */ +/* 'a' => '1', */ +/* 'b' => '2', */ +/* 'c' => '2', */ +/* ) */ +/* ), */ +/* 'cn=c' => array( */ +/* 'dn' => 'cn=c', */ +/* 'data' => array( */ +/* 'a' => '1', */ +/* 'b' => '2', */ +/* 'c' => '3', */ +/* ) */ +/* ), */ +/* 'cn=d' => array( */ +/* 'dn' => 'cn=d', */ +/* 'data' => array( */ +/* 'a' => '2', */ +/* 'b' => '2', */ +/* 'c' => '1', */ +/* ) */ +/* ), */ +/* ) */ +/* ) */ +/* ); */ + +/* $a = $db->search('(c=1)'); */ +/* $this->assertNoError($a); */ +/* $this->assertEquals( */ +/* array( */ +/* array( */ +/* 'dn' => 'cn=a', */ +/* 'data' => array( */ +/* 'a' => '1', */ +/* 'b' => '1', */ +/* 'c' => '1', */ +/* ) */ +/* ), */ +/* array( */ +/* 'dn' => 'cn=d', */ +/* 'data' => array( */ +/* 'a' => '2', */ +/* 'b' => '2', */ +/* 'c' => '1', */ +/* ) */ +/* ), */ +/* ), */ +/* $a */ +/* ); */ + +/* $a = $db->_search('(c=3)'); */ +/* $this->assertNoError($a); */ +/* $this->assertEquals( */ +/* array( */ +/* array( */ +/* 'dn' => 'cn=c', */ +/* 'data' => array( */ +/* 'a' => '1', */ +/* 'b' => '2', */ +/* 'c' => '3', */ +/* ) */ +/* ), */ +/* ), */ +/* $a */ +/* ); */ + +/* $a = $db->_search('(c=3)', array('a')); */ +/* $this->assertNoError($a); */ +/* $this->assertEquals( */ +/* array( */ +/* array( */ +/* 'dn' => 'cn=c', */ +/* 'data' => array( */ +/* 'a' => '1', */ +/* ) */ +/* ), */ +/* ), */ +/* $a */ +/* ); */ + +/* $a = $db->_search('(&(a=1)(b=2))', array('a', 'b')); */ +/* $this->assertNoError($a); */ +/* $this->assertEquals( */ +/* array( */ +/* array( */ +/* 'dn' => 'cn=b', */ +/* 'data' => array( */ +/* 'a' => '1', */ +/* 'b' => '2', */ +/* ) */ +/* ), */ +/* array( */ +/* 'dn' => 'cn=c', */ +/* 'data' => array( */ +/* 'a' => '1', */ +/* 'b' => '2', */ +/* ) */ +/* ), */ +/* ), */ +/* $a */ +/* ); */ + +/* $a = $db->_search('(&(b=2))', array('b')); */ +/* $this->assertNoError($a); */ +/* $this->assertEquals( */ +/* array( */ +/* array( */ +/* 'dn' => 'cn=b', */ +/* 'data' => array( */ +/* 'b' => '2', */ +/* ) */ +/* ), */ +/* array( */ +/* 'dn' => 'cn=c', */ +/* 'data' => array( */ +/* 'b' => '2', */ +/* ) */ +/* ), */ +/* array( */ +/* 'dn' => 'cn=d', */ +/* 'data' => array( */ +/* 'b' => '2', */ +/* ) */ +/* ), */ +/* ), */ +/* $a */ +/* ); */ + +/* $a = $db->_search('(!(b=2))', array('a', 'b')); */ +/* $this->assertNoError($a); */ +/* $this->assertEquals( */ +/* array( */ +/* array( */ +/* 'dn' => 'cn=a', */ +/* 'data' => array( */ +/* 'a' => '1', */ +/* 'b' => '1', */ +/* ) */ +/* ), */ +/* ), */ +/* $a */ +/* ); */ + +/* $a = $db->_search('(&(!(x=2))(b=1))', array('b')); */ +/* $this->assertNoError($a); */ +/* $this->assertEquals( */ +/* array( */ +/* array( */ +/* 'dn' => 'cn=a', */ +/* 'data' => array( */ +/* 'b' => '1', */ +/* ) */ +/* ), */ +/* ), */ +/* $a */ +/* ); */ + } + +} diff --git a/framework/Kolab_Server/test/Horde/Kolab/Server/ldapTest.php b/framework/Kolab_Server/test/Horde/Kolab/Server/ldapTest.php deleted file mode 100644 index 086e3b1ba..000000000 --- a/framework/Kolab_Server/test/Horde/Kolab/Server/ldapTest.php +++ /dev/null @@ -1,229 +0,0 @@ - - * @license http://www.fsf.org/copyleft/lgpl.html LGPL - * @link http://pear.horde.org/index.php?package=Kolab_Server - */ - -/** - * The Autoloader allows us to omit "require/include" statements. - */ -require_once 'Horde/Autoloader.php'; - -/** - * Test the LDAP backend. - * - * Copyright 2008-2009 The Horde Project (http://www.horde.org/) - * - * See the enclosed file COPYING for license information (LGPL). If you - * did not receive this file, see http://www.fsf.org/copyleft/lgpl.html. - * - * @category Kolab - * @package Kolab_Server - * @author Gunnar Wrobel - * @license http://www.fsf.org/copyleft/lgpl.html LGPL - * @link http://pear.horde.org/index.php?package=Kolab_Server - */ -class Horde_Kolab_Server_ldapTest extends PHPUnit_Framework_TestCase -{ - - /** - * Test handling of object classes. - * - * @return NULL - */ - public function testGetObjectClasses() - { -/* $ldap = $this->getMock('Horde_Kolab_Server_ldap', array('read')); */ -/* $ldap->expects($this->any()) */ -/* ->method('read') */ -/* ->will($this->returnValue(array ( */ -/* 'objectClass' => */ -/* array ( */ -/* 'count' => 4, */ -/* 0 => 'top', */ -/* 1 => 'inetOrgPerson', */ -/* 2 => 'kolabInetOrgPerson', */ -/* 3 => 'hordePerson', */ -/* ), */ -/* 0 => 'objectClass', */ -/* 'count' => 1))); */ - -/* $classes = $ldap->getObjectClasses('cn=Gunnar Wrobel,dc=example,dc=org'); */ -/* if ($classes instanceOf PEAR_Error) { */ -/* $this->assertEquals('', $classes->getMessage()); */ -/* } */ -/* $this->assertContains('top', $classes); */ -/* $this->assertContains('kolabinetorgperson', $classes); */ -/* $this->assertContains('hordeperson', $classes); */ - -/* $ldap = $this->getMock('Horde_Kolab_Server_ldap', array('read')); */ -/* $ldap->expects($this->any()) */ -/* ->method('read') */ -/* ->will($this->returnValue(PEAR::raiseError('LDAP Error: No such object: cn=DOES NOT EXIST,dc=example,dc=org: No such object'))); */ - -/* $classes = $ldap->getObjectClasses('cn=DOES NOT EXIST,dc=example,dc=org'); */ -/* $this->assertEquals('LDAP Error: No such object: cn=DOES NOT EXIST,dc=example,dc=org: No such object', */ -/* $classes->message); */ - } - - /** - * Test retrieving a primary mail for a mail or uid. - * - * @return NULL - */ -/* public function testMailForUidOrMail() */ -/* { */ -/* $ldap = $this->getMock('Horde_Kolab_Server_ldap', array('getAttributes', */ -/* 'search', 'count', */ -/* 'firstEntry')); */ -/* $ldap->expects($this->any()) */ -/* ->method('_getAttributes') */ -/* ->will($this->returnValue(array ( */ -/* 'mail' => */ -/* array ( */ -/* 'count' => 1, */ -/* 0 => 'wrobel@example.org', */ -/* ), */ -/* 0 => 'mail', */ -/* 'count' => 1))); */ -/* $ldap->expects($this->any()) */ -/* ->method('_search') */ -/* ->will($this->returnValue('cn=Gunnar Wrobel,dc=example,dc=org')); */ -/* $ldap->expects($this->any()) */ -/* ->method('_count') */ -/* ->will($this->returnValue(1)); */ -/* $ldap->expects($this->any()) */ -/* ->method('_firstEntry') */ -/* ->will($this->returnValue(1)); */ - -/* $mail = $ldap->mailForIdOrMail('wrobel'); */ -/* $this->assertEquals('wrobel@example.org', $mail); */ - -/* $ldap = $this->getMock('Horde_Kolab_Server_ldap', array('_getAttributes', */ -/* '_search', */ -/* '_count', */ -/* '_firstEntry', */ -/* '_errno', */ -/* '_error')); */ -/* $ldap->expects($this->any()) */ -/* ->method('_getAttributes') */ -/* ->will($this->returnValue(false)); */ -/* $ldap->expects($this->any()) */ -/* ->method('_search') */ -/* ->will($this->returnValue('cn=Gunnar Wrobel,dc=example,dc=org')); */ -/* $ldap->expects($this->any()) */ -/* ->method('_count') */ -/* ->will($this->returnValue(1)); */ -/* $ldap->expects($this->any()) */ -/* ->method('_firstEntry') */ -/* ->will($this->returnValue(1)); */ -/* $ldap->expects($this->any()) */ -/* ->method('_errno') */ -/* ->will($this->returnValue(1)); */ -/* $ldap->expects($this->any()) */ -/* ->method('_error') */ -/* ->will($this->returnValue('cn=DOES NOT EXIST,dc=example,dc=org: No such object')); */ - -/* $mail = $ldap->mailForIdOrMail('wrobel'); */ -/* $this->assertEquals('Retrieving attributes failed. Error was: cn=DOES NOT EXIST,dc=example,dc=org: No such object', */ -/* $mail->message); */ - -/* $ldap = $this->getMock('Horde_Kolab_Server_ldap', array('_getAttributes', */ -/* '_search', */ -/* '_count')); */ -/* $ldap->expects($this->any()) */ -/* ->method('_getAttributes') */ -/* ->will($this->returnValue(false)); */ -/* $ldap->expects($this->any()) */ -/* ->method('_search') */ -/* ->will($this->returnValue('cn=Gunnar Wrobel,dc=example,dc=org')); */ -/* $ldap->expects($this->any()) */ -/* ->method('_count') */ -/* ->will($this->returnValue(4)); */ - -/* $mail = $ldap->mailForIdOrMail('wrobel'); */ -/* $this->assertEquals('Found 4 results when expecting only one!', */ -/* $mail->message); */ -/* } */ - -/* /\** */ -/* * Test retrieving a DN for a mail or uid. */ -/* * */ -/* * @return NULL */ -/* *\/ */ -/* public function testDnForUidOrMail() */ -/* { */ -/* $ldap = $this->getMock('Horde_Kolab_Server_ldap', array('_getDn', */ -/* '_search', '_count', */ -/* '_firstEntry')); */ -/* $ldap->expects($this->any()) */ -/* ->method('_getDn') */ -/* ->will($this->returnValue('cn=Gunnar Wrobel,dc=example,dc=org')); */ -/* $ldap->expects($this->any()) */ -/* ->method('_search') */ -/* ->will($this->returnValue('cn=Gunnar Wrobel,dc=example,dc=org')); */ -/* $ldap->expects($this->any()) */ -/* ->method('_count') */ -/* ->will($this->returnValue(1)); */ -/* $ldap->expects($this->any()) */ -/* ->method('_firstEntry') */ -/* ->will($this->returnValue(1)); */ - -/* $dn = $ldap->uidForIdOrMail('wrobel'); */ -/* $this->assertEquals('cn=Gunnar Wrobel,dc=example,dc=org', $dn); */ - -/* $ldap = $this->getMock('Horde_Kolab_Server_ldap', array('_getDn', */ -/* '_search', */ -/* '_count', */ -/* '_firstEntry', */ -/* '_errno', */ -/* '_error')); */ -/* $ldap->expects($this->any()) */ -/* ->method('_getDn') */ -/* ->will($this->returnValue(false)); */ -/* $ldap->expects($this->any()) */ -/* ->method('_search') */ -/* ->will($this->returnValue('cn=Gunnar Wrobel,dc=example,dc=org')); */ -/* $ldap->expects($this->any()) */ -/* ->method('_count') */ -/* ->will($this->returnValue(1)); */ -/* $ldap->expects($this->any()) */ -/* ->method('_firstEntry') */ -/* ->will($this->returnValue(1)); */ -/* $ldap->expects($this->any()) */ -/* ->method('_errno') */ -/* ->will($this->returnValue(1)); */ -/* $ldap->expects($this->any()) */ -/* ->method('_error') */ -/* ->will($this->returnValue('cn=DOES NOT EXIST,dc=example,dc=org: No such object')); */ - -/* $dn = $ldap->uidForIdOrMail('wrobel'); */ -/* $this->assertEquals('Retrieving DN failed. Error was: cn=DOES NOT EXIST,dc=example,dc=org: No such object', */ -/* $dn->message); */ - -/* $ldap = $this->getMock('Horde_Kolab_Server_ldap', array('_getDn', */ -/* '_search', */ -/* '_count')); */ -/* $ldap->expects($this->any()) */ -/* ->method('_getDn') */ -/* ->will($this->returnValue(false)); */ -/* $ldap->expects($this->any()) */ -/* ->method('_search') */ -/* ->will($this->returnValue('cn=Gunnar Wrobel,dc=example,dc=org')); */ -/* $ldap->expects($this->any()) */ -/* ->method('_count') */ -/* ->will($this->returnValue(4)); */ - -/* $dn = $ldap->uidForIdOrMail('wrobel'); */ -/* $this->assertEquals('Found 4 results when expecting only one!', */ -/* $dn->message); */ -/* } */ - -} diff --git a/framework/Kolab_Server/test/Horde/Kolab/Server/testTest.php b/framework/Kolab_Server/test/Horde/Kolab/Server/testTest.php deleted file mode 100644 index f28321f98..000000000 --- a/framework/Kolab_Server/test/Horde/Kolab/Server/testTest.php +++ /dev/null @@ -1,656 +0,0 @@ - - * @license http://www.fsf.org/copyleft/lgpl.html LGPL - * @link http://pear.horde.org/index.php?package=Kolab_Server - */ - -/** - * The Autoloader allows us to omit "require/include" statements. - */ -require_once 'Horde/Autoloader.php'; - -/** - * Test the test backend. - * - * Copyright 2008-2009 The Horde Project (http://www.horde.org/) - * - * See the enclosed file COPYING for license information (LGPL). If you - * did not receive this file, see http://www.fsf.org/copyleft/lgpl.html. - * - * @category Kolab - * @package Kolab_Server - * @author Gunnar Wrobel - * @license http://www.fsf.org/copyleft/lgpl.html LGPL - * @link http://pear.horde.org/index.php?package=Kolab_Server - */ -class Horde_Kolab_Server_testTest extends Horde_Kolab_Test_Server -{ - - /** - * Test search base. - * - * @dataProvider provideServerTypes - * - * @return NULL - */ - public function testSearchBase($type) - { - $server = &$this->prepareBasicServer($type); - - $result = $server->search('(objectClass=top)', array('objectClass')); - $this->assertEquals(13, count($result)); - - $result = $server->search('(objectClass=top)', - array('objectClass'), - 'cn=internal,dc=example,dc=org'); - $this->assertNoError($result); - $this->assertEquals(4, count($result)); - } - - /** - * Test sorting. - * - * @dataProvider provideServerTypes - * - * @return NULL - */ - public function testSorting($type) - { - $server = &$this->prepareBasicServer($type); - -/* $result = $server->search('(mail=*)', array('mail')); */ -/* $this->assertNoError($result); */ -/* $this->assertEquals(5, count($result)); */ -/* $server->sort($result, 'mail'); */ -/* foreach ($result as $object) { */ -/* if (isset($object['data']['dn'])) { */ -/* switch ($object['data']['dn']) { */ -/* case 'cn=Test Address,cn=external,dc=example,dc=org': */ -/* $this->assertContains('address@example.org', $object['data']['mail']); */ -/* break; */ -/* case '': */ -/* $this->assertContains('address@example.org', $object['data']['mail']); */ -/* break; */ -/* } */ -/* } */ -/* } */ - } - - /** - * Test listing objects. - * - * @dataProvider provideServerTypes - * - * @return NULL - */ - public function testListObjects($type) - { - $server = &$this->prepareBasicServer($type); - - $filter = '(&(objectClass=kolabInetOrgPerson)(uid=*)(mail=*)(sn=*))'; - $attributes = array( - Horde_Kolab_Server_Object_base::ATTRIBUTE_SN, - Horde_Kolab_Server_Object_base::ATTRIBUTE_CN, - Horde_Kolab_Server_Object::ATTRIBUTE_UID, - Horde_Kolab_Server_Object_base::ATTRIBUTE_MAIL, - Horde_Kolab_Server_Object_base::ATTRIBUTE_DELETED, - ); - - $sort = Horde_Kolab_Server_Object_base::ATTRIBUTE_SN; - $result = $server->search($filter); - $this->assertNoError($result); - $this->assertEquals(2, count($result)); - - $result = $server->listObjects('Horde_Kolab_Server_Object_user'); - $this->assertNoError($result); - $this->assertEquals(2, count($result)); - $this->assertEquals('Horde_Kolab_Server_Object_user', get_class(array_shift($result))); - - $result = $server->listObjects('Horde_Kolab_Server_Object_sharedfolder'); - $this->assertNoError($result); - $this->assertEquals(1, count($result)); - $this->assertEquals('Horde_Kolab_Server_Object_sharedfolder', get_class(array_shift($result))); - } - - /** - * Test handling of object classes. - * - * @dataProvider provideServerTypes - * - * @return NULL - */ - public function testGetObjectClasses($type) - { - $server = &$this->prepareBasicServer($type); - - $classes = $server->getObjectClasses('cn=Gunnar Wrobel,dc=example,dc=org'); - $this->assertNoError($classes); - $this->assertContains('top', $classes); - $this->assertContains('kolabinetorgperson', $classes); - $this->assertContains('hordeperson', $classes); - - try { - $classes = $server->getObjectClasses('cn=DOES NOT EXIST,dc=example,dc=org'); - } catch (Horde_Kolab_Server_Exception $classes) { - } - $this->assertError($classes, - 'No such object: cn=DOES NOT EXIST,dc=example,dc=org'); - - $classes = $server->getObjectClasses('cn=The Administrator,dc=example,dc=org'); - $this->assertNoError($classes); - $this->assertContains('kolabinetorgperson', $classes); - } - - /** - * Test handling of object types. - * - * @dataProvider provideServerTypes - * - * @return NULL - */ - public function testDetermineType($type) - { - $server = &$this->prepareBasicServer($type); - - $type = $server->determineType('cn=empty.group@example.org,dc=example,dc=org'); - $this->assertNoError($type); - $this->assertEquals('Horde_Kolab_Server_Object_group', $type); - - $type = $server->determineType('cn=shared@example.org,dc=example,dc=org'); - $this->assertNoError($type); - $this->assertEquals('Horde_Kolab_Server_Object_sharedfolder', $type); - - $type = $server->determineType('cn=The Administrator,dc=example,dc=org'); - $this->assertNoError($type); - $this->assertEquals('Horde_Kolab_Server_Object_administrator', $type); - - $type = $server->determineType('cn=Main Tainer,dc=example,dc=org'); - $this->assertNoError($type); - $this->assertEquals('Horde_Kolab_Server_Object_maintainer', $type); - - $type = $server->determineType('cn=Domain Maintainer,dc=example,dc=org'); - $this->assertNoError($type); - $this->assertEquals('Horde_Kolab_Server_Object_domainmaintainer', $type); - - $type = $server->determineType('cn=Test Address,cn=external,dc=example,dc=org'); - $this->assertNoError($type); - $this->assertEquals('Horde_Kolab_Server_Object_address', $type); - - $type = $server->determineType('cn=Gunnar Wrobel,dc=example,dc=org'); - $this->assertNoError($type); - $this->assertEquals('Horde_Kolab_Server_Object_user', $type); - } - - /** - * Test retrieving a primary mail for a mail or id. - * - * @dataProvider provideServerTypes - * - * @return NULL - */ - public function testMailForIdOrMail($type) - { - $server = &$this->prepareBasicServer($type); - - $mail = $server->mailForIdOrMail('wrobel'); - $this->assertEquals('wrobel@example.org', $mail); - - $mail = $server->mailForIdOrMail('wrobel@example.org'); - $this->assertNoError($mail); - $this->assertEquals('wrobel@example.org', $mail); - - $mail = $server->mailForIdOrMail('DOES NOT EXIST'); - $this->assertNoError($mail); - $this->assertSame(false, $mail); - } - - /** - * Test retrieving a UID for a mail or id. - * - * @dataProvider provideServerTypes - * - * @return NULL - */ - public function testUidForIdOrMail($type) - { - $server = &$this->prepareBasicServer($type); - - $uid = $server->uidForIdOrMail('wrobel'); - $this->assertNoError($uid); - $this->assertEquals('cn=Gunnar Wrobel,dc=example,dc=org', $uid); - - $uid = $server->uidForIdOrMail('wrobel@example.org'); - $this->assertNoError($uid); - $this->assertEquals('cn=Gunnar Wrobel,dc=example,dc=org', $uid); - - $uid = $server->uidForIdOrMail('DOES NOT EXIST'); - $this->assertNoError($uid); - $this->assertSame(false, $uid); - } - - /** - * Test retrieving a UID for a mail or id. - * - * @dataProvider provideServerTypes - * - * @return NULL - */ - public function testUidForMailOrIdOrAlias($type) - { - $server = &$this->prepareBasicServer($type); - - $uid = $server->uidForIdOrMailOrAlias('g.wrobel@example.org'); - $this->assertNoError($uid); - $this->assertEquals('cn=Gunnar Wrobel,dc=example,dc=org', $uid); - - $uid = $server->uidForIdOrMailOrAlias('wrobel@example.org'); - $this->assertNoError($uid); - $this->assertEquals('cn=Gunnar Wrobel,dc=example,dc=org', $uid); - - $uid = $server->uidForIdOrMailOrAlias('wrobel'); - $this->assertNoError($uid); - $this->assertEquals('cn=Gunnar Wrobel,dc=example,dc=org', $uid); - - $uid = $server->uidForIdOrMailOrAlias('DOES NOT EXIST'); - $this->assertNoError($uid); - $this->assertSame(false, $uid); - } - - /** - * Test retrieving all addresses for a mail or id. - * - * @dataProvider provideServerTypes - * - * @return NULL - */ - public function testAddrsForIdOrMail($type) - { - $server = &$this->prepareBasicServer($type); - - $addrs = $server->addrsForIdOrMail('wrobel'); - - $testuser = $server->fetch('cn=Test Test,dc=example,dc=org'); - $this->assertNoError($testuser); - $this->assertContains('wrobel@example.org', - $testuser->get(Horde_Kolab_Server_Object_base::ATTRIBUTE_DELEGATE, false)); - - $this->assertNoError($addrs); - $this->assertContains('wrobel@example.org', $addrs); - $this->assertContains('test@example.org', $addrs); - $this->assertContains('t.test@example.org', $addrs); - $this->assertContains('g.wrobel@example.org', $addrs); - $this->assertContains('gunnar@example.org', $addrs); - - $addrs = $server->addrsForIdOrMail('test@example.org'); - $this->assertNoError($addrs); - $this->assertContains('test@example.org', $addrs); - $this->assertContains('t.test@example.org', $addrs); - } - - /** - * Test retrieving a UID for a primary mail. - * - * @dataProvider provideServerTypes - * - * @return NULL - */ - public function testUidForMailAddress($type) - { - $server = &$this->prepareBasicServer($type); - - $uid = $server->uidForIdOrMailOrAlias('wrobel@example.org'); - $this->assertNoError($uid); - $this->assertEquals('cn=Gunnar Wrobel,dc=example,dc=org', $uid); - - $uid = $server->uidForIdOrMailOrAlias('test@example.org'); - $this->assertNoError($uid); - $this->assertEquals('cn=Test Test,dc=example,dc=org', $uid); - - $uid = $server->uidForIdOrMailOrAlias('gunnar@example.org'); - $this->assertNoError($uid); - $this->assertEquals('cn=Gunnar Wrobel,dc=example,dc=org', $uid); - - $uid = $server->uidForIdOrMailOrAlias('wrobel'); - $this->assertNoError($uid); - $this->assertEquals('cn=Gunnar Wrobel,dc=example,dc=org', $uid); - } - - /** - * Test retrieving a UID for an attribute. - * - * @dataProvider provideServerTypes - * - * @return NULL - */ - public function testUidForAttr($type) - { - $server = &$this->prepareBasicServer($type); - - $uid = $server->uidForSearch(array('AND' => array(array('field' => 'alias', - 'op' => '=', - 'test' => 'g.wrobel@example.org')))); - $this->assertNoError($uid); - $this->assertEquals('cn=Gunnar Wrobel,dc=example,dc=org', $uid); - } - - /** - * Test group membership testing. - * - * @dataProvider provideServerTypes - * - * @return NULL - */ - public function testMemberOfGroupAddress($type) - { - $server = &$this->prepareBasicServer($type); - - $uid = $server->uidForIdOrMailOrAlias('g.wrobel@example.org'); - $this->assertNoError($uid); - $member = $server->memberOfGroupAddress($uid, 'group@example.org'); - $this->assertNoError($member); - $this->assertTrue($member); - - $member = $server->memberOfGroupAddress( - $server->uidForIdOrMailOrAlias('test@example.org'), - 'group@example.org'); - $this->assertNoError($member); - $this->assertTrue($member); - - $member = $server->memberOfGroupAddress( - $server->uidForIdOrMailOrAlias('somebody@example.org'), - 'group@example.org'); - $this->assertNoError($member); - $this->assertFalse($member); - } - - /** - * Test group fetching. - * - * @dataProvider provideServerTypes - * - * @return NULL - */ - public function testGetGroups($type) - { - $server = &$this->prepareBasicServer($type); - - $filter = '(&(objectClass=kolabGroupOfNames)(member=' - . Horde_LDAP::quote('cn=The Administrator,dc=example,dc=org') . '))'; - $result = $server->search($filter, array()); - $this->assertNoError($result); - $this->assertTrue(!empty($result)); - -/* $entry = $server->_firstEntry($result); */ -/* $this->assertNoError($entry); */ -/* $this->assertTrue(!empty($entry)); */ - -/* $uid = $server->_getDn($entry); */ -/* $this->assertNoError($uid); */ -/* $this->assertTrue(!empty($uid)); */ - -/* $entry = $server->_nextEntry($entry); */ -/* $this->assertNoError($entry); */ -/* $this->assertTrue(empty($entry)); */ - -/* $entries = $server->_getDns($result); */ -/* $this->assertNoError($entries); */ -/* $this->assertTrue(!empty($entries)); */ - - $groups = $server->getGroups('cn=The Administrator,dc=example,dc=org'); - $this->assertNoError($groups); - $this->assertTrue(!empty($groups)); - - $groups = $server->getGroups($server->uidForIdOrMailOrAlias('g.wrobel@example.org')); - $this->assertNoError($groups); - $this->assertContains('cn=group@example.org,dc=example,dc=org', $groups); - - $groups = $server->getGroups($server->uidForIdOrMailOrAlias('test@example.org')); - $this->assertNoError($groups); - $this->assertContains('cn=group@example.org,dc=example,dc=org', $groups); - - $groups = $server->getGroups('nobody'); - $this->assertNoError($groups); - $this->assertTrue(empty($groups)); - - } - - /** - * Test parsing of LDAP filters. - * - * @return NULL - */ - public function testFilterParse() - { - $db = &Horde_Kolab_Server::factory('test', array()); - - $a = $db->parse('(a=b)'); - $this->assertNoError($a); - $this->assertEquals(array('att' => 'a', 'log' => '=', 'val' => 'b'), - $a); - - $a = $db->parse('(&(a=b)(c=d))'); - $this->assertNoError($a); - $this->assertEquals(array('op' => '&', 'sub' => array( - array('att' => 'a', 'log' => '=', 'val' => 'b'), - array('att' => 'c', 'log' => '=', 'val' => 'd'), - )), $a); - - $a = $db->parse('(&(a=1)(|(b=2)(c=3)))'); - $this->assertNoError($a); - $this->assertEquals(array('op' => '&', 'sub' => array( - array('att' => 'a', 'log' => '=', 'val' => '1'), - array('op' => '|', 'sub' => - array( - array('att' => 'b', 'log' => '=', 'val' => '2'), - array('att' => 'c', 'log' => '=', 'val' => '3'), - )))), $a); - - $a = $db->parseSub('(!(x=2))(b=1)'); - $this->assertNoError($a); - $this->assertEquals(array(array('op' => '!', 'sub' => - array( - array('att' => 'x', 'log' => '=', 'val' => '2'), - ) - ), - array('att' => 'b', 'log' => '=', 'val' => '1'), - ), $a); - - $a = $db->parse('(&(!(x=2))(b=1))'); - $this->assertNoError($a); - $this->assertEquals(array('op' => '&', 'sub' => array( - array('op' => '!', 'sub' => - array( - array('att' => 'x', 'log' => '=', 'val' => '2'), - ) - ), - array('att' => 'b', 'log' => '=', 'val' => '1'), - )), $a); - - } - - /** - * Test searching in the simulated LDAP data. - * - * @return NULL - */ - public function testSearch() - { -/* $db = &Horde_Kolab_Server::factory('test', */ -/* array('data' => */ -/* array( */ -/* 'cn=a' => array( */ -/* 'dn' => 'cn=a', */ -/* 'data' => array( */ -/* 'a' => '1', */ -/* 'b' => '1', */ -/* 'c' => '1', */ -/* ) */ -/* ), */ -/* 'cn=b' => array( */ -/* 'dn' => 'cn=b', */ -/* 'data' => array( */ -/* 'a' => '1', */ -/* 'b' => '2', */ -/* 'c' => '2', */ -/* ) */ -/* ), */ -/* 'cn=c' => array( */ -/* 'dn' => 'cn=c', */ -/* 'data' => array( */ -/* 'a' => '1', */ -/* 'b' => '2', */ -/* 'c' => '3', */ -/* ) */ -/* ), */ -/* 'cn=d' => array( */ -/* 'dn' => 'cn=d', */ -/* 'data' => array( */ -/* 'a' => '2', */ -/* 'b' => '2', */ -/* 'c' => '1', */ -/* ) */ -/* ), */ -/* ) */ -/* ) */ -/* ); */ - -/* $a = $db->search('(c=1)'); */ -/* $this->assertNoError($a); */ -/* $this->assertEquals( */ -/* array( */ -/* array( */ -/* 'dn' => 'cn=a', */ -/* 'data' => array( */ -/* 'a' => '1', */ -/* 'b' => '1', */ -/* 'c' => '1', */ -/* ) */ -/* ), */ -/* array( */ -/* 'dn' => 'cn=d', */ -/* 'data' => array( */ -/* 'a' => '2', */ -/* 'b' => '2', */ -/* 'c' => '1', */ -/* ) */ -/* ), */ -/* ), */ -/* $a */ -/* ); */ - -/* $a = $db->_search('(c=3)'); */ -/* $this->assertNoError($a); */ -/* $this->assertEquals( */ -/* array( */ -/* array( */ -/* 'dn' => 'cn=c', */ -/* 'data' => array( */ -/* 'a' => '1', */ -/* 'b' => '2', */ -/* 'c' => '3', */ -/* ) */ -/* ), */ -/* ), */ -/* $a */ -/* ); */ - -/* $a = $db->_search('(c=3)', array('a')); */ -/* $this->assertNoError($a); */ -/* $this->assertEquals( */ -/* array( */ -/* array( */ -/* 'dn' => 'cn=c', */ -/* 'data' => array( */ -/* 'a' => '1', */ -/* ) */ -/* ), */ -/* ), */ -/* $a */ -/* ); */ - -/* $a = $db->_search('(&(a=1)(b=2))', array('a', 'b')); */ -/* $this->assertNoError($a); */ -/* $this->assertEquals( */ -/* array( */ -/* array( */ -/* 'dn' => 'cn=b', */ -/* 'data' => array( */ -/* 'a' => '1', */ -/* 'b' => '2', */ -/* ) */ -/* ), */ -/* array( */ -/* 'dn' => 'cn=c', */ -/* 'data' => array( */ -/* 'a' => '1', */ -/* 'b' => '2', */ -/* ) */ -/* ), */ -/* ), */ -/* $a */ -/* ); */ - -/* $a = $db->_search('(&(b=2))', array('b')); */ -/* $this->assertNoError($a); */ -/* $this->assertEquals( */ -/* array( */ -/* array( */ -/* 'dn' => 'cn=b', */ -/* 'data' => array( */ -/* 'b' => '2', */ -/* ) */ -/* ), */ -/* array( */ -/* 'dn' => 'cn=c', */ -/* 'data' => array( */ -/* 'b' => '2', */ -/* ) */ -/* ), */ -/* array( */ -/* 'dn' => 'cn=d', */ -/* 'data' => array( */ -/* 'b' => '2', */ -/* ) */ -/* ), */ -/* ), */ -/* $a */ -/* ); */ - -/* $a = $db->_search('(!(b=2))', array('a', 'b')); */ -/* $this->assertNoError($a); */ -/* $this->assertEquals( */ -/* array( */ -/* array( */ -/* 'dn' => 'cn=a', */ -/* 'data' => array( */ -/* 'a' => '1', */ -/* 'b' => '1', */ -/* ) */ -/* ), */ -/* ), */ -/* $a */ -/* ); */ - -/* $a = $db->_search('(&(!(x=2))(b=1))', array('b')); */ -/* $this->assertNoError($a); */ -/* $this->assertEquals( */ -/* array( */ -/* array( */ -/* 'dn' => 'cn=a', */ -/* 'data' => array( */ -/* 'b' => '1', */ -/* ) */ -/* ), */ -/* ), */ -/* $a */ -/* ); */ - } - -}