{"record":{"id":"270e54c9a37a5b0c","repo":"apereo/cas","slug":"multiple-principal-values-are-not-allowed-princi","errorCode":null,"errorMessage":"Multiple principal values are not allowed: [principalAttr]","messagePattern":"Multiple principal values are not allowed: \\[principalAttr\\]","errorType":"exception","errorClass":"LoginException","httpStatus":null,"severity":"error","filePath":"support/cas-server-support-ldap-core/src/main/java/org/apereo/cas/authentication/LdapAuthenticationHandler.java","lineNumber":213,"sourceCode":"        if (StringUtils.isNotBlank(this.principalIdAttribute)) {\n            val principalAttr = ldapEntry.getAttribute(this.principalIdAttribute);\n            if (principalAttr == null || principalAttr.size() == 0) {\n                if (this.allowMissingPrincipalAttributeValue) {\n                    LOGGER.warn(\"The principal id attribute [{}] is not found. CAS cannot construct the final authenticated principal \"\n                            + \"if it's unable to locate the attribute that is designated as the principal id. \"\n                            + \"Attributes available on the LDAP entry are [{}]. Since principal id attribute is not available, CAS will \"\n                            + \"fall back to construct the principal based on the provided user id: [{}]\",\n                        this.principalIdAttribute, ldapEntry.getAttributes(), username);\n                    return username;\n                }\n                LOGGER.error(\"The principal id attribute [{}] is not found. CAS is configured to disallow missing principal attributes\",\n                    this.principalIdAttribute);\n                throw new LoginException(\"Principal id attribute is not found for \" + principalAttr);\n            }\n            val value = principalAttr.getStringValue();\n            if (principalAttr.size() > 1) {\n                if (!this.allowMultiplePrincipalAttributeValues) {\n                    throw new LoginException(\"Multiple principal values are not allowed: \" + principalAttr);\n                }\n                LOGGER.warn(\"Found multiple values for principal id attribute: [{}]. Using first value=[{}].\", principalAttr, value);\n            }\n            LOGGER.debug(\"Retrieved principal id attribute [{}]\", value);\n            return value;\n        }\n        LOGGER.debug(\"Principal id attribute is not defined. Using the default provided user id [{}]\", username);\n        return username;\n    }\n\n    private AuthenticationResponse getLdapAuthenticationResponse(final UsernamePasswordCredential upc) throws PreventedException {\n        try {\n            LOGGER.debug(\"Attempting LDAP authentication for [{}]. Authenticator pre-configured attributes are [{}], \"\n                    + \"additional requested attributes for this authentication request are [{}]\", upc, authenticator.getReturnAttributes(),\n                authenticatedEntryAttributes);\n            var ldaptiveCred = new Credential(upc.getPassword());\n            val request = new AuthenticationRequest(upc.getUsername(), ldaptiveCred, authenticatedEntryAttributes);\n            request.setControls(new PasswordPolicyControl());","sourceCodeStart":195,"sourceCodeEnd":231,"githubUrl":"https://github.com/apereo/cas/blob/e7288fc434b4f4505b8452e1a57e8fb3111bb863/support/cas-server-support-ldap-core/src/main/java/org/apereo/cas/authentication/LdapAuthenticationHandler.java#L195-L231","documentation":"LdapAuthenticationHandler reads the principal id attribute from the LDAP entry returned by bind/search. If the attribute holds more than one value and allowMultiplePrincipalAttributeValues is false (the default), the handler aborts the login with a LoginException rather than guess which value identifies the principal.","triggerScenarios":"Configured principalIdAttribute (e.g. uid, mail) is multivalued in the directory for the authenticating user — common with mail, memberOf-style attributes, or entries that merged two records — while cas.authn.ldap[x].allow-multiple-principal-attribute-values is not enabled.","commonSituations":"Directory cleanup after org merges leaves a user with two mail values; admin points principalIdAttribute at a multivalued attribute like mail or employeeType; upgrading CAS to a stricter handler version surfaces previously hidden duplicate values.","solutions":["Set cas.authn.ldap[x].allow-multiple-principal-attribute-values=true so the first value is used with a warning","Clean the directory entry so the principal id attribute has exactly one value","Point principalIdAttribute at an attribute guaranteed single-valued (e.g. uid, sAMAccountName, entryUUID)","Add the search filter a constraint (or refine base DN) so only entries with a single value match"],"exampleFix":"// before (application.yml)\ncas.authn.ldap[0].principal-attribute-list=mail\n// after\ncas.authn.ldap[0].principal-attribute-list=mail\ncas.authn.ldap[0].allow-multiple-principal-attribute-values=true","handlingStrategy":"validation","validationCode":"// in directory management / before enabling handler\nString filter = \"(uid=\" + username + \")\";\nSearchResult entry = LdapUtils.searchForEntry(props, filter);\nAttribute attr = entry.getAttribute(principalIdAttr);\nif (attr != null && attr.size() > 1) {\n    throw new IllegalStateException(\"Principal id attribute is multivalued for \" + username);\n}","typeGuard":null,"tryCatchPattern":"try {\n    handler.authenticate(transaction);\n} catch (LoginException e) {\n    if (e.getMessage().startsWith(\"Multiple principal values are not allowed\")) {\n        // flag entry for directory cleanup or enable allow-multiple-principal-attribute-values\n    }\n}","preventionTips":["Only choose single-valued attributes (uid, entryUUID, sAMAccountName) as principalIdAttribute","Run a directory audit for multivalued attributes before enabling strict checking","Enable allow-multiple-principal-attribute-values in environments known to have duplicate values","Monitor the WARN log \"Found multiple values for principal id attribute\""],"tags":["ldap","authentication","configuration"],"backgroundTag":"invalid-config-value","analyzedSha":"e7288fc434b4f4505b8452e1a57e8fb3111bb863","analyzedAt":"2026-09-08T15:39:16.015Z","contentChangedAt":"2026-09-08T15:39:16.015Z","schemaVersion":2},"datasetVersion":"2026-09-15T23:17:13.987Z"}