Howto wrap LdapAuthenticationProvider in a DaoAuthenticationProvidor?
I need to use a LdapAuthenticationProvider to authenticate against a LDAP server. I have this working fine. I'm wondering if it's possible to wrap the LdapAuthenticationProvider in a DaoAuthenticationProvider to make use of its user cache feature. I tried using a LdapUserDetailsService on the DaoAuthenticationProvider w/ no luck:
daoAuthProvider = new DaoAuthenticationProvider();
daoAuthProvider.setUserDetailsService(new LdapUserDetailsService(filterBasedLdapUserSearch, ldapAuthoritiesPopulator));
The ldap search is successful and the granted authorities are retrieved, but the DaoAuthenticationProvider throws a BadCredentialsException. I guess I'm missing some LdapAuthentication part or that this wrapping thing isn't even possible.
I'v done a simular thing, but I did it another way. I'v create a custom provider that has both ldap en dao provider as a property. In my custom provider, I provide the custom logic. == what to do when failing ldap, what to do when failing dao.
Example:
Code:
public class BossAuthenticationProvider implements AuthenticationProvider {
private Log log = LogFactory.getLog(BossAuthenticationProvider.class);
private DaoAuthenticationProvider daoAuthenticationProvider;
private LdapAuthenticationProvider ldapAuthenticationProvider;
private LdapUserSearch ldapSearch;
private UserDetailsService daoSearch;
/** * {@inheritDoc}lt;brgt; * * @see org.acegisecurity.providers.AuthenticationProvider#authenticate(org.acegisecurity.Authentication) */ public Authentication authenticate(Authentication authentication) throws AuthenticationException { Authentication result = null;
log.debug(quot;Try to search the user in the ldap. UserName = quot; + authentication.getName()); DirContextOperations user = null; try { user = ldapSearch.searchForUser(authentication.getName()); } catch (UsernameNotFoundException unfe) { log.debug(quot;User not found in ldap: quot; + unfe.getMessage(), unfe); } catch (DataAccessException dae) { /* * When a dataAccessException is thrown when searching for a user, the * authenticate is failed by the same exception. This exception means * that there is something bad with the ldap. We want to continue with * the application, so a warning will be logged. */ log.error(dae.getMessage(), dae); }
if (user != null) { log.debug(quot;User found in ldap, check credentials with ldap.quot;); result = ldapAuthenticationProvider.authenticate(authentication); if (result != null) { log.debug(quot;Authentication with ldap succesfull. Check quot;+ quot;if user exist in DBquot;); try { daoSearch.loadUserByUsername(authentication.getName()); } catch (UsernameNotFoundException e) { throw new AuthenticationCredentialsNotFoundException( quot;User successfull autheticated with ldap, quot; + quot;but no user found in Databasequot;, e); } } } else { log.debug(quot;User NOT found in ldap, try with daoProviderquot;); result = daoAuthenticationProvider.authenticate(authentication); } return result; }
/** * {@inheritDoc}lt;brgt; * * @see org.acegisecurity.providers.AuthenticationProvider#supports(java.lang.Class) */ @SuppressWarnings(quot;uncheckedquot;) public boolean supports(Class authentication) { return (UsernamePasswordAuthenticationToken.class .isAssignableFrom(authentication)); }
/** * Sets the daoAuthenticationProvider. * * @param daoAuthenticationProvider * the daoAuthenticationProvider to set */ @Required public void setDaoAuthenticationProvider( DaoAuthenticationProvider daoAuthenticationProvider) { this.daoAuthenticationProvider = daoAuthenticationProvider; }
/** * Sets the ldapAuthenticationProvider. * * @param ldapAuthenticationProvider * the ldapAuthenticationProvider to set */ @Required public void setLdapAuthenticationProvider( LdapAuthenticationProvider ldapAuthenticationProvider) { this.ldapAuthenticationProvider = ldapAuthenticationProvider; }
/** * Sets the userSearch. * * @param ldapSearch * the userSearch to set */ @Required public void setLdapSearch(LdapUserSearch ldapSearch) { this.ldapSearch = ldapSearch; }
/** * Sets the dao search. * * @param daoSearch * the new dao search */ @Required public void setDaoSearch(UserDetailsService daoSearch) { this.daoSearch = daoSearch; }
}
Configuration:
Code:
lt;bean id=quot;bossAuthenticationProviderquot; class=quot;be.boss.spring.security.BossAuthenticationProviderquot;gt; lt;sec:custom-authentication-provider /gt; lt;property name=quot;ldapAuthenticationProviderquot; ref=quot;ldapAuthProviderquot; /gt; lt;property name=quot;daoAuthenticationProviderquot; ref=quot;daoAuthenticationProviderquot; /gt; lt;property name=quot;ldapSearchquot; ref=quot;ldapUserSearchquot; /gt; lt;property name=quot;daoSearchquot; ref=quot;daoUserSearchquot; /gt;
lt;/beangt;
Hope this helps.
Good class !
but, i need this ...
First, you login in the form, before that the UserName is search in LDAP and when de user is Autentificated, Spring Security search the Roles in a Database.
maybe you can help me |