Skip to content

Commit 4d18d06

Browse files
Adjust createNewSessionIfAllowed to prevent NPE
Ensure that isTransientAuthentication reuses the same authentication object from saveContext Closes gh-8947
1 parent 9d0db20 commit 4d18d06

File tree

2 files changed

+21
-5
lines changed

2 files changed

+21
-5
lines changed

web/src/main/java/org/springframework/security/web/context/HttpSessionSecurityContextRepository.java

+4-4
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2002-2016 the original author or authors.
2+
* Copyright 2002-2021 the original author or authors.
33
*
44
* Licensed under the Apache License, Version 2.0 (the "License");
55
* you may not use this file except in compliance with the License.
@@ -348,7 +348,7 @@ protected void saveContext(SecurityContext context) {
348348
}
349349
return;
350350
}
351-
httpSession = (httpSession != null) ? httpSession : createNewSessionIfAllowed(context);
351+
httpSession = (httpSession != null) ? httpSession : createNewSessionIfAllowed(context, authentication);
352352
// If HttpSession exists, store current SecurityContext but only if it has
353353
// actually changed in this thread (see SEC-37, SEC-1307, SEC-1528)
354354
if (httpSession != null) {
@@ -369,8 +369,8 @@ private boolean contextChanged(SecurityContext context) {
369369
|| context.getAuthentication() != this.authBeforeExecution;
370370
}
371371

372-
private HttpSession createNewSessionIfAllowed(SecurityContext context) {
373-
if (isTransientAuthentication(context.getAuthentication())) {
372+
private HttpSession createNewSessionIfAllowed(SecurityContext context, Authentication authentication) {
373+
if (isTransientAuthentication(authentication)) {
374374
return null;
375375
}
376376
if (this.httpSessionExistedAtStartOfRequest) {

web/src/test/java/org/springframework/security/web/context/HttpSessionSecurityContextRepositoryTests.java

+17-1
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2002-2016 the original author or authors.
2+
* Copyright 2002-2021 the original author or authors.
33
*
44
* Licensed under the Apache License, Version 2.0 (the "License");
55
* you may not use this file except in compliance with the License.
@@ -628,6 +628,22 @@ public void saveContextWhenTransientAuthenticationWithCustomAnnotationThenSkippe
628628
assertThat(session).isNull();
629629
}
630630

631+
// gh-8947
632+
@Test
633+
public void saveContextWhenSecurityContextAuthenticationUpdatedToNullThenSkipped() {
634+
HttpSessionSecurityContextRepository repo = new HttpSessionSecurityContextRepository();
635+
MockHttpServletRequest request = new MockHttpServletRequest();
636+
MockHttpServletResponse response = new MockHttpServletResponse();
637+
HttpRequestResponseHolder holder = new HttpRequestResponseHolder(request, response);
638+
SomeOtherTransientAuthentication authentication = new SomeOtherTransientAuthentication();
639+
repo.loadContext(holder);
640+
SecurityContext context = mock(SecurityContext.class);
641+
given(context.getAuthentication()).willReturn(authentication).willReturn(null);
642+
repo.saveContext(context, holder.getRequest(), holder.getResponse());
643+
MockHttpSession session = (MockHttpSession) request.getSession(false);
644+
assertThat(session).isNull();
645+
}
646+
631647
private SecurityContext createSecurityContext(UserDetails userDetails) {
632648
UsernamePasswordAuthenticationToken token = new UsernamePasswordAuthenticationToken(userDetails,
633649
userDetails.getPassword(), userDetails.getAuthorities());

0 commit comments

Comments
 (0)