Spring Security 3: Password Change Issue

I have a simple application in which I can register users and verify their authenticity. I have passwords encoded using and successfully authenticated. I am using Spring 3, Spring Security 3 and Hibernate 3 in my application.

Now I want to salt my passwords with a user ID, but I cannot achieve this functionality. Can someone help me with this? I have been trying to do this for some time, but cannot do it.

Here is the code that I have for salting users with their identifier and authentication.

XYZ-security.xml

<http auto-config="true" use-expressions="true"> <intercept-url pattern="/welcome.do" access="hasRole('ROLE_USER')" /> <form-login login-page="/login.do" authentication-failure-url="/login.do?login_error=1"/> <logout invalidate-session="true" logout-url="/logout" logout-success-url="/"/> </http> <beans:bean id="daoAuthenticationProvider" class="org.springframework.security.authentication.dao.DaoAuthenticationProvider"> <beans:property name="userDetailsService" ref="userDetailsService"/> </beans:bean> <beans:bean id="authenticationManager" class="org.springframework.security.authentication.ProviderManager"> <beans:property name="providers"> <beans:list> <beans:ref local="daoAuthenticationProvider" /> </beans:list> </beans:property> </beans:bean> <authentication-manager> <authentication-provider user-service-ref="userDetailsService"> <password-encoder ref="passwordEncoder"> <salt-source ref="saltSource"/> </password-encoder> </authentication-provider> </authentication-manager> <!-- For hashing and salting user passwords --> <beans:bean id="passwordEncoder" class="org.springframework.security.authentication.encoding.ShaPasswordEncoder"/> <beans:bean id="saltSource" class="org.springframework.security.authentication.dao.ReflectionSaltSource" p:userPropertyToUse="id"/> 

UserDetailsAdapter.java

 @Service("userDetailsAdapter") public class UserDetailsAdapter { private Long id; org.springframework.security.core.userdetails.User buildUserFromUserEntity(User userEntity) { String username = userEntity.getUsername(); String password = userEntity.getPassword(); boolean enabled = userEntity.isEnabled(); boolean accountNonExpired = true; boolean credentialsNonExpired = true; boolean accountNonLocked = true; Collection<GrantedAuthority> authorities = new ArrayList<GrantedAuthority>(); for (String authority: userEntity.getAuthorities()) { authorities.add(new GrantedAuthorityImpl(authority)); } this.id = userEntity.getId(); org.springframework.security.core.userdetails.User user = new org.springframework.security.core.userdetails.User(username, password, enabled, accountNonExpired, credentialsNonExpired, accountNonLocked, authorities); return user; } public Long getId() { return id; } } 

UserDetailsServiceImpl

 @Service("userDetailsService") public class UserDetailsServiceImpl implements UserDetailsService { @Autowired private UserDao userDao; @Autowired private UserDetailsAdapter userDetailsAdapter; public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException, DataAccessException { UserDetails userDetails = null; User userEntity = userDao.findByUsername(username); if (userEntity == null) { throw new UsernameNotFoundException("user not found"); } userDetails = userDetailsAdapter.buildUserFromUserEntity(userEntity); return userDetails; } } 

UserServiceImpl

 @Service public class UserServiceImpl implements UserService { @Autowired private UserDao userDao; @Autowired private PasswordEncoder passwordEncoder; @Autowired private SaltSource saltSource; public User getByUsername(String username) { return userDao.findByUsername(username); } public User getByEmail(String email) { return userDao.findByEmail(email); } public void createUser(User user) { userDao.create(user); UserDetailsAdapter userDetailsAdapter = new UserDetailsAdapter(); org.springframework.security.core.userdetails.User userDetails = userDetailsAdapter.buildUserFromUserEntity(user); String password = userDetails.getPassword(); Object salt = saltSource.getSalt(userDetails); user.setPassword(passwordEncoder.encodePassword(password, salt)); userDao.update(user); } public void updateUser(User user) { userDao.update(user); } } 

Can someone help me understand what I am missing here? Thank you very much.

+8
spring-security hibernate salt
Feb 11 '11 at 11:55
source share
2 answers

ReflectionSaltSource extracts salt from an instance of UserDetails . But you use org.springframework.security.core.userdetails.User as an implementation of UserDetails , and it does not have a property called id (instead you have this property in the UserDetailsAdapter , this does not make sense, since the UserDetailsAdapter is single).

So, you need to subclass org.springframework.security.core.userdetails.User with the id property and return it from your UserDetailsAdapter .

+7
Feb 11 '11 at 13:11
source share

Here are the updated files that made it work:

UserDetailsAdapter.java

 public class UserDetailsAdapter extends org.springframework.security.core.userdetails.User { private final Long id; public UserDetailsAdapter(User userEntity) { super(userEntity.getUsername(), userEntity.getPassword(), userEntity.isEnabled(), true, true, true, toAuthorities(userEntity.getAuthorities())); this.id = userEntity.getId(); } private static Collection<GrantedAuthority> toAuthorities(List<String> authorities) { Collection<GrantedAuthority> authorityList = new ArrayList<GrantedAuthority>(); for (String authority: authorities) { authorityList.add(new GrantedAuthorityImpl(authority)); } return authorityList; } public Long getId() { return id; } } 

UserDetailsServiceImpl.java

 @Service("userDetailsService") public class UserDetailsServiceImpl implements UserDetailsService { @Autowired private UserDao userDao; public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException, DataAccessException { UserDetails userDetails = null; User userEntity = userDao.findByUsername(username); if (userEntity == null) { throw new UsernameNotFoundException("user not found"); } userDetails = new UserDetailsAdapter(userEntity); return userDetails; } } 

UserServiceImpl.java

 @Service public class UserServiceImpl implements UserService { ... public void createUser(User user) { userDao.create(user); UserDetailsAdapter userDetails = new UserDetailsAdapter(user); String password = userDetails.getPassword(); Object salt = saltSource.getSalt(userDetails); user.setPassword(passwordEncoder.encodePassword(password, salt)); userDao.update(user); } ... } 

Thank:)

+7
Feb 25 '11 at 19:55
source share



All Articles