Spring使用TestRestTemplate丢失会话身份验证

时间:2017-06-05 09:27:56

标签: java rest spring-boot spring-security integration-testing

我正在使用Spring的TestRestTemplate运行测试,按顺序执行2个api调用。 我的测试有这样的基础知识:

@RunWith(SpringRunner.class)
@SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT)

Api致电1:

  • GET
  • HttpSecurity始终允许此请求
  • @PreAuthorize("isAnonymous()")
  • 使用以下内容自动登录用户:

final Authentication myCustomAuthentication = ...MyCustomObjectForNewLogin)
eventPublisher.publishEvent(new AuthenticationSuccessEvent(myCustomAuthentication));
SecurityContextHolder.getContext().setAuthentication(myCustomAuthentication);
((ServletRequestAttributes) RequestContextHolder.currentRequestAttributes()).getRequest().getSession(true).setAttribute("SPRING_SECURITY_CONTEXT", SecurityContextHolder.getContext());

Api电话2:   - POST   - @PreAuthorize("hasAuthority('MyAuthorityThatHeAlwaysHasWhenLoggedIn')")

问题是: 在第二次通话时,我总是得到401 Unauthorized。我已将其追溯到以下内容: 在春课AnonymousAuthenticationFilter#doFilter:96 这种情况正在发生:

if (SecurityContextHolder.getContext().getAuthentication() == null) {
            SecurityContextHolder.getContext().setAuthentication(
                    createAuthentication((HttpServletRequest) req));

            if (logger.isDebugEnabled()) {
                logger.debug("Populated SecurityContextHolder with anonymous token: '"
                        + SecurityContextHolder.getContext().getAuthentication() + "'");
            }
        }

由于某种原因,它看起来像上下文丢失了身份验证,因此被重新填充为匿名用户。我在某些情况下读到这个值是一个ThreadLocal,这就是为什么我也在会话中设置属性所以它可以重新加载,但似乎没有重新加载。我怎么能强迫它重新加载或将值注入该持有者。 (注意这一系列的api调用通过postman完成。只在测试中失败。)

我正在执行以下呼叫:

@Autowired
private TestRestTemplate rest;

rest.getForEntity(UriComponentsBuilder.fromPath("/api1/").queryParam("myparm", "val").build(true).toUri(), String.class));
rest.postForEntity("/api2/", new HttpEntity<>(myExpectedObject, state), String.class)

0 个答案:

没有答案