Spaces:
Sleeping
Sleeping
| /* vim: set expandtab tabstop=4 shiftwidth=4: */ | |
| // +--------------------------------------------------------------------------+ | |
| // | Net_LDAP | | |
| // +--------------------------------------------------------------------------+ | |
| // | Copyright (c) 1997-2003 The PHP Group | | |
| // +--------------------------------------------------------------------------+ | |
| // | This library is free software; you can redistribute it and/or | | |
| // | modify it under the terms of the GNU Lesser General Public | | |
| // | License as published by the Free Software Foundation; either | | |
| // | version 2.1 of the License, or (at your option) any later version. | | |
| // | | | |
| // | This library is distributed in the hope that it will be useful, | | |
| // | but WITHOUT ANY WARRANTY; without even the implied warranty of | | |
| // | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | | |
| // | Lesser General Public License for more details. | | |
| // | | | |
| // | You should have received a copy of the GNU Lesser General Public | | |
| // | License along with this library; if not, write to the Free Software | | |
| // | Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA | | |
| // +--------------------------------------------------------------------------+ | |
| // | Authors: Tarjej Huse | | |
| // +--------------------------------------------------------------------------+ | |
| // | |
| // $Id: Entry.php 4831 2006-02-06 09:59:09Z nbm $ | |
| /** | |
| * This class represents an LDAP entry | |
| * | |
| * @package Net_LDAP | |
| * @author Tarjei Huse | |
| * @version $Revision: 4831 $ | |
| */ | |
| class Net_LDAP_Entry extends PEAR | |
| { | |
| /**#@+ | |
| * Array of the attributes | |
| * | |
| * @access private | |
| * @var array | |
| */ | |
| var $_attrs = array(); | |
| /** | |
| * Array of attributes to be deleted upon update() | |
| */ | |
| var $_delAttrs = array(); | |
| /** | |
| * Array of attributes to be modified upon update() | |
| */ | |
| var $_modAttrs = array(); | |
| /** | |
| * Array of attributes to be added upon update() | |
| */ | |
| var $_addAttrs = array(); | |
| /**#@-*/ | |
| /** | |
| * The distinguished name of the entry | |
| * | |
| * @access private | |
| * @var string | |
| */ | |
| var $_dn = ''; | |
| /** | |
| * LDAP resource link | |
| * | |
| * @access private | |
| * @var resource | |
| */ | |
| var $_link = null; | |
| /** | |
| * Value of old DN if DN has changed | |
| * | |
| * @access private | |
| * @var string | |
| */ | |
| var $_olddn = ''; | |
| /**#@+ | |
| * Array of errors for debugging class | |
| * | |
| * @access private | |
| */ | |
| var $_error = array(); | |
| /** | |
| * updatechecks | |
| */ | |
| var $updateCheck = array('newdn' => false, | |
| 'modify' => false, | |
| 'newEntry' => true | |
| ); // since the entry is not changed before the update(); | |
| /** | |
| * Net_LDAP_Schema object TO BE REMOVED | |
| */ | |
| var $_schema; | |
| /**#@-*/ | |
| /** Constructor | |
| * | |
| * @param - link - ldap_resource_link, dn = string entry dn, attributes - array entry attributes array. | |
| * @return - none | |
| **/ | |
| function Net_LDAP_Entry($link = null, $dn = null, $attributes = null) | |
| { | |
| if (!is_null($link)) { | |
| $this->_link = $link; | |
| } | |
| if (!is_null($dn)) { | |
| $this->_set_dn($dn); | |
| } | |
| if (is_array($attributes) && count($attributes) > 0) { | |
| $this->_set_attributes($attributes); | |
| } else { | |
| $this->updateCheck['newEntry'] = true; | |
| } | |
| } | |
| /** | |
| * Set the reasourcelink to the ldapserver. | |
| * | |
| * @access private | |
| * @param resource LDAP link | |
| */ | |
| function _set_link(&$link) | |
| { | |
| $this->_link = $link; | |
| } | |
| /** | |
| * set the entrys DN | |
| * | |
| * @access private | |
| * @param string | |
| */ | |
| function _set_dn($dn) | |
| { | |
| $this->_dn = $dn; | |
| } | |
| /** | |
| * sets the internal array of the entrys attributes. | |
| * | |
| * @access private | |
| * @param array | |
| */ | |
| function _set_attributes($attributes= array()) | |
| { | |
| $this->_attrs = $attributes; | |
| // this is the sign that the entry exists in the first place: | |
| $this->updateCheck['newEntry'] = false; | |
| } | |
| /** | |
| * removes [count] entries from the array. | |
| * | |
| * remove all the count elements in the array: | |
| * Used before ldap_modify, ldap_add | |
| * | |
| * @access private | |
| * @return array Cleaned array of attributes | |
| */ | |
| function _clean_entry() | |
| { | |
| $attributes = array(); | |
| for ($i=0; $i < $this->_attrs['count'] ; $i++) { | |
| $attr = $this->_attrs[$i]; | |
| if ($this->_attrs[$attr]['count'] == 1) { | |
| $attributes[$this->_attrs[$i]] = $this->_attrs[$attr][0]; | |
| } else { | |
| $attributes[$attr] = $this->_attrs[$attr]; | |
| unset ($attributes[ $attr ]['count']); | |
| } | |
| } | |
| return $attributes; | |
| } | |
| /** | |
| * returns an assosiative array of all the attributes in the array | |
| * | |
| * attributes - returns an assosiative array of all the attributes in the array | |
| * of the form array ('attributename'=>'singelvalue' , 'attribute'=>array('multiple','values')) | |
| * | |
| * @param none | |
| * @return array Array of attributes and values. | |
| */ | |
| function attributes() | |
| { | |
| return $this->_clean_entry(); | |
| } | |
| /** | |
| * Add one or more attribute to the entry | |
| * | |
| * The values given will be added to the values which already exist for the given attributes. | |
| * usage: | |
| * $entry->add ( array('sn'=>'huse',objectclass=>array(top,posixAccount))) | |
| * | |
| * @param array Array of attributes | |
| * @return mixed Net_Ldap_Error if error, else true. | |
| */ | |
| function add($attr = array()) | |
| { | |
| if (!isset($this->_attrs['count'])) { | |
| $this->_attrs['count'] = 0; | |
| } | |
| if (!is_array($attr)) { | |
| return $this->raiseError("Net_LDAP::add : the parameter supplied is not an array, $attr", 1000); | |
| } | |
| /* if you passed an empty array, that is your problem! */ | |
| if (count ($attr)==0) { | |
| return true; | |
| } | |
| foreach ($attr as $k => $v ) { | |
| // empty entrys should not be added to the entry. | |
| if ($v == '') { | |
| continue; | |
| } | |
| if ($this->exists($k)) { | |
| if (!is_array($this->_attrs[$k])) { | |
| return $this->raiseError("Possible malformed array as parameter to Net_LDAP::add()."); | |
| } | |
| array_push($this->_attrs[$k],$v); | |
| $this->_attrs[$k]['count']++; | |
| } else { | |
| $this->_attrs[$k][0] = $v; | |
| $this->_attrs[$k]['count'] = 1; | |
| $this->_attrs[$this->_attrs['count']] = $k; | |
| $this->_attrs['count']++; | |
| } | |
| // Fix for bug #952 | |
| if (empty($this->_addAttrs[$k])) { | |
| $this->_addAttrs[$k] = array(); | |
| } | |
| if (false == is_array($v)) { | |
| $v = array($v); | |
| } | |
| foreach ($v as $value) { | |
| array_push($this->_addAttrs[$k], $value); | |
| } | |
| } | |
| return true; | |
| } | |
| /** | |
| * Set or get the DN for the object | |
| * | |
| * If a new dn is supplied, this will move the object when running $obj->update(); | |
| * | |
| * @param string DN | |
| */ | |
| function dn($newdn = '') | |
| { | |
| if ($newdn == '') { | |
| return $this->_dn; | |
| } | |
| $this->_olddn = $this->_dn; | |
| $this->_dn = $newdn; | |
| $this->updateCheck['newdn'] = true; | |
| } | |
| /** | |
| * check if a certain attribute exists in the directory | |
| * | |
| * @param string attribute name. | |
| * @return boolean | |
| */ | |
| function exists($attr) | |
| { | |
| if (array_key_exists($attr, $this->_attrs)) { | |
| return true; | |
| } | |
| return false; | |
| } | |
| /** | |
| * get_value get the values for a attribute | |
| * | |
| * returns either an array or a string | |
| * possible values for option: | |
| * alloptions - returns an array with the values + a countfield. | |
| * i.e.: array (count=>1, 'sn'=>'huse'); | |
| * single - returns the, first value in the array as a string. | |
| * | |
| * @param $attr string attribute name | |
| * @param $options array | |
| */ | |
| function get_value($attr = '', $options = '') | |
| { | |
| if (array_key_exists($attr, $this->_attrs)) { | |
| if ($options == 'single') { | |
| if (is_array($this->_attrs[$attr])) { | |
| return $this->_attrs[$attr][0]; | |
| } else { | |
| return $this->_attrs[$attr]; | |
| } | |
| } | |
| $value = $this->_attrs[$attr]; | |
| if (!$options == 'alloptions') { | |
| unset ($value['count']); | |
| } | |
| return $value; | |
| } else { | |
| return ''; | |
| } | |
| } | |
| /** | |
| * add/delete/modify attributes | |
| * | |
| * this function tries to do all the things that replace(),delete() and add() does on an object. | |
| * Syntax: | |
| * array ( 'attribute' => newval, 'delattribute' => '', newattrivute => newval); | |
| * Note: You cannot use this function to modify parts of an attribute. You must modify the whole attribute. | |
| * You may call the function many times before running $entry->update(); | |
| * | |
| * @param array attributes to be modified | |
| * @return mixed errorObject if failure, true if success. | |
| */ | |
| function modify($attrs = array()) { | |
| if (!is_array($attrs) || count ($attrs) < 1 ) { | |
| return $this->raiseError("You did not supply an array as expected",1000); | |
| } | |
| foreach ($attrs as $k => $v) { | |
| // empty values are deleted (ldap v3 handling is in update() ) | |
| if ($v == '' && $this->exists($k)) { | |
| $this->_delAttrs[$k] = ''; | |
| continue; | |
| } | |
| /* existing attributes are modified*/ | |
| if ($this->exists($k) ) { | |
| if (is_array($v)) { | |
| $this->_modAttrs[$k] = $v; | |
| } else { | |
| $this->_modAttrs[$k][0] = $v; | |
| } | |
| } else { | |
| /* new ones are created */ | |
| if (is_array($v) ) { | |
| // an empty array is deleted... | |
| if (count($v) == 0 ) { | |
| $this->_delAttrs[$k] = ''; | |
| } else { | |
| $this->_addAttrs[$k] = $v; | |
| } | |
| } else { | |
| // dont't add empty attributes | |
| if ($v != null) $this->_addAttrs[$k][0] = $v; | |
| } | |
| } | |
| } | |
| return true; | |
| } | |
| /** | |
| * replace a certain attributes value | |
| * | |
| * replace - replace a certain attributes value | |
| * example: | |
| * $entry->replace(array('uid'=>array('tarjei'))); | |
| * | |
| * @param array attributes to be replaced | |
| * @return mixed error if failure, true if sucess. | |
| */ | |
| function replace($attrs = array() ) | |
| { | |
| foreach ($attrs as $k => $v) { | |
| if ($this->exists($k)) { | |
| if (is_array($v)) { | |
| $this->_attrs[$k] = $v; | |
| $this->_attrs[$k]['count'] = count($v); | |
| $this->_modAttrs[$k] = $v; | |
| } else { | |
| $this->_attrs[$k]['count'] = 1; | |
| $this->_attrs[$k][0] = $v; | |
| $this->_modAttrs[$k][0] = $v; | |
| } | |
| } else { | |
| return $this->raiseError("Attribute $k does not exist",16); // 16 = no such attribute exists. | |
| } | |
| } | |
| return true; | |
| } | |
| /** | |
| * delete attributes | |
| * | |
| * Use this function to delete certain attributes from an object. | |
| * | |
| * @param - array of attributes to be deleted | |
| * @return mixed Net_Ldap_Error if failure, true if success. | |
| */ | |
| function delete($attrs = array()) | |
| { | |
| foreach ($attrs as $k => $v) { | |
| if ($this->exists ($k)) { | |
| // if v is a null, then remove the whole attribute, else only the value. | |
| if ($v == '') { | |
| unset($this->_attrs[$k]); | |
| $this->_delAttrs[$k] = ""; | |
| // else we remove only the correct value. | |
| } else { | |
| for ($i = 0;$i< $this->_attrs[$k]['count'];$i++) { | |
| if ($this->_attrs[$k][$i] == $v ) { | |
| unset ($this->_attrs[$k][$i]); | |
| $this->_delAttrs[$k] = $v; | |
| continue; | |
| } | |
| } | |
| } | |
| } else { | |
| $this->raiseError("You tried to delete a nonexisting attribute!",16); | |
| } | |
| } | |
| return true; | |
| } | |
| /** | |
| * update the Entry in LDAP | |
| * | |
| * After modifying an object, you must run update() to | |
| * make the updates on the ldap server. Before that, they only exists in the object. | |
| * | |
| * @param object Net_LDAP | |
| * @return mixed Net_LDAP_Error object on failure or true on success | |
| */ | |
| function update ($ldapObject = null) | |
| { | |
| if ($ldapObject == null && $this->_link == null ) { | |
| $this->raiseError("No link to database"); | |
| } | |
| if ($ldapObject != null) { | |
| $this->_link =& $ldapObject->_link; | |
| } | |
| //if it's a new | |
| if ($this->updateCheck['newdn'] && !$this->updateCheck['newEntry']) { | |
| if (@ldap_get_option( $this->_link, LDAP_OPT_PROTOCOL_VERSION, $version) && $version != 3) { | |
| return $this->raiseError("Moving or renaming an dn is only supported in LDAP V3!", 80); | |
| } | |
| $newparent = ldap_explode_dn($this->_dn, 0); | |
| unset($newparent['count']); | |
| $relativeDn = array_shift($newparent); | |
| $newparent = join(',', $newparent); | |
| if (!@ldap_rename($this->_link, $this->_olddn, $relativeDn, $newparent, true)) { | |
| return $this->raiseError("DN not renamed: " . ldap_error($this->_link), ldap_errno($this->_link)); | |
| } | |
| } | |
| if ($this->updateCheck['newEntry']) { | |
| //print "<br>"; print_r($this->_clean_entry()); | |
| if (!@ldap_add($this->_link, $this->dn(), $this->_clean_entry()) ) { | |
| return $this->raiseError("Entry" . $this->dn() . " not added!" . | |
| ldap_error($this->_link), ldap_errno($this->_link)); | |
| } else { | |
| return true; | |
| } | |
| // update existing entry | |
| } else { | |
| $this->_error['first'] = $this->_modAttrs; | |
| $this->_error['count'] = count($this->_modAttrs); | |
| // modified attributes | |
| if (( count($this->_modAttrs)>0) && | |
| !ldap_modify($this->_link, $this->dn(), $this->_modAttrs)) | |
| { | |
| return $this->raiseError("Entry " . $this->dn() . " not modified(attribs not modified): " . | |
| ldap_error($this->_link),ldap_errno($this->_link)); | |
| } | |
| // attributes to be deleted | |
| if (( count($this->_delAttrs) > 0 )) | |
| { | |
| // in ldap v3 we need to supply the old attribute values for deleting | |
| if (@ldap_get_option( $this->_link, LDAP_OPT_PROTOCOL_VERSION, $version) && $version == 3) { | |
| foreach ( $this->_delAttrs as $k => $v ) { | |
| if ( $v == '' && $this->exists($k) ) { | |
| $this->_delAttrs[$k] = $this->get_value( $k ); | |
| } | |
| } | |
| } | |
| if ( !ldap_mod_del($this->_link, $this->dn(), $this->_delAttrs) ) { | |
| return $this->raiseError("Entry " . $this->dn() . " not modified (attributes not deleted): " . | |
| ldap_error($this->_link),ldap_errno($this->_link)); | |
| } | |
| } | |
| // new attributes | |
| if ((count($this->_addAttrs)) > 0 && !ldap_modify($this->_link, $this->dn(), $this->_addAttrs)) { | |
| return $this->raiseError( "Entry " . $this->dn() . " not modified (attributes not added): " . | |
| ldap_error($this->_link),ldap_errno($this->_link)); | |
| } | |
| return true; | |
| } | |
| } | |
| } | |