Java Code Examples for javax.naming.directory.Attribute#getAll()

The following examples show how to use javax.naming.directory.Attribute#getAll() . You can vote up the ones you like or vote down the ones you don't like, and go to the original project or source file by following the links above each example. You may check out the related API usage on the sidebar.
Example 1
Source File: LDAPCertStore.java    From jdk8u-dev-jdk with GNU General Public License v2.0 6 votes vote down vote up
/**
 * Get the values for the given attribute. If the attribute is null
 * or does not contain any values, a zero length byte array is
 * returned. NOTE that it is assumed that all values are byte arrays.
 */
private byte[][] getAttributeValues(Attribute attr)
        throws NamingException {
    byte[][] values;
    if (attr == null) {
        values = BB0;
    } else {
        values = new byte[attr.size()][];
        int i = 0;
        NamingEnumeration<?> enum_ = attr.getAll();
        while (enum_.hasMore()) {
            Object obj = enum_.next();
            if (debug != null) {
                if (obj instanceof String) {
                    debug.println("LDAPCertStore.getAttrValues() "
                        + "enum.next is a string!: " + obj);
                }
            }
            byte[] value = (byte[])obj;
            values[i++] = value;
        }
    }
    return values;
}
 
Example 2
Source File: LdapSender.java    From iaf with Apache License 2.0 6 votes vote down vote up
protected XmlBuilder attributesToXml(Attributes atts)
	throws NamingException {
	XmlBuilder attributesElem = new XmlBuilder("attributes");
	
	NamingEnumeration all = atts.getAll();
	while (all.hasMore()) {
		Attribute attribute = (Attribute) all.next();
		XmlBuilder attributeElem = new XmlBuilder("attribute");
		attributeElem.addAttribute("name", attribute.getID());
		if (attribute.size() == 1 && attribute.get() != null) {
			attributeElem.addAttribute("value", attribute.get().toString());
		} else {
			NamingEnumeration values = attribute.getAll();
			while (values.hasMore()) {
				Object value = values.next();
				XmlBuilder itemElem = new XmlBuilder("item");
				itemElem.addAttribute("value", value.toString());
				attributeElem.addSubElement(itemElem);
			}
		}
		attributesElem.addSubElement(attributeElem);
	}
	return attributesElem;
}
 
Example 3
Source File: LDAPCertStore.java    From hottub with GNU General Public License v2.0 6 votes vote down vote up
/**
 * Get the values for the given attribute. If the attribute is null
 * or does not contain any values, a zero length byte array is
 * returned. NOTE that it is assumed that all values are byte arrays.
 */
private byte[][] getAttributeValues(Attribute attr)
        throws NamingException {
    byte[][] values;
    if (attr == null) {
        values = BB0;
    } else {
        values = new byte[attr.size()][];
        int i = 0;
        NamingEnumeration<?> enum_ = attr.getAll();
        while (enum_.hasMore()) {
            Object obj = enum_.next();
            if (debug != null) {
                if (obj instanceof String) {
                    debug.println("LDAPCertStore.getAttrValues() "
                        + "enum.next is a string!: " + obj);
                }
            }
            byte[] value = (byte[])obj;
            values[i++] = value;
        }
    }
    return values;
}
 
Example 4
Source File: LdapAuthenticator.java    From onedev with MIT License 6 votes vote down vote up
@Nullable
private Collection<String> retrieveSshKeys(Attributes searchResultAttributes) {
	Attribute attribute = searchResultAttributes.get(getUserSshKeyAttribute());
	if (attribute != null) {
		Collection<String> sshKeys = new ArrayList<>();
		try {
			NamingEnumeration<?> ldapValues = attribute.getAll();
			while (ldapValues.hasMore()) {
				Object value = ldapValues.next();
				if (value instanceof String) 
					sshKeys.add((String) value);
				else 
					logger.error("SSH key from ldap is not a String");
			}

		} catch (NamingException e) {
			logger.error("Error retrieving SSH keys", e);
		}
		return sshKeys;
	} else {
		return null;
	}
}
 
Example 5
Source File: DnsClient.java    From ews-java-api with MIT License 5 votes vote down vote up
/**
 * Performs Dns query.
 *
 * @param <T>              the generic type
 * @param cls              DnsRecord Type
 * @param domain           the domain
 * @param dnsServerAddress IPAddress of DNS server to use (may be null)
 * @return DnsRecord The DNS record list (never null but may be empty)
 * @throws DnsException the dns exception
 */

public static <T extends DnsRecord> List<T> dnsQuery(Class<T> cls, String domain, String dnsServerAddress) throws
                                                                                                           DnsException {

  List<T> dnsRecordList = new ArrayList<T>();
  try {
    // Create initial context
    DirContext ictx = new InitialDirContext(getEnv(dnsServerAddress));

    // Retrieve SRV record context attribute for the specified domain
    Attributes contextAttributes = ictx.getAttributes(domain,
        new String[] {EWSConstants.SRVRECORD});
    if (contextAttributes != null) {
      NamingEnumeration<?> attributes = contextAttributes.getAll();
      if (attributes != null) {
        while (attributes.hasMore()) {
          Attribute attr = (Attribute) attributes.next();
          NamingEnumeration<?> srvValues = attr.getAll();
          if (srvValues != null) {
            while (srvValues.hasMore()) {
              T dnsRecord = cls.newInstance();

              // Loads the DNS SRV record
              dnsRecord.load((String) srvValues.next());
              dnsRecordList.add(dnsRecord);
            }
          }
        }
      }
    }
  } catch (NamingException ne) {
    throw new DnsException(ne.getMessage());
  } catch (Exception e) {
    throw new DnsException(e.getMessage());
  }
  return dnsRecordList;
}
 
Example 6
Source File: JNDIRealm.java    From tomcatsrc with Apache License 2.0 5 votes vote down vote up
/**
 * Add values of a specified attribute to a list
 *
 * @param attrId Attribute name
 * @param attrs Attributes containing the new values
 * @param values ArrayList containing values found so far
 *
 * @exception NamingException if a directory server error occurs
 */
private ArrayList<String> addAttributeValues(String attrId,
                                     Attributes attrs,
                                     ArrayList<String> values)
    throws NamingException{

    if (containerLog.isTraceEnabled())
        containerLog.trace("  retrieving values for attribute " + attrId);
    if (attrId == null || attrs == null)
        return values;
    if (values == null)
        values = new ArrayList<String>();
    Attribute attr = attrs.get(attrId);
    if (attr == null)
        return values;
    NamingEnumeration<?> e = attr.getAll();
    try {
        while(e.hasMore()) {
            String value = (String)e.next();
            values.add(value);
        }
    } catch (PartialResultException ex) {
        if (!adCompat)
            throw ex;
    } finally {
        e.close();
    }
    return values;
}
 
Example 7
Source File: DirContextAdapter.java    From spring-ldap with Apache License 2.0 5 votes vote down vote up
private void collectModifications(Attribute originalAttr,
		Attribute changedAttr, List<ModificationItem> modificationList)
		throws NamingException {

	Attribute originalClone = (Attribute) originalAttr.clone();
	Attribute addedValuesAttribute = new NameAwareAttribute(originalAttr
			.getID());

       NamingEnumeration<?> allValues = changedAttr.getAll();
       while(allValues.hasMoreElements()) {
           Object attributeValue = allValues.nextElement();
           if (!originalClone.remove(attributeValue)) {
               addedValuesAttribute.add(attributeValue);
           }
       }

       // We have now traversed and removed all values from the original that
       // were also present in the new values. The remaining values in the
       // original must be the ones that were removed.
       if(originalClone.size() > 0 && originalClone.size() == originalAttr.size()) {
           // This is actually a complete replacement of the attribute values.
           // Fall back to REPLACE
           modificationList.add(new ModificationItem(DirContext.REPLACE_ATTRIBUTE,
                   addedValuesAttribute));
       } else {
           if (originalClone.size() > 0) {
               modificationList.add(new ModificationItem(
                       DirContext.REMOVE_ATTRIBUTE, originalClone));
           }

           if (addedValuesAttribute.size() > 0) {
               modificationList.add(new ModificationItem(DirContext.ADD_ATTRIBUTE,
                       addedValuesAttribute));
           }
       }
}
 
Example 8
Source File: LDAPInput.java    From pentaho-kettle with Apache License 2.0 5 votes vote down vote up
private String extractString( Attribute attr ) throws Exception {
  StringBuilder attrStr = new StringBuilder();
  for ( NamingEnumeration<?> eattr = attr.getAll(); eattr.hasMore(); ) {
    if ( attrStr.length() > 0 ) {
      attrStr.append( data.multi_valuedFieldSeparator );
    }
    attrStr.append( eattr.next().toString() );
  }
  return attrStr.toString();
}
 
Example 9
Source File: LDAPLoginManagerImpl.java    From olat with Apache License 2.0 5 votes vote down vote up
private boolean isPagedResultControlSupported(final LdapContext ctx) {
    try {
        final SearchControls ctl = new SearchControls();
        ctl.setReturningAttributes(new String[] { "supportedControl" });
        ctl.setSearchScope(SearchControls.OBJECT_SCOPE);

        /* search for the rootDSE object */
        final NamingEnumeration<SearchResult> results = ctx.search("", "(objectClass=*)", ctl);

        while (results.hasMore()) {
            final SearchResult entry = results.next();
            final NamingEnumeration<? extends Attribute> attrs = entry.getAttributes().getAll();
            while (attrs.hasMore()) {
                final Attribute attr = attrs.next();
                final NamingEnumeration<?> vals = attr.getAll();
                while (vals.hasMore()) {
                    final String value = (String) vals.next();
                    if (value.equals(PAGED_RESULT_CONTROL_OID)) {
                        return true;
                    }
                }
            }
        }
        return false;
    } catch (final Exception e) {
        log.error("Exception when trying to know if the server support paged results.", e);
        return false;
    }
}
 
Example 10
Source File: LdapClient.java    From iaf with Apache License 2.0 5 votes vote down vote up
public void mapMultiValuedAttribute(NamingEnumeration<SearchResult> searchResultEnum, Callback<Attribute,Object> callback) throws NamingException {
  	try {
   	while (searchResultEnum.hasMore()) {
   		Attributes attributes=searchResultEnum.next().getAttributes();
   		NamingEnumeration<? extends Attribute> attrenum=attributes.getAll();
   		try {
   			while (attrenum.hasMore()) {
   				Attribute attr=attrenum.next();
   	    		NamingEnumeration<?> multivalueattribute=attr.getAll();
   	    		try {
   	    			while (multivalueattribute.hasMore()) {
   	    				callback.handle(attr,multivalueattribute.next());
   	    			}
   	    		} finally {
   	    			multivalueattribute.close();
   	    		}
   			}
   		} finally {
   			attrenum.close();
   		}
   	}
} catch(PartialResultException e) {
	if (log.isDebugEnabled()) log.debug("ignoring Exception: "+e); 
} finally {
	searchResultEnum.close();
}
  }
 
Example 11
Source File: LdapUtils.java    From cloudstack with Apache License 2.0 5 votes vote down vote up
public static List<String> getAttributeValues(final Attributes attributes, final String attributeName) throws NamingException {
    ArrayList<String> memberships = new ArrayList<>();
    final Attribute attribute = attributes.get(attributeName);
    if (attribute != null) {
        NamingEnumeration<?> values = attribute.getAll();
        while(values.hasMore()) {
            memberships.add(String.valueOf(values.next()));
        }
    }
    return memberships;
}
 
Example 12
Source File: JNDIProviderImpl.java    From ldapchai with GNU Lesser General Public License v2.1 5 votes vote down vote up
private Map<String, List<String>> parseAttributeValues(
        final NamingEnumeration attributeEnum,
        final boolean returnAllValues
)
        throws NamingException
{
    final Map<String, List<String>> attrValues = new HashMap<String, List<String>>();
    if ( attributeEnum != null && attributeEnum.hasMore() )
    {
        while ( attributeEnum.hasMore() )
        {
            final Attribute loopAttribute = ( Attribute ) attributeEnum.next();
            final String attrName = loopAttribute.getID();
            final List<String> valueList = new ArrayList<String>();
            for ( NamingEnumeration attrValueEnum = loopAttribute.getAll(); attrValueEnum.hasMore(); )
            {
                final Object value = attrValueEnum.next();
                valueList.add( value.toString() );
                if ( !returnAllValues )
                {
                    attrValueEnum.close();
                    break;
                }
            }
            attrValues.put( attrName, Collections.unmodifiableList( valueList ) );
        }
    }
    return Collections.unmodifiableMap( attrValues );
}
 
Example 13
Source File: MailValidation.java    From hop with Apache License 2.0 5 votes vote down vote up
private static ArrayList<String> getMX( String hostName ) throws NamingException {
  // Perform a DNS lookup for MX records in the domain
  Hashtable<String, String> env = new Hashtable<String, String>();
  env.put( "java.naming.factory.initial", "com.sun.jndi.dns.DnsContextFactory" );
  DirContext ictx = new InitialDirContext( env );
  Attributes attrs = ictx.getAttributes( hostName, new String[] { "MX" } );
  Attribute attr = attrs.get( "MX" );

  // if we don't have an MX record, try the machine itself
  if ( ( attr == null ) || ( attr.size() == 0 ) ) {
    attrs = ictx.getAttributes( hostName, new String[] { "A" } );
    attr = attrs.get( "A" );
    if ( attr == null ) {
      throw new NamingException( BaseMessages.getString( PKG, "MailValidator.NoMatchName", hostName ) );
    }
  }

  // Huzzah! we have machines to try. Return them as an array list
  // NOTE: We SHOULD take the preference into account to be absolutely
  // correct. This is left as an exercise for anyone who cares.
  ArrayList<String> res = new ArrayList<String>();
  NamingEnumeration<?> en = attr.getAll();

  while ( en.hasMore() ) {
    String x = (String) en.next();
    String[] f = x.split( " " );
    if ( f[ 1 ].endsWith( "." ) ) {
      f[ 1 ] = f[ 1 ].substring( 0, ( f[ 1 ].length() - 1 ) );
    }
    res.add( f[ 1 ] );
  }
  return res;
}
 
Example 14
Source File: ReadOnlyLDAPGroupRestriction.java    From james-project with Apache License 2.0 5 votes vote down vote up
/**
 * Extracts the DNs for members of the group with the given LDAP context
 * attributes. This is achieved by extracting all the values of the LDAP
 * attribute, with name equivalent to the field value
 * {@link #memberAttribute}, from the attributes collection.
 *
 * @param groupAttributes The attributes taken from the group's LDAP context.
 * @return A collection of distinguished-names for the users belonging to
 *         the group with the specified attributes.
 * @throws NamingException Propagated from underlying LDAP communication layer.
 */
private Collection<String> extractMembers(Attributes groupAttributes) throws NamingException {
    Collection<String> result = new ArrayList<>();
    Attribute members = groupAttributes.get(memberAttribute);
    NamingEnumeration<?> memberDNs = members.getAll();

    while (memberDNs.hasMore()) {
        result.add(memberDNs.next().toString());
    }

    return result;
}
 
Example 15
Source File: OpenLdapUserManagerImpl.java    From cloudstack with Apache License 2.0 5 votes vote down vote up
@Override
public List<LdapUser> getUsersInGroup(String groupName, LdapContext context, Long domainId) throws NamingException {
    String attributeName = _ldapConfiguration.getGroupUniqueMemberAttribute(domainId);
    final SearchControls controls = new SearchControls();
    controls.setSearchScope(_ldapConfiguration.getScope());
    controls.setReturningAttributes(new String[] {attributeName});

    NamingEnumeration<SearchResult> result = context.search(_ldapConfiguration.getBaseDn(domainId), generateGroupSearchFilter(groupName, domainId), controls);

    final List<LdapUser> users = new ArrayList<LdapUser>();
    //Expecting only one result which has all the users
    if (result.hasMoreElements()) {
        Attribute attribute = result.nextElement().getAttributes().get(attributeName);
        NamingEnumeration<?> values = attribute.getAll();

        while (values.hasMoreElements()) {
            String userdn = String.valueOf(values.nextElement());
            try{
                users.add(getUserForDn(userdn, context, domainId));
            } catch (NamingException e){
                LOGGER.info("Userdn: " + userdn + " Not Found:: Exception message: " + e.getMessage());
            }
        }
    }

    Collections.sort(users);

    return users;
}
 
Example 16
Source File: DirContextURLConnection.java    From tomcatsrc with Apache License 2.0 4 votes vote down vote up
/**
 * Returns an unmodifiable Map of the header fields.
 */
@Override
public Map<String,List<String>> getHeaderFields() {

  if (!connected) {
      // Try to connect (silently)
      try {
          connect();
      } catch (IOException e) {
          //Ignore
      }
  }

  if (attributes == null)
      return (Collections.emptyMap());

  HashMap<String,List<String>> headerFields =
      new HashMap<String,List<String>>(attributes.size());
  NamingEnumeration<String> attributeEnum = attributes.getIDs();
  try {
      while (attributeEnum.hasMore()) {
          String attributeID = attributeEnum.next();
          Attribute attribute = attributes.get(attributeID);
          if (attribute == null) continue;
          ArrayList<String> attributeValueList =
              new ArrayList<String>(attribute.size());
          NamingEnumeration<?> attributeValues = attribute.getAll();
          while (attributeValues.hasMore()) {
              Object attrValue = attributeValues.next();
              attributeValueList.add(getHeaderValueAsString(attrValue));
          }
          attributeValueList.trimToSize(); // should be a no-op if attribute.size() didn't lie
          headerFields.put(attributeID, Collections.unmodifiableList(attributeValueList));
      }
  } catch (NamingException ne) {
        // Shouldn't happen
  }

  return Collections.unmodifiableMap(headerFields);

}
 
Example 17
Source File: DefaultObjectDirectoryMapper.java    From spring-ldap with Apache License 2.0 4 votes vote down vote up
@Override
public <T> T mapFromLdapDataEntry(LdapDataEntry context, Class<T> clazz) {
    if (LOG.isDebugEnabled()) {
        LOG.debug(String.format("Converting to Java Entry class %1$s from %2$s", clazz, context));
    }

    // The Java representation of the LDAP entry
    T result;

    ObjectMetaData metaData=getEntityData(clazz).metaData;

    try {
        // The result class must have a zero argument constructor
        result = clazz.newInstance();

        // Build a map of JNDI attribute names to values
        Map<CaseIgnoreString, Attribute> attributeValueMap = new HashMap<CaseIgnoreString, Attribute>();
        // Get a NamingEnumeration to loop through the JNDI attributes in the entry
        Attributes attributes = context.getAttributes();
        NamingEnumeration<? extends Attribute> attributesEnumeration = attributes.getAll();
        // Loop through all of the JNDI attributes
        while (attributesEnumeration.hasMoreElements()) {
            Attribute currentAttribute = attributesEnumeration.nextElement();
            // Add the current attribute to the map keyed on the lowercased (case indep) id of the attribute
            attributeValueMap.put(new CaseIgnoreString(currentAttribute.getID()), currentAttribute);
        }


        // If this is the objectclass attribute then check that values correspond to the metadata we have
        // for the Java representation
        Attribute ocAttribute = attributeValueMap.get(OBJECT_CLASS_ATTRIBUTE_CI);
        if (ocAttribute != null) {
            // Get all object class values from the JNDI attribute
            Set<CaseIgnoreString> objectClassesFromJndi = new HashSet<CaseIgnoreString>();
            NamingEnumeration<?> objectClassesFromJndiEnum = ocAttribute.getAll();
            while (objectClassesFromJndiEnum.hasMoreElements()) {
                objectClassesFromJndi.add(new CaseIgnoreString((String)objectClassesFromJndiEnum.nextElement()));
            }
            // OK - checks its the same as the meta-data we have
            if(!collectionContainsAll(objectClassesFromJndi, metaData.getObjectClasses())) {
                return null;
            }
        } else {
            throw new InvalidEntryException(String.format("No object classes were returned for class %1$s",
                    clazz.getName()));
        }

        // Now loop through all the fields in the Java representation populating it with values from the
        // attributeValueMap
        for (Field field : metaData) {
            // Get the current field
            AttributeMetaData attributeInfo = metaData.getAttribute(field);
            // We deal with the Id field specially
            Name dn = context.getDn();
            if (!attributeInfo.isTransient() && !attributeInfo.isId()) {
                // Not the ID - but is is multi valued?
                if (!attributeInfo.isCollection()) {
                    // No - its single valued, grab the JNDI attribute that corresponds to the metadata on the
                    // current field
                    populateSingleValueField(result, attributeValueMap, field, attributeInfo);
                } else {
                    // We are dealing with a multi valued attribute
                    populateMultiValueField(result, attributeValueMap, field, attributeInfo);
                }
            } else if(attributeInfo.isId()) { // The id field
                field.set(result, converterManager.convert(dn, attributeInfo.getSyntax(),
                        attributeInfo.getValueClass()));
            }

            DnAttribute dnAttribute = attributeInfo.getDnAttribute();
            if(dnAttribute != null) {
                String dnValue;
                int index = dnAttribute.index();

                if(index != -1) {
                    dnValue = LdapUtils.getStringValue(dn, index);
                } else {
                    dnValue = LdapUtils.getStringValue(dn, dnAttribute.value());
                }
                field.set(result, dnValue);
            }
        }
    } catch (NamingException ne) {
        throw new InvalidEntryException(String.format("Problem creating %1$s from LDAP Entry %2$s",
                clazz, context), ne);
    } catch (IllegalAccessException iae) {
        throw new InvalidEntryException(String.format(
                "Could not create an instance of %1$s could not access field", clazz.getName()), iae);
    } catch (InstantiationException ie) {
        throw new InvalidEntryException(String.format("Could not instantiate %1$s", clazz), ie);
    }

    if (LOG.isDebugEnabled()) {
        LOG.debug(String.format("Converted object - %1$s", result));
    }

    return result;
}
 
Example 18
Source File: AbstractContextSource.java    From spring-ldap with Apache License 2.0 4 votes vote down vote up
static String formatForUrl(LdapName ldapName) {
    StringBuilder sb = new StringBuilder();
    ListIterator<Rdn> it = ldapName.getRdns().listIterator(ldapName.size());
    while (it.hasPrevious()) {
        Rdn component = it.previous();

        Attributes attributes = component.toAttributes();

        // Loop through all attribute of the rdn (usually just one, but more are supported by RFC)
        NamingEnumeration<? extends Attribute> allAttributes = attributes.getAll();
        while(allAttributes.hasMoreElements()) {
            Attribute oneAttribute = allAttributes.nextElement();
            String encodedAttributeName = nameEncodeForUrl(oneAttribute.getID());

            // Loop through all values of the attribute (usually just one, but more are supported by RFC)
            NamingEnumeration <?> allValues;
            try {
                allValues = oneAttribute.getAll();
            } catch (NamingException e) {
                throw new UncategorizedLdapException("Unexpected error occurred formatting base URL", e);
            }

            while(allValues.hasMoreElements()) {
                sb.append(encodedAttributeName).append('=');

                Object oneValue = allValues.nextElement();
                if (oneValue instanceof String) {
                    String oneString = (String) oneValue;
                    sb.append(nameEncodeForUrl(oneString));
                } else {
                    throw new IllegalArgumentException("Binary attributes not supported for base URL");
                }

                if(allValues.hasMoreElements()) {
                    sb.append('+');
                }
            }
            if(allAttributes.hasMoreElements()) {
                sb.append('+');
            }
        }

        if(it.hasPrevious()) {
            sb.append(',');
        }
    }
    return sb.toString();
}
 
Example 19
Source File: GUISSOLdapClient.java    From uavstack with Apache License 2.0 4 votes vote down vote up
@SuppressWarnings("rawtypes")
private String formatEmailInfo(Attribute attr) {

    if (null == attr) {
        return "";
    }

    StringBuilder values = new StringBuilder();
    boolean isFormat = false;
    try {

        String formatS = "=";
        String attrId = attr.getID();
        String groupKey = ldapConfig.get("groupKey");
        String groupTag = ldapConfig.get("groupTag");
        for (NamingEnumeration vals = attr.getAll(); vals.hasMore();) {
            String strValue = vals.next().toString();
            if (groupKey.equals(attrId) && strValue.indexOf(groupTag) >= 0) {

                values.append(",");
                isFormat = true;

                if (strValue.indexOf(formatS) == -1) {
                    values.append(strValue);
                    continue;
                }

                int begin = strValue.indexOf(formatS) + formatS.length();
                int end = strValue.indexOf(",");
                values.append(strValue.substring(begin, end));

            }
        }
    }
    catch (Exception e) {
        loggerError("formatEmailInfo 555", "", e);
        throw new ApphubException(e);
    }
    /**
     * 去除第一个逗号
     */
    String result = "";
    if (isFormat) {
        result = values.toString().substring(1);
    }
    return result;
}
 
Example 20
Source File: LdapUserProvider.java    From Openfire with Apache License 2.0 4 votes vote down vote up
@Override
public User loadUser(String username) throws UserNotFoundException {
    if(username.contains("@")) {
        if (!XMPPServer.getInstance().isLocal(new JID(username))) {
            throw new UserNotFoundException("Cannot load user of remote server: " + username);
        }
        username = username.substring(0,username.lastIndexOf("@"));
    }
    // Un-escape username.
    username = JID.unescapeNode(username);
    DirContext ctx = null;
    try {
        Rdn[] userRDN = manager.findUserRDN(username);
        // Load record.
        final List<String> attributes = new ArrayList<>();
        attributes.add( manager.getUsernameField() );
        attributes.addAll( manager.getNameField().getFields() );
        attributes.add( manager.getEmailField() );
        attributes.add( "createTimestamp" );
        attributes.add( "modifyTimestamp" );

        ctx = manager.getContext(manager.getUsersBaseDN(username));
        Attributes attrs = ctx.getAttributes(LdapManager.escapeForJNDI(userRDN), attributes.toArray(new String[0]));
        String name = LdapUserTester.getPropertyValue(manager.getNameField(), attrs);
        String email = null;
        Attribute emailField = attrs.get(manager.getEmailField());
        if (emailField != null) {
            email = (String)emailField.get();
        }
        Date creationDate = new Date();
        Attribute creationDateField = attrs.get("createTimestamp");
        if (creationDateField != null && "".equals(((String) creationDateField.get()).trim())) {
            creationDate = parseLDAPDate((String) creationDateField.get());
        }
        Date modificationDate = new Date();
        Attribute modificationDateField = attrs.get("modifyTimestamp");
        if (modificationDateField != null && "".equals(((String) modificationDateField.get()).trim())) {
            modificationDate = parseLDAPDate((String)modificationDateField.get());
        }
        // Escape the username so that it can be used as a JID.
        username = JID.escapeNode(username);
        
        // As defined by RFC5803.
        Attribute authPassword = attrs.get("authPassword");
        User user = new User(username, name, email, creationDate, modificationDate);
        if (manager.isFindUsersFromGroupsEnabled() && GroupManager.getInstance().getGroups(user).isEmpty()) {
            throw new UserNotFoundException("User exists in LDAP but is not a member of any Openfire groups");
        }
        if (authPassword != null) {
            // The authPassword attribute can be multivalued.
            // Not sure if this is the right API to loop through them.
            NamingEnumeration values = authPassword.getAll();
            while (values.hasMore()) {
                Attribute authPasswordValue = (Attribute) values.next();
                String[] parts = ((String) authPasswordValue.get()).split("$");
                String[] authInfo = parts[1].split(":");
                String[] authValue = parts[2].split(":");

                String scheme = parts[0].trim();

                // We only support SCRAM-SHA-1 at the moment.
                if ("SCRAM-SHA-1".equals(scheme)) {
                    int iterations = Integer.valueOf(authInfo[0].trim());
                    String salt = authInfo[1].trim();
                    String storedKey = authValue[0].trim();
                    String serverKey = authValue[1].trim();
                    
                    user.setSalt(salt);
                    user.setStoredKey(storedKey);
                    user.setServerKey(serverKey);
                    user.setIterations(iterations);
                    
                    break;
                }
            }
        }
        return user;
    }
    catch (Exception e) {
        throw new UserNotFoundException(e);
    }
    finally {
        try {
            if (ctx != null) {
                ctx.close();
            }
        }
        catch (Exception ex) {
            Log.debug( "An exception occurred while closing the LDAP context after attempting to load user {}", username, ex);
        }
    }
}