Getting more attributes from CAS than just user id

前端 未结 5 1296
青春惊慌失措
青春惊慌失措 2021-01-04 04:29

I am using CAS with JDBC Authentication handler and was wondering is it possible to get the other attributes of principal object (for e.g. firstname, lastname) not just the

5条回答
  •  暖寄归人
    2021-01-04 04:49

    To get any user attributes from DB I did the following: use PersonDirectoryPrincipalResolver

    in deployerConfigContext.xml:

    
        
    
    

    instead of using standard SingleRowJdbcPersonAttributeDao class create your own implementation which returns not only one row from a query result but aggregated data from all returned rows:

    copy all code from SingleRowJdbcPersonAttributeDao and change only one method parseAttributeMapFromResults. you will have something like that:

    public class SingleRowJdbcPersonMultiplyAttributeDao extends AbstractJdbcPersonAttributeDao> {
        ...
    
        @Override
        protected List parseAttributeMapFromResults(final List> queryResults, final String queryUserName) {
            final List peopleAttributes = new ArrayList(queryResults.size());
            Map> attributes = new HashMap>();
    
            for (final Map queryResult : queryResults) {
    
                for (final Map.Entry seedEntry : queryResult.entrySet()) {
                    final String seedName = seedEntry.getKey();
                    final Object seedValue = seedEntry.getValue();
    
                    if (attributes.get(seedName) != null && !attributes.get(seedName).get(0).equals(seedValue)) {
                        attributes.get(seedName).add(seedValue);
                    } else {
                        List list = new ArrayList();
                        list.add(seedValue);
                        attributes.put(seedName, list);
                    }
    
                }
            }
    
            final IPersonAttributes person;
            final String userNameAttribute = this.getConfiguredUserNameAttribute();
            if (this.isUserNameAttributeConfigured() && attributes.containsKey(userNameAttribute)) {
                // Option #1:  An attribute is named explicitly in the config,
                // and that attribute is present in the results from LDAP;  use it
                person = new CaseInsensitiveAttributeNamedPersonImpl(userNameAttribute, attributes);
            } else if (queryUserName != null) {
                // Option #2:  Use the userName attribute provided in the query
                // parameters.  (NB:  I'm not entirely sure this choice is
                // preferable to Option #3.  Keeping it because it most closely
                // matches the legacy behavior there the new option -- Option #1
                // -- doesn't apply.  ~drewwills)
                person = new CaseInsensitiveNamedPersonImpl(queryUserName, attributes);
            } else {
                // Option #3:  Create the IPersonAttributes doing a best-guess
                // at a userName attribute
                person = new CaseInsensitiveAttributeNamedPersonImpl(userNameAttribute, attributes);
            }
    
            peopleAttributes.add(person);
            return peopleAttributes;
        }
    
        ...
    }
    
    
    

    and in deployerConfigContext.xml:

    
            
            
        
            
                
            
        
    
    

    Also in my case I used SAML protocol.

    As a result you will get on the client all attributes which your select returns. For example, if user have many roles you could have on the client:

    User: username, firstname, lastname, email, ... , [ROLE_1, ROLE_2, ROLE_3]

    My case works with Spring Security and Grails.

    I'm not sure this is 100% Feng Shui solution :) as it's fast cooked but it works in our case.

    Hope it helps.

    提交回复
    热议问题