java - Spring Boot WebMvcTest 对于 GET 方法返回 302 而不是 401

标签 java spring-boot testing spring-security jwt

我有一个带有 REST 端点的应用程序,这些端点通过 JWT 身份验证(外部资源服务器)进行保护。将我的项目从 spring-boot 2.2.7 升级到 2.4.3 后,一些 WebMvcTest 集成测试失败。具体来说,没有 JWT token 的 GET 请求的测试用例 - 以前它们会返回 401 UNAUTHORIZED,现在它们返回 302 REDIRECThttp://localhost/oauth2/authorization/keycloak

@Test
void shouldNotAllowAccessForUnauthenticatedUsers() throws Exception {
    // given
    var params = createParams();

    // when / then
    mockMvc.perform(get(MY_URI)
            .params(params)
            .contentType(MediaType.APPLICATION_JSON)
            .content(new byte[0]))
            .andExpect(status().isUnauthorized());
}

不导入自定义 Web 安全配置,仅导入 @WebMvcTest@AutoConfigureMockMvc 以及相关 Controller 和映射器 bean 的 @ContextConfiguration

没有身份验证的测试中的

POST 方法返回 403(与升级之前一样)。此问题仅在测试中出现 - 当应用程序运行时,调用任何没有 token 的端点都会导致 401

有没有办法将WebMvcTest配置为返回401而不是302

最佳答案

Andy Wilkinson 的问题启发我更深入地研究这个问题,因为没有真正将 Keycloak 适配器添加为显式依赖项(仅 spring-boot-starter-securityspring-boot-starter -oauth2-clientspring-boot-starter-oauth2-resource-server),但是这里的配置中提到了keycloak:

  security:
    oauth2:
      resourceserver:
        jwt:
          issuer-uri: ...
      client:
        registration:
          keycloak:
            client-id: ...
            client-secret: ...
            authorization-grant-type: ...
            scope: ...
        provider:
          keycloak:
            authorization-uri: ...
            token-uri: ...

对应用端点的请求使用来自颁发者 uri 的 JWT token 进行身份验证,但对其他服务的 HTTP 客户端调用则使用 Keycloak 中的客户端注册进行身份验证(用于服务到服务身份验证)。

无论如何,我相信升级后的这种行为变化是由于 Spring Boot 2.3 中引入的功能造成的。 ,具体来说:“@WebMvcTest 中的 OAuth2 参数绑定(bind)”。 OAuth2 自动配置现已包含在 @WebMvcTest 中,这导致此测试尝试使用客户端配置重定向到 keycloak(在运行时仅用于服务到服务)。

我通过使用注释测试类解决了该问题:

@ImportAutoConfiguration(exclude = {OAuth2ClientAutoConfiguration.class, OAuth2ResourceServerAutoConfiguration.class})

(还必须排除资源服务器配置才能正确处理模拟的 JWT。)

也许有人会发现这很有帮助。

关于java - Spring Boot WebMvcTest 对于 GET 方法返回 302 而不是 401,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/67904791/

相关文章:

java - 创建主方法与静态方法的实例

java - 学生投票写入文件和从文件读取

java - 从 json 响应中解析一个值,其中大部分负载都是冗余的

java - 使用 LibGDX 顺时针旋转图像

java - IntelliJ 下的 Scala 调试非常慢

ruby - 如何根据特征实现 FactoryGirl 的条件行为

c# - 在 Entity Framework 中测试 View 模型

testing - 强制在另一个之前运行代码接受测试

java - 在 Spring 中,我可以将 @RequestBody 中的单个字段设为可选吗?

java - 无法序列化 Jackson xml 中的 OffsetDateTime