"Fossies" - the Fresh Open Source Software Archive

Member "adLDAP-4.0.4/src/classes/adLDAPGroups.php" (13 Apr 2013, 23532 Bytes) of package /linux/www/old/adLDAP-4.0.4.tar.gz:


As a special service "Fossies" has tried to format the requested source page into HTML format using (guessed) PHP source code syntax highlighting (style: standard) with prefixed line numbers and code folding option. Alternatively you can here view or download the uninterpreted source code file. For more information about "adLDAPGroups.php" see the Fossies "Dox" file reference documentation.

    1 <?php
    2 /**
    3  * PHP LDAP CLASS FOR MANIPULATING ACTIVE DIRECTORY 
    4  * Version 4.0.4
    5  * 
    6  * PHP Version 5 with SSL and LDAP support
    7  * 
    8  * Written by Scott Barnett, Richard Hyland
    9  *   email: scott@wiggumworld.com, adldap@richardhyland.com
   10  *   http://adldap.sourceforge.net/
   11  * 
   12  * Copyright (c) 2006-2012 Scott Barnett, Richard Hyland
   13  * 
   14  * We'd appreciate any improvements or additions to be submitted back
   15  * to benefit the entire community :)
   16  * 
   17  * This library is free software; you can redistribute it and/or
   18  * modify it under the terms of the GNU Lesser General Public
   19  * License as published by the Free Software Foundation; either
   20  * version 2.1 of the License.
   21  * 
   22  * This library is distributed in the hope that it will be useful,
   23  * but WITHOUT ANY WARRANTY; without even the implied warranty of
   24  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
   25  * Lesser General Public License for more details.
   26  * 
   27  * @category ToolsAndUtilities
   28  * @package adLDAP
   29  * @subpackage Groups
   30  * @author Scott Barnett, Richard Hyland
   31  * @copyright (c) 2006-2012 Scott Barnett, Richard Hyland
   32  * @license http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html LGPLv2.1
   33  * @revision $Revision: 97 $
   34  * @version 4.0.4
   35  * @link http://adldap.sourceforge.net/
   36  */
   37 require_once(dirname(__FILE__) . '/../adLDAP.php');
   38 require_once(dirname(__FILE__) . '/../collections/adLDAPGroupCollection.php');
   39 
   40 /**
   41 * GROUP FUNCTIONS
   42 */
   43 class adLDAPGroups {
   44     /**
   45     * The current adLDAP connection via dependency injection
   46     * 
   47     * @var adLDAP
   48     */
   49     protected $adldap;
   50     
   51     public function __construct(adLDAP $adldap) {
   52         $this->adldap = $adldap;
   53     }
   54     
   55     /**
   56     * Add a group to a group
   57     * 
   58     * @param string $parent The parent group name
   59     * @param string $child The child group name
   60     * @return bool
   61     */
   62     public function addGroup($parent,$child){
   63 
   64         // Find the parent group's dn
   65         $parentGroup = $this->ginfo($parent, array("cn"));
   66         if ($parentGroup[0]["dn"] === NULL){
   67             return false; 
   68         }
   69         $parentDn = $parentGroup[0]["dn"];
   70         
   71         // Find the child group's dn
   72         $childGroup = $this->info($child, array("cn"));
   73         if ($childGroup[0]["dn"] === NULL){ 
   74             return false; 
   75         }
   76         $childDn = $childGroup[0]["dn"];
   77                 
   78         $add = array();
   79         $add["member"] = $childDn;
   80         
   81         $result = @ldap_mod_add($this->adldap->getLdapConnection(), $parentDn, $add);
   82         if ($result == false) { 
   83             return false; 
   84         }
   85         return true;
   86     }
   87     
   88     /**
   89     * Add a user to a group
   90     * 
   91     * @param string $group The group to add the user to
   92     * @param string $user The user to add to the group
   93     * @param bool $isGUID Is the username passed a GUID or a samAccountName
   94     * @return bool
   95     */
   96     public function addUser($group, $user, $isGUID = false)
   97     {
   98         // Adding a user is a bit fiddly, we need to get the full DN of the user
   99         // and add it using the full DN of the group
  100         
  101         // Find the user's dn
  102         $userDn = $this->adldap->user()->dn($user, $isGUID);
  103         if ($userDn === false) { 
  104             return false; 
  105         }
  106         
  107         // Find the group's dn
  108         $groupInfo = $this->info($group, array("cn"));
  109         if ($groupInfo[0]["dn"] === NULL) { 
  110             return false; 
  111         }
  112         $groupDn = $groupInfo[0]["dn"];
  113         
  114         $add = array();
  115         $add["member"] = $userDn;
  116         
  117         $result = @ldap_mod_add($this->adldap->getLdapConnection(), $groupDn, $add);
  118         if ($result == false) { 
  119             return false; 
  120         }
  121         return true;
  122     }
  123     
  124     /**
  125     * Add a contact to a group
  126     * 
  127     * @param string $group The group to add the contact to
  128     * @param string $contactDn The DN of the contact to add
  129     * @return bool
  130     */
  131     public function addContact($group, $contactDn)
  132     {
  133         // To add a contact we take the contact's DN
  134         // and add it using the full DN of the group
  135         
  136         // Find the group's dn
  137         $groupInfo = $this->info($group, array("cn"));
  138         if ($groupInfo[0]["dn"] === NULL) { 
  139             return false; 
  140         }
  141         $groupDn = $groupInfo[0]["dn"];
  142         
  143         $add = array();
  144         $add["member"] = $contactDn;
  145         
  146         $result = @ldap_mod_add($this->adldap->getLdapConnection(), $groupDn, $add);
  147         if ($result == false) { 
  148             return false; 
  149         }
  150         return true;
  151     }
  152 
  153     /**
  154     * Create a group
  155     * 
  156     * @param array $attributes Default attributes of the group
  157     * @return bool
  158     */
  159     public function create($attributes)
  160     {
  161         if (!is_array($attributes)){ return "Attributes must be an array"; }
  162         if (!array_key_exists("group_name", $attributes)){ return "Missing compulsory field [group_name]"; }
  163         if (!array_key_exists("container", $attributes)){ return "Missing compulsory field [container]"; }
  164         if (!array_key_exists("description", $attributes)){ return "Missing compulsory field [description]"; }
  165         if (!is_array($attributes["container"])){ return "Container attribute must be an array."; }
  166         $attributes["container"] = array_reverse($attributes["container"]);
  167 
  168         //$member_array = array();
  169         //$member_array[0] = "cn=user1,cn=Users,dc=yourdomain,dc=com";
  170         //$member_array[1] = "cn=administrator,cn=Users,dc=yourdomain,dc=com";
  171         
  172         $add = array();
  173         $add["cn"] = $attributes["group_name"];
  174         $add["samaccountname"] = $attributes["group_name"];
  175         $add["objectClass"] = "Group";
  176         $add["description"] = $attributes["description"];
  177         //$add["member"] = $member_array; UNTESTED
  178 
  179         $container = "OU=" . implode(",OU=", $attributes["container"]);
  180         $result = ldap_add($this->adldap->getLdapConnection(), "CN=" . $add["cn"] . ", " . $container . "," . $this->adldap->getBaseDn(), $add);
  181         if ($result != true) { 
  182             return false; 
  183         }
  184         return true;
  185     }
  186     
  187     /**
  188     * Delete a group account 
  189     * 
  190     * @param string $group The group to delete (please be careful here!) 
  191     * 
  192     * @return array 
  193     */
  194     public function delete($group) {
  195         if (!$this->adldap->getLdapBind()){ return false; }
  196         if ($group === null){ return "Missing compulsory field [group]"; }
  197         
  198         $groupInfo = $this->info($group, array("*"));
  199         $dn = $groupInfo[0]['distinguishedname'][0]; 
  200         $result = $this->adldap->folder()->delete($dn); 
  201         if ($result !== true) { 
  202             return false; 
  203         } return true;   
  204     }
  205 
  206     /**
  207     * Remove a group from a group
  208     * 
  209     * @param string $parent The parent group name
  210     * @param string $child The child group name
  211     * @return bool
  212     */
  213     public function removeGroup($parent , $child)
  214     {
  215     
  216         // Find the parent dn
  217         $parentGroup = $this->info($parent, array("cn"));
  218         if ($parentGroup[0]["dn"] === NULL) { 
  219             return false; 
  220         }
  221         $parentDn = $parentGroup[0]["dn"];
  222         
  223         // Find the child dn
  224         $childGroup = $this->info($child, array("cn"));
  225         if ($childGroup[0]["dn"] === NULL) { 
  226             return false; 
  227         }
  228         $childDn = $childGroup[0]["dn"];
  229         
  230         $del = array();
  231         $del["member"] = $childDn;
  232         
  233         $result = @ldap_mod_del($this->adldap->getLdapConnection(), $parentDn, $del);
  234         if ($result == false) { 
  235             return false; 
  236         }
  237         return true;
  238     }
  239     
  240     /**
  241     * Remove a user from a group
  242     * 
  243     * @param string $group The group to remove a user from
  244     * @param string $user The AD user to remove from the group
  245     * @param bool $isGUID Is the username passed a GUID or a samAccountName
  246     * @return bool
  247     */
  248     public function removeUser($group, $user, $isGUID = false)
  249     {
  250     
  251         // Find the parent dn
  252         $groupInfo = $this->info($group, array("cn"));
  253         if ($groupInfo[0]["dn"] === NULL){ 
  254             return false; 
  255         }
  256         $groupDn = $groupInfo[0]["dn"];
  257         
  258         // Find the users dn
  259         $userDn = $this->adldap->user()->dn($user, $isGUID);
  260         if ($userDn === false) {
  261             return false; 
  262         }
  263 
  264         $del = array();
  265         $del["member"] = $userDn;
  266         
  267         $result = @ldap_mod_del($this->adldap->getLdapConnection(), $groupDn, $del);
  268         if ($result == false) {
  269             return false; 
  270         }
  271         return true;
  272     }
  273     
  274     /**
  275     * Remove a contact from a group
  276     * 
  277     * @param string $group The group to remove a user from
  278     * @param string $contactDn The DN of a contact to remove from the group
  279     * @return bool
  280     */
  281     public function removeContact($group, $contactDn)
  282     {
  283     
  284         // Find the parent dn
  285         $groupInfo = $this->info($group, array("cn"));
  286         if ($groupInfo[0]["dn"] === NULL) { 
  287             return false; 
  288         }
  289         $groupDn = $groupInfo[0]["dn"];
  290     
  291         $del = array();
  292         $del["member"] = $contactDn;
  293         
  294         $result = @ldap_mod_del($this->adldap->getLdapConnection(), $groupDn, $del);
  295         if ($result == false) { 
  296             return false; 
  297         }
  298         return true;
  299     }
  300     
  301     /**
  302     * Return a list of groups in a group
  303     * 
  304     * @param string $group The group to query
  305     * @param bool $recursive Recursively get groups
  306     * @return array
  307     */
  308     public function inGroup($group, $recursive = NULL)
  309     {
  310         if (!$this->adldap->getLdapBind()){ return false; }
  311         if ($recursive === NULL){ $recursive = $this->adldap->getRecursiveGroups(); } // Use the default option if they haven't set it 
  312         
  313         // Search the directory for the members of a group
  314         $info = $this->info($group, array("member","cn"));
  315         $groups = $info[0]["member"];
  316         if (!is_array($groups)) {
  317             return false;   
  318         }
  319  
  320         $groupArray = array();
  321 
  322         for ($i=0; $i<$groups["count"]; $i++){ 
  323              $filter = "(&(objectCategory=group)(distinguishedName=" . $this->adldap->utilities()->ldapSlashes($groups[$i]) . "))";
  324              $fields = array("samaccountname", "distinguishedname", "objectClass");
  325              $sr = ldap_search($this->adldap->getLdapConnection(), $this->adldap->getBaseDn(), $filter, $fields);
  326              $entries = ldap_get_entries($this->adldap->getLdapConnection(), $sr);
  327 
  328              // not a person, look for a group  
  329              if ($entries['count'] == 0 && $recursive == true) {  
  330                 $filter = "(&(objectCategory=group)(distinguishedName=" . $this->adldap->utilities()->ldapSlashes($groups[$i]) . "))";  
  331                 $fields = array("distinguishedname");  
  332                 $sr = ldap_search($this->adldap->getLdapConnection(), $this->adldap->getBaseDn(), $filter, $fields);  
  333                 $entries = ldap_get_entries($this->adldap->getLdapConnection(), $sr);  
  334                 if (!isset($entries[0]['distinguishedname'][0])) {
  335                     continue;  
  336                 }
  337                 $subGroups = $this->inGroup($entries[0]['distinguishedname'][0], $recursive);  
  338                 if (is_array($subGroups)) {
  339                     $groupArray = array_merge($groupArray, $subGroups); 
  340                     $groupArray = array_unique($groupArray);  
  341                 }
  342                 continue;  
  343              } 
  344 
  345              $groupArray[] = $entries[0]['distinguishedname'][0];
  346         }
  347         return $groupArray;
  348     }
  349     
  350     /**
  351     * Return a list of members in a group
  352     * 
  353     * @param string $group The group to query
  354     * @param bool $recursive Recursively get group members
  355     * @return array
  356     */
  357     public function members($group, $recursive = NULL)
  358     {
  359         if (!$this->adldap->getLdapBind()){ return false; }
  360         if ($recursive === NULL){ $recursive = $this->adldap->getRecursiveGroups(); } // Use the default option if they haven't set it 
  361         // Search the directory for the members of a group
  362         $info = $this->info($group, array("member","cn"));
  363         $users = $info[0]["member"];
  364         if (!is_array($users)) {
  365             return false;   
  366         }
  367  
  368         $userArray = array();
  369 
  370         for ($i=0; $i<$users["count"]; $i++){ 
  371              $filter = "(&(objectCategory=person)(distinguishedName=" . $this->adldap->utilities()->ldapSlashes($users[$i]) . "))";
  372              $fields = array("samaccountname", "distinguishedname", "objectClass");
  373              $sr = ldap_search($this->adldap->getLdapConnection(), $this->adldap->getBaseDn(), $filter, $fields);
  374              $entries = ldap_get_entries($this->adldap->getLdapConnection(), $sr);
  375 
  376              // not a person, look for a group  
  377              if ($entries['count'] == 0 && $recursive == true) {  
  378                 $filter = "(&(objectCategory=group)(distinguishedName=" . $this->adldap->utilities()->ldapSlashes($users[$i]) . "))";  
  379                 $fields = array("samaccountname");  
  380                 $sr = ldap_search($this->adldap->getLdapConnection(), $this->adldap->getBaseDn(), $filter, $fields);  
  381                 $entries = ldap_get_entries($this->adldap->getLdapConnection(), $sr);  
  382                 if (!isset($entries[0]['samaccountname'][0])) {
  383                     continue;  
  384                 }
  385                 $subUsers = $this->members($entries[0]['samaccountname'][0], $recursive);  
  386                 if (is_array($subUsers)) {
  387                     $userArray = array_merge($userArray, $subUsers); 
  388                     $userArray = array_unique($userArray);  
  389                 }
  390                 continue;  
  391              } 
  392              else if ($entries['count'] == 0) {   
  393                 continue; 
  394              } 
  395 
  396              if ((!isset($entries[0]['samaccountname'][0]) || $entries[0]['samaccountname'][0] === NULL) && $entries[0]['distinguishedname'][0] !== NULL) {
  397                  $userArray[] = $entries[0]['distinguishedname'][0];
  398              }
  399              else if ($entries[0]['samaccountname'][0] !== NULL) {
  400                 $userArray[] = $entries[0]['samaccountname'][0];
  401              }
  402         }
  403         return $userArray;
  404     }
  405     
  406     /**
  407     * Group Information.  Returns an array of raw information about a group.
  408     * The group name is case sensitive
  409     * 
  410     * @param string $groupName The group name to retrieve info about
  411     * @param array $fields Fields to retrieve
  412     * @return array
  413     */
  414     public function info($groupName, $fields = NULL)
  415     {
  416         if ($groupName === NULL) { return false; }
  417         if (!$this->adldap->getLdapBind()) { return false; }
  418         
  419         if (stristr($groupName, '+')) {
  420             $groupName = stripslashes($groupName);   
  421         }
  422         
  423         $filter = "(&(objectCategory=group)(name=" . $this->adldap->utilities()->ldapSlashes($groupName) . "))";
  424         if ($fields === NULL) { 
  425             $fields = array("member","memberof","cn","description","distinguishedname","objectcategory","samaccountname"); 
  426         }
  427         $sr = ldap_search($this->adldap->getLdapConnection(), $this->adldap->getBaseDn(), $filter, $fields);
  428         $entries = ldap_get_entries($this->adldap->getLdapConnection(), $sr);
  429 
  430         return $entries;
  431     }
  432     
  433     /**
  434     * Group Information.  Returns an collection
  435     * The group name is case sensitive
  436     * 
  437     * @param string $groupName The group name to retrieve info about
  438     * @param array $fields Fields to retrieve
  439     * @return adLDAPGroupCollection
  440     */
  441     public function infoCollection($groupName, $fields = NULL)
  442     {
  443         if ($groupName === NULL) { return false; }
  444         if (!$this->adldap->getLdapBind()) { return false; }
  445         
  446         $info = $this->info($groupName, $fields);
  447         if ($info !== false) {
  448             $collection = new adLDAPGroupCollection($info, $this->adldap);
  449             return $collection;
  450         }
  451         return false;
  452     }
  453     
  454     /**
  455     * Return a complete list of "groups in groups"
  456     * 
  457     * @param string $group The group to get the list from
  458     * @return array
  459     */
  460     public function recursiveGroups($group)
  461     {
  462         if ($group === NULL) { return false; }
  463 
  464         $stack = array(); 
  465         $processed = array(); 
  466         $retGroups = array(); 
  467      
  468         array_push($stack, $group); // Initial Group to Start with 
  469         while (count($stack) > 0) {
  470             $parent = array_pop($stack);
  471             array_push($processed, $parent);
  472             
  473             $info = $this->info($parent, array("memberof"));
  474             
  475             if (isset($info[0]["memberof"]) && is_array($info[0]["memberof"])) {
  476                 $groups = $info[0]["memberof"]; 
  477                 if ($groups) {
  478                     $groupNames = $this->adldap->utilities()->niceNames($groups);  
  479                     $retGroups = array_merge($retGroups, $groupNames); //final groups to return
  480                     foreach ($groupNames as $id => $groupName) { 
  481                         if (!in_array($groupName, $processed)) {
  482                             array_push($stack, $groupName);
  483                         }
  484                     }
  485                 }
  486             }
  487         }
  488         
  489         return $retGroups;
  490     }
  491     
  492     /**
  493     * Returns a complete list of the groups in AD based on a SAM Account Type  
  494     * 
  495     * @param string $sAMAaccountType The account type to return
  496     * @param bool $includeDescription Whether to return a description
  497     * @param string $search Search parameters
  498     * @param bool $sorted Whether to sort the results
  499     * @return array
  500     */
  501     public function search($sAMAaccountType = adLDAP::ADLDAP_SECURITY_GLOBAL_GROUP, $includeDescription = false, $search = "*", $sorted = true) {
  502         if (!$this->adldap->getLdapBind()) { return false; }
  503         
  504         $filter = '(&(objectCategory=group)';
  505         if ($sAMAaccountType !== null) {
  506             $filter .= '(samaccounttype='. $sAMAaccountType .')';
  507         }
  508         $filter .= '(cn=' . $search . '))';
  509         // Perform the search and grab all their details
  510         $fields = array("samaccountname", "description");
  511         $sr = ldap_search($this->adldap->getLdapConnection(), $this->adldap->getBaseDn(), $filter, $fields);
  512         $entries = ldap_get_entries($this->adldap->getLdapConnection(), $sr);
  513 
  514         $groupsArray = array();        
  515         for ($i=0; $i<$entries["count"]; $i++){
  516             if ($includeDescription && strlen($entries[$i]["description"][0]) > 0 ) {
  517                 $groupsArray[$entries[$i]["samaccountname"][0]] = $entries[$i]["description"][0];
  518             }
  519             else if ($includeDescription){
  520                 $groupsArray[$entries[$i]["samaccountname"][0]] = $entries[$i]["samaccountname"][0];
  521             }
  522             else {
  523                 array_push($groupsArray, $entries[$i]["samaccountname"][0]);
  524             }
  525         }
  526         if ($sorted) { 
  527             asort($groupsArray); 
  528         }
  529         return $groupsArray;
  530     }
  531     
  532     /**
  533     * Returns a complete list of all groups in AD
  534     * 
  535     * @param bool $includeDescription Whether to return a description
  536     * @param string $search Search parameters
  537     * @param bool $sorted Whether to sort the results
  538     * @return array
  539     */
  540     public function all($includeDescription = false, $search = "*", $sorted = true){
  541         $groupsArray = $this->search(null, $includeDescription, $search, $sorted);
  542         return $groupsArray;
  543     }
  544     
  545     /**
  546     * Returns a complete list of security groups in AD
  547     * 
  548     * @param bool $includeDescription Whether to return a description
  549     * @param string $search Search parameters
  550     * @param bool $sorted Whether to sort the results
  551     * @return array
  552     */
  553     public function allSecurity($includeDescription = false, $search = "*", $sorted = true){
  554         $groupsArray = $this->search(adLDAP::ADLDAP_SECURITY_GLOBAL_GROUP, $includeDescription, $search, $sorted);
  555         return $groupsArray;
  556     }
  557     
  558     /**
  559     * Returns a complete list of distribution lists in AD
  560     * 
  561     * @param bool $includeDescription Whether to return a description
  562     * @param string $search Search parameters
  563     * @param bool $sorted Whether to sort the results
  564     * @return array
  565     */
  566     public function allDistribution($includeDescription = false, $search = "*", $sorted = true){
  567         $groupsArray = $this->search(adLDAP::ADLDAP_DISTRIBUTION_GROUP, $includeDescription, $search, $sorted);
  568         return $groupsArray;
  569     }
  570     
  571     /**
  572     * Coping with AD not returning the primary group
  573     * http://support.microsoft.com/?kbid=321360 
  574     * 
  575     * This is a re-write based on code submitted by Bruce which prevents the 
  576     * need to search each security group to find the true primary group
  577     * 
  578     * @param string $gid Group ID
  579     * @param string $usersid User's Object SID
  580     * @return mixed
  581     */
  582     public function getPrimaryGroup($gid, $usersid)
  583     {
  584         if ($gid === NULL || $usersid === NULL) { return false; }
  585         $sr = false;
  586 
  587         $gsid = substr_replace($usersid, pack('V',$gid), strlen($usersid)-4,4);
  588         $filter = '(objectsid=' . $this->adldap->utilities()->getTextSID($gsid).')';
  589         $fields = array("samaccountname","distinguishedname");
  590         $sr = ldap_search($this->adldap->getLdapConnection(), $this->adldap->getBaseDn(), $filter, $fields);
  591         $entries = ldap_get_entries($this->adldap->getLdapConnection(), $sr);
  592 
  593         if (isset($entries[0]['distinguishedname'][0])) {
  594             return $entries[0]['distinguishedname'][0];
  595         }
  596         return false;
  597      }
  598      
  599      /**
  600     * Coping with AD not returning the primary group
  601     * http://support.microsoft.com/?kbid=321360 
  602     * 
  603     * For some reason it's not possible to search on primarygrouptoken=XXX
  604     * If someone can show otherwise, I'd like to know about it :)
  605     * this way is resource intensive and generally a pain in the @#%^
  606     * 
  607     * @deprecated deprecated since version 3.1, see get get_primary_group
  608     * @param string $gid Group ID
  609     * @return string
  610     */
  611     public function cn($gid){    
  612         if ($gid === NULL) { return false; }
  613         $sr = false;
  614         $r = '';
  615         
  616         $filter = "(&(objectCategory=group)(samaccounttype=" . adLDAP::ADLDAP_SECURITY_GLOBAL_GROUP . "))";
  617         $fields = array("primarygrouptoken", "samaccountname", "distinguishedname");
  618         $sr = ldap_search($this->adldap->getLdapConnection(), $this->adldap->getBaseDn(), $filter, $fields);
  619         $entries = ldap_get_entries($this->adldap->getLdapConnection(), $sr);
  620         
  621         for ($i=0; $i<$entries["count"]; $i++){
  622             if ($entries[$i]["primarygrouptoken"][0] == $gid) {
  623                 $r = $entries[$i]["distinguishedname"][0];
  624                 $i = $entries["count"];
  625             }
  626         }
  627 
  628         return $r;
  629     }
  630 }
  631 ?>