Spring Security OAuth2 JWT 自定义token携带的信息

oauth2在jwt仅支持用户名和权限。

以下方法实现 token 中添加自定义的参数:

  1. 自定义 UserDetails 

public class CustomerDetails implements UserDetails {
	
	private String id;

	private String username;

	private String password;
	
	private Set<GrantedAuthority> authorities;

	private boolean accountNonExpired;

	private boolean accountNonLocked;

	private boolean credentialsNonExpired;

	private boolean enabled;
	
	public CustomerDetails() {
		authorities = new HashSet<GrantedAuthority>();
	}
	
	public void isConfig() {
		this.accountNonExpired = true;
		this.accountNonLocked = true;
		this.credentialsNonExpired = true;
		this.enabled = true;
	}

	@Override
	public Collection<? extends GrantedAuthority> getAuthorities() {
		return authorities;
	}
	
	public void addAuthorities(GrantedAuthority authority) {
		authorities.add(authority);
	}
	
	public void setAuthorities(Collection<? extends GrantedAuthority> authorities) {
		this.authorities = Collections.unmodifiableSet(sortAuthorities(authorities));
	}
	
	private static SortedSet<GrantedAuthority> sortAuthorities(Collection<? extends GrantedAuthority> authorities) {
		Assert.notNull(authorities, "Cannot pass a null GrantedAuthority collection");
		SortedSet<GrantedAuthority> sortedAuthorities = new TreeSet<>(new AuthorityComparator());
		for (GrantedAuthority grantedAuthority : authorities) {
			Assert.notNull(grantedAuthority, "GrantedAuthority list cannot contain any null elements");
			sortedAuthorities.add(grantedAuthority);
		}
		return sortedAuthorities;
	}

	public String getId() {
		return id;
	}

	public void setId(String id) {
		this.id = id;
	}

	@Override
	public String getPassword() {
		return this.password;
	}
	
	
	public void setPassword(String password) {
		this.password = password;
	}

	@Override
	public String getUsername() {
		return this.username;
	}
	
	public void setUsername(String username) {
		this.username = username;
	}

	@Override
	public boolean isEnabled() {
		return this.enabled;
	}
	
	public void setEnabled(boolean enabled) {
		this.enabled = enabled;
	}

	@Override
	public boolean isAccountNonExpired() {
		return this.accountNonExpired;
	}
	
	public void setAccountNonExpired(boolean accountNonExpired) {
		this.accountNonExpired = accountNonExpired;
	}

	@Override
	public boolean isAccountNonLocked() {
		return this.accountNonLocked;
	}
	
	public void setAccountNonLocked(boolean accountNonLocked) {
		this.accountNonLocked = accountNonLocked;
	}

	@Override
	public boolean isCredentialsNonExpired() {
		return true; //this.credentialsNonExpired;
	}
	
	public void setCredentialsNonExpired(boolean credentialsNonExpired) {
		this.credentialsNonExpired = credentialsNonExpired;
	}
	
	private static class AuthorityComparator implements Comparator<GrantedAuthority>, Serializable {

		private static final long serialVersionUID = SpringSecurityCoreVersion.SERIAL_VERSION_UID;

		@Override
		public int compare(GrantedAuthority g1, GrantedAuthority g2) {
			// Neither should ever be null as each entry is checked before adding it to
			// the set. If the authority is null, it is a custom authority and should
			// precede others.
			if (g2.getAuthority() == null) {
				return -1;
			}
			if (g1.getAuthority() == null) {
				return 1;
			}
			return g1.getAuthority().compareTo(g2.getAuthority());
		}
	}
}

2. UserDetailsService 中使用上面的 CustomerDetails

@Service
public class UserDaoSecurityService implements UserDetailsService{
	
	@Autowired
	private UserDao userDao;
	
	@Autowired
	private PermissionDao pDao;	
	
	@Override
	public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {
		//读取数据库中的用户信息创建 UserDetails
		PiUser user = userDao.findByUsername(username);
		CustomerDetails userDetails = new CustomerDetails();
		if(user != null) {
			List<PiPermission> permissions = pDao.findUserPermissions(user.id);
			List<GrantedAuthority> authList = new ArrayList<GrantedAuthority>();
			for (PiPermission per : permissions) {
				authList.add(new SimpleGrantedAuthority(per.getCode()));
			}
			userDetails.setId("" + user.id);
			userDetails.setUsername(user.username);
			userDetails.setPassword(user.password);
			userDetails.setAuthorities(authList);
			userDetails.isConfig();
			//userDetails = User.withUsername(user.username).password(user.password).authorities(authList).build();
		}else {
			throw new BadCredentialsException("用户名不存在");
		}
		return userDetails;
	}
}

3. 自定义 DefaultAccessTokenConverter

public class JwtCustomerAccessTokenConverter extends DefaultAccessTokenConverter {

	public JwtCustomerAccessTokenConverter() {
		super.setUserTokenConverter(new CustomerUserAuthenticationConverter());
	}

	private class CustomerUserAuthenticationConverter extends DefaultUserAuthenticationConverter {

		@Override
		public Map<String, ?> convertUserAuthentication(Authentication authentication) {
			LinkedHashMap<String, Object> response = new LinkedHashMap<String, Object>();
			//这里添加你的参数
			response.put("id", ((PiUserDetails) authentication.getPrincipal()).getId());
			response.put("username", ((PiUserDetails) authentication.getPrincipal()).getUsername());
			if (authentication.getAuthorities() != null && !authentication.getAuthorities().isEmpty()) {
				response.put("authorities", AuthorityUtils.authorityListToSet(authentication.getAuthorities()));
			}

			return response;
		}
	}
}

4. 配置 token 生成策略

@Configuration
public class JwtTokeStoreConfig {
	
	private String KEY = "aaa";
	
	@Bean
	public JwtTokenStore tokenStore() {
		return new JwtTokenStore(accessTokenConverter());
	}
	
	@Bean
	public JwtAccessTokenConverter accessTokenConverter() {
		JwtAccessTokenConverter converter = new JwtAccessTokenConverter();
		converter.setSigningKey(KEY);
		//使用自定义的 TokenConverter
		converter.setAccessTokenConverter(new JwtCustomerAccessTokenConverter());
		return converter;
	}		

}

 

  • 1
    点赞
  • 9
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值