diff --git a/cas/src/main/java/org/springframework/security/cas/SamlServiceProperties.java b/cas/src/main/java/org/springframework/security/cas/SamlServiceProperties.java new file mode 100644 index 0000000000..85e69e67cd --- /dev/null +++ b/cas/src/main/java/org/springframework/security/cas/SamlServiceProperties.java @@ -0,0 +1,20 @@ +package org.springframework.security.cas; + +/** + * Sets the appropriate parameters for CAS's implementation of SAML (which is not guaranteed to be actually SAML compliant). + * + * @author Scott Battaglia + * @version $Revision$ $Date$ + * @since 3.0 + */ +public final class SamlServiceProperties extends ServiceProperties { + + public static final String DEFAULT_SAML_ARTIFACT_PARAMETER = "SAMLart"; + + public static final String DEFAULT_SAML_SERVICE_PARAMETER = "TARGET"; + + public SamlServiceProperties() { + super.setArtifactParameter(DEFAULT_SAML_ARTIFACT_PARAMETER); + super.setServiceParameter(DEFAULT_SAML_SERVICE_PARAMETER); + } +} diff --git a/cas/src/main/java/org/springframework/security/cas/ServiceProperties.java b/cas/src/main/java/org/springframework/security/cas/ServiceProperties.java index 8da38064bb..1004a3d100 100644 --- a/cas/src/main/java/org/springframework/security/cas/ServiceProperties.java +++ b/cas/src/main/java/org/springframework/security/cas/ServiceProperties.java @@ -30,15 +30,27 @@ import org.springframework.util.Assert; * @version $Id$ */ public class ServiceProperties implements InitializingBean { + + public static final String DEFAULT_CAS_ARTIFACT_PARAMETER = "ticket"; + + public static final String DEFAULT_CAS_SERVICE_PARAMETER = "service"; + //~ Instance fields ================================================================================================ private String service; + private boolean sendRenew = false; + private String artifactParameter = DEFAULT_CAS_ARTIFACT_PARAMETER; + + private String serviceParameter = DEFAULT_CAS_SERVICE_PARAMETER; + //~ Methods ======================================================================================================== public void afterPropertiesSet() throws Exception { Assert.hasLength(this.service, "service must be specified."); + Assert.hasLength(this.artifactParameter, "artifactParameter cannot be empty."); + Assert.hasLength(this.serviceParameter, "serviceParameter cannot be empty."); } /** @@ -52,8 +64,8 @@ public class ServiceProperties implements InitializingBean { * * @return the URL of the service the user is authenticating to */ - public String getService() { - return service; + public final String getService() { + return this.service; } /** @@ -67,15 +79,41 @@ public class ServiceProperties implements InitializingBean { * * @return whether to send the renew parameter to CAS */ - public boolean isSendRenew() { - return sendRenew; + public final boolean isSendRenew() { + return this.sendRenew; } - public void setSendRenew(boolean sendRenew) { + public final void setSendRenew(final boolean sendRenew) { this.sendRenew = sendRenew; } - public void setService(String service) { + public final void setService(final String service) { this.service = service; } + + public final String getArtifactParameter() { + return this.artifactParameter; + } + + /** + * Configures the Request Parameter to look for when attempting to see if a CAS ticket was sent from the server. + * + * @param artifactParameter the id to use. Default is "ticket". + */ + public final void setArtifactParameter(final String artifactParameter) { + this.artifactParameter = artifactParameter; + } + + /** + * Configures the Request parameter to look for when attempting to send a request to CAS. + * + * @return the service parameter to use. Default is "service". + */ + public final String getServiceParameter() { + return serviceParameter; + } + + public final void setServiceParameter(final String serviceParameter) { + this.serviceParameter = serviceParameter; + } } diff --git a/cas/src/main/java/org/springframework/security/cas/authentication/CasAssertionAuthenticationToken.java b/cas/src/main/java/org/springframework/security/cas/authentication/CasAssertionAuthenticationToken.java new file mode 100644 index 0000000000..c1f0798d7a --- /dev/null +++ b/cas/src/main/java/org/springframework/security/cas/authentication/CasAssertionAuthenticationToken.java @@ -0,0 +1,41 @@ +package org.springframework.security.cas.authentication; + +import org.springframework.security.authentication.AbstractAuthenticationToken; +import org.springframework.security.core.GrantedAuthority; +import org.jasig.cas.client.validation.Assertion; + +import java.util.List; +import java.util.ArrayList; + +/** + * Temporary authentication object needed to load the user details service. + * + * @author Scott Battaglia + * @version $Revision$ $Date$ + * @since 3.0 + */ +public final class CasAssertionAuthenticationToken extends AbstractAuthenticationToken { + + private final Assertion assertion; + + private final String ticket; + + public CasAssertionAuthenticationToken(final Assertion assertion, final String ticket) { + super(new ArrayList()); + + this.assertion = assertion; + this.ticket = ticket; + } + + public Object getPrincipal() { + return this.assertion.getPrincipal().getName(); + } + + public Object getCredentials() { + return this.ticket; + } + + public Assertion getAssertion() { + return this.assertion; + } +} diff --git a/cas/src/main/java/org/springframework/security/cas/authentication/CasAuthenticationProvider.java b/cas/src/main/java/org/springframework/security/cas/authentication/CasAuthenticationProvider.java index 018017446b..52728a1dc0 100644 --- a/cas/src/main/java/org/springframework/security/cas/authentication/CasAuthenticationProvider.java +++ b/cas/src/main/java/org/springframework/security/cas/authentication/CasAuthenticationProvider.java @@ -31,9 +31,7 @@ import org.springframework.security.cas.web.CasProcessingFilter; import org.springframework.security.core.Authentication; import org.springframework.security.core.AuthenticationException; import org.springframework.security.core.SpringSecurityMessageSource; -import org.springframework.security.core.userdetails.UserDetails; -import org.springframework.security.core.userdetails.UserDetailsChecker; -import org.springframework.security.core.userdetails.UserDetailsService; +import org.springframework.security.core.userdetails.*; import org.springframework.util.Assert; @@ -47,13 +45,15 @@ import org.springframework.util.Assert; * It can also validate a previously created {@link CasAuthenticationToken}. * * @author Ben Alex + * @author Scott Battaglia * @version $Id$ */ public class CasAuthenticationProvider implements AuthenticationProvider, InitializingBean, MessageSourceAware { //~ Instance fields ================================================================================================ - private UserDetailsService userDetailsService; + private AuthenticationUserDetailsService authenticationUserDetailsService; + private UserDetailsChecker userDetailsChecker = new AccountStatusUserDetailsChecker(); protected MessageSourceAccessor messages = SpringSecurityMessageSource.getAccessor(); private StatelessTicketCache statelessTicketCache = new NullStatelessTicketCache(); @@ -64,7 +64,7 @@ public class CasAuthenticationProvider implements AuthenticationProvider, Initia //~ Methods ======================================================================================================== public void afterPropertiesSet() throws Exception { - Assert.notNull(this.userDetailsService, "A userDetailsService must be set"); + Assert.notNull(this.authenticationUserDetailsService, "An authenticationUserDetailsService must be set"); Assert.notNull(this.ticketValidator, "A ticketValidator must be set"); Assert.notNull(this.statelessTicketCache, "A statelessTicketCache must be set"); Assert.hasText(this.key, "A Key is required so CasAuthenticationProvider can identify tokens it previously authenticated"); @@ -127,7 +127,7 @@ public class CasAuthenticationProvider implements AuthenticationProvider, Initia return result; } - private final CasAuthenticationToken authenticateNow(final Authentication authentication) throws AuthenticationException { + private CasAuthenticationToken authenticateNow(final Authentication authentication) throws AuthenticationException { try { final Assertion assertion = this.ticketValidator.validate(authentication.getCredentials().toString(), serviceProperties.getService()); final UserDetails userDetails = loadUserByAssertion(assertion); @@ -143,18 +143,23 @@ public class CasAuthenticationProvider implements AuthenticationProvider, Initia * can override this method and retrieve the user based on any criteria they desire. * * @param assertion The CAS Assertion. - * @returns the UserDetails. + * @return the UserDetails. */ protected UserDetails loadUserByAssertion(final Assertion assertion) { - return this.userDetailsService.loadUserByUsername(assertion.getPrincipal().getName()); - } - - protected UserDetailsService getUserDetailsService() { - return userDetailsService; + final CasAssertionAuthenticationToken token = new CasAssertionAuthenticationToken(assertion, ""); + return this.authenticationUserDetailsService.loadUserDetails(token); } + @Deprecated + /** + * @deprecated as of 3.0. Use the {@link org.springframework.security.cas.authentication.CasAuthenticationProvider#setAuthenticationUserDetailsService(org.springframework.security.core.userdetails.AuthenticationUserDetailsService)} instead. + */ public void setUserDetailsService(final UserDetailsService userDetailsService) { - this.userDetailsService = userDetailsService; + this.authenticationUserDetailsService = new UserDetailsByNameServiceWrapper(userDetailsService); + } + + public void setAuthenticationUserDetailsService(final AuthenticationUserDetailsService authenticationUserDetailsService) { + this.authenticationUserDetailsService = authenticationUserDetailsService; } public void setServiceProperties(final ServiceProperties serviceProperties) { diff --git a/cas/src/main/java/org/springframework/security/cas/authentication/EhCacheBasedTicketCache.java b/cas/src/main/java/org/springframework/security/cas/authentication/EhCacheBasedTicketCache.java index 3103847432..bef07631cc 100644 --- a/cas/src/main/java/org/springframework/security/cas/authentication/EhCacheBasedTicketCache.java +++ b/cas/src/main/java/org/springframework/security/cas/authentication/EhCacheBasedTicketCache.java @@ -51,32 +51,27 @@ public class EhCacheBasedTicketCache implements StatelessTicketCache, Initializi Assert.notNull(cache, "cache mandatory"); } - public CasAuthenticationToken getByTicketId(String serviceTicket) { - Element element = null; - + public CasAuthenticationToken getByTicketId(final String serviceTicket) { try { - element = cache.get(serviceTicket); + final Element element = cache.get(serviceTicket); + + if (logger.isDebugEnabled()) { + logger.debug("Cache hit: " + (element != null) + "; service ticket: " + serviceTicket); + } + + return element == null ? null : (CasAuthenticationToken) element.getValue(); + } catch (CacheException cacheException) { throw new DataRetrievalFailureException("Cache failure: " + cacheException.getMessage()); } - - if (logger.isDebugEnabled()) { - logger.debug("Cache hit: " + (element != null) + "; service ticket: " + serviceTicket); - } - - if (element == null) { - return null; - } else { - return (CasAuthenticationToken) element.getValue(); - } } public Ehcache getCache() { return cache; } - public void putTicketInCache(CasAuthenticationToken token) { - Element element = new Element(token.getCredentials().toString(), token); + public void putTicketInCache(final CasAuthenticationToken token) { + final Element element = new Element(token.getCredentials().toString(), token); if (logger.isDebugEnabled()) { logger.debug("Cache put: " + element.getKey()); @@ -85,7 +80,7 @@ public class EhCacheBasedTicketCache implements StatelessTicketCache, Initializi cache.put(element); } - public void removeTicketFromCache(CasAuthenticationToken token) { + public void removeTicketFromCache(final CasAuthenticationToken token) { if (logger.isDebugEnabled()) { logger.debug("Cache remove: " + token.getCredentials().toString()); } @@ -93,11 +88,11 @@ public class EhCacheBasedTicketCache implements StatelessTicketCache, Initializi this.removeTicketFromCache(token.getCredentials().toString()); } - public void removeTicketFromCache(String serviceTicket) { + public void removeTicketFromCache(final String serviceTicket) { cache.remove(serviceTicket); } - public void setCache(Ehcache cache) { + public void setCache(final Ehcache cache) { this.cache = cache; } } diff --git a/cas/src/main/java/org/springframework/security/cas/userdetails/AbstractCasAssertionUserDetailsService.java b/cas/src/main/java/org/springframework/security/cas/userdetails/AbstractCasAssertionUserDetailsService.java new file mode 100644 index 0000000000..f9547ff058 --- /dev/null +++ b/cas/src/main/java/org/springframework/security/cas/userdetails/AbstractCasAssertionUserDetailsService.java @@ -0,0 +1,35 @@ +package org.springframework.security.cas.userdetails; + +import org.springframework.security.core.userdetails.AuthenticationUserDetailsService; +import org.springframework.security.core.userdetails.UserDetails; +import org.springframework.security.core.userdetails.UsernameNotFoundException; +import org.springframework.security.core.Authentication; +import org.springframework.security.cas.authentication.CasAuthenticationToken; +import org.springframework.security.cas.authentication.CasAssertionAuthenticationToken; +import org.springframework.util.Assert; +import org.jasig.cas.client.validation.Assertion; + +/** + * Abstract class for using the provided CAS assertion to construct a new User object. This generally is most + * useful when combined with a SAML-based response from the CAS Server/client. + * + * @author Scott Battaglia + * @version $Revision$ $Date$ + * @since 3.0 + */ +public abstract class AbstractCasAssertionUserDetailsService implements AuthenticationUserDetailsService { + + public final UserDetails loadUserDetails(final Authentication token) throws UsernameNotFoundException { + Assert.isInstanceOf(CasAuthenticationToken.class, token, "The provided token MUST be an instance of CasAuthenticationToken.class"); + return loadUserDetails(((CasAssertionAuthenticationToken) token).getAssertion()); + } + + /** + * Protected template method for construct a {@link org.springframework.security.core.userdetails.UserDetails} via the supplied CAS + * assertion. + * + * @param assertion the assertion to use to construct the new UserDetails. CANNOT be NULL. + * @return the newly constructed UserDetails. + */ + protected abstract UserDetails loadUserDetails(Assertion assertion); +} diff --git a/cas/src/main/java/org/springframework/security/cas/userdetails/GrantedAuthorityFromAssertionAttributesUserDetailsService.java b/cas/src/main/java/org/springframework/security/cas/userdetails/GrantedAuthorityFromAssertionAttributesUserDetailsService.java new file mode 100644 index 0000000000..53b98a0fcf --- /dev/null +++ b/cas/src/main/java/org/springframework/security/cas/userdetails/GrantedAuthorityFromAssertionAttributesUserDetailsService.java @@ -0,0 +1,57 @@ +package org.springframework.security.cas.userdetails; + +import org.springframework.security.core.userdetails.UserDetails; +import org.springframework.security.core.userdetails.User; +import org.springframework.security.core.GrantedAuthority; +import org.springframework.security.core.authority.GrantedAuthorityImpl; +import org.springframework.beans.factory.InitializingBean; +import org.springframework.util.Assert; +import org.jasig.cas.client.validation.Assertion; + +import java.util.List; +import java.util.ArrayList; + +/** + * Populates the {@link org.springframework.security.core.GrantedAuthority}s for a user by reading a list of attributes that were returned as + * part of the CAS response. Each attribute is read and each value of the attribute is turned into a GrantedAuthority. If the attribute has no + * value then its not added. + * + * @author Scott Battaglia + * @version $Revision$ $Date$ + * @since 3.0 + */ +public final class GrantedAuthorityFromAssertionAttributesUserDetailsService extends AbstractCasAssertionUserDetailsService implements InitializingBean { + + private String[] attributes; + + @Override + protected UserDetails loadUserDetails(final Assertion assertion) { + final List grantedAuthorities = new ArrayList(); + + for (final String attribute : this.attributes) { + final Object attributes = assertion.getPrincipal().getAttributes().get(attribute); + + if (attributes == null) { + continue; + } + + if (attributes instanceof List) { + final List list = (List) attributes; + + for (final Object o : list) { + grantedAuthorities.add(new GrantedAuthorityImpl(o.toString())); + } + + } else { + grantedAuthorities.add(new GrantedAuthorityImpl(attributes.toString())); + } + + } + + return new User(assertion.getPrincipal().getName(), null, true, true, true, true, grantedAuthorities); + } + + public void afterPropertiesSet() throws Exception { + Assert.isTrue(attributes != null && attributes.length > 0, "At least one attribute is required to retrieve roles from."); + } +} diff --git a/cas/src/main/java/org/springframework/security/cas/web/CasProcessingFilter.java b/cas/src/main/java/org/springframework/security/cas/web/CasProcessingFilter.java index 732bdd88da..65b68ef9db 100644 --- a/cas/src/main/java/org/springframework/security/cas/web/CasProcessingFilter.java +++ b/cas/src/main/java/org/springframework/security/cas/web/CasProcessingFilter.java @@ -79,6 +79,8 @@ public class CasProcessingFilter extends AbstractAuthenticationProcessingFilter */ private ProxyGrantingTicketStorage proxyGrantingTicketStorage; + private String artifactParameter = ServiceProperties.DEFAULT_CAS_ARTIFACT_PARAMETER; + //~ Constructors =================================================================================================== public CasProcessingFilter() { @@ -87,16 +89,16 @@ public class CasProcessingFilter extends AbstractAuthenticationProcessingFilter //~ Methods ======================================================================================================== - public Authentication attemptAuthentication(final HttpServletRequest request, HttpServletResponse response) + public Authentication attemptAuthentication(final HttpServletRequest request, final HttpServletResponse response) throws AuthenticationException { final String username = CAS_STATEFUL_IDENTIFIER; - String password = request.getParameter("ticket"); + String password = request.getParameter(this.artifactParameter); if (password == null) { password = ""; } - UsernamePasswordAuthenticationToken authRequest = new UsernamePasswordAuthenticationToken(username, password); + final UsernamePasswordAuthenticationToken authRequest = new UsernamePasswordAuthenticationToken(username, password); authRequest.setDetails(authenticationDetailsSource.buildDetails(request)); @@ -129,4 +131,8 @@ public class CasProcessingFilter extends AbstractAuthenticationProcessingFilter final ProxyGrantingTicketStorage proxyGrantingTicketStorage) { this.proxyGrantingTicketStorage = proxyGrantingTicketStorage; } + + public final void setServiceProperties(final ServiceProperties serviceProperties) { + this.artifactParameter = serviceProperties.getArtifactParameter(); + } } diff --git a/cas/src/main/java/org/springframework/security/cas/web/CasProcessingFilterEntryPoint.java b/cas/src/main/java/org/springframework/security/cas/web/CasProcessingFilterEntryPoint.java index 72c85bf346..f0299b562f 100644 --- a/cas/src/main/java/org/springframework/security/cas/web/CasProcessingFilterEntryPoint.java +++ b/cas/src/main/java/org/springframework/security/cas/web/CasProcessingFilterEntryPoint.java @@ -45,8 +45,8 @@ import org.springframework.util.Assert; */ public class CasProcessingFilterEntryPoint implements AuthenticationEntryPoint, InitializingBean { //~ Instance fields ================================================================================================ - private ServiceProperties serviceProperties; + private String loginUrl; /** @@ -66,12 +66,11 @@ public class CasProcessingFilterEntryPoint implements AuthenticationEntryPoint, Assert.notNull(this.serviceProperties, "serviceProperties must be specified"); } - public void commence(final HttpServletRequest servletRequest, final HttpServletResponse servletResponse, + public void commence(final HttpServletRequest servletRequest, final HttpServletResponse response, final AuthenticationException authenticationException) throws IOException, ServletException { - final HttpServletResponse response = (HttpServletResponse) servletResponse; - final String urlEncodedService = CommonUtils.constructServiceUrl(null, response, this.serviceProperties.getService(), null, "ticket", this.encodeServiceUrlWithSessionId); - final String redirectUrl = CommonUtils.constructRedirectUrl(this.loginUrl, "service", urlEncodedService, this.serviceProperties.isSendRenew(), false); + final String urlEncodedService = CommonUtils.constructServiceUrl(null, response, this.serviceProperties.getService(), null, this.serviceProperties.getArtifactParameter(), this.encodeServiceUrlWithSessionId); + final String redirectUrl = CommonUtils.constructRedirectUrl(this.loginUrl, this.serviceProperties.getServiceParameter(), urlEncodedService, this.serviceProperties.isSendRenew(), false); response.sendRedirect(redirectUrl); } diff --git a/cas/src/test/java/org/springframework/security/cas/authentication/CasAuthenticationProviderTests.java b/cas/src/test/java/org/springframework/security/cas/authentication/CasAuthenticationProviderTests.java index 743ade5209..1b14e426c7 100644 --- a/cas/src/test/java/org/springframework/security/cas/authentication/CasAuthenticationProviderTests.java +++ b/cas/src/test/java/org/springframework/security/cas/authentication/CasAuthenticationProviderTests.java @@ -29,10 +29,7 @@ import org.springframework.security.core.AuthenticationException; import org.springframework.security.core.GrantedAuthority; import org.springframework.security.core.authority.AuthorityUtils; import org.springframework.security.core.authority.GrantedAuthorityImpl; -import org.springframework.security.core.userdetails.User; -import org.springframework.security.core.userdetails.UserDetails; -import org.springframework.security.core.userdetails.UserDetailsService; - +import org.springframework.security.core.userdetails.*; import java.util.HashMap; @@ -77,7 +74,7 @@ public class CasAuthenticationProviderTests { @Test public void statefulAuthenticationIsSuccessful() throws Exception { CasAuthenticationProvider cap = new CasAuthenticationProvider(); - cap.setUserDetailsService(new MockAuthoritiesPopulator()); + cap.setAuthenticationUserDetailsService(new MockAuthoritiesPopulator()); cap.setKey("qwerty"); StatelessTicketCache cache = new MockStatelessTicketCache(); @@ -119,7 +116,7 @@ public class CasAuthenticationProviderTests { @Test public void statelessAuthenticationIsSuccessful() throws Exception { CasAuthenticationProvider cap = new CasAuthenticationProvider(); - cap.setUserDetailsService(new MockAuthoritiesPopulator()); + cap.setAuthenticationUserDetailsService(new MockAuthoritiesPopulator()); cap.setKey("qwerty"); StatelessTicketCache cache = new MockStatelessTicketCache(); @@ -158,7 +155,7 @@ public class CasAuthenticationProviderTests { @Test(expected = BadCredentialsException.class) public void missingTicketIdIsDetected() throws Exception { CasAuthenticationProvider cap = new CasAuthenticationProvider(); - cap.setUserDetailsService(new MockAuthoritiesPopulator()); + cap.setAuthenticationUserDetailsService(new MockAuthoritiesPopulator()); cap.setKey("qwerty"); StatelessTicketCache cache = new MockStatelessTicketCache(); @@ -177,7 +174,7 @@ public class CasAuthenticationProviderTests { public void invalidKeyIsDetected() throws Exception { final Assertion assertion = new AssertionImpl("test"); CasAuthenticationProvider cap = new CasAuthenticationProvider(); - cap.setUserDetailsService(new MockAuthoritiesPopulator()); + cap.setAuthenticationUserDetailsService(new MockAuthoritiesPopulator()); cap.setKey("qwerty"); StatelessTicketCache cache = new MockStatelessTicketCache(); @@ -205,7 +202,7 @@ public class CasAuthenticationProviderTests { @Test(expected = IllegalArgumentException.class) public void detectsMissingKey() throws Exception { CasAuthenticationProvider cap = new CasAuthenticationProvider(); - cap.setUserDetailsService(new MockAuthoritiesPopulator()); + cap.setAuthenticationUserDetailsService(new MockAuthoritiesPopulator()); cap.setStatelessTicketCache(new MockStatelessTicketCache()); cap.setTicketValidator(new MockTicketValidator(true)); cap.setServiceProperties(makeServiceProperties()); @@ -217,7 +214,7 @@ public class CasAuthenticationProviderTests { CasAuthenticationProvider cap = new CasAuthenticationProvider(); // set this explicitly to null to test failure cap.setStatelessTicketCache(null); - cap.setUserDetailsService(new MockAuthoritiesPopulator()); + cap.setAuthenticationUserDetailsService(new MockAuthoritiesPopulator()); cap.setKey("qwerty"); cap.setTicketValidator(new MockTicketValidator(true)); cap.setServiceProperties(makeServiceProperties()); @@ -227,7 +224,7 @@ public class CasAuthenticationProviderTests { @Test(expected = IllegalArgumentException.class) public void detectsMissingTicketValidator() throws Exception { CasAuthenticationProvider cap = new CasAuthenticationProvider(); - cap.setUserDetailsService(new MockAuthoritiesPopulator()); + cap.setAuthenticationUserDetailsService(new MockAuthoritiesPopulator()); cap.setKey("qwerty"); cap.setStatelessTicketCache(new MockStatelessTicketCache()); cap.setServiceProperties(makeServiceProperties()); @@ -237,14 +234,15 @@ public class CasAuthenticationProviderTests { @Test public void gettersAndSettersMatch() throws Exception { CasAuthenticationProvider cap = new CasAuthenticationProvider(); - cap.setUserDetailsService(new MockAuthoritiesPopulator()); + cap.setAuthenticationUserDetailsService(new MockAuthoritiesPopulator()); cap.setKey("qwerty"); cap.setStatelessTicketCache(new MockStatelessTicketCache()); cap.setTicketValidator(new MockTicketValidator(true)); cap.setServiceProperties(makeServiceProperties()); cap.afterPropertiesSet(); - assertTrue(cap.getUserDetailsService() != null); +// TODO disabled because why do we need to expose this? +// assertTrue(cap.getUserDetailsService() != null); assertEquals("qwerty", cap.getKey()); assertTrue(cap.getStatelessTicketCache() != null); assertTrue(cap.getTicketValidator() != null); @@ -253,7 +251,7 @@ public class CasAuthenticationProviderTests { @Test public void ignoresClassesItDoesNotSupport() throws Exception { CasAuthenticationProvider cap = new CasAuthenticationProvider(); - cap.setUserDetailsService(new MockAuthoritiesPopulator()); + cap.setAuthenticationUserDetailsService(new MockAuthoritiesPopulator()); cap.setKey("qwerty"); cap.setStatelessTicketCache(new MockStatelessTicketCache()); cap.setTicketValidator(new MockTicketValidator(true)); @@ -271,7 +269,7 @@ public class CasAuthenticationProviderTests { @Test public void ignoresUsernamePasswordAuthenticationTokensWithoutCasIdentifiersAsPrincipal() throws Exception { CasAuthenticationProvider cap = new CasAuthenticationProvider(); - cap.setUserDetailsService(new MockAuthoritiesPopulator()); + cap.setAuthenticationUserDetailsService(new MockAuthoritiesPopulator()); cap.setKey("qwerty"); cap.setStatelessTicketCache(new MockStatelessTicketCache()); cap.setTicketValidator(new MockTicketValidator(true)); @@ -292,8 +290,9 @@ public class CasAuthenticationProviderTests { //~ Inner Classes ================================================================================================== - private class MockAuthoritiesPopulator implements UserDetailsService { - public UserDetails loadUserByUsername(String casUserId) throws AuthenticationException { + private class MockAuthoritiesPopulator implements AuthenticationUserDetailsService { + + public UserDetails loadUserDetails(final Authentication token) throws UsernameNotFoundException { return makeUserDetailsFromAuthoritiesPopulator(); } }