Example usage for javax.naming.directory Attribute size

List of usage examples for javax.naming.directory Attribute size

Introduction

In this page you can find the example usage for javax.naming.directory Attribute size.

Prototype

int size();

Source Link

Document

Retrieves the number of values in this attribute.

Usage

From source file:org.talend.dataquality.email.checkerImpl.CallbackMailServerCheckerImpl.java

private List<String> getMX(String hostName) throws NamingException {
    // Perform a DNS lookup for MX records in the domain
    Attributes attrs = ictx.getAttributes(hostName, new String[] { "MX" }); //$NON-NLS-1$
    Attribute attr = attrs.get("MX"); //$NON-NLS-1$
    List<String> res = new ArrayList<String>();

    // 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" }); //$NON-NLS-1$
        attr = attrs.get("A"); //$NON-NLS-1$
        if (attr == null) {
            if (LOG.isInfoEnabled()) {
                LOG.info(HEADER + "No match for hostname '" + hostName + "'"); //$NON-NLS-1$ //$NON-NLS-2$
            }//  w w w  .  jav  a  2 s.  c o m
            return res;
        }
    }
    // we have machines to try. Return them as an array list
    NamingEnumeration<?> en = attr.getAll();
    Map<Integer, String> map = new TreeMap<Integer, String>();

    while (en.hasMore()) {
        String mailhost;
        String x = (String) en.next();
        String f[] = x.split(" "); //$NON-NLS-1$
        Integer key = 0;
        if (f.length == 1) {
            mailhost = f[0];
        } else if (f[1].endsWith(".")) { //$NON-NLS-1$
            mailhost = f[1].substring(0, f[1].length() - 1);
            key = Integer.valueOf(f[0]);
        } else {
            mailhost = f[1];
            key = Integer.valueOf(f[0]);
        }
        map.put(key, mailhost);
    }
    // NOTE: We SHOULD take the preference into account to be absolutely
    // correct.
    Iterator<Integer> keyInterator = map.keySet().iterator();
    while (keyInterator.hasNext()) {
        res.add(map.get(keyInterator.next()));
    }
    return res;
}

From source file:net.e2.bw.servicereg.ldap.ServiceInstanceLdapService.java

/** Converts a search result to a service instance entry */
private CachedServiceInstance toServiceInstance(SearchResult sr) {

    if (sr == null) {
        return null;
    }//from  w  w w .ja  v  a  2 s. c om

    Attributes attrs = sr.getAttributes();
    String serviceInstanceId = getAttributeValue(attrs, "uid");
    String name = getAttributeValue(attrs, "cn");
    String summary = getAttributeValue(attrs, "description");
    String organizationId = extractGroupId(getAttributeValue(attrs, "serviceOrganization"));
    String serviceSpecificationId = extractServiceSpecificationId(
            getAttributeValue(attrs, "serviceSpecification"));
    List<Area> coverage = decompressCoverage(getAttributeValue(attrs, "serviceCoverage"));

    List<ServiceEndpoint> endpoints = new ArrayList<>();
    Attribute endpointAttr = attrs.get("serviceEndpoint");
    for (int i = 0; endpointAttr != null && i < endpointAttr.size(); ++i) {
        try {
            endpoints.add(new ServiceEndpoint((String) endpointAttr.get(i)));
        } catch (Exception ignored) {
        }
    }

    Map<String, List<String>> roleUserMap = getRoleUsers(getServiceInstanceDN(serviceInstanceId));

    return new CachedServiceInstance(serviceInstanceId, organizationId, serviceSpecificationId, name, summary,
            coverage, endpoints, roleUserMap);
}

From source file:com.liferay.portal.security.ldap.internal.exportimport.LDAPUserExporterImpl.java

@Override
public void exportUser(long userId, long userGroupId, UserOperation userOperation) throws Exception {

    User user = _userLocalService.getUser(userId);

    long companyId = user.getCompanyId();

    StopWatch stopWatch = new StopWatch();

    if (_log.isDebugEnabled()) {
        stopWatch.start();/*from   w w  w  .j ava 2 s.co  m*/

        _log.debug(StringBundler.concat("Exporting user ", String.valueOf(user), " in user group ",
                String.valueOf(userGroupId)));
    }

    if (!_ldapSettings.isExportEnabled(companyId) || !_ldapSettings.isExportGroupEnabled(companyId)) {

        return;
    }

    long ldapServerId = _portalLDAP.getLdapServerId(companyId, user.getScreenName(), user.getEmailAddress());

    LdapContext ldapContext = _portalLDAP.getContext(ldapServerId, companyId);

    if (ldapContext == null) {
        return;
    }

    UserGroup userGroup = _userGroupLocalService.getUserGroup(userGroupId);

    Properties groupMappings = _ldapSettings.getGroupMappings(ldapServerId, companyId);
    Properties userMappings = _ldapSettings.getUserMappings(ldapServerId, companyId);

    Binding binding = _portalLDAP.getGroup(ldapServerId, companyId, userGroup.getName());

    if (binding == null) {
        if (userOperation == UserOperation.ADD) {
            addGroup(ldapServerId, ldapContext, userGroup, user, groupMappings, userMappings);
        } else {
            if (_log.isWarnEnabled()) {
                _log.warn("Unable to get or add LDAP bindings for user group " + userGroup.getName());
            }
        }

        return;
    }

    try {
        Name name = new CompositeName();

        name.add(binding.getNameInNamespace());

        Modifications modifications = _portalToLDAPConverter.getLDAPGroupModifications(ldapServerId, userGroup,
                user, groupMappings, userMappings, userOperation);

        ModificationItem[] modificationItems = modifications.getItems();

        ldapContext.modifyAttributes(name, modificationItems);
    } catch (SchemaViolationException sve) {
        if (_log.isInfoEnabled()) {
            _log.info("Unable to update LDAP bindings for user group " + userGroup.getName(), sve);
        }

        String fullGroupDN = binding.getNameInNamespace();

        Attributes attributes = _portalLDAP.getGroupAttributes(ldapServerId, companyId, ldapContext,
                fullGroupDN, true);

        Attribute groupMembers = attributes.get(groupMappings.getProperty(GroupConverterKeys.USER));

        if ((groupMembers != null) && (groupMembers.size() == 1)) {
            ldapContext.unbind(fullGroupDN);
        }
    } finally {
        if (ldapContext != null) {
            ldapContext.close();
        }

        if (_log.isDebugEnabled()) {
            _log.debug(StringBundler.concat("Finished exporting user ", String.valueOf(user), " in user group ",
                    String.valueOf(userGroupId), " in ", String.valueOf(stopWatch.getTime()), "ms"));
        }
    }
}

From source file:com.alfaariss.oa.engine.user.provisioning.storage.external.jndi.JNDIExternalStorage.java

/**
 * Returns the values of the specified fields for the supplied id. 
 * @see IExternalStorage#getFields(java.lang.String, java.util.List)
 *//*from  w w w.  java2 s .  c  o m*/
public Hashtable<String, Object> getFields(String id, List<String> fields) throws UserException {
    Hashtable<String, Object> htReturn = new Hashtable<String, Object>();
    DirContext oDirContext = null;
    NamingEnumeration oNamingEnumeration = null;
    try {
        try {
            oDirContext = new InitialDirContext(_htJNDIEnvironment);
        } catch (NamingException e) {
            _logger.error("Could not create the connection: " + _htJNDIEnvironment);
            throw new UserException(SystemErrors.ERROR_RESOURCE_CONNECT, e);
        }

        SearchControls oScope = new SearchControls();
        oScope.setSearchScope(SearchControls.SUBTREE_SCOPE);
        String[] saFields = fields.toArray(new String[0]);
        oScope.setReturningAttributes(saFields);

        String searchFilter = resolveSearchQuery(id);
        try {
            oNamingEnumeration = oDirContext.search(_sDNBase, searchFilter, oScope);
        } catch (InvalidSearchFilterException e) {
            StringBuffer sbFailed = new StringBuffer("Wrong filter: ");
            sbFailed.append(searchFilter);
            sbFailed.append(" while searching for attributes '");
            sbFailed.append(fields);
            sbFailed.append("' for id: ");
            sbFailed.append(id);
            _logger.error(sbFailed.toString(), e);
            throw new UserException(SystemErrors.ERROR_RESOURCE_RETRIEVE, e);
        } catch (NamingException e) {
            _logger.error("User unknown: " + id);
            throw new UserException(SystemErrors.ERROR_RESOURCE_RETRIEVE, e);
        }

        if (!oNamingEnumeration.hasMore()) {
            StringBuffer sbFailed = new StringBuffer("User with id '");
            sbFailed.append(id);
            sbFailed.append("' not found after LDAP search with filter: ");
            sbFailed.append(searchFilter);
            _logger.error(sbFailed.toString());
            throw new UserException(SystemErrors.ERROR_RESOURCE_RETRIEVE);
        }

        SearchResult oSearchResult = (SearchResult) oNamingEnumeration.next();
        Attributes oAttributes = oSearchResult.getAttributes();
        NamingEnumeration neAttributes = oAttributes.getAll();
        while (neAttributes.hasMore()) {
            Attribute oAttribute = (Attribute) neAttributes.next();
            String sAttributeName = oAttribute.getID();

            if (oAttribute.size() > 1) {
                Vector<Object> vValue = new Vector<Object>();
                NamingEnumeration neAttribute = oAttribute.getAll();
                while (neAttribute.hasMore())
                    vValue.add(neAttribute.next());

                htReturn.put(sAttributeName, vValue);
            } else {
                Object oValue = oAttribute.get();
                if (oValue == null)
                    oValue = "";
                htReturn.put(sAttributeName, oValue);
            }
        }
    } catch (UserException e) {
        throw e;
    } catch (Exception e) {
        _logger.fatal("Could not retrieve fields: " + fields, e);
        throw new UserException(SystemErrors.ERROR_INTERNAL, e);
    } finally {
        if (oNamingEnumeration != null) {
            try {
                oNamingEnumeration.close();
            } catch (Exception e) {
                _logger.error("Could not close Naming Enumeration after searching for user with id: " + id, e);
            }
        }
        if (oDirContext != null) {
            try {
                oDirContext.close();
            } catch (NamingException e) {
                _logger.error("Could not close Dir Context after searching for user with id: " + id, e);
            }
        }
    }
    return htReturn;
}

From source file:ru.efo.security.ADUserDetailsService.java

private void describeRoles(DirContext context, Attribute memberOf, Set<String> groups, Set<String> roles)
        throws NamingException {
    if (memberOf != null) {
        for (int i = 0; i < memberOf.size(); i++) {
            Attribute attr = context.getAttributes(memberOf.get(i).toString(), new String[] { "CN" }).get("CN");
            if (attr != null) {
                final String role = attr.get().toString();
                if (rolesMapping != null) {
                    for (String key : rolesMapping.keySet()) {
                        if (role.matches(rolesMapping.get(key))) {
                            if (logger.isLoggable(Level.FINE)) {
                                if (!roles.contains(key)) {
                                    logger.log(Level.FINE, "Role: " + key);
                                }/*from   w  ww.  jav a2  s.  c  o m*/
                            }
                            roles.add(key);
                        }
                    }
                } else {
                    final String roleWithPrefix = (rolePrefix == null ? "" : rolePrefix)
                            + role.toUpperCase().replaceAll("(\\s|-)+", "_");
                    if (logger.isLoggable(Level.FINE)) {
                        if (!roles.contains(role)) {
                            logger.log(Level.FINE, "Role: " + roleWithPrefix);
                        }
                    }
                    roles.add(roleWithPrefix);
                }
                groups.add(role);

                if (recursiveRoleSearch) {
                    SearchControls controls = new SearchControls();
                    controls.setSearchScope(SearchControls.SUBTREE_SCOPE);
                    NamingEnumeration<SearchResult> renum = context.search(
                            groupSearchBase != null ? groupSearchBase : userSearchBase, "(CN=" + role + ")",
                            controls);
                    if (renum.hasMore()) {
                        SearchResult searchResult = renum.next();
                        attr = searchResult.getAttributes().get("memberOf");
                        describeRoles(context, attr, groups, roles);
                    }
                }
            }
        }
    }
}

From source file:org.apache.directory.server.operations.bind.SaslBindIT.java

/**
 * Tests to make sure the server properly returns the supportedSASLMechanisms.
 *///w  w w.  j a v a 2s . com
@Test
public void testSupportedSASLMechanisms() throws Exception {
    // We have to tell the server that it should accept anonymous
    // auth, because we are reading the rootDSE
    getLdapServer().getDirectoryService().setAllowAnonymousAccess(true);

    // Point on rootDSE
    DirContext context = new InitialDirContext();

    Attributes attrs = context.getAttributes(Network.ldapLoopbackUrl(getLdapServer().getPort()),
            new String[] { "supportedSASLMechanisms" });

    //             Thread.sleep( 10 * 60 * 1000 );
    NamingEnumeration<? extends Attribute> answer = attrs.getAll();
    Attribute result = answer.next();
    assertEquals(6, result.size());
    assertTrue(result.contains(SupportedSaslMechanisms.GSSAPI));
    assertTrue(result.contains(SupportedSaslMechanisms.DIGEST_MD5));
    assertTrue(result.contains(SupportedSaslMechanisms.CRAM_MD5));
    assertTrue(result.contains(SupportedSaslMechanisms.NTLM));
    assertTrue(result.contains(SupportedSaslMechanisms.PLAIN));
    assertTrue(result.contains(SupportedSaslMechanisms.GSS_SPNEGO));
}

From source file:org.wso2.carbon.appfactory.s4.integration.DomainMappingManagementService.java

/**
 * Resolve CNAME and A records for the given {@code hostname}.
 *
 * @param domain             hostname to be resolved.
 * @param environmentConfigs environment configuration
 * @return {@link com.google.common.collect.Multimap} of resolved dns entries. This {@link com.google.common.collect.Multimap} will contain the resolved
 * "CNAME" and "A" records from the given {@code hostname}
 * @throws AppFactoryException if error occurred while the operation
 */// w  w  w  .  j  a va 2 s  .c  o m
public Multimap<String, String> resolveDNS(String domain, Hashtable<String, String> environmentConfigs)
        throws AppFactoryException, DomainMappingVerificationException {
    // result mutimap of dns records. Contains the cname and records resolved by the given hostname
    // ex:  CNAME   => foo.com,bar.com
    //      A       => 192.1.2.3 , 192.3.4.5
    Multimap<String, String> dnsRecordsResult = ArrayListMultimap.create();
    Attributes dnsRecords;
    boolean isARecordFound = false;
    boolean isCNAMEFound = false;

    try {
        if (log.isDebugEnabled()) {
            log.debug("DNS validation: resolving DNS for " + domain + " " + "(A/CNAME)");
        }
        DirContext context = new InitialDirContext(environmentConfigs);
        String[] dnsRecordsToCheck = new String[] { DNS_A_RECORD, DNS_CNAME_RECORD };
        dnsRecords = context.getAttributes(domain, dnsRecordsToCheck);
    } catch (NamingException e) {
        String msg = "DNS validation: DNS query failed for: " + domain + ". Error occurred while configuring "
                + "directory context.";
        log.error(msg, e);
        throw new AppFactoryException(msg, e);
    }

    try {
        // looking for for A records
        Attribute aRecords = dnsRecords.get(DNS_A_RECORD);
        if (aRecords != null && aRecords.size() > 0) { // if an A record exists
            NamingEnumeration aRecordHosts = aRecords.getAll(); // get all resolved A entries
            String aHost;
            while (aRecordHosts.hasMore()) {
                isARecordFound = true;
                aHost = (String) aRecordHosts.next();
                dnsRecordsResult.put(DNS_A_RECORD, aHost);
                if (log.isDebugEnabled()) {
                    log.debug("DNS validation: A record found: " + aHost);
                }
            }
        }

        // looking for CNAME records
        Attribute cnameRecords = dnsRecords.get(DNS_CNAME_RECORD);
        if (cnameRecords != null && cnameRecords.size() > 0) { // if CNAME record exists
            NamingEnumeration cnameRecordHosts = cnameRecords.getAll(); // get all resolved CNAME entries for hostname
            String cnameHost;
            while (cnameRecordHosts.hasMore()) {
                isCNAMEFound = true;
                cnameHost = (String) cnameRecordHosts.next();
                if (cnameHost.endsWith(".")) {
                    // Since DNS records are end with "." we are removing it.
                    // For example real dns entry for www.google.com is www.google.com.
                    cnameHost = cnameHost.substring(0, cnameHost.lastIndexOf('.'));
                }
                dnsRecordsResult.put(DNS_CNAME_RECORD, cnameHost);
                if (log.isDebugEnabled()) {
                    log.debug("DNS validation: recurring on CNAME record towards host " + cnameHost);
                }
                dnsRecordsResult.putAll(resolveDNS(cnameHost, environmentConfigs)); // recursively resolve cnameHost
            }
        }

        if (!isARecordFound && !isCNAMEFound && log.isDebugEnabled()) {
            log.debug("DNS validation: No CNAME or A record found for domain: '" + domain);
        }
        return dnsRecordsResult;
    } catch (NamingException ne) {
        String msg = "DNS validation: DNS query failed for: " + domain + ". Provided domain: " + domain
                + " might be a " + "non existing domain.";
        // we are logging this as warn messages since this is caused, due to an user error. For example if the
        // user entered a rubbish custom url(Or a url which is, CNAME record is not propagated at the
        // time of adding the url), then url validation will fail but it is not an system error
        log.warn(msg, ne);
        throw new DomainMappingVerificationException(msg, ne);
    }
}

From source file:com.surevine.ldap2alfresco.ProfileFieldTextConverter.java

/**
 * Encode some attributes as JSON./*from   ww  w . jav a  2 s .c  om*/
 * @param json The JSON object to insert into
 * @param attributes Collection of attributes
 */
public void toJson(final JSONObject json, final Attributes attributes) {

    Attribute attribute = attributes.get(attributeLabel);

    if (attribute == null) {
        LOGGER.debug("Missing attribute: " + attributeLabel);

        // just put an empty entry into the JSON
        try {
            if (allowMultiples) {
                json.put(jsonLabel, new JSONArray());
            } else {
                json.put(jsonLabel, "");
            }
        } catch (JSONException e) {
            logException(Level.ERROR, e);
        }

        return;
    }

    int numValues = attribute.size();

    if (numValues == 0) {
        LOGGER.error("Attribute " + attributeLabel + " contains no values");
        return;
    }

    try {
        if (allowMultiples) {

            JSONArray values = new JSONArray();

            NamingEnumeration<?> valueEnum = attribute.getAll();

            while (valueEnum.hasMore()) {
                String value = valueEnum.next().toString();
                if (value != null && value.length() > MAX_STRING_LENGTH) {
                    value = value.substring(0, MAX_STRING_LENGTH - 1);
                }
                values.put(value);
            }

            json.put(jsonLabel, values);
        } else {
            // expecting only one value
            if (numValues != 1) {
                LOGGER.error("Expected single value in attribute " + attributeLabel + ", found " + numValues);
                return;
            }

            String value = attribute.get().toString();
            if (value != null && value.length() > MAX_STRING_LENGTH) {
                value = value.substring(0, MAX_STRING_LENGTH - 1);
            }

            json.put(jsonLabel, value);
        }
    } catch (NamingException e) {
        logException(Level.ERROR, e);
        return;
    } catch (JSONException e) {
        logException(Level.ERROR, e);
        return;
    }
}

From source file:com.alfaariss.oa.engine.attribute.gather.processor.jndi.JNDIGatherer.java

/**
 * Gathers attributes from JNDI storage to the supplied attributes object.
 * @see com.alfaariss.oa.engine.core.attribute.gather.processor.IProcessor#process(java.lang.String, com.alfaariss.oa.api.attribute.IAttributes)
 *//*from  ww  w.  j  ava2 s . co  m*/
public void process(String sUserId, IAttributes oAttributes) throws AttributeException {
    DirContext oDirContext = null;
    NamingEnumeration oNamingEnumeration = null;
    try {
        try {
            oDirContext = new InitialDirContext(_htJNDIEnvironment);
        } catch (NamingException e) {
            _logger.error("Could not create the connection: " + _htJNDIEnvironment);
            throw new AttributeException(SystemErrors.ERROR_RESOURCE_CONNECT, e);
        }

        SearchControls oScope = new SearchControls();
        oScope.setSearchScope(SearchControls.SUBTREE_SCOPE);
        if (_listGather.size() > 0) {
            String[] saAttributes = _listGather.toArray(new String[0]);
            oScope.setReturningAttributes(saAttributes);
        }

        String searchFilter = resolveSearchQuery(sUserId);
        try {
            oNamingEnumeration = oDirContext.search(_sDNBase, searchFilter, oScope);
        } catch (InvalidSearchFilterException e) {
            StringBuffer sbFailed = new StringBuffer("Wrong filter: ");
            sbFailed.append(searchFilter);
            sbFailed.append(" while searching for attributes for id: ");
            sbFailed.append(sUserId);
            _logger.error(sbFailed.toString(), e);
            throw new AttributeException(SystemErrors.ERROR_RESOURCE_RETRIEVE, e);
        } catch (NamingException e) {
            _logger.debug("User unknown: " + sUserId);
            return;
        }

        if (oNamingEnumeration.hasMore()) {
            SearchResult oSearchResult = (SearchResult) oNamingEnumeration.next();
            Attributes oSearchedAttributes = oSearchResult.getAttributes();
            NamingEnumeration neAttributes = oSearchedAttributes.getAll();
            while (neAttributes.hasMore()) {
                Attribute oAttribute = (Attribute) neAttributes.next();
                String sAttributeName = oAttribute.getID();
                String sMappedName = _htMapper.get(sAttributeName);
                if (sMappedName != null)
                    sAttributeName = sMappedName;

                if (oAttribute.size() > 1) {
                    Vector<Object> vValue = new Vector<Object>();
                    NamingEnumeration neAttribute = oAttribute.getAll();
                    while (neAttribute.hasMore())
                        vValue.add(neAttribute.next());

                    oAttributes.put(sAttributeName, vValue);
                } else {
                    Object oValue = oAttribute.get();
                    if (oValue == null)
                        oValue = "";
                    oAttributes.put(sAttributeName, oValue);
                }
            }
        }
    } catch (AttributeException e) {
        throw e;
    } catch (NamingException e) {
        _logger.debug("Failed to fetch attributes for user: " + sUserId, e);
    } catch (Exception e) {
        _logger.fatal("Could not retrieve fields for user with id: " + sUserId, e);
        throw new AttributeException(SystemErrors.ERROR_INTERNAL);
    } finally {
        if (oNamingEnumeration != null) {
            try {
                oNamingEnumeration.close();
            } catch (Exception e) {
                _logger.error("Could not close Naming Enumeration after searching for user with id: " + sUserId,
                        e);
            }
        }
        if (oDirContext != null) {
            try {
                oDirContext.close();
            } catch (NamingException e) {
                _logger.error("Could not close Dir Context after searching for user with id: " + sUserId, e);
            }
        }
    }
}

From source file:com.evolveum.midpoint.model.common.expression.functions.BasicExpressionFunctions.java

public String determineLdapSingleAttributeValue(String dn, String attributeName, Collection<?> values)
        throws NamingException {
    if (values == null || values.isEmpty()) {
        return null;
    }//from w  w w . j ava 2s .  c  o m

    Collection<String> stringValues = null;
    // Determine item type, try to convert to strings
    Object firstElement = values.iterator().next();
    if (firstElement instanceof String) {
        stringValues = (Collection) values;
    } else if (firstElement instanceof Element) {
        stringValues = new ArrayList<String>(values.size());
        for (Object value : values) {
            Element element = (Element) value;
            stringValues.add(element.getTextContent());
        }
    } else {
        throw new IllegalArgumentException("Unexpected value type " + firstElement.getClass());
    }

    if (stringValues.size() == 1) {
        return stringValues.iterator().next();
    }

    if (StringUtils.isBlank(dn)) {
        throw new IllegalArgumentException(
                "No dn argument specified, cannot determine which of " + values.size() + " values to use");
    }

    LdapName parsedDn = new LdapName(dn);
    for (int i = 0; i < parsedDn.size(); i++) {
        Rdn rdn = parsedDn.getRdn(i);
        Attributes rdnAttributes = rdn.toAttributes();
        NamingEnumeration<String> rdnIDs = rdnAttributes.getIDs();
        while (rdnIDs.hasMore()) {
            String rdnID = rdnIDs.next();
            Attribute attribute = rdnAttributes.get(rdnID);
            if (attributeName.equals(attribute.getID())) {
                for (int j = 0; j < attribute.size(); j++) {
                    Object value = attribute.get(j);
                    if (stringValues.contains(value)) {
                        return (String) value;
                    }
                }
            }
        }
    }

    // Fallback. No values in DN. Just return the first alphabetically-wise value.
    return Collections.min(stringValues);
}