Skip to content

Commit 0228570

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

File tree

2 files changed

+22
-9
lines changed

2 files changed

+22
-9
lines changed

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

Lines changed: 4 additions & 8 deletions
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.
@@ -354,11 +354,7 @@ protected void saveContext(SecurityContext context) {
354354
}
355355
return;
356356
}
357-
358-
if (httpSession == null) {
359-
httpSession = createNewSessionIfAllowed(context);
360-
}
361-
357+
httpSession = (httpSession != null) ? httpSession : createNewSessionIfAllowed(context, authentication);
362358
// If HttpSession exists, store current SecurityContext but only if it has
363359
// actually changed in this thread (see SEC-37, SEC-1307, SEC-1528)
364360
if (httpSession != null) {
@@ -381,8 +377,8 @@ private boolean contextChanged(SecurityContext context) {
381377
|| context.getAuthentication() != authBeforeExecution;
382378
}
383379

384-
private HttpSession createNewSessionIfAllowed(SecurityContext context) {
385-
if (isTransientAuthentication(context.getAuthentication())) {
380+
private HttpSession createNewSessionIfAllowed(SecurityContext context, Authentication authentication) {
381+
if (isTransientAuthentication(authentication)) {
386382
return null;
387383
}
388384

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

Lines changed: 18 additions & 1 deletion
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.
@@ -53,6 +53,7 @@
5353

5454
import static org.assertj.core.api.Assertions.assertThat;
5555
import static org.mockito.ArgumentMatchers.anyBoolean;
56+
import static org.mockito.BDDMockito.given;
5657
import static org.mockito.Mockito.never;
5758
import static org.mockito.Mockito.reset;
5859
import static org.mockito.Mockito.verify;
@@ -719,6 +720,22 @@ public void saveContextWhenTransientAuthenticationWithCustomAnnotationThenSkippe
719720
assertThat(session).isNull();
720721
}
721722

723+
// gh-8947
724+
@Test
725+
public void saveContextWhenSecurityContextAuthenticationUpdatedToNullThenSkipped() {
726+
HttpSessionSecurityContextRepository repo = new HttpSessionSecurityContextRepository();
727+
MockHttpServletRequest request = new MockHttpServletRequest();
728+
MockHttpServletResponse response = new MockHttpServletResponse();
729+
HttpRequestResponseHolder holder = new HttpRequestResponseHolder(request, response);
730+
SomeOtherTransientAuthentication authentication = new SomeOtherTransientAuthentication();
731+
repo.loadContext(holder);
732+
SecurityContext context = mock(SecurityContext.class);
733+
given(context.getAuthentication()).willReturn(authentication).willReturn(null);
734+
repo.saveContext(context, holder.getRequest(), holder.getResponse());
735+
MockHttpSession session = (MockHttpSession) request.getSession(false);
736+
assertThat(session).isNull();
737+
}
738+
722739
private SecurityContext createSecurityContext(UserDetails userDetails) {
723740
UsernamePasswordAuthenticationToken token = new UsernamePasswordAuthenticationToken(userDetails,
724741
userDetails.getPassword(), userDetails.getAuthorities());

0 commit comments

Comments
 (0)