0、自定义登录返回的用户信息(增加个性化字段)
package middol.auth
import grails.plugin.springsecurity.userdetails.GrailsUser
import org.springframework.security.core.GrantedAuthority
/**
* @Description: 自定义登录返的用户信息(增加个性化字段,邮箱和手机号码)
* @Author: zhangjiayu@middol.com
* @CreateDate: 2020/8/5 10:46
* @Version: 1.0
*/
class MiddolUserDetails extends GrailsUser{
final String email
final String phoneNum
/**
* Constructor.
*
* @param username the username presented to the
* <code>DaoAuthenticationProvider</code>
* @param password the password that should be presented to the
* <code>DaoAuthenticationProvider</code>
* @param enabled set to <code>true</code> if the user is enabled
* @param accountNonExpired set to <code>true</code> if the account has not expired
* @param credentialsNonExpired set to <code>true</code> if the credentials have not expired
* @param accountNonLocked set to <code>true</code> if the account is not locked
* @param authorities the authorities that should be granted to the caller if they
* presented the correct username and password and the user is enabled. Not null.
* @param id the id of the domain class instance used to populate this
*/
MiddolUserDetails(String username, String password, boolean enabled, boolean accountNonExpired, boolean credentialsNonExpired, boolean accountNonLocked, Collection<GrantedAuthority> authorities, Object id, String email, String phoneNum) {
super(username, password, enabled, accountNonExpired, credentialsNonExpired, accountNonLocked, authorities, id)
this.email = email
this.phoneNum = phoneNum
}
}
1、自定义 MiddolCustomUserDetailsService 并实现 GrailsUserDetailsService
package middol.auth
import grails.core.GrailsApplication
import grails.gorm.transactions.Transactional
import grails.plugin.springsecurity.SpringSecurityUtils
import grails.plugin.springsecurity.userdetails.GrailsUser
import grails.plugin.springsecurity.userdetails.GrailsUserDetailsService
import grails.plugin.springsecurity.userdetails.NoStackUsernameNotFoundException
import groovy.transform.CompileStatic
import groovy.util.logging.Slf4j
import org.springframework.beans.factory.annotation.Autowired
import org.springframework.dao.DataAccessException
import org.springframework.security.core.authority.SimpleGrantedAuthority
import org.springframework.security.core.userdetails.UserDetails
import org.springframework.security.core.userdetails.UsernameNotFoundException
/**
* @Description: 多种登录方式(用户名,邮箱,手机号)
* @Author: zhangjiayu@middol.com
* @CreateDate: 2020/8/5 9:47
* @Version: 1.0
*/
@Slf4j
//@CompileStatic
class MiddolCustomUserDetailsService implements GrailsUserDetailsService{
@Autowired
GrailsApplication grailsApplication
static final List NO_ROLES = [new SimpleGrantedAuthority(SpringSecurityUtils.NO_ROLE)]
@Override
UserDetails loadUserByUsername(String username, boolean loadRoles) throws UsernameNotFoundException, DataAccessException {
return loadUserByUsername(username)
}
@Override
@Transactional(readOnly=true, noRollbackFor=[IllegalArgumentException, UsernameNotFoundException])
UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {
def conf = SpringSecurityUtils.securityConfig
//获取用户类名称
String userClassName = conf.userLookup?.userDomainClassName
//抓取domain
def domainClass = grailsApplication.getDomainClass(userClassName)
if (!domainClass) {
throw new IllegalArgumentException("The specified user domain class '$userClassName' is not a domain class")
}
//反射
Class<?> User = domainClass.clazz
def user = User.createCriteria().get {
or{
if (conf.userLookup.usernameIgnoreCase) {
eq((conf.userLookup.usernamePropertyName), username, [ignoreCase: true])
eq("email", username, [ignoreCase: true])
eq("phoneNum", username, [ignoreCase: true])
} else {
eq((conf.userLookup.usernamePropertyName), username)
eq("email", username)
eq("phoneNum", username)
}
}
}
if (!user) throw new NoStackUsernameNotFoundException()
def roles = user.authorities
// or if you are using role groups:
// def roles = user.authorities.collect { it.authorities }.flatten().unique()
def authorities = roles.collect {
new SimpleGrantedAuthority(it.authority)
}
return new MiddolUserDetails(user.username, user.password, user.enabled,
!user.accountExpired, !user.passwordExpired,
!user.accountLocked, authorities ?: NO_ROLES, user.id, user.email, user.phoneNum)
}
}
2、grails-app/conf/spring/resources.gorovy
中注入
userPasswordEncoderListener(UserPasswordEncoderListener)
第二种,简单写法
package middol.auth
import grails.gorm.transactions.Transactional
import grails.plugin.springsecurity.SpringSecurityUtils
import grails.plugin.springsecurity.userdetails.GrailsUser
import grails.plugin.springsecurity.userdetails.GrailsUserDetailsService
import grails.plugin.springsecurity.userdetails.NoStackUsernameNotFoundException
import groovy.transform.CompileStatic
import groovy.util.logging.Slf4j
import org.springframework.dao.DataAccessException
import org.springframework.security.core.authority.SimpleGrantedAuthority
import org.springframework.security.core.userdetails.UserDetails
import org.springframework.security.core.userdetails.UsernameNotFoundException
/**
* @Description: 多种登录方式(用户名,邮箱,手机号)
* @Author: zhangjiayu@middol.com
* @CreateDate: 2020/8/5 9:47
* @Version: 1.0
*/
@Slf4j
//@CompileStatic
class MiddolCustomUserDetailsService implements GrailsUserDetailsService{
static final List NO_ROLES = [new SimpleGrantedAuthority(SpringSecurityUtils.NO_ROLE)]
@Override
UserDetails loadUserByUsername(String username, boolean loadRoles) throws UsernameNotFoundException, DataAccessException {
return loadUserByUsername(username)
}
@Override
@Transactional(readOnly=true, noRollbackFor=[IllegalArgumentException, UsernameNotFoundException])
UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {
User user = User.findByUsernameOrEmailOrPhoneNum(username, username, username)
if (!user) throw new NoStackUsernameNotFoundException()
def roles = user.authorities
// or if you are using role groups:
// def roles = user.authorities.collect { it.authorities }.flatten().unique()
def authorities = roles.collect {
new SimpleGrantedAuthority(it.authority)
}
return new GrailsUser(user.username, user.password, user.enabled,
!user.accountExpired, !user.passwordExpired,
!user.accountLocked, authorities ?: NO_ROLES, user.id)
}
}
3、效果