Add support for session save mode
This commit introduces SaveMode enum that individual SessionRepository implementations use to allow customization of the way they handle save operation in terms of tracking delta of changes. Resolves: #1466
This commit is contained in:
@@ -51,6 +51,7 @@ import org.springframework.session.FindByIndexNameSessionRepository;
|
||||
import org.springframework.session.IndexResolver;
|
||||
import org.springframework.session.MapSession;
|
||||
import org.springframework.session.PrincipalNameIndexResolver;
|
||||
import org.springframework.session.SaveMode;
|
||||
import org.springframework.session.Session;
|
||||
import org.springframework.transaction.PlatformTransactionManager;
|
||||
import org.springframework.transaction.TransactionDefinition;
|
||||
@@ -237,6 +238,8 @@ public class JdbcOperationsSessionRepository
|
||||
|
||||
private LobHandler lobHandler = new DefaultLobHandler();
|
||||
|
||||
private SaveMode saveMode = SaveMode.ON_SET_ATTRIBUTE;
|
||||
|
||||
/**
|
||||
* Create a new {@link JdbcOperationsSessionRepository} instance which uses the
|
||||
* provided {@link JdbcOperations} to manage sessions.
|
||||
@@ -383,13 +386,22 @@ public class JdbcOperationsSessionRepository
|
||||
this.conversionService = conversionService;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the save mode.
|
||||
* @param saveMode the save mode
|
||||
*/
|
||||
public void setSaveMode(SaveMode saveMode) {
|
||||
Assert.notNull(saveMode, "saveMode must not be null");
|
||||
this.saveMode = saveMode;
|
||||
}
|
||||
|
||||
@Override
|
||||
public JdbcSession createSession() {
|
||||
JdbcSession session = new JdbcSession();
|
||||
MapSession delegate = new MapSession();
|
||||
if (this.defaultMaxInactiveInterval != null) {
|
||||
session.setMaxInactiveInterval(Duration.ofSeconds(this.defaultMaxInactiveInterval));
|
||||
delegate.setMaxInactiveInterval(Duration.ofSeconds(this.defaultMaxInactiveInterval));
|
||||
}
|
||||
return session;
|
||||
return new JdbcSession(delegate, UUID.randomUUID().toString(), true);
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -708,17 +720,13 @@ public class JdbcOperationsSessionRepository
|
||||
|
||||
private Map<String, DeltaValue> delta = new HashMap<>();
|
||||
|
||||
JdbcSession() {
|
||||
this.delegate = new MapSession();
|
||||
this.isNew = true;
|
||||
this.primaryKey = UUID.randomUUID().toString();
|
||||
}
|
||||
|
||||
JdbcSession(String primaryKey, Session delegate) {
|
||||
Assert.notNull(primaryKey, "primaryKey cannot be null");
|
||||
Assert.notNull(delegate, "Session cannot be null");
|
||||
this.primaryKey = primaryKey;
|
||||
JdbcSession(MapSession delegate, String primaryKey, boolean isNew) {
|
||||
this.delegate = delegate;
|
||||
this.primaryKey = primaryKey;
|
||||
this.isNew = isNew;
|
||||
if (this.isNew || (JdbcOperationsSessionRepository.this.saveMode == SaveMode.ALWAYS)) {
|
||||
getAttributeNames().forEach((attributeName) -> this.delta.put(attributeName, DeltaValue.UPDATED));
|
||||
}
|
||||
}
|
||||
|
||||
boolean isNew() {
|
||||
@@ -757,7 +765,15 @@ public class JdbcOperationsSessionRepository
|
||||
@Override
|
||||
public <T> T getAttribute(String attributeName) {
|
||||
Supplier<T> supplier = this.delegate.getAttribute(attributeName);
|
||||
return (supplier != null) ? supplier.get() : null;
|
||||
if (supplier == null) {
|
||||
return null;
|
||||
}
|
||||
T attributeValue = supplier.get();
|
||||
if (attributeValue != null
|
||||
&& JdbcOperationsSessionRepository.this.saveMode.equals(SaveMode.ON_GET_ATTRIBUTE)) {
|
||||
this.delta.put(attributeName, DeltaValue.UPDATED);
|
||||
}
|
||||
return attributeValue;
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -848,7 +864,7 @@ public class JdbcOperationsSessionRepository
|
||||
delegate.setCreationTime(Instant.ofEpochMilli(rs.getLong("CREATION_TIME")));
|
||||
delegate.setLastAccessedTime(Instant.ofEpochMilli(rs.getLong("LAST_ACCESS_TIME")));
|
||||
delegate.setMaxInactiveInterval(Duration.ofSeconds(rs.getInt("MAX_INACTIVE_INTERVAL")));
|
||||
session = new JdbcSession(primaryKey, delegate);
|
||||
session = new JdbcSession(delegate, primaryKey, false);
|
||||
}
|
||||
String attributeName = rs.getString("ATTRIBUTE_NAME");
|
||||
if (attributeName != null) {
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2014-2017 the original author or authors.
|
||||
* Copyright 2014-2019 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -27,6 +27,7 @@ import javax.sql.DataSource;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.context.annotation.Import;
|
||||
import org.springframework.session.MapSession;
|
||||
import org.springframework.session.SaveMode;
|
||||
import org.springframework.session.config.annotation.web.http.EnableSpringHttpSession;
|
||||
import org.springframework.session.jdbc.JdbcOperationsSessionRepository;
|
||||
import org.springframework.session.web.http.SessionRepositoryFilter;
|
||||
@@ -96,4 +97,12 @@ public @interface EnableJdbcHttpSession {
|
||||
*/
|
||||
String cleanupCron() default JdbcHttpSessionConfiguration.DEFAULT_CLEANUP_CRON;
|
||||
|
||||
/**
|
||||
* Save mode for the session. The default is {@link SaveMode#ON_SET_ATTRIBUTE}, which
|
||||
* only saves changes made to session.
|
||||
* @return the save mode
|
||||
* @since 2.2.0
|
||||
*/
|
||||
SaveMode saveMode() default SaveMode.ON_SET_ATTRIBUTE;
|
||||
|
||||
}
|
||||
|
||||
@@ -43,6 +43,7 @@ import org.springframework.scheduling.annotation.EnableScheduling;
|
||||
import org.springframework.scheduling.annotation.SchedulingConfigurer;
|
||||
import org.springframework.scheduling.config.ScheduledTaskRegistrar;
|
||||
import org.springframework.session.MapSession;
|
||||
import org.springframework.session.SaveMode;
|
||||
import org.springframework.session.config.annotation.web.http.SpringHttpSessionConfiguration;
|
||||
import org.springframework.session.jdbc.JdbcOperationsSessionRepository;
|
||||
import org.springframework.session.jdbc.config.annotation.SpringSessionDataSource;
|
||||
@@ -77,6 +78,8 @@ public class JdbcHttpSessionConfiguration extends SpringHttpSessionConfiguration
|
||||
|
||||
private String cleanupCron = DEFAULT_CLEANUP_CRON;
|
||||
|
||||
private SaveMode saveMode = SaveMode.ON_SET_ATTRIBUTE;
|
||||
|
||||
private DataSource dataSource;
|
||||
|
||||
private PlatformTransactionManager transactionManager;
|
||||
@@ -100,6 +103,7 @@ public class JdbcHttpSessionConfiguration extends SpringHttpSessionConfiguration
|
||||
sessionRepository.setTableName(this.tableName);
|
||||
}
|
||||
sessionRepository.setDefaultMaxInactiveInterval(this.maxInactiveIntervalInSeconds);
|
||||
sessionRepository.setSaveMode(this.saveMode);
|
||||
if (this.lobHandler != null) {
|
||||
sessionRepository.setLobHandler(this.lobHandler);
|
||||
}
|
||||
@@ -142,6 +146,10 @@ public class JdbcHttpSessionConfiguration extends SpringHttpSessionConfiguration
|
||||
this.cleanupCron = cleanupCron;
|
||||
}
|
||||
|
||||
public void setSaveMode(SaveMode saveMode) {
|
||||
this.saveMode = saveMode;
|
||||
}
|
||||
|
||||
@Autowired
|
||||
public void setDataSource(@SpringSessionDataSource ObjectProvider<DataSource> springSessionDataSource,
|
||||
ObjectProvider<DataSource> dataSource) {
|
||||
@@ -199,6 +207,7 @@ public class JdbcHttpSessionConfiguration extends SpringHttpSessionConfiguration
|
||||
if (StringUtils.hasText(cleanupCron)) {
|
||||
this.cleanupCron = cleanupCron;
|
||||
}
|
||||
this.saveMode = attributes.getEnum("saveMode");
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -22,6 +22,8 @@ import java.util.ArrayList;
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.UUID;
|
||||
import java.util.function.Supplier;
|
||||
|
||||
import org.junit.jupiter.api.BeforeEach;
|
||||
import org.junit.jupiter.api.Test;
|
||||
@@ -36,6 +38,7 @@ import org.springframework.security.core.Authentication;
|
||||
import org.springframework.security.core.authority.AuthorityUtils;
|
||||
import org.springframework.session.FindByIndexNameSessionRepository;
|
||||
import org.springframework.session.MapSession;
|
||||
import org.springframework.session.SaveMode;
|
||||
import org.springframework.session.Session;
|
||||
import org.springframework.transaction.PlatformTransactionManager;
|
||||
import org.springframework.transaction.TransactionDefinition;
|
||||
@@ -224,6 +227,12 @@ class JdbcOperationsSessionRepositoryTests {
|
||||
.withMessage("conversionService must not be null");
|
||||
}
|
||||
|
||||
@Test
|
||||
void setSaveModeNull() {
|
||||
assertThatIllegalArgumentException().isThrownBy(() -> this.repository.setSaveMode(null))
|
||||
.withMessage("saveMode must not be null");
|
||||
}
|
||||
|
||||
@Test
|
||||
void createSessionDefaultMaxInactiveInterval() {
|
||||
JdbcOperationsSessionRepository.JdbcSession session = this.repository.createSession();
|
||||
@@ -292,8 +301,8 @@ class JdbcOperationsSessionRepositoryTests {
|
||||
|
||||
@Test
|
||||
void saveUpdatedAddSingleAttribute() {
|
||||
JdbcOperationsSessionRepository.JdbcSession session = this.repository.new JdbcSession("primaryKey",
|
||||
new MapSession());
|
||||
JdbcOperationsSessionRepository.JdbcSession session = this.repository.new JdbcSession(new MapSession(),
|
||||
"primaryKey", false);
|
||||
session.setAttribute("testName", "testValue");
|
||||
|
||||
this.repository.save(session);
|
||||
@@ -307,8 +316,8 @@ class JdbcOperationsSessionRepositoryTests {
|
||||
|
||||
@Test
|
||||
void saveUpdatedAddMultipleAttributes() {
|
||||
JdbcOperationsSessionRepository.JdbcSession session = this.repository.new JdbcSession("primaryKey",
|
||||
new MapSession());
|
||||
JdbcOperationsSessionRepository.JdbcSession session = this.repository.new JdbcSession(new MapSession(),
|
||||
"primaryKey", false);
|
||||
session.setAttribute("testName1", "testValue1");
|
||||
session.setAttribute("testName2", "testValue2");
|
||||
|
||||
@@ -323,8 +332,8 @@ class JdbcOperationsSessionRepositoryTests {
|
||||
|
||||
@Test
|
||||
void saveUpdatedModifySingleAttribute() {
|
||||
JdbcOperationsSessionRepository.JdbcSession session = this.repository.new JdbcSession("primaryKey",
|
||||
new MapSession());
|
||||
JdbcOperationsSessionRepository.JdbcSession session = this.repository.new JdbcSession(new MapSession(),
|
||||
"primaryKey", false);
|
||||
session.setAttribute("testName", "testValue");
|
||||
session.clearChangeFlags();
|
||||
session.setAttribute("testName", "testValue");
|
||||
@@ -340,8 +349,8 @@ class JdbcOperationsSessionRepositoryTests {
|
||||
|
||||
@Test
|
||||
void saveUpdatedModifyMultipleAttributes() {
|
||||
JdbcOperationsSessionRepository.JdbcSession session = this.repository.new JdbcSession("primaryKey",
|
||||
new MapSession());
|
||||
JdbcOperationsSessionRepository.JdbcSession session = this.repository.new JdbcSession(new MapSession(),
|
||||
"primaryKey", false);
|
||||
session.setAttribute("testName1", "testValue1");
|
||||
session.setAttribute("testName2", "testValue2");
|
||||
session.clearChangeFlags();
|
||||
@@ -359,8 +368,8 @@ class JdbcOperationsSessionRepositoryTests {
|
||||
|
||||
@Test
|
||||
void saveUpdatedRemoveSingleAttribute() {
|
||||
JdbcOperationsSessionRepository.JdbcSession session = this.repository.new JdbcSession("primaryKey",
|
||||
new MapSession());
|
||||
JdbcOperationsSessionRepository.JdbcSession session = this.repository.new JdbcSession(new MapSession(),
|
||||
"primaryKey", false);
|
||||
session.setAttribute("testName", "testValue");
|
||||
session.clearChangeFlags();
|
||||
session.removeAttribute("testName");
|
||||
@@ -376,8 +385,8 @@ class JdbcOperationsSessionRepositoryTests {
|
||||
|
||||
@Test
|
||||
void saveUpdatedRemoveNonExistingAttribute() {
|
||||
JdbcOperationsSessionRepository.JdbcSession session = this.repository.new JdbcSession("primaryKey",
|
||||
new MapSession());
|
||||
JdbcOperationsSessionRepository.JdbcSession session = this.repository.new JdbcSession(new MapSession(),
|
||||
"primaryKey", false);
|
||||
session.removeAttribute("testName");
|
||||
|
||||
this.repository.save(session);
|
||||
@@ -389,8 +398,8 @@ class JdbcOperationsSessionRepositoryTests {
|
||||
|
||||
@Test
|
||||
void saveUpdatedRemoveMultipleAttributes() {
|
||||
JdbcOperationsSessionRepository.JdbcSession session = this.repository.new JdbcSession("primaryKey",
|
||||
new MapSession());
|
||||
JdbcOperationsSessionRepository.JdbcSession session = this.repository.new JdbcSession(new MapSession(),
|
||||
"primaryKey", false);
|
||||
session.setAttribute("testName1", "testValue1");
|
||||
session.setAttribute("testName2", "testValue2");
|
||||
session.clearChangeFlags();
|
||||
@@ -408,8 +417,8 @@ class JdbcOperationsSessionRepositoryTests {
|
||||
|
||||
@Test // gh-1070
|
||||
void saveUpdatedAddAndModifyAttribute() {
|
||||
JdbcOperationsSessionRepository.JdbcSession session = this.repository.new JdbcSession("primaryKey",
|
||||
new MapSession());
|
||||
JdbcOperationsSessionRepository.JdbcSession session = this.repository.new JdbcSession(new MapSession(),
|
||||
"primaryKey", false);
|
||||
session.setAttribute("testName", "testValue1");
|
||||
session.setAttribute("testName", "testValue2");
|
||||
|
||||
@@ -424,8 +433,8 @@ class JdbcOperationsSessionRepositoryTests {
|
||||
|
||||
@Test // gh-1070
|
||||
void saveUpdatedAddAndRemoveAttribute() {
|
||||
JdbcOperationsSessionRepository.JdbcSession session = this.repository.new JdbcSession("primaryKey",
|
||||
new MapSession());
|
||||
JdbcOperationsSessionRepository.JdbcSession session = this.repository.new JdbcSession(new MapSession(),
|
||||
"primaryKey", false);
|
||||
session.setAttribute("testName", "testValue");
|
||||
session.removeAttribute("testName");
|
||||
|
||||
@@ -438,8 +447,8 @@ class JdbcOperationsSessionRepositoryTests {
|
||||
|
||||
@Test // gh-1070
|
||||
void saveUpdatedModifyAndRemoveAttribute() {
|
||||
JdbcOperationsSessionRepository.JdbcSession session = this.repository.new JdbcSession("primaryKey",
|
||||
new MapSession());
|
||||
JdbcOperationsSessionRepository.JdbcSession session = this.repository.new JdbcSession(new MapSession(),
|
||||
"primaryKey", false);
|
||||
session.setAttribute("testName", "testValue1");
|
||||
session.clearChangeFlags();
|
||||
session.setAttribute("testName", "testValue2");
|
||||
@@ -456,8 +465,8 @@ class JdbcOperationsSessionRepositoryTests {
|
||||
|
||||
@Test // gh-1070
|
||||
void saveUpdatedRemoveAndAddAttribute() {
|
||||
JdbcOperationsSessionRepository.JdbcSession session = this.repository.new JdbcSession("primaryKey",
|
||||
new MapSession());
|
||||
JdbcOperationsSessionRepository.JdbcSession session = this.repository.new JdbcSession(new MapSession(),
|
||||
"primaryKey", false);
|
||||
session.setAttribute("testName", "testValue1");
|
||||
session.clearChangeFlags();
|
||||
session.removeAttribute("testName");
|
||||
@@ -474,8 +483,8 @@ class JdbcOperationsSessionRepositoryTests {
|
||||
|
||||
@Test
|
||||
void saveUpdatedLastAccessedTime() {
|
||||
JdbcOperationsSessionRepository.JdbcSession session = this.repository.new JdbcSession("primaryKey",
|
||||
new MapSession());
|
||||
JdbcOperationsSessionRepository.JdbcSession session = this.repository.new JdbcSession(new MapSession(),
|
||||
"primaryKey", false);
|
||||
session.setLastAccessedTime(Instant.now());
|
||||
|
||||
this.repository.save(session);
|
||||
@@ -489,8 +498,8 @@ class JdbcOperationsSessionRepositoryTests {
|
||||
|
||||
@Test
|
||||
void saveUnchanged() {
|
||||
JdbcOperationsSessionRepository.JdbcSession session = this.repository.new JdbcSession("primaryKey",
|
||||
new MapSession());
|
||||
JdbcOperationsSessionRepository.JdbcSession session = this.repository.new JdbcSession(new MapSession(),
|
||||
"primaryKey", false);
|
||||
|
||||
this.repository.save(session);
|
||||
|
||||
@@ -516,7 +525,7 @@ class JdbcOperationsSessionRepositoryTests {
|
||||
@Test
|
||||
@SuppressWarnings("unchecked")
|
||||
void getSessionExpired() {
|
||||
Session expired = this.repository.new JdbcSession();
|
||||
Session expired = this.repository.createSession();
|
||||
expired.setLastAccessedTime(Instant.now().minusSeconds(MapSession.DEFAULT_MAX_INACTIVE_INTERVAL_SECONDS + 1));
|
||||
given(this.jdbcOperations.query(isA(String.class), isA(PreparedStatementSetter.class),
|
||||
isA(ResultSetExtractor.class))).willReturn(Collections.singletonList(expired));
|
||||
@@ -533,7 +542,7 @@ class JdbcOperationsSessionRepositoryTests {
|
||||
@Test
|
||||
@SuppressWarnings("unchecked")
|
||||
void getSessionFound() {
|
||||
Session saved = this.repository.new JdbcSession("primaryKey", new MapSession());
|
||||
Session saved = this.repository.new JdbcSession(new MapSession(), "primaryKey", false);
|
||||
saved.setAttribute("savedName", "savedValue");
|
||||
given(this.jdbcOperations.query(isA(String.class), isA(PreparedStatementSetter.class),
|
||||
isA(ResultSetExtractor.class))).willReturn(Collections.singletonList(saved));
|
||||
@@ -592,10 +601,10 @@ class JdbcOperationsSessionRepositoryTests {
|
||||
Authentication authentication = new UsernamePasswordAuthenticationToken(principal, "notused",
|
||||
AuthorityUtils.createAuthorityList("ROLE_USER"));
|
||||
List<Session> saved = new ArrayList<>(2);
|
||||
Session saved1 = this.repository.new JdbcSession();
|
||||
Session saved1 = this.repository.createSession();
|
||||
saved1.setAttribute(SPRING_SECURITY_CONTEXT, authentication);
|
||||
saved.add(saved1);
|
||||
Session saved2 = this.repository.new JdbcSession();
|
||||
Session saved2 = this.repository.createSession();
|
||||
saved2.setAttribute(SPRING_SECURITY_CONTEXT, authentication);
|
||||
saved.add(saved2);
|
||||
given(this.jdbcOperations.query(isA(String.class), isA(PreparedStatementSetter.class),
|
||||
@@ -647,8 +656,8 @@ class JdbcOperationsSessionRepositoryTests {
|
||||
@Test
|
||||
void saveUpdatedWithoutTransaction() {
|
||||
this.repository = new JdbcOperationsSessionRepository(this.jdbcOperations);
|
||||
JdbcOperationsSessionRepository.JdbcSession session = this.repository.new JdbcSession("primaryKey",
|
||||
new MapSession());
|
||||
JdbcOperationsSessionRepository.JdbcSession session = this.repository.new JdbcSession(new MapSession(),
|
||||
"primaryKey", false);
|
||||
session.setLastAccessedTime(Instant.now());
|
||||
|
||||
this.repository.save(session);
|
||||
@@ -709,6 +718,61 @@ class JdbcOperationsSessionRepositoryTests {
|
||||
verifyZeroInteractions(this.transactionManager);
|
||||
}
|
||||
|
||||
@Test
|
||||
void saveWithSaveModeOnSetAttribute() {
|
||||
this.repository.setSaveMode(SaveMode.ON_SET_ATTRIBUTE);
|
||||
MapSession delegate = new MapSession();
|
||||
delegate.setAttribute("attribute1", (Supplier<String>) () -> "value1");
|
||||
delegate.setAttribute("attribute2", (Supplier<String>) () -> "value2");
|
||||
delegate.setAttribute("attribute3", (Supplier<String>) () -> "value3");
|
||||
JdbcOperationsSessionRepository.JdbcSession session = this.repository.new JdbcSession(delegate,
|
||||
UUID.randomUUID().toString(), false);
|
||||
session.getAttribute("attribute2");
|
||||
session.setAttribute("attribute3", "value4");
|
||||
this.repository.save(session);
|
||||
verify(this.jdbcOperations).update(startsWith("UPDATE SPRING_SESSION_ATTRIBUTES SET"),
|
||||
isA(PreparedStatementSetter.class));
|
||||
verifyZeroInteractions(this.jdbcOperations);
|
||||
}
|
||||
|
||||
@Test
|
||||
void saveWithSaveModeOnGetAttribute() {
|
||||
this.repository.setSaveMode(SaveMode.ON_GET_ATTRIBUTE);
|
||||
MapSession delegate = new MapSession();
|
||||
delegate.setAttribute("attribute1", (Supplier<String>) () -> "value1");
|
||||
delegate.setAttribute("attribute2", (Supplier<String>) () -> "value2");
|
||||
delegate.setAttribute("attribute3", (Supplier<String>) () -> "value3");
|
||||
JdbcOperationsSessionRepository.JdbcSession session = this.repository.new JdbcSession(delegate,
|
||||
UUID.randomUUID().toString(), false);
|
||||
session.getAttribute("attribute2");
|
||||
session.setAttribute("attribute3", "value4");
|
||||
this.repository.save(session);
|
||||
ArgumentCaptor<BatchPreparedStatementSetter> captor = ArgumentCaptor
|
||||
.forClass(BatchPreparedStatementSetter.class);
|
||||
verify(this.jdbcOperations).batchUpdate(startsWith("UPDATE SPRING_SESSION_ATTRIBUTES SET"), captor.capture());
|
||||
assertThat(captor.getValue().getBatchSize()).isEqualTo(2);
|
||||
verifyZeroInteractions(this.jdbcOperations);
|
||||
}
|
||||
|
||||
@Test
|
||||
void saveWithSaveModeAlways() {
|
||||
this.repository.setSaveMode(SaveMode.ALWAYS);
|
||||
MapSession delegate = new MapSession();
|
||||
delegate.setAttribute("attribute1", (Supplier<String>) () -> "value1");
|
||||
delegate.setAttribute("attribute2", (Supplier<String>) () -> "value2");
|
||||
delegate.setAttribute("attribute3", (Supplier<String>) () -> "value3");
|
||||
JdbcOperationsSessionRepository.JdbcSession session = this.repository.new JdbcSession(delegate,
|
||||
UUID.randomUUID().toString(), false);
|
||||
session.getAttribute("attribute2");
|
||||
session.setAttribute("attribute3", "value4");
|
||||
this.repository.save(session);
|
||||
ArgumentCaptor<BatchPreparedStatementSetter> captor = ArgumentCaptor
|
||||
.forClass(BatchPreparedStatementSetter.class);
|
||||
verify(this.jdbcOperations).batchUpdate(startsWith("UPDATE SPRING_SESSION_ATTRIBUTES SET"), captor.capture());
|
||||
assertThat(captor.getValue().getBatchSize()).isEqualTo(3);
|
||||
verifyZeroInteractions(this.jdbcOperations);
|
||||
}
|
||||
|
||||
private void assertPropagationRequiresNew() {
|
||||
ArgumentCaptor<TransactionDefinition> argument = ArgumentCaptor.forClass(TransactionDefinition.class);
|
||||
verify(this.transactionManager, atLeastOnce()).getTransaction(argument.capture());
|
||||
|
||||
@@ -31,6 +31,7 @@ import org.springframework.core.convert.ConversionService;
|
||||
import org.springframework.jdbc.core.JdbcOperations;
|
||||
import org.springframework.jdbc.support.lob.LobHandler;
|
||||
import org.springframework.mock.env.MockEnvironment;
|
||||
import org.springframework.session.SaveMode;
|
||||
import org.springframework.session.jdbc.JdbcOperationsSessionRepository;
|
||||
import org.springframework.session.jdbc.config.annotation.SpringSessionDataSource;
|
||||
import org.springframework.test.util.ReflectionTestUtils;
|
||||
@@ -135,6 +136,20 @@ class JdbcHttpSessionConfigurationTests {
|
||||
assertThat(ReflectionTestUtils.getField(configuration, "cleanupCron")).isEqualTo(CLEANUP_CRON_EXPRESSION);
|
||||
}
|
||||
|
||||
@Test
|
||||
void customSaveModeAnnotation() {
|
||||
registerAndRefresh(DataSourceConfiguration.class, CustomSaveModeExpressionAnnotationConfiguration.class);
|
||||
assertThat(this.context.getBean(JdbcHttpSessionConfiguration.class)).hasFieldOrPropertyWithValue("saveMode",
|
||||
SaveMode.ALWAYS);
|
||||
}
|
||||
|
||||
@Test
|
||||
void customSaveModeSetter() {
|
||||
registerAndRefresh(DataSourceConfiguration.class, CustomSaveModeExpressionSetterConfiguration.class);
|
||||
assertThat(this.context.getBean(JdbcHttpSessionConfiguration.class)).hasFieldOrPropertyWithValue("saveMode",
|
||||
SaveMode.ALWAYS);
|
||||
}
|
||||
|
||||
@Test
|
||||
void qualifiedDataSourceConfiguration() {
|
||||
registerAndRefresh(DataSourceConfiguration.class, QualifiedDataSourceConfiguration.class);
|
||||
@@ -300,6 +315,20 @@ class JdbcHttpSessionConfigurationTests {
|
||||
|
||||
}
|
||||
|
||||
@EnableJdbcHttpSession(saveMode = SaveMode.ALWAYS)
|
||||
static class CustomSaveModeExpressionAnnotationConfiguration {
|
||||
|
||||
}
|
||||
|
||||
@Configuration
|
||||
static class CustomSaveModeExpressionSetterConfiguration extends JdbcHttpSessionConfiguration {
|
||||
|
||||
CustomSaveModeExpressionSetterConfiguration() {
|
||||
setSaveMode(SaveMode.ALWAYS);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EnableJdbcHttpSession
|
||||
static class QualifiedDataSourceConfiguration {
|
||||
|
||||
|
||||
Reference in New Issue
Block a user