示例#1
0
 /**
  * Gets an associative array of AttributeType objects for the specified
  * server. Each array entry's key is the name of the attributeType
  * in lower-case and the value is an AttributeType object.
  *
  * @param string $dn (optional) It is easier to fetch schema if a DN is provided
  *             which defines the subschemaSubEntry attribute (all entries should).
  *
  * @return array An array of AttributeType objects.
  */
 public function SchemaAttributes($method = null, $dn = '')
 {
     if (DEBUG_ENABLED && (($fargs = func_get_args()) || ($fargs = 'NOARGS'))) {
         debug_log('Entered (%%)', 25, 0, __FILE__, __LINE__, __METHOD__, $fargs);
     }
     # Set default return
     $return = null;
     if ($return = get_cached_item($this->index, 'schema', 'attributes')) {
         if (DEBUG_ENABLED) {
             debug_log('(): Returning CACHED [%s] (%s)', 25, 0, __FILE__, __LINE__, __METHOD__, $this->index, 'attributes');
         }
         return $return;
     }
     $raw = $this->getRawSchema($method, 'attributeTypes', $dn);
     if ($raw) {
         # build the array of attribueTypes
         $syntaxes = $this->SchemaSyntaxes($method, $dn);
         $attrs = array();
         /**
          * bug 856832: create two arrays - one indexed by name (the standard
          * $attrs array above) and one indexed by oid (the new $attrs_oid array
          * below). This will help for directory servers, like IBM's, that use OIDs
          * in their attribute definitions of SUP, etc
          */
         $attrs_oid = array();
         foreach ($raw as $line) {
             if (is_null($line) || !strlen($line)) {
                 continue;
             }
             $attr = new AttributeType($line);
             if (isset($syntaxes[$attr->getSyntaxOID()])) {
                 $syntax = $syntaxes[$attr->getSyntaxOID()];
                 $attr->setType($syntax->getDescription());
             }
             $attrs[$attr->getName()] = $attr;
             /**
              * bug 856832: create an entry in the $attrs_oid array too. This
              * will be a ref to the $attrs entry for maintenance and performance
              * reasons
              */
             $attrs_oid[$attr->getOID()] =& $attrs[$attr->getName()];
         }
         # go back and add data from aliased attributeTypes
         foreach ($attrs as $name => $attr) {
             $aliases = $attr->getAliases();
             if (is_array($aliases) && count($aliases) > 0) {
                 /* foreach of the attribute's aliases, create a new entry in the attrs array
                  * with its name set to the alias name, and all other data copied.*/
                 foreach ($aliases as $alias_attr_name) {
                     $new_attr = clone $attr;
                     $new_attr->setName($alias_attr_name);
                     $new_attr->addAlias($attr->getName(false));
                     $new_attr->removeAlias($alias_attr_name);
                     $new_attr_key = strtolower($alias_attr_name);
                     $attrs[$new_attr_key] = $new_attr;
                 }
             }
         }
         # go back and add any inherited descriptions from parent attributes (ie, cn inherits name)
         foreach ($attrs as $key => $attr) {
             $sup_attr_name = $attr->getSupAttribute();
             $sup_attr = null;
             if (trim($sup_attr_name)) {
                 /* This loop really should traverse infinite levels of inheritance (SUP) for attributeTypes,
                  * but just in case we get carried away, stop at 100. This shouldn't happen, but for
                  * some weird reason, we have had someone report that it has happened. Oh well.*/
                 $i = 0;
                 while ($i++ < 100) {
                     if (isset($attrs_oid[$sup_attr_name])) {
                         $attr->setSupAttribute($attrs_oid[$sup_attr_name]->getName());
                         $sup_attr_name = $attr->getSupAttribute();
                     }
                     if (!isset($attrs[strtolower($sup_attr_name)])) {
                         error(sprintf('Schema error: attributeType "%s" inherits from "%s", but attributeType "%s" does not exist.', $attr->getName(), $sup_attr_name, $sup_attr_name), 'error', 'index.php');
                         return;
                     }
                     $sup_attr = $attrs[strtolower($sup_attr_name)];
                     $sup_attr_name = $sup_attr->getSupAttribute();
                     # Does this superior attributeType not have a superior attributeType?
                     if (is_null($sup_attr_name) || strlen(trim($sup_attr_name)) == 0) {
                         /* Since this attribute's superior attribute does not have another superior
                          * attribute, clone its properties for this attribute. Then, replace
                          * those cloned values with those that can be explicitly set by the child
                          * attribute attr). Save those few properties which the child can set here:*/
                         $tmp_name = $attr->getName(false);
                         $tmp_oid = $attr->getOID();
                         $tmp_sup = $attr->getSupAttribute();
                         $tmp_aliases = $attr->getAliases();
                         $tmp_single_val = $attr->getIsSingleValue();
                         $tmp_desc = $attr->getDescription();
                         /* clone the SUP attributeType and populate those values
                          * that were set by the child attributeType */
                         $attr = clone $sup_attr;
                         $attr->setOID($tmp_oid);
                         $attr->setName($tmp_name);
                         $attr->setSupAttribute($tmp_sup);
                         $attr->setAliases($tmp_aliases);
                         $attr->setDescription($tmp_desc);
                         /* only overwrite the SINGLE-VALUE property if the child explicitly sets it
                          * (note: All LDAP attributes default to multi-value if not explicitly set SINGLE-VALUE) */
                         if ($tmp_single_val) {
                             $attr->setIsSingleValue(true);
                         }
                         /* replace this attribute in the attrs array now that we have populated
                         		 new values therein */
                         $attrs[$key] = $attr;
                         # very important: break out after we are done with this attribute
                         $sup_attr_name = null;
                         $sup_attr = null;
                         break;
                     }
                 }
             }
         }
         ksort($attrs);
         # Add the used in and required_by values.
         $socs = $this->SchemaObjectClasses($method);
         if (!is_array($socs)) {
             return array();
         }
         foreach ($socs as $object_class) {
             $must_attrs = $object_class->getMustAttrNames();
             $may_attrs = $object_class->getMayAttrNames();
             $oclass_attrs = array_unique(array_merge($must_attrs, $may_attrs));
             # Add Used In.
             foreach ($oclass_attrs as $attr_name) {
                 if (isset($attrs[strtolower($attr_name)])) {
                     $attrs[strtolower($attr_name)]->addUsedInObjectClass($object_class->getName(false));
                 }
             }
             # Add Required By.
             foreach ($must_attrs as $attr_name) {
                 if (isset($attrs[strtolower($attr_name)])) {
                     $attrs[strtolower($attr_name)]->addRequiredByObjectClass($object_class->getName(false));
                 }
             }
             # Force May
             foreach ($object_class->getForceMayAttrs() as $attr_name) {
                 if (isset($attrs[strtolower($attr_name->name)])) {
                     $attrs[strtolower($attr_name->name)]->setForceMay();
                 }
             }
         }
         $return = $attrs;
         # cache the schema to prevent multiple schema fetches from LDAP server
         set_cached_item($this->index, 'schema', 'attributes', $return);
     }
     if (DEBUG_ENABLED) {
         debug_log('Returning (%s)', 25, 0, __FILE__, __LINE__, __METHOD__, $return);
     }
     return $return;
 }