java - 为什么刷新访问 token 会未经授权?

标签 java spring-boot jwt

随着访问 token 过期,客户端使用/refresh 端点发送 GET 请求,但以 401-unauthorized 结束。

我已在 webConfig 中配置了此请求。因此,它不需要授权。我已在/refresh 请求的 header 中传递了访问 token 。

注意:如果我不在/refresh 请求的 header 中传递 token ,则效果很好。

JwtAuthenticationController.java:

@RestController
public class JwtAuthenticationController {

    @RequestMapping(value = "/refresh", method = RequestMethod.GET)
    public ResponseEntity<?> refreshAuthenticationToken(HttpServletRequest request) {

        final String token = request.getHeader("Authorization");

        final String username = jwtUtils.getUsernameFromToken(token);
        final UserDetails user =  userDetailsService.loadUserByUsername(username);

        if ((user.getUsername()).equals(username) && jwtUtils.isTokenExpired(token)) {
            final String refreshedToken = jwtUtils.refreshToken(token);
            return ResponseEntity.ok(new JwtAuthenticationResponse(refreshedToken));
        } 
        else {
            return ResponseEntity.badRequest().body(null);
        }
    }
}

WebSecurityConfig.java

@Configuration
@EnableWebSecurity
@EnableGlobalMethodSecurity(prePostEnabled = true)
public class WebSecurityConfig extends WebSecurityConfigurerAdapter {

    @Override
    protected void configure(HttpSecurity httpSecurity) throws Exception {
        httpSecurity.csrf().disable()             
                .exceptionHandling()
               .antMatchers("/register","/refresh")
               .permitAll()                   
               .anyRequest().authenticated();                     

        httpSecurity.addFilterBefore(authenticationTokenFilterBean(), UsernamePasswordAuthenticationFilter.class);
        httpSecurity.headers().cacheControl().disable();
    }
}

JwtAuthenticationFilter.java

@Component
public class JwtAuthenticationFilter extends OncePerRequestFilter {
    @Override
    protected void doFilterInternal(HttpServletRequest request, HttpServletResponse response, FilterChain chain)
        throws ServletException, IOException {
        String authToken = request.getHeader(AUTHORIZATION_HEADER);

        if (authToken != null && authToken.startsWith(BEARER_PREFIX)) {
            try {
                authToken = authToken.substring(BEARER_PREFIX_LENGTH);
                username = jwtUtils.getUsernameFromToken(authToken);
            }catch (IllegalArgumentException e) {
                System.out.println("Unable to get JWT Token");
            } catch (ExpiredJwtException e) {
                System.out.println("JWT Token has expired");
            }
        }
        else {
        logger.warn("JWT Token does not begin with Bearer String");
   }
}

JwtUtils.java

private Claims getClaimsFromToken(String token) {
     return Jwts.parser()
                .setSigningKey(secret)
                .requireIssuer(issuer)
                .parseClaimsJws(token)
                .getBody();
}

error log

我无法找出为什么会发生这种情况?使用客户端发送的刷新 token 获取新访问 token 的解决方案是什么。

最佳答案

If I don't pass token in header of /refresh request, It worked fine.

这可能是由于 JwtAuthenticationFilter 造成的。我认为您还应该从检查中排除 /refresh ,因此:

   if (!request.getRequestURI().contains("/refresh") {
    if (authToken != null && authToken.startsWith(BEARER_PREFIX)) {
    //same logic
    }
   }

关于java - 为什么刷新访问 token 会未经授权?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/58788903/

相关文章:

java - Mockito - 使用本地方法模拟类

java - JBI 和 SCA 之间有何区别/相似之处

java - 在 Spring Boot 应用程序中加载不同的应用程序上下文

spring-boot - 从 redis 中删除键/值 - 幻键未删除

javascript - Redux和Token认证: how to redirect the user

python - 我应该如何处理 @jwt_required 装饰器中引发的异常? (在 flask-jwt-extended 中)

java - JodaTime 如何正确解析 dd-MM YYyy 到 DateTime

java - 在 Android 中使用 android.net 或 java.net 哪个 Socket API 进行 UDP 通信?

spring - 用于开发的Jar和用于Gradle部署的War

node.js - 如何使用 Express-JWT 处理错误