Compare commits

..

1 Commits

Author SHA1 Message Date
Rob Winch
23ccfa6666 Release version 1.3.1.RELEASE 2017-04-27 14:56:58 -05:00
73 changed files with 345 additions and 918 deletions

4
.gitignore vendored
View File

@@ -10,5 +10,5 @@ target
out
.springBeans
*.rdb
.checkstyle
!etc/eclipse/.checkstyle
!eclispe/.checkstyle
.checkstyle

View File

@@ -19,7 +19,7 @@ plugins {
group = 'org.springframework.session'
ext.springBootVersion = '1.4.7.RELEASE'
ext.springBootVersion = '1.4.2.RELEASE'
ext.IDE_GRADLE = "$rootDir/gradle/ide.gradle"
ext.JAVA_GRADLE = "$rootDir/gradle/java.gradle"
ext.SPRING3_GRADLE = "$rootDir/gradle/spring3.gradle"
@@ -51,14 +51,12 @@ sonarqube {
}
}
task configDocsZip(dependsOn: [':docs:asciidoctor',':spring-session:javadoc']) {
doLast {
project.tasks.docsZip.from(project(':docs').asciidoctor) {
into('reference')
}
project.tasks.docsZip.from(project(':spring-session').javadoc) {
into('api')
}
task configDocsZip(dependsOn: [':docs:asciidoctor',':spring-session:javadoc']) << {
project.tasks.docsZip.from(project(':docs').asciidoctor) {
into('reference')
}
project.tasks.docsZip.from(project(':spring-session').javadoc) {
into('api')
}
}

View File

@@ -25,7 +25,7 @@ If you are using Maven, ensure to add the following dependencies:
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-redis</artifactId>
<artifactId>spring-boot-starter-redis</artifactId>
</dependency>
</dependencies>
----

View File

@@ -127,6 +127,3 @@ Alternatively, you can also delete the explicit key. Enter the following into yo
$ redis-cli del spring:session:sessions:7e8383a4-082c-4ffe-a4bc-c40fd3363c5e
Now visit the application at http://localhost:8080/test/index and observe that we are no longer authenticated.
NOTE: Spring Session will not work with grails flash scope without additional work. +
See this answer for an explanation: https://stackoverflow.com/a/43311427

View File

@@ -95,7 +95,7 @@ and managed by GemFire. As well, we have specified an arbitrary expiration attr
for when the Session will timeout, which is triggered by a GemFire Region entry expiration event that also invalidates
the Session object in the Region.
<2> Next, we define a few `Properties` that allow us to configure certain aspects of the GemFire Server using
http://gemfire.docs.pivotal.io/docs-gemfire/latest/reference/topics/gemfire_properties.html[GemFire's System properties].
http://gemfire.docs.pivotal.io/docs-gemfire/reference/topics/gemfire_properties.html[GemFire's System properties].
<3> Then, we create an instance of the GemFire `Cache` using our defined `Properties`.
<4> Finally, we configure and start a `CacheServer` running in the GemFire Server to listen for connections
from cache clients. The `CacheServer's` `Socket` will be used to connect our GemFire cache client,
@@ -159,7 +159,7 @@ and GemFire out-of-the-box using the following attributes:
* `maxInactiveIntervalInSeconds` - controls _HttpSession_ idle-timeout expiration (defaults to **30 minutes**).
* `regionName` - specifies the name of the GemFire Region used to store `HttpSession` state (defaults is "*ClusteredSpringSessions*").
* `clientRegionShort` - specifies GemFire's http://gemfire.docs.pivotal.io/docs-gemfire/latest/developing/management_all_region_types/chapter_overview.html[data management policy]
with a GemFire http://data-docs-samples.cfapps.io/docs-gemfire/latest/javadocs/japi/com/gemstone/gemfire/cache/client/ClientRegionShortcut.html[ClientRegionShortcut]
with a GemFire http://gemfire.docs.pivotal.io/docs-gemfire/latest/javadocs/japi/com/gemstone/gemfire/cache/client/ClientRegionShortcut.html[ClientRegionShortcut]
(default is `PROXY`). This attribute is only used when configuring client Region.
* `poolName` - name of the dedicated GemFire Pool used to connect a client to the cluster of servers. The attribute
is only used when the application is a GemFire cache client. Defaults to `gemfirePool`.
@@ -230,7 +230,7 @@ Go ahead and view the cookies (click for help with https://developer.chrome.com/
or https://getfirebug.com/wiki/index.php/Cookies_Panel#Cookies_List[Firefox]).
NOTE: The following instructions assume you have a local GemFire installation. For more information on installation,
see http://gemfire.docs.pivotal.io/docs-gemfire/getting_started/installation/install_intro.html[Installing Pivotal GemFire].
see http://gemfire.docs.pivotal.io/docs-gemfire/latest/getting_started/installation/install_intro.html[Installing Pivotal GemFire].
NOTE: In order to run the following, you must uncomment the lines in the `GemFireServer` class, `gemfireProperties` bean
for the following GemFire System properties: `jmx-manager` and `jmx-manager-start`.

View File

@@ -92,7 +92,7 @@ bean to replace placeholders in the Spring XML configuration meta-data with the
at the designated host/port is running and listening for client connections, blocking client startup until
the server is available and ready.
<4> Next, we include a `Properties` bean to configure certain aspects of the GemFire client cache using
http://gemfire.docs.pivotal.io/docs-gemfire/latest/reference/topics/gemfire_properties.html[GemFire's System Properties].
http://gemfire.docs.pivotal.io/docs-gemfire/reference/topics/gemfire_properties.html[GemFire's System Properties].
In this case, we are just setting GemFire's `log-level` from a application-specific System property, defaulting
to `warning` if unspecified.
<5> Then we create a instance of a GemFire `ClientCache` initialized with our `gemfireProperties`.
@@ -234,7 +234,7 @@ Go ahead and view the cookies (click for help with https://developer.chrome.com/
or https://getfirebug.com/wiki/index.php/Cookies_Panel#Cookies_List[Firefox]).
NOTE: The following instructions assume you have a local GemFire installation. For more information on installation,
see https://gemfire.docs.pivotal.io/gemfire/getting_started/installation/install_intro.html[Installing Pivotal GemFire].
see http://gemfire.docs.pivotal.io/docs-gemfire/latest/getting_started/installation/install_intro.html[Installing Pivotal GemFire].
If you like, you can easily remove the session using `gfsh`. For example, on a Linux-based system type the following
at the command-line:

View File

@@ -87,12 +87,12 @@ include::{samples-dir}httpsession-gemfire-clientserver/src/main/java/sample/Clie
implements `Filter`. The filter is what replaces the `HttpSession` with an implementation backed by Spring Session
and GemFire.
<2> Next, we register a `Properties` bean that allows us to configure certain aspects of the GemFire client cache
using http://gemfire.docs.pivotal.io/docs-gemfire/latest/reference/topics/gemfire_properties.html[GemFire's System properties].
using http://gemfire.docs.pivotal.io/docs-gemfire/reference/topics/gemfire_properties.html[GemFire's System properties].
<3> We use the `Properties` to configure an instance of a GemFire `ClientCache`.
<4> Then, we configure a `Pool` of client connections to talk to the GemFire Server in our Client/Server topology. In our
configuration, we have used sensible settings for timeouts, number of connections and so on. Also, the `Pool` has been
configured to connect directly to a server. Learn more about various `Pool` configuration settings from the
http://data-docs-samples.cfapps.io/docs-gemfire/latest/javadocs/japi/com/gemstone/gemfire/cache/client/PoolFactory.html[PoolFactory API].
http://gemfire.docs.pivotal.io/docs-gemfire/latest/javadocs/japi/com/gemstone/gemfire/cache/client/PoolFactory.html[PoolFactory API].
<56> Finally, we include a Spring `BeanPostProcessor` to block the client until our GemFire Server is up and running,
listening for and accepting client connections.
@@ -100,7 +100,7 @@ The `gemfireCacheServerReadyBeanPostProcessor` is necessary in order to coordina
an automated fashion during testing, but unnecessary in situations where the GemFire cluster is already presently
running, such as in production.
The `BeanPostProcessor` uses a GemFire https://data-docs-samples.cfapps.io/docs-gemfire/latest/javadocs/japi/com/gemstone/gemfire/management/membership/ClientMembershipListener.html[ClientMembershipListener]
The `BeanPostProcessor` uses a GemFire http://gemfire.docs.pivotal.io/docs-gemfire/latest/javadocs/japi/com/gemstone/gemfire/management/membership/ClientMembershipListener.html[ClientMembershipListener]
that will be notified when the client has successfully connected to the server. Once a connection has been established,
the listener releases the latch that the `BeanPostProcessor` will wait on (up to the specified timeout) in the
`postProcessAfterInitialization` callback to block the client.
@@ -118,7 +118,7 @@ and GemFire out-of-the-box using the following attributes:
* `maxInactiveIntervalInSeconds` - controls _HttpSession_ idle-timeout expiration (defaults to **30 minutes**).
* `regionName` - specifies the name of the GemFire Region used to store `HttpSession` state (defaults is "*ClusteredSpringSessions*").
* `clientRegionShort` - specifies GemFire's http://gemfire.docs.pivotal.io/docs-gemfire/latest/developing/management_all_region_types/chapter_overview.html[data management policy]
with a GemFire https://data-docs-samples.cfapps.io/docs-gemfire/latest/javadocs/japi/com/gemstone/gemfire/cache/client/ClientRegionShortcut.html[ClientRegionShortcut]
with a GemFire http://gemfire.docs.pivotal.io/docs-gemfire/latest/javadocs/japi/com/gemstone/gemfire/cache/client/ClientRegionShortcut.html[ClientRegionShortcut]
(default is `PROXY`). This attribute is only used when configuring client Region.
* `poolName` - name of the dedicated GemFire Pool used to connect a client to the cluster of servers. The attribute
is only used when the application is a GemFire cache client. Defaults to `gemfirePool`.
@@ -233,7 +233,7 @@ Go ahead and view the cookies (click for help with https://developer.chrome.com/
or https://getfirebug.com/wiki/index.php/Cookies_Panel#Cookies_List[Firefox]).
NOTE: The following instructions assume you have a local GemFire installation. For more information on installation,
see https://gemfire.docs.pivotal.io/gemfire/getting_started/installation/install_intro.html[Installing Pivotal GemFire].
see http://gemfire.docs.pivotal.io/docs-gemfire/latest/getting_started/installation/install_intro.html[Installing Pivotal GemFire].
If you like, you can easily remove the session using `gfsh`. For example, on a Linux-based system type the following
at the command-line:

View File

@@ -176,7 +176,7 @@ Go ahead and view the cookies (click for help with https://developer.chrome.com/
or https://getfirebug.com/wiki/index.php/Cookies_Panel#Cookies_List[Firefox]).
NOTE: The following instructions assume you have a local GemFire installation. For more information on installation,
see http://gemfire.docs.pivotal.io/gemfire/getting_started/installation/install_intro.html[Installing Pivotal GemFire].
see http://gemfire.docs.pivotal.io/docs-gemfire/latest/getting_started/installation/install_intro.html[Installing Pivotal GemFire].
If you like, you can easily remove the session using `gfsh`. For example, on a Linux-based system type the following
at the command-line:

View File

@@ -104,7 +104,7 @@ and GemFire out-of-the-box using the following attributes:
* `maxInactiveIntervalInSeconds` - controls HttpSession idle-timeout expiration (defaults to **30 minutes**).
* `regionName` - specifies the name of the GemFire Region used to store `HttpSession` state (defaults is "_ClusteredSpringSessions_").
* `serverRegionShort` - specifies GemFire http://gemfire.docs.pivotal.io/docs-gemfire/latest/developing/management_all_region_types/chapter_overview.html[data management policies]
with a GemFire https://data-docs-samples.cfapps.io/docs-gemfire/latest/javadocs/japi/com/gemstone/gemfire/cache/RegionShortcut.html[RegionShortcut]
with a GemFire http://gemfire.docs.pivotal.io/docs-gemfire/latest/javadocs/japi/com/gemstone/gemfire/cache/RegionShortcut.html[RegionShortcut]
(default is `PARTITION`).
NOTE: `clientRegionShort` is ignored in a peer cache configuration and only applies when a client-server topology,
@@ -175,7 +175,7 @@ Go ahead and view the cookies (click for help with https://developer.chrome.com/
or https://getfirebug.com/wiki/index.php/Cookies_Panel#Cookies_List[Firefox]).
NOTE: The following instructions assume you have a local GemFire installation. For more information on installation,
see https://gemfire.docs.pivotal.io/gemfire/getting_started/installation/install_intro.html[Installing Pivotal GemFire].
see http://gemfire.docs.pivotal.io/docs-gemfire/latest/getting_started/installation/install_intro.html[Installing Pivotal GemFire].
If you like, you can easily remove the session using `gfsh`. For example, on a Linux-based system type the following
at the command-line:

View File

@@ -192,7 +192,7 @@ The two most common topologies to manage Spring Sessions using GemFire include:
* <<httpsession-gemfire-clientserver,Client-Server>>
* <<httpsession-gemfire-p2p,Peer-To-Peer (P2P)>>
Additionally, GemFire supports site-to-site replication using http://gemfire.docs.pivotal.io/docs-gemfire/latest/topologies_and_comm/multi_site_configuration/chapter_overview.html[WAN functionality].
Additionally, GemFire supports site-to-site replication using http://gemfire.docs.pivotal.io/docs-gemfire/topologies_and_comm/multi_site_configuration/chapter_overview.html[WAN functionality].
The ability to configure and use GemFire's WAN support is independent of Spring Session, and is beyond the scope
of this document. More details on GemFire WAN functionality can be found http://docs.spring.io/spring-data-gemfire/docs/current/reference/html/#bootstrap:gateway[here].
@@ -829,12 +829,12 @@ EXPIRE spring:session:sessions:expires:33fdd1b6-b496-4b33-9f7d-df96679d32fe 1800
When a session expires key is deleted or expires, the keyspace notification triggers a lookup of the actual session and a SessionDestroyedEvent is fired.
One problem with relying on Redis expiration exclusively is that Redis makes no guarantee of when the expired event will be fired if the key has not been accessed.
One problem with relying on Redis expiration exclusively is that Redis makes no guarantee of when the expired event will be fired if they key has not been accessed.
Specifically the background task that Redis uses to clean up expired keys is a low priority task and may not trigger the key expiration.
For additional details see http://redis.io/topics/notifications[Timing of expired events] section in the Redis documentation.
To circumvent the fact that expired events are not guaranteed to happen we can ensure that each key is accessed when it is expected to expire.
This means that if the TTL is expired on the key, Redis will remove the key and fire the expired event when we try to access the key.
This means that if the TTL is expired on the key, Redis will remove the key and fire the expired event when we try to access they key.
For this reason, each session expiration is also tracked to the nearest minute.
This allows a background task to access the potentially expired sessions to ensure that Redis expired events are fired in a more deterministic fashion.
@@ -846,7 +846,7 @@ EXPIRE spring:session:expirations1439245080000 2100
----
The background task will then use these mappings to explicitly request each key.
By accessing the key, rather than deleting it, we ensure that Redis deletes the key for us only if the TTL is expired.
By accessing they key, rather than deleting it, we ensure that Redis deletes the key for us only if the TTL is expired.
[NOTE]
====
@@ -1199,17 +1199,8 @@ Spring Session is Open Source software released under the http://www.apache.org/
[[community-extensions]]
=== Community Extensions
|===
| Name | Location
| Spring Session OrientDB
| https://github.com/maseev/spring-session-orientdb
| Spring Session Infinispan
| http://infinispan.org/docs/dev/user_guide/user_guide.html#externalizing_session_using_spring_session
|===
https://github.com/maseev/spring-session-orientdb[Spring Session OrientDB]
http://infinispan.org/docs/dev/user_guide/user_guide.html#externalizing_session_using_spring_session[Spring Session Infinispan]
[[minimum-requirements]]
== Minimum Requirements

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2014-2018 the original author or authors.
* Copyright 2014-2016 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.
@@ -22,6 +22,7 @@ import org.springframework.security.config.annotation.web.configuration.EnableWe
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
import org.springframework.security.core.userdetails.User;
import org.springframework.security.provisioning.InMemoryUserDetailsManager;
import org.springframework.security.web.authentication.RememberMeServices;
import org.springframework.session.MapSessionRepository;
import org.springframework.session.config.annotation.web.http.EnableSpringHttpSession;
import org.springframework.session.security.web.authentication.SpringSessionRememberMeServices;
@@ -51,7 +52,7 @@ public class RememberMeSecurityConfiguration extends WebSecurityConfigurerAdapte
// tag::rememberme-bean[]
@Bean
public SpringSessionRememberMeServices rememberMeServices() {
RememberMeServices rememberMeServices() {
SpringSessionRememberMeServices rememberMeServices =
new SpringSessionRememberMeServices();
// optionally customize

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2014-2019 the original author or authors.
* Copyright 2014-2016 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.
@@ -21,6 +21,7 @@ import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
import org.springframework.session.ExpiringSession;
import org.springframework.session.FindByIndexNameSessionRepository;
import org.springframework.session.security.SpringSessionBackedSessionRegistry;
@@ -32,7 +33,7 @@ import org.springframework.session.security.SpringSessionBackedSessionRegistry;
public class SecurityConfiguration extends WebSecurityConfigurerAdapter {
@Autowired
private FindByIndexNameSessionRepository sessionRepository;
FindByIndexNameSessionRepository<ExpiringSession> sessionRepository;
@Override
protected void configure(HttpSecurity http) throws Exception {
@@ -44,8 +45,7 @@ public class SecurityConfiguration extends WebSecurityConfigurerAdapter {
}
@Bean
@SuppressWarnings("unchecked")
public SpringSessionBackedSessionRegistry sessionRegistry() {
SpringSessionBackedSessionRegistry sessionRegistry() {
return new SpringSessionBackedSessionRegistry(this.sessionRepository);
}
}

View File

@@ -59,7 +59,7 @@ cleanup_profile=_Spring Boot Cleanup Conventions
cleanup_settings_version=2
eclipse.preferences.version=1
editor_save_participant_org.eclipse.jdt.ui.postsavelistener.cleanup=true
formatter_profile=Spring Session Java Conventions
formatter_profile=_Spring Boot Java Conventions
formatter_settings_version=12
org.eclipse.jdt.ui.exception.name=e
org.eclipse.jdt.ui.gettersetter.use.is=true

View File

@@ -1,31 +1,32 @@
bootstrapVersion=2.3.2
commonsPoolVersion=2.4.2
jacksonVersion=2.8.8
jspApiVersion=2.0
servletApiVersion=3.0.1
jstlelVersion=1.2.5
version=1.3.5.RELEASE
springDataRedisVersion=1.7.11.RELEASE
html5ShivVersion=3.7.3
commonsLoggingVersion=1.2
junitVersion=4.12
springDataRedisSpring3Version=1.7.1.RELEASE
lettuceVersion=3.5.0.Final
gebVersion=0.13.1
mockitoVersion=1.10.19
hazelcastVersion=3.6.8
seleniumVersion=2.52.0
springDataGeodeVersion=1.0.0.INCUBATING-RELEASE
springSecurityVersion=4.2.11.RELEASE
springVersion=4.3.19.RELEASE
httpClientVersion=4.5.3
h2Version=1.4.195
jedisVersion=2.8.2
springDataMongoVersion=1.9.11.RELEASE
springShellVersion=1.1.0.RELEASE
springDataGemFireVersion=1.8.11.RELEASE
assertjVersion=2.5.0
spockVersion=1.0-groovy-2.4
webjarsTaglibVersion=0.3
bootstrapVersion=2.3.2
commonsLoggingVersion=1.2
commonsPoolVersion=2.4.2
gebVersion=0.13.1
groovyVersion=2.4.4
h2Version=1.4.192
hazelcastVersion=3.6.5
html5ShivVersion=3.7.3
httpClientVersion=4.5.1
jacksonVersion=2.6.5
jedisVersion=2.8.1
jspApiVersion=2.0
jstlVersion=1.2.1
groovyVersion=2.4.11
jstlelVersion=1.2.5
junitVersion=4.12
lettuceVersion=3.5.0.Final
mockitoVersion=1.10.19
seleniumVersion=2.52.0
servletApiVersion=3.0.1
spockVersion=1.0-groovy-2.4
springVersion=4.3.4.RELEASE
springDataGemFireVersion=1.8.10.RELEASE
springDataGeodeVersion=1.0.0.INCUBATING-RELEASE
springDataMongoVersion=1.9.4.RELEASE
springDataRedisVersion=1.7.10.RELEASE
# We cannot go beyond this version with Spring 3 support
springDataRedisSpring3Version=1.7.1.RELEASE
springSecurityVersion=4.2.0.RELEASE
springShellVersion=1.1.0.RELEASE
webjarsTaglibVersion=0.3
version=1.3.1.RELEASE

View File

@@ -78,7 +78,7 @@ task integrationTest(type: Test, dependsOn: jar) {
check.dependsOn integrationTest
checkstyle {
configFile = rootProject.file('etc/checkstyle/checkstyle.xml')
configFile = rootProject.file('config/checkstyle/checkstyle.xml')
configProperties.configDir = configFile.parentFile
toolVersion = '6.16.1'
}

Binary file not shown.

View File

@@ -1,6 +1,6 @@
#Mon Jan 29 18:35:20 CET 2018
#Fri Nov 11 19:46:57 CET 2016
distributionBase=GRADLE_USER_HOME
distributionPath=wrapper/dists
zipStoreBase=GRADLE_USER_HOME
zipStorePath=wrapper/dists
distributionUrl=https\://services.gradle.org/distributions/gradle-3.5.1-bin.zip
distributionUrl=https\://services.gradle.org/distributions/gradle-3.1-bin.zip

19
gradlew vendored
View File

@@ -1,4 +1,4 @@
#!/usr/bin/env sh
#!/usr/bin/env bash
##############################################################################
##
@@ -154,19 +154,16 @@ if $cygwin ; then
esac
fi
# Escape application args
save ( ) {
for i do printf %s\\n "$i" | sed "s/'/'\\\\''/g;1s/^/'/;\$s/\$/' \\\\/" ; done
echo " "
# Split up the JVM_OPTS And GRADLE_OPTS values into an array, following the shell quoting and substitution rules
function splitJvmOpts() {
JVM_OPTS=("$@")
}
APP_ARGS=$(save "$@")
# Collect all arguments for the java command, following the shell quoting and substitution rules
eval set -- $DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS "\"-Dorg.gradle.appname=$APP_BASE_NAME\"" -classpath "\"$CLASSPATH\"" org.gradle.wrapper.GradleWrapperMain "$APP_ARGS"
eval splitJvmOpts $DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS
JVM_OPTS[${#JVM_OPTS[*]}]="-Dorg.gradle.appname=$APP_BASE_NAME"
# by default we should be in the correct project dir, but when run from Finder on Mac, the cwd is wrong
if [ "$(uname)" = "Darwin" ] && [ "$HOME" = "$PWD" ]; then
if [[ "$(uname)" == "Darwin" ]] && [[ "$HOME" == "$PWD" ]]; then
cd "$(dirname "$0")"
fi
exec "$JAVACMD" "$@"
exec "$JAVACMD" "${JVM_OPTS[@]}" -classpath "$CLASSPATH" org.gradle.wrapper.GradleWrapperMain "$@"

View File

@@ -14,11 +14,9 @@ apply from: SAMPLE_GRADLE
group = 'samples'
ext['spring-security.version'] = springSecurityVersion
dependencies {
compile project(':spring-session'),
"org.springframework.boot:spring-boot-starter-data-redis",
"org.springframework.boot:spring-boot-starter-redis",
"org.springframework.boot:spring-boot-starter-web",
"org.springframework.boot:spring-boot-starter-thymeleaf",
"org.springframework.boot:spring-boot-starter-security",

View File

@@ -14,11 +14,9 @@ apply from: SAMPLE_GRADLE
group = 'samples'
ext['spring-security.version'] = springSecurityVersion
dependencies {
compile project(':spring-session'),
"org.springframework.boot:spring-boot-starter-data-redis",
"org.springframework.boot:spring-boot-starter-redis",
"org.springframework.boot:spring-boot-starter-web",
"org.springframework.boot:spring-boot-starter-security",
"org.springframework.boot:spring-boot-starter-thymeleaf",

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2014-2018 the original author or authors.
* Copyright 2014-2016 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.
@@ -42,8 +42,7 @@ public class SessionConfig {
int port = SocketUtils.findAvailableTcpPort();
config.getNetworkConfig()
.setPort(port)
.getJoin().getMulticastConfig().setEnabled(false);
.setPort(port);
System.out.println("Hazelcast port #: " + port);

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2014-2018 the original author or authors.
* Copyright 2014-2016 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.
@@ -52,7 +52,6 @@ public class Initializer implements ServletContextListener {
Config cfg = new Config();
NetworkConfig netConfig = new NetworkConfig();
netConfig.setPort(getAvailablePort());
netConfig.getJoin().getMulticastConfig().setEnabled(false);
cfg.setNetworkConfig(netConfig);
SerializerConfig serializer = new SerializerConfig().setTypeClass(Object.class)
.setImplementation(new ObjectStreamSerializer());

View File

@@ -10,9 +10,12 @@ buildscript {
apply from: JAVA_GRADLE
apply plugin: "application"
apply plugin: 'org.springframework.boot'
apply from: SAMPLE_GRADLE
ext['spring-security.version'] = springSecurityVersion
tasks.findByPath("artifactoryPublish")?.enabled = false
sonarqube {
skipProject = true
}
dependencies {
compile project(':spring-session-data-gemfire'),
@@ -21,14 +24,14 @@ dependencies {
"org.webjars:bootstrap:$bootstrapVersion",
"org.webjars:webjars-locator"
runtime "org.springframework.shell:spring-shell:$springShellVersion"
runtime "org.springframework.shell:spring-shell:1.0.0.RELEASE"
testCompile "org.springframework.boot:spring-boot-starter-test"
integrationTestCompile gebDependencies,
"org.spockframework:spock-spring:$spockVersion"
integrationTestRuntime "org.springframework.shell:spring-shell:$springShellVersion"
integrationTestRuntime "org.springframework.shell:spring-shell:1.0.0.RELEASE"
}
run {
@@ -41,26 +44,24 @@ springBoot {
mainClass = 'sample.client.Application'
}
task runGemFireServer() {
doLast {
println 'STARTING GEMFIRE SERVER...'
task runGemFireServer() << {
println 'STARTING GEMFIRE SERVER...'
ext.port = reservePort()
ext.port = reservePort()
String classpath = sourceSets.main.runtimeClasspath.collect { it }.join(File.pathSeparator)
String classpath = sourceSets.main.runtimeClasspath.collect { it }.join(File.pathSeparator)
String[] commandLine = ['java', '-server', '-ea', '-classpath', classpath,
"-Dgemfire.cache.server.port=$port",
"-Dgemfire.log-level=" + System.getProperty('gemfire.log.level', 'warning'),
'sample.server.GemFireServer']
String[] commandLine = ['java', '-server', '-ea', '-classpath', classpath,
"-Dgemfire.cache.server.port=$port",
"-Dgemfire.log-level=" + System.getProperty('gemfire.log.level', 'warning'),
'sample.server.GemFireServer']
//println commandLine
//println commandLine
ext.process = commandLine.execute()
process.in.close()
process.out.close()
process.err.close()
}
ext.process = commandLine.execute()
process.in.close()
process.out.close()
process.err.close()
}

View File

@@ -1,7 +1,12 @@
apply from: JAVA_GRADLE
apply from: TOMCAT_7_GRADLE
apply plugin: "application"
apply from: SAMPLE_GRADLE
tasks.findByPath("artifactoryPublish")?.enabled = false
sonarqube {
skipProject = true
}
dependencies {
compile project(':spring-session-data-gemfire'),
@@ -12,13 +17,13 @@ dependencies {
providedCompile "javax.servlet:javax.servlet-api:$servletApiVersion"
runtime "org.springframework.shell:spring-shell:$springShellVersion"
runtime "org.springframework.shell:spring-shell:1.0.0.RELEASE"
testCompile "junit:junit:$junitVersion"
integrationTestCompile gebDependencies
integrationTestRuntime "org.springframework.shell:spring-shell:$springShellVersion"
integrationTestRuntime "org.springframework.shell:spring-shell:1.0.0.RELEASE"
}
mainClassName = 'sample.Application'
@@ -26,33 +31,29 @@ mainClassName = 'sample.Application'
def port
def process
task availablePort() {
doLast {
def serverSocket = new ServerSocket(0)
port = serverSocket.localPort
serverSocket.close()
}
task availablePort() << {
def serverSocket = new ServerSocket(0)
port = serverSocket.localPort
serverSocket.close()
}
task runGemFireServer(dependsOn: availablePort) {
doLast {
println 'STARTING GEMFIRE SERVER...'
task runGemFireServer(dependsOn: availablePort) << {
println 'STARTING GEMFIRE SERVER...'
String classpath = sourceSets.main.runtimeClasspath.collect { it }.join(File.pathSeparator)
String classpath = sourceSets.main.runtimeClasspath.collect { it }.join(File.pathSeparator)
String[] commandLine = ['java', '-server', '-ea',
"-Dspring.session.data.gemfire.port=$port",
"-Dsample.httpsession.gemfire.log-level="
+ System.getProperty('sample.httpsession.gemfire.log-level', 'warning'),
'-classpath', classpath, 'sample.Application']
String[] commandLine = ['java', '-server', '-ea',
"-Dspring.session.data.gemfire.port=$port",
"-Dsample.httpsession.gemfire.log-level="
+ System.getProperty('sample.httpsession.gemfire.log-level', 'warning'),
'-classpath', classpath, 'sample.Application' ]
//println commandLine
//println commandLine
process = commandLine.execute()
process.in.close()
process.out.close()
process.err.close()
}
process = commandLine.execute()
process.in.close()
process.out.close()
process.err.close()
}
integrationTest.doLast {

View File

@@ -12,13 +12,13 @@ dependencies {
providedCompile "javax.servlet:javax.servlet-api:$servletApiVersion"
runtime "org.springframework.shell:spring-shell:$springShellVersion"
runtime "org.springframework.shell:spring-shell:1.0.0.RELEASE"
testCompile "junit:junit:$junitVersion"
integrationTestCompile gebDependencies
integrationTestRuntime "org.springframework.shell:spring-shell:$springShellVersion"
integrationTestRuntime "org.springframework.shell:spring-shell:1.0.0.RELEASE"
}
@@ -27,33 +27,29 @@ def process
mainClassName = "sample.ServerConfig"
task availablePort() {
doLast {
def serverSocket = new ServerSocket(0)
port = serverSocket.localPort
serverSocket.close()
}
task availablePort() << {
def serverSocket = new ServerSocket(0)
port = serverSocket.localPort
serverSocket.close()
}
task runGemFireServer(dependsOn: availablePort) {
doLast {
println 'STARTING GEMFIRE SERVER...'
task runGemFireServer(dependsOn: availablePort) << {
println 'STARTING GEMFIRE SERVER...'
String classpath = sourceSets.main.runtimeClasspath.collect { it }.join(File.pathSeparator)
String classpath = sourceSets.main.runtimeClasspath.collect { it }.join(File.pathSeparator)
String[] commandLine = ['java', '-server', '-ea',
"-Dspring.session.data.gemfire.port=$port",
"-Dsample.httpsession.gemfire.log-level="
+ System.getProperty('sample.httpsession.gemfire.log-level', 'warning'),
'-classpath', classpath, 'sample.ServerConfig']
String[] commandLine = ['java', '-server', '-ea',
"-Dspring.session.data.gemfire.port=$port",
"-Dsample.httpsession.gemfire.log-level="
+ System.getProperty('sample.httpsession.gemfire.log-level', 'warning'),
'-classpath', classpath, 'sample.ServerConfig']
//println commandLine
//println commandLine
process = commandLine.execute()
process.in.close()
process.out.close()
process.err.close()
}
process = commandLine.execute()
process.in.close()
process.out.close()
process.err.close()
}
integrationTest.doLast {

View File

@@ -15,5 +15,5 @@ dependencies {
integrationTestCompile gebDependencies
integrationTestRuntime "org.springframework.shell:spring-shell:$springShellVersion"
integrationTestRuntime "org.springframework.shell:spring-shell:1.0.0.RELEASE"
}

View File

@@ -15,5 +15,5 @@ dependencies {
integrationTestCompile gebDependencies
integrationTestRuntime "org.springframework.shell:spring-shell:$springShellVersion"
integrationTestRuntime "org.springframework.shell:spring-shell:1.0.0.RELEASE"
}

View File

@@ -14,8 +14,6 @@ apply from: SAMPLE_GRADLE
group = 'samples'
ext['spring-security.version'] = springSecurityVersion
dependencies {
compile project(':spring-session-jdbc'),
"org.springframework.boot:spring-boot-starter-jdbc",

View File

@@ -10,18 +10,20 @@ buildscript {
apply plugin: 'org.springframework.boot'
apply from: JAVA_GRADLE
apply from: SAMPLE_GRADLE
//tasks.findByPath("artifactoryPublish")?.enabled = false
group = 'samples'
ext {
jsonassertVersion="1.3.0"
assertjVersion = "2.4.0"
}
ext['spring-security.version'] = springSecurityVersion
dependencies {
compile project(':spring-session'),
"org.springframework.boot:spring-boot-starter-data-redis",
"org.springframework.boot:spring-boot-starter-redis",
"org.springframework.boot:spring-boot-starter-web",
"org.springframework.boot:spring-boot-starter-thymeleaf",
"org.springframework.boot:spring-boot-starter-security",
@@ -64,4 +66,4 @@ def reservePort() {
def result = socket.localPort
socket.close()
result
}
}

View File

@@ -14,8 +14,6 @@ apply from: SAMPLE_GRADLE
group = 'samples'
ext['spring-security.version'] = springSecurityVersion
dependencies {
compile project(':spring-session'),
"org.springframework.boot:spring-boot-starter-data-mongodb",

View File

@@ -15,8 +15,6 @@ apply from: SAMPLE_GRADLE
group = 'samples'
ext['spring-security.version'] = springSecurityVersion
dependencies {
compile(project(':spring-session-data-redis')) {
exclude module: 'jedis'

View File

@@ -23,6 +23,7 @@ include 'samples:security'
include 'samples:users'
include 'samples:websocket'
include 'samples:mongo'
include 'samples:grails3'
include 'spring-session'
include 'spring-session-data-gemfire'

View File

@@ -29,14 +29,14 @@ dependencies {
"org.springframework.security:spring-security-web:$springSecurityVersion"
provided "javax.servlet:javax.servlet-api:$servletApiVersion"
integrationTestCompile "redis.clients:jedis:$jedisVersion",
"org.apache.commons:commons-pool2:$commonsPoolVersion",
"org.apache.commons:commons-pool2:2.2",
"com.hazelcast:hazelcast-client:$hazelcastVersion",
"com.h2database:h2:$h2Version",
"org.hsqldb:hsqldb:2.3.3",
"org.apache.derby:derby:10.12.1.1",
"de.flapdoodle.embed:de.flapdoodle.embed.mongo:1.50.5"
"de.flapdoodle.embed:de.flapdoodle.embed.mongo:1.50.2"
integrationTestRuntime "org.springframework.shell:spring-shell:$springShellVersion"
integrationTestRuntime "org.springframework.shell:spring-shell:1.0.0.RELEASE"
testCompile "junit:junit:$junitVersion",
"org.mockito:mockito-core:$mockitoVersion",

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2014-2018 the original author or authors.
* Copyright 2014-2016 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.
@@ -18,17 +18,9 @@ package org.springframework.session.hazelcast;
import com.hazelcast.core.HazelcastInstance;
import com.hazelcast.core.IMap;
import com.hazelcast.instance.HazelcastInstanceProxy;
import org.junit.Assume;
import org.junit.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.authority.AuthorityUtils;
import org.springframework.security.core.context.SecurityContext;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.session.FindByIndexNameSessionRepository;
import org.springframework.session.MapSession;
import org.springframework.session.hazelcast.HazelcastSessionRepository.HazelcastSession;
@@ -42,10 +34,8 @@ import static org.assertj.core.api.Assertions.assertThat;
*/
public abstract class AbstractHazelcastRepositoryITests {
private static final String SPRING_SECURITY_CONTEXT = "SPRING_SECURITY_CONTEXT";
@Autowired
private HazelcastInstance hazelcastInstance;
private HazelcastInstance hazelcast;
@Autowired
private HazelcastSessionRepository repository;
@@ -55,8 +45,8 @@ public abstract class AbstractHazelcastRepositoryITests {
HazelcastSession sessionToSave = this.repository.createSession();
String sessionId = sessionToSave.getId();
IMap<String, MapSession> hazelcastMap = this.hazelcastInstance
.getMap("spring:session:sessions");
IMap<String, MapSession> hazelcastMap = this.hazelcast.getMap(
"spring:session:sessions");
assertThat(hazelcastMap.size()).isEqualTo(0);
@@ -70,70 +60,4 @@ public abstract class AbstractHazelcastRepositoryITests {
assertThat(hazelcastMap.size()).isEqualTo(0);
}
@Test // gh-1076
public void attemptToUpdateSessionAfterDelete() {
HazelcastSession session = this.repository.createSession();
String sessionId = session.getId();
this.repository.save(session);
session = this.repository.getSession(sessionId);
session.setAttribute("attributeName", "attributeValue");
this.repository.delete(sessionId);
this.repository.save(session);
assertThat(this.repository.getSession(sessionId)).isNull();
}
@Test
public void createAndUpdateSession() {
HazelcastSession session = this.repository.createSession();
String sessionId = session.getId();
this.repository.save(session);
session = this.repository.getSession(sessionId);
session.setAttribute("attributeName", "attributeValue");
this.repository.save(session);
assertThat(this.repository.getSession(sessionId)).isNotNull();
}
@Test
public void createSessionWithSecurityContextAndFindById() {
HazelcastSession session = this.repository.createSession();
String sessionId = session.getId();
Authentication authentication = new UsernamePasswordAuthenticationToken(
"saves-" + System.currentTimeMillis(), "password",
AuthorityUtils.createAuthorityList("ROLE_USER"));
SecurityContext securityContext = SecurityContextHolder.createEmptyContext();
securityContext.setAuthentication(authentication);
session.setAttribute(SPRING_SECURITY_CONTEXT, securityContext);
this.repository.save(session);
assertThat(this.repository.getSession(sessionId)).isNotNull();
}
@Test
public void createSessionWithSecurityContextAndFindByPrincipal() {
Assume.assumeTrue("Hazelcast runs in embedded server topology",
this.hazelcastInstance instanceof HazelcastInstanceProxy);
HazelcastSession session = this.repository.createSession();
String username = "saves-" + System.currentTimeMillis();
Authentication authentication = new UsernamePasswordAuthenticationToken(username,
"password", AuthorityUtils.createAuthorityList("ROLE_USER"));
SecurityContext securityContext = SecurityContextHolder.createEmptyContext();
securityContext.setAuthentication(authentication);
session.setAttribute(SPRING_SECURITY_CONTEXT, securityContext);
this.repository.save(session);
assertThat(this.repository.findByIndexNameAndIndexValue(
FindByIndexNameSessionRepository.PRINCIPAL_NAME_INDEX_NAME, username))
.isNotNull();
}
}

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2014-2018 the original author or authors.
* Copyright 2014-2016 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.
@@ -49,12 +49,12 @@ public class HazelcastClientRepositoryITests extends AbstractHazelcastRepository
private static HazelcastInstance hazelcastInstance;
@BeforeClass
public static void setUpClass() {
public static void setup() {
hazelcastInstance = HazelcastITestUtils.embeddedHazelcastServer(PORT);
}
@AfterClass
public static void tearDownClass() {
public static void teardown() {
if (hazelcastInstance != null) {
hazelcastInstance.shutdown();
}
@@ -65,7 +65,7 @@ public class HazelcastClientRepositoryITests extends AbstractHazelcastRepository
static class HazelcastSessionConfig {
@Bean
public HazelcastInstance hazelcastInstance() {
public HazelcastInstance embeddedHazelcastClient() {
ClientConfig clientConfig = new ClientConfig();
clientConfig.getNetworkConfig().addAddress("127.0.0.1:" + PORT);
return HazelcastClient.newHazelcastClient(clientConfig);

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2014-2018 the original author or authors.
* Copyright 2014-2016 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.
@@ -19,7 +19,6 @@ package org.springframework.session.hazelcast;
import com.hazelcast.config.Config;
import com.hazelcast.config.MapAttributeConfig;
import com.hazelcast.config.MapIndexConfig;
import com.hazelcast.config.NetworkConfig;
import com.hazelcast.core.Hazelcast;
import com.hazelcast.core.HazelcastInstance;
@@ -47,12 +46,8 @@ public final class HazelcastITestUtils {
Config config = new Config();
NetworkConfig networkConfig = config.getNetworkConfig();
networkConfig.setPort(port);
networkConfig.getJoin()
.getMulticastConfig().setEnabled(false);
config.getNetworkConfig()
.setPort(port);
config.getMapConfig("spring:session:sessions")
.addMapAttributeConfig(attributeConfig)

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2014-2018 the original author or authors.
* Copyright 2014-2016 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.
@@ -43,7 +43,7 @@ public class HazelcastServerRepositoryITests extends AbstractHazelcastRepository
static class HazelcastSessionConfig {
@Bean
public HazelcastInstance hazelcastInstance() {
public HazelcastInstance embeddedHazelcastServer() {
return HazelcastITestUtils.embeddedHazelcastServer();
}

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2014-2018 the original author or authors.
* Copyright 2014-2016 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.
@@ -34,8 +34,10 @@ import org.springframework.security.core.Authentication;
import org.springframework.security.core.authority.AuthorityUtils;
import org.springframework.security.core.context.SecurityContext;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.session.ExpiringSession;
import org.springframework.session.FindByIndexNameSessionRepository;
import org.springframework.session.MapSession;
import org.springframework.session.Session;
import org.springframework.session.jdbc.config.annotation.web.http.EnableJdbcHttpSession;
import org.springframework.test.context.ContextConfiguration;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
@@ -80,19 +82,6 @@ public abstract class AbstractJdbcOperationsSessionRepositoryITests {
AuthorityUtils.createAuthorityList("ROLE_USER")));
}
@Test
public void saveWhenNoAttributesThenCanBeFound() {
JdbcOperationsSessionRepository.JdbcSession toSave = this.repository
.createSession();
this.repository.save(toSave);
JdbcOperationsSessionRepository.JdbcSession session = this.repository.getSession(toSave.getId());
assertThat(session).isNotNull();
assertThat(session.isChanged()).isFalse();
assertThat(session.getDelta()).isEmpty();
}
@Test
public void saves() throws InterruptedException {
String username = "saves-" + System.currentTimeMillis();
@@ -111,11 +100,9 @@ public abstract class AbstractJdbcOperationsSessionRepositoryITests {
this.repository.save(toSave);
JdbcOperationsSessionRepository.JdbcSession session = this.repository.getSession(toSave.getId());
Session session = this.repository.getSession(toSave.getId());
assertThat(session.getId()).isEqualTo(toSave.getId());
assertThat(session.isChanged()).isFalse();
assertThat(session.getDelta()).isEmpty();
assertThat(session.getAttributeNames()).isEqualTo(toSave.getAttributeNames());
assertThat(session.getAttribute(expectedAttributeName))
.isEqualTo(toSave.getAttribute(expectedAttributeName));
@@ -148,9 +135,7 @@ public abstract class AbstractJdbcOperationsSessionRepositoryITests {
this.repository.save(toSave);
toSave = this.repository.getSession(toSave.getId());
JdbcOperationsSessionRepository.JdbcSession session = this.repository.getSession(toSave.getId());
assertThat(session.isChanged()).isFalse();
assertThat(session.getDelta()).isEmpty();
Session session = this.repository.getSession(toSave.getId());
assertThat(session.getAttributeNames().size()).isEqualTo(2);
assertThat(session.getAttribute("a")).isEqualTo("b");
assertThat(session.getAttribute("1")).isEqualTo("2");
@@ -171,11 +156,9 @@ public abstract class AbstractJdbcOperationsSessionRepositoryITests {
toSave.setLastAccessedTime(lastAccessedTime);
this.repository.save(toSave);
JdbcOperationsSessionRepository.JdbcSession session = this.repository.getSession(toSave.getId());
ExpiringSession session = this.repository.getSession(toSave.getId());
assertThat(session).isNotNull();
assertThat(session.isChanged()).isFalse();
assertThat(session.getDelta()).isEmpty();
assertThat(session.isExpired()).isFalse();
assertThat(session.getLastAccessedTime()).isEqualTo(lastAccessedTime);
}
@@ -242,10 +225,6 @@ public abstract class AbstractJdbcOperationsSessionRepositoryITests {
assertThat(findByPrincipalName).hasSize(1);
assertThat(findByPrincipalName.keySet()).containsOnly(toSave.getId());
for (JdbcOperationsSessionRepository.JdbcSession session : findByPrincipalName.values()) {
assertThat(session.isChanged()).isFalse();
assertThat(session.getDelta()).isEmpty();
}
}
@Test
@@ -268,10 +247,6 @@ public abstract class AbstractJdbcOperationsSessionRepositoryITests {
assertThat(findByPrincipalName).hasSize(1);
assertThat(findByPrincipalName.keySet()).containsOnly(toSave.getId());
for (JdbcOperationsSessionRepository.JdbcSession session : findByPrincipalName.values()) {
assertThat(session.isChanged()).isFalse();
assertThat(session.getDelta()).isEmpty();
}
}
@Test
@@ -314,10 +289,6 @@ public abstract class AbstractJdbcOperationsSessionRepositoryITests {
assertThat(findByPrincipalName).hasSize(1);
assertThat(findByPrincipalName.keySet()).containsOnly(toSave.getId());
for (JdbcOperationsSessionRepository.JdbcSession session : findByPrincipalName.values()) {
assertThat(session.isChanged()).isFalse();
assertThat(session.getDelta()).isEmpty();
}
}
@Test
@@ -365,10 +336,6 @@ public abstract class AbstractJdbcOperationsSessionRepositoryITests {
assertThat(findByPrincipalName).hasSize(1);
assertThat(findByPrincipalName.keySet()).containsOnly(toSave.getId());
for (JdbcOperationsSessionRepository.JdbcSession session : findByPrincipalName.values()) {
assertThat(session.isChanged()).isFalse();
assertThat(session.getDelta()).isEmpty();
}
}
@Test
@@ -428,10 +395,6 @@ public abstract class AbstractJdbcOperationsSessionRepositoryITests {
assertThat(findByPrincipalName).hasSize(1);
assertThat(findByPrincipalName.keySet()).containsOnly(toSave.getId());
for (JdbcOperationsSessionRepository.JdbcSession session : findByPrincipalName.values()) {
assertThat(session.isChanged()).isFalse();
assertThat(session.getDelta()).isEmpty();
}
}
@Test
@@ -453,10 +416,6 @@ public abstract class AbstractJdbcOperationsSessionRepositoryITests {
assertThat(findByPrincipalName).hasSize(1);
assertThat(findByPrincipalName.keySet()).containsOnly(toSave.getId());
for (JdbcOperationsSessionRepository.JdbcSession session : findByPrincipalName.values()) {
assertThat(session.isChanged()).isFalse();
assertThat(session.getDelta()).isEmpty();
}
}
@Test
@@ -496,10 +455,6 @@ public abstract class AbstractJdbcOperationsSessionRepositoryITests {
assertThat(findByPrincipalName).hasSize(1);
assertThat(findByPrincipalName.keySet()).containsOnly(toSave.getId());
for (JdbcOperationsSessionRepository.JdbcSession session : findByPrincipalName.values()) {
assertThat(session.isChanged()).isFalse();
assertThat(session.getDelta()).isEmpty();
}
}
@Test
@@ -544,10 +499,6 @@ public abstract class AbstractJdbcOperationsSessionRepositoryITests {
assertThat(findByPrincipalName).hasSize(1);
assertThat(findByPrincipalName.keySet()).containsOnly(toSave.getId());
for (JdbcOperationsSessionRepository.JdbcSession session : findByPrincipalName.values()) {
assertThat(session.isChanged()).isFalse();
assertThat(session.getDelta()).isEmpty();
}
}
@Test
@@ -608,46 +559,6 @@ public abstract class AbstractJdbcOperationsSessionRepositoryITests {
assertThat(this.repository.getSession(session.getId())).isNull();
}
@Test // gh-1031
public void saveDeleted() {
JdbcOperationsSessionRepository.JdbcSession session = this.repository.createSession();
this.repository.save(session);
session = this.repository.getSession(session.getId());
this.repository.delete(session.getId());
session.setLastAccessedTime(System.currentTimeMillis());
this.repository.save(session);
assertThat(this.repository.getSession(session.getId())).isNull();
}
@Test // gh-1031
public void saveDeletedAddAttribute() {
JdbcOperationsSessionRepository.JdbcSession session = this.repository.createSession();
this.repository.save(session);
session = this.repository.getSession(session.getId());
this.repository.delete(session.getId());
session.setLastAccessedTime(System.currentTimeMillis());
session.setAttribute("testName", "testValue1");
this.repository.save(session);
assertThat(this.repository.getSession(session.getId())).isNull();
}
@Test // gh-1203
public void saveWithLargeAttribute() {
String attributeName = "largeAttribute";
int arraySize = 4000;
JdbcOperationsSessionRepository.JdbcSession session = this.repository
.createSession();
session.setAttribute(attributeName, new byte[arraySize]);
this.repository.save(session);
session = this.repository.getSession(session.getId());
assertThat(session).isNotNull();
assertThat((byte[]) session.getAttribute(attributeName)).hasSize(arraySize);
}
private String getSecurityName() {
return this.context.getAuthentication().getName();
}

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2014-2018 the original author or authors.
* Copyright 2014-2016 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.
@@ -52,7 +52,7 @@ public interface FindByIndexNameSessionRepository<S extends Session>
* {@link FindByIndexNameSessionRepository#PRINCIPAL_NAME_INDEX_NAME} and the value of
* the specified principal name.
*
* @param indexName the name of the index (i.e.
* @param indexName the name if the index (i.e.
* {@link FindByIndexNameSessionRepository#PRINCIPAL_NAME_INDEX_NAME})
* @param indexValue the value of the index to search for.
* @return a Map (never null) of the session id to the {@link Session} of all sessions

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2014-2018 the original author or authors.
* Copyright 2014-2016 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.
@@ -18,7 +18,6 @@ package org.springframework.session;
import java.io.Serializable;
import java.util.HashMap;
import java.util.HashSet;
import java.util.Map;
import java.util.Set;
import java.util.UUID;
@@ -142,7 +141,7 @@ public final class MapSession implements ExpiringSession, Serializable {
}
public Set<String> getAttributeNames() {
return new HashSet<String>(this.sessionAttrs.keySet());
return this.sessionAttrs.keySet();
}
public void setAttribute(String attributeName, Object attributeValue) {

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2014-2018 the original author or authors.
* Copyright 2014-2016 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.
@@ -201,7 +201,7 @@ import org.springframework.util.Assert;
*
* <p>
* One problem with relying on Redis expiration exclusively is that Redis makes no
* guarantee of when the expired event will be fired if the key has not been accessed.
* guarantee of when the expired event will be fired if they key has not been accessed.
* Specifically the background task that Redis uses to clean up expired keys is a low
* priority task and may not trigger the key expiration. For additional details see
* <a href="http://redis.io/topics/notifications">Timing of expired events</a> section in
@@ -212,7 +212,7 @@ import org.springframework.util.Assert;
* To circumvent the fact that expired events are not guaranteed to happen we can ensure
* that each key is accessed when it is expected to expire. This means that if the TTL is
* expired on the key, Redis will remove the key and fire the expired event when we try to
* access the key.
* access they key.
* </p>
*
* <p>
@@ -277,7 +277,7 @@ public class RedisOperationsSessionRepository implements
static final String LAST_ACCESSED_ATTR = "lastAccessedTime";
/**
* The prefix of the key used for session attributes. The suffix is the name of
* The prefix of the key for used for session attributes. The suffix is the name of
* the session attribute. For example, if the session contained an attribute named
* attributeName, then there would be an entry in the hash named
* sessionAttr:attributeName that mapped to its value.
@@ -518,12 +518,6 @@ public class RedisOperationsSessionRepository implements
RedisSession session = getSession(sessionId, true);
if (session == null) {
logger.warn("Unable to publish SessionDestroyedEvent for session "
+ sessionId);
return;
}
if (logger.isDebugEnabled()) {
logger.debug("Publishing SessionDestroyedEvent for session " + sessionId);
}
@@ -531,15 +525,20 @@ public class RedisOperationsSessionRepository implements
cleanupPrincipalIndex(session);
if (isDeleted) {
handleDeleted(session);
handleDeleted(sessionId, session);
}
else {
handleExpired(session);
handleExpired(sessionId, session);
}
return;
}
}
private void cleanupPrincipalIndex(RedisSession session) {
if (session == null) {
return;
}
String sessionId = session.getId();
String principal = PRINCIPAL_NAME_RESOLVER.resolvePrincipal(session);
if (principal != null) {
@@ -554,12 +553,22 @@ public class RedisOperationsSessionRepository implements
publishEvent(new SessionCreatedEvent(this, session));
}
private void handleDeleted(RedisSession session) {
publishEvent(new SessionDeletedEvent(this, session));
private void handleDeleted(String sessionId, RedisSession session) {
if (session == null) {
publishEvent(new SessionDeletedEvent(this, sessionId));
}
else {
publishEvent(new SessionDeletedEvent(this, session));
}
}
private void handleExpired(RedisSession session) {
publishEvent(new SessionExpiredEvent(this, session));
private void handleExpired(String sessionId, RedisSession session) {
if (session == null) {
publishEvent(new SessionExpiredEvent(this, sessionId));
}
else {
publishEvent(new SessionExpiredEvent(this, session));
}
}
private void publishEvent(ApplicationEvent event) {

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2014-2018 the original author or authors.
* Copyright 2014-2016 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.
@@ -108,7 +108,8 @@ import org.springframework.util.Assert;
*/
public class HazelcastSessionRepository implements
FindByIndexNameSessionRepository<HazelcastSessionRepository.HazelcastSession>,
EntryAddedListener<String, MapSession>, EntryEvictedListener<String, MapSession>,
EntryAddedListener<String, MapSession>,
EntryEvictedListener<String, MapSession>,
EntryRemovedListener<String, MapSession> {
/**
@@ -199,24 +200,11 @@ public class HazelcastSessionRepository implements
}
public void save(HazelcastSession session) {
if (session.isNew) {
this.sessions.set(session.getId(), session.getDelegate(),
if (session.isChanged()) {
this.sessions.put(session.getId(), session.getDelegate(),
session.getMaxInactiveIntervalInSeconds(), TimeUnit.SECONDS);
session.markUnchanged();
}
else if (session.hasChanges()) {
SessionUpdateEntryProcessor entryProcessor = new SessionUpdateEntryProcessor();
if (session.lastAccessedTimeChanged) {
entryProcessor.setLastAccessedTime(session.getLastAccessedTime());
}
if (session.maxInactiveIntervalChanged) {
entryProcessor.setMaxInactiveInterval(session.getMaxInactiveIntervalInSeconds());
}
if (!session.delta.isEmpty()) {
entryProcessor.setDelta(session.delta);
}
this.sessions.executeOnKey(session.getId(), entryProcessor);
}
session.clearChangeFlags();
}
public HazelcastSession getSession(String id) {
@@ -235,13 +223,13 @@ public class HazelcastSessionRepository implements
this.sessions.remove(id);
}
public Map<String, HazelcastSession> findByIndexNameAndIndexValue(String indexName,
String indexValue) {
public Map<String, HazelcastSession> findByIndexNameAndIndexValue(
String indexName, String indexValue) {
if (!PRINCIPAL_NAME_INDEX_NAME.equals(indexName)) {
return Collections.emptyMap();
}
Collection<MapSession> sessions = this.sessions
.values(Predicates.equal(PRINCIPAL_NAME_ATTRIBUTE, indexValue));
Collection<MapSession> sessions = this.sessions.values(
Predicates.equal(PRINCIPAL_NAME_ATTRIBUTE, indexValue));
Map<String, HazelcastSession> sessionMap = new HashMap<String, HazelcastSession>(
sessions.size());
for (MapSession session : sessions) {
@@ -282,16 +270,7 @@ public class HazelcastSessionRepository implements
final class HazelcastSession implements ExpiringSession {
private final MapSession delegate;
private boolean isNew;
private boolean sessionIdChanged;
private boolean lastAccessedTimeChanged;
private boolean maxInactiveIntervalChanged;
private Map<String, Object> delta = new HashMap<String, Object>();
private boolean changed;
/**
* Creates a new instance ensuring to mark all of the new attributes to be
@@ -299,7 +278,7 @@ public class HazelcastSessionRepository implements
*/
HazelcastSession() {
this(new MapSession());
this.isNew = true;
this.changed = true;
flushImmediateIfNecessary();
}
@@ -315,7 +294,7 @@ public class HazelcastSessionRepository implements
public void setLastAccessedTime(long lastAccessedTime) {
this.delegate.setLastAccessedTime(lastAccessedTime);
this.lastAccessedTimeChanged = true;
this.changed = true;
flushImmediateIfNecessary();
}
@@ -337,7 +316,7 @@ public class HazelcastSessionRepository implements
public void setMaxInactiveIntervalInSeconds(int interval) {
this.delegate.setMaxInactiveIntervalInSeconds(interval);
this.maxInactiveIntervalChanged = true;
this.changed = true;
flushImmediateIfNecessary();
}
@@ -355,33 +334,28 @@ public class HazelcastSessionRepository implements
public void setAttribute(String attributeName, Object attributeValue) {
this.delegate.setAttribute(attributeName, attributeValue);
this.delta.put(attributeName, attributeValue);
this.changed = true;
flushImmediateIfNecessary();
}
public void removeAttribute(String attributeName) {
this.delegate.removeAttribute(attributeName);
this.delta.put(attributeName, null);
this.changed = true;
flushImmediateIfNecessary();
}
boolean isChanged() {
return this.changed;
}
void markUnchanged() {
this.changed = false;
}
MapSession getDelegate() {
return this.delegate;
}
boolean hasChanges() {
return (this.lastAccessedTimeChanged || this.maxInactiveIntervalChanged
|| !this.delta.isEmpty());
}
void clearChangeFlags() {
this.isNew = false;
this.lastAccessedTimeChanged = false;
this.sessionIdChanged = false;
this.maxInactiveIntervalChanged = false;
this.delta.clear();
}
private void flushImmediateIfNecessary() {
if (HazelcastSessionRepository.this.hazelcastFlushMode == HazelcastFlushMode.IMMEDIATE) {
HazelcastSessionRepository.this.save(this);

View File

@@ -1,85 +0,0 @@
/*
* Copyright 2014-2018 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.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.springframework.session.hazelcast;
import java.util.Map;
import com.hazelcast.map.AbstractEntryProcessor;
import com.hazelcast.map.EntryProcessor;
import org.springframework.session.MapSession;
/**
* Hazelcast {@link EntryProcessor} responsible for handling updates to session.
*
* @author Vedran Pavic
* @since 1.3.4
* @see HazelcastSessionRepository#save(HazelcastSessionRepository.HazelcastSession)
*/
public class SessionUpdateEntryProcessor
extends AbstractEntryProcessor<String, MapSession> {
private long lastAccessedTime;
private boolean lastAccessedTimeSet;
private int maxInactiveInterval;
private boolean maxInactiveIntervalSet;
private Map<String, Object> delta;
public Object process(Map.Entry<String, MapSession> entry) {
MapSession value = entry.getValue();
if (value == null) {
return Boolean.FALSE;
}
if (this.lastAccessedTimeSet) {
value.setLastAccessedTime(this.lastAccessedTime);
}
if (this.maxInactiveIntervalSet) {
value.setMaxInactiveIntervalInSeconds(this.maxInactiveInterval);
}
if (this.delta != null) {
for (final Map.Entry<String, Object> attribute : this.delta.entrySet()) {
if (attribute.getValue() != null) {
value.setAttribute(attribute.getKey(), attribute.getValue());
}
else {
value.removeAttribute(attribute.getKey());
}
}
}
entry.setValue(value);
return Boolean.TRUE;
}
void setLastAccessedTime(long lastAccessedTime) {
this.lastAccessedTime = lastAccessedTime;
this.lastAccessedTimeSet = true;
}
void setMaxInactiveInterval(int maxInactiveInterval) {
this.maxInactiveInterval = maxInactiveInterval;
this.maxInactiveIntervalSet = true;
}
void setDelta(Map<String, Object> delta) {
this.delta = delta;
}
}

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2014-2018 the original author or authors.
* Copyright 2014-2016 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.
@@ -105,7 +105,6 @@ import org.springframework.util.StringUtils;
* );
*
* CREATE INDEX SPRING_SESSION_IX1 ON SPRING_SESSION (LAST_ACCESS_TIME);
* CREATE INDEX SPRING_SESSION_IX2 ON SPRING_SESSION (PRINCIPAL_NAME);
*
* CREATE TABLE SPRING_SESSION_ATTRIBUTES (
* SESSION_ID CHAR(36),
@@ -143,9 +142,7 @@ public class JdbcOperationsSessionRepository implements
private static final String CREATE_SESSION_ATTRIBUTE_QUERY =
"INSERT INTO %TABLE_NAME%_ATTRIBUTES(SESSION_ID, ATTRIBUTE_NAME, ATTRIBUTE_BYTES) " +
"SELECT SESSION_ID, ?, ? " +
"FROM %TABLE_NAME% " +
"WHERE SESSION_ID = ?";
"VALUES (?, ?, ?)";
private static final String GET_SESSION_QUERY =
"SELECT S.SESSION_ID, S.CREATION_TIME, S.LAST_ACCESS_TIME, S.MAX_INACTIVE_INTERVAL, SA.ATTRIBUTE_NAME, SA.ATTRIBUTE_BYTES " +
@@ -190,7 +187,8 @@ public class JdbcOperationsSessionRepository implements
private final TransactionOperations transactionOperations;
private final ResultSetExtractor<List<JdbcSession>> extractor = new SessionResultSetExtractor();
private final ResultSetExtractor<List<ExpiringSession>> extractor =
new ExpiringSessionResultSetExtractor();
/**
* The name of database table used by Spring Session to store sessions.
@@ -400,9 +398,9 @@ public class JdbcOperationsSessionRepository implements
public void setValues(PreparedStatement ps, int i) throws SQLException {
String attributeName = attributeNames.get(i);
ps.setString(1, attributeName);
serialize(ps, 2, session.getAttribute(attributeName));
ps.setString(3, session.getId());
ps.setString(1, session.getId());
ps.setString(2, attributeName);
serialize(ps, 3, session.getAttribute(attributeName));
}
public int getBatchSize() {
@@ -467,9 +465,9 @@ public class JdbcOperationsSessionRepository implements
new PreparedStatementSetter() {
public void setValues(PreparedStatement ps) throws SQLException {
ps.setString(1, entry.getKey());
serialize(ps, 2, entry.getValue());
ps.setString(3, session.getId());
ps.setString(1, session.getId());
ps.setString(2, entry.getKey());
serialize(ps, 3, entry.getValue());
}
});
@@ -485,10 +483,10 @@ public class JdbcOperationsSessionRepository implements
}
public JdbcSession getSession(final String id) {
final JdbcSession session = this.transactionOperations.execute(new TransactionCallback<JdbcSession>() {
final ExpiringSession session = this.transactionOperations.execute(new TransactionCallback<ExpiringSession>() {
public JdbcSession doInTransaction(TransactionStatus status) {
List<JdbcSession> sessions = JdbcOperationsSessionRepository.this.jdbcOperations.query(
public ExpiringSession doInTransaction(TransactionStatus status) {
List<ExpiringSession> sessions = JdbcOperationsSessionRepository.this.jdbcOperations.query(
JdbcOperationsSessionRepository.this.getSessionQuery,
new PreparedStatementSetter() {
@@ -512,7 +510,7 @@ public class JdbcOperationsSessionRepository implements
delete(id);
}
else {
return session;
return new JdbcSession(session);
}
}
return null;
@@ -535,9 +533,9 @@ public class JdbcOperationsSessionRepository implements
return Collections.emptyMap();
}
List<JdbcSession> sessions = this.transactionOperations.execute(new TransactionCallback<List<JdbcSession>>() {
List<ExpiringSession> sessions = this.transactionOperations.execute(new TransactionCallback<List<ExpiringSession>>() {
public List<JdbcSession> doInTransaction(TransactionStatus status) {
public List<ExpiringSession> doInTransaction(TransactionStatus status) {
return JdbcOperationsSessionRepository.this.jdbcOperations.query(
JdbcOperationsSessionRepository.this.listSessionsByPrincipalNameQuery,
new PreparedStatementSetter() {
@@ -556,8 +554,8 @@ public class JdbcOperationsSessionRepository implements
Map<String, JdbcSession> sessionMap = new HashMap<String, JdbcSession>(
sessions.size());
for (JdbcSession session : sessions) {
sessionMap.put(session.getId(), session);
for (ExpiringSession session : sessions) {
sessionMap.put(session.getId(), new JdbcSession(session));
}
return sessionMap;
@@ -765,33 +763,33 @@ public class JdbcOperationsSessionRepository implements
}
private class SessionResultSetExtractor implements ResultSetExtractor<List<JdbcSession>> {
private class ExpiringSessionResultSetExtractor
implements ResultSetExtractor<List<ExpiringSession>> {
public List<JdbcSession> extractData(ResultSet rs) throws SQLException, DataAccessException {
List<JdbcSession> sessions = new ArrayList<JdbcSession>();
public List<ExpiringSession> extractData(ResultSet rs) throws SQLException, DataAccessException {
List<ExpiringSession> sessions = new ArrayList<ExpiringSession>();
while (rs.next()) {
String id = rs.getString("SESSION_ID");
JdbcSession session;
MapSession session;
if (sessions.size() > 0 && getLast(sessions).getId().equals(id)) {
session = getLast(sessions);
session = (MapSession) getLast(sessions);
}
else {
MapSession delegate = new MapSession(id);
delegate.setCreationTime(rs.getLong("CREATION_TIME"));
delegate.setLastAccessedTime(rs.getLong("LAST_ACCESS_TIME"));
delegate.setMaxInactiveIntervalInSeconds(rs.getInt("MAX_INACTIVE_INTERVAL"));
session = new JdbcSession(delegate);
session = new MapSession(id);
session.setCreationTime(rs.getLong("CREATION_TIME"));
session.setLastAccessedTime(rs.getLong("LAST_ACCESS_TIME"));
session.setMaxInactiveIntervalInSeconds(rs.getInt("MAX_INACTIVE_INTERVAL"));
}
String attributeName = rs.getString("ATTRIBUTE_NAME");
if (attributeName != null) {
session.delegate.setAttribute(attributeName, deserialize(rs, "ATTRIBUTE_BYTES"));
session.setAttribute(attributeName, deserialize(rs, "ATTRIBUTE_BYTES"));
}
sessions.add(session);
}
return sessions;
}
private JdbcSession getLast(List<JdbcSession> sessions) {
private ExpiringSession getLast(List<ExpiringSession> sessions) {
return sessions.get(sessions.size() - 1);
}

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2014-2018 the original author or authors.
* Copyright 2014-2016 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.
@@ -33,10 +33,8 @@ import org.springframework.core.convert.support.GenericConversionService;
import org.springframework.core.serializer.support.DeserializingConverter;
import org.springframework.core.serializer.support.SerializingConverter;
import org.springframework.core.type.AnnotationMetadata;
import org.springframework.jdbc.core.JdbcOperations;
import org.springframework.jdbc.core.JdbcTemplate;
import org.springframework.jdbc.support.JdbcUtils;
import org.springframework.jdbc.support.MetaDataAccessException;
import org.springframework.jdbc.support.lob.DefaultLobHandler;
import org.springframework.jdbc.support.lob.LobHandler;
import org.springframework.scheduling.annotation.EnableScheduling;
import org.springframework.session.config.annotation.web.http.SpringHttpSessionConfiguration;
@@ -87,7 +85,7 @@ public class JdbcHttpSessionConfiguration extends SpringHttpSessionConfiguration
@Bean
public JdbcOperationsSessionRepository sessionRepository(
@Qualifier("springSessionJdbcOperations") JdbcTemplate jdbcOperations,
@Qualifier("springSessionJdbcOperations") JdbcOperations jdbcOperations,
PlatformTransactionManager transactionManager) {
JdbcOperationsSessionRepository sessionRepository =
new JdbcOperationsSessionRepository(jdbcOperations, transactionManager);
@@ -100,11 +98,6 @@ public class JdbcHttpSessionConfiguration extends SpringHttpSessionConfiguration
if (this.lobHandler != null) {
sessionRepository.setLobHandler(this.lobHandler);
}
else if (requiresTemporaryLob(jdbcOperations.getDataSource())) {
DefaultLobHandler lobHandler = new DefaultLobHandler();
lobHandler.setCreateTemporaryLob(true);
sessionRepository.setLobHandler(lobHandler);
}
if (this.springSessionConversionService != null) {
sessionRepository.setConversionService(this.springSessionConversionService);
}
@@ -118,22 +111,11 @@ public class JdbcHttpSessionConfiguration extends SpringHttpSessionConfiguration
return sessionRepository;
}
private static boolean requiresTemporaryLob(DataSource dataSource) {
try {
String productName = (String) JdbcUtils.extractDatabaseMetaData(dataSource,
"getDatabaseProductName");
return "Oracle".equalsIgnoreCase(JdbcUtils.commonDatabaseName(productName));
}
catch (MetaDataAccessException ex) {
return false;
}
}
/**
* This must be a separate method because some ClassLoaders load the entire method
* definition even if an if statement guards against it loading. This means that older
* versions of Spring would cause a NoSuchMethodError if this were defined in
* {@link #sessionRepository(JdbcTemplate, PlatformTransactionManager)}.
* {@link #sessionRepository(JdbcOperations, PlatformTransactionManager)}.
*
* @return the default {@link ConversionService}
*/

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2014-2018 the original author or authors.
* Copyright 2014-2016 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.
@@ -250,18 +250,18 @@ public final class CookieHttpSessionStrategy
return sessionIds.values().iterator().next();
}
StringBuilder sb = new StringBuilder();
StringBuffer buffer = new StringBuffer();
for (Map.Entry<String, String> entry : sessionIds.entrySet()) {
String alias = entry.getKey();
String id = entry.getValue();
sb.append(alias);
sb.append(this.serializationDelimiter);
sb.append(id);
sb.append(this.serializationDelimiter);
buffer.append(alias);
buffer.append(this.serializationDelimiter);
buffer.append(id);
buffer.append(this.serializationDelimiter);
}
sb.deleteCharAt(sb.length() - 1);
return sb.toString();
buffer.deleteCharAt(buffer.length() - 1);
return buffer.toString();
}
public void onInvalidateSession(HttpServletRequest request,

View File

@@ -26,9 +26,6 @@ import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
/**
* The default implementation of {@link CookieSerializer}.
*
@@ -38,8 +35,6 @@ import org.apache.commons.logging.LogFactory;
*/
public class DefaultCookieSerializer implements CookieSerializer {
private static final Log logger = LogFactory.getLog(DefaultCookieSerializer.class);
private String cookieName = "SESSION";
private Boolean useSecureCookie;
@@ -143,7 +138,6 @@ public class DefaultCookieSerializer implements CookieSerializer {
return new String(decodedCookieBytes);
}
catch (Exception e) {
logger.debug("Unable to Base64 decode value: " + base64Value);
return null;
}
}

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2014-2018 the original author or authors.
* Copyright 2014-2016 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.
@@ -22,11 +22,8 @@ import java.util.HashMap;
import java.util.Map;
import javax.servlet.FilterChain;
import javax.servlet.RequestDispatcher;
import javax.servlet.ServletContext;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletRequestWrapper;
import javax.servlet.http.HttpServletResponse;
@@ -51,7 +48,7 @@ import org.springframework.session.SessionRepository;
* {@link org.springframework.session.SessionRepository}.
*
* The {@link SessionRepositoryFilter} uses a {@link HttpSessionStrategy} (default
* {@link CookieHttpSessionStrategy}) to bridge logic between an
* {@link CookieHttpSessionStrategy} to bridge logic between an
* {@link javax.servlet.http.HttpSession} and the
* {@link org.springframework.session.Session} abstraction. Specifically:
*
@@ -75,7 +72,6 @@ import org.springframework.session.SessionRepository;
* @param <S> the {@link ExpiringSession} type.
* @since 1.0
* @author Rob Winch
* @author Josh Cummings
*/
@Order(SessionRepositoryFilter.DEFAULT_ORDER)
public class SessionRepositoryFilter<S extends ExpiringSession>
@@ -293,10 +289,9 @@ public class SessionRepositoryFilter<S extends ExpiringSession>
setCurrentSession(null);
HttpSessionWrapper newSession = getSession();
int originalMaxInactiveInterval = session.getMaxInactiveInterval();
original.setSession(newSession.getSession());
newSession.setMaxInactiveInterval(originalMaxInactiveInterval);
newSession.setMaxInactiveInterval(session.getMaxInactiveInterval());
for (Map.Entry<String, Object> attr : attrs.entrySet()) {
String attrName = attr.getKey();
Object attrValue = attr.getValue();
@@ -401,12 +396,6 @@ public class SessionRepositoryFilter<S extends ExpiringSession>
.getRequestedSessionId(this);
}
@Override
public RequestDispatcher getRequestDispatcher(String path) {
RequestDispatcher requestDispatcher = super.getRequestDispatcher(path);
return new SessionCommittingRequestDispatcher(requestDispatcher);
}
/**
* Allows creating an HttpSession from a Session instance.
*
@@ -427,34 +416,6 @@ public class SessionRepositoryFilter<S extends ExpiringSession>
SessionRepositoryFilter.this.sessionRepository.delete(getId());
}
}
/**
* Ensures session is committed before issuing an include.
*
* @since 1.3.4
*/
private final class SessionCommittingRequestDispatcher
implements RequestDispatcher {
private final RequestDispatcher delegate;
SessionCommittingRequestDispatcher(RequestDispatcher delegate) {
this.delegate = delegate;
}
public void forward(ServletRequest request, ServletResponse response)
throws ServletException, IOException {
this.delegate.forward(request, response);
}
public void include(ServletRequest request, ServletResponse response)
throws ServletException, IOException {
SessionRepositoryRequestWrapper.this.commitSession();
this.delegate.include(request, response);
}
}
}
/**

View File

@@ -8,7 +8,6 @@ CREATE TABLE SPRING_SESSION (
);
CREATE INDEX SPRING_SESSION_IX1 ON SPRING_SESSION (LAST_ACCESS_TIME);
CREATE INDEX SPRING_SESSION_IX2 ON SPRING_SESSION (PRINCIPAL_NAME);
CREATE TABLE SPRING_SESSION_ATTRIBUTES (
SESSION_ID CHAR(36) NOT NULL,

View File

@@ -8,7 +8,6 @@ CREATE TABLE SPRING_SESSION (
);
CREATE INDEX SPRING_SESSION_IX1 ON SPRING_SESSION (LAST_ACCESS_TIME);
CREATE INDEX SPRING_SESSION_IX2 ON SPRING_SESSION (PRINCIPAL_NAME);
CREATE TABLE SPRING_SESSION_ATTRIBUTES (
SESSION_ID CHAR(36) NOT NULL,

View File

@@ -8,7 +8,6 @@ CREATE TABLE SPRING_SESSION (
);
CREATE INDEX SPRING_SESSION_IX1 ON SPRING_SESSION (LAST_ACCESS_TIME);
CREATE INDEX SPRING_SESSION_IX2 ON SPRING_SESSION (PRINCIPAL_NAME);
CREATE TABLE SPRING_SESSION_ATTRIBUTES (
SESSION_ID CHAR(36) NOT NULL,

View File

@@ -8,7 +8,6 @@ CREATE TABLE SPRING_SESSION (
);
CREATE INDEX SPRING_SESSION_IX1 ON SPRING_SESSION (LAST_ACCESS_TIME);
CREATE INDEX SPRING_SESSION_IX2 ON SPRING_SESSION (PRINCIPAL_NAME);
CREATE TABLE SPRING_SESSION_ATTRIBUTES (
SESSION_ID CHAR(36) NOT NULL,

View File

@@ -8,7 +8,6 @@ CREATE TABLE SPRING_SESSION (
) ENGINE=InnoDB;
CREATE INDEX SPRING_SESSION_IX1 ON SPRING_SESSION (LAST_ACCESS_TIME);
CREATE INDEX SPRING_SESSION_IX2 ON SPRING_SESSION (PRINCIPAL_NAME);
CREATE TABLE SPRING_SESSION_ATTRIBUTES (
SESSION_ID CHAR(36) NOT NULL,

View File

@@ -8,7 +8,6 @@ CREATE TABLE SPRING_SESSION (
);
CREATE INDEX SPRING_SESSION_IX1 ON SPRING_SESSION (LAST_ACCESS_TIME);
CREATE INDEX SPRING_SESSION_IX2 ON SPRING_SESSION (PRINCIPAL_NAME);
CREATE TABLE SPRING_SESSION_ATTRIBUTES (
SESSION_ID CHAR(36) NOT NULL,

View File

@@ -8,7 +8,6 @@ CREATE TABLE SPRING_SESSION (
);
CREATE INDEX SPRING_SESSION_IX1 ON SPRING_SESSION (LAST_ACCESS_TIME);
CREATE INDEX SPRING_SESSION_IX2 ON SPRING_SESSION (PRINCIPAL_NAME);
CREATE TABLE SPRING_SESSION_ATTRIBUTES (
SESSION_ID CHAR(36) NOT NULL,

View File

@@ -8,7 +8,6 @@ CREATE TABLE SPRING_SESSION (
);
CREATE INDEX SPRING_SESSION_IX1 ON SPRING_SESSION (LAST_ACCESS_TIME);
CREATE INDEX SPRING_SESSION_IX2 ON SPRING_SESSION (PRINCIPAL_NAME);
CREATE TABLE SPRING_SESSION_ATTRIBUTES (
SESSION_ID CHAR(36) NOT NULL,

View File

@@ -8,7 +8,6 @@ CREATE TABLE SPRING_SESSION (
);
CREATE INDEX SPRING_SESSION_IX1 ON SPRING_SESSION (LAST_ACCESS_TIME);
CREATE INDEX SPRING_SESSION_IX2 ON SPRING_SESSION (PRINCIPAL_NAME);
CREATE TABLE SPRING_SESSION_ATTRIBUTES (
SESSION_ID CHAR(36) NOT NULL,

View File

@@ -8,7 +8,6 @@ CREATE TABLE SPRING_SESSION (
) LOCK DATAROWS;
CREATE INDEX SPRING_SESSION_IX1 ON SPRING_SESSION (LAST_ACCESS_TIME);
CREATE INDEX SPRING_SESSION_IX2 ON SPRING_SESSION (PRINCIPAL_NAME);
CREATE TABLE SPRING_SESSION_ATTRIBUTES (
SESSION_ID CHAR(36) NOT NULL,

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2014-2018 the original author or authors.
* Copyright 2014-2016 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.
@@ -64,18 +64,4 @@ public class MapSessionRepositoryTests {
assertThat(session.getMaxInactiveIntervalInSeconds())
.isEqualTo(expectedMaxInterval);
}
@Test // gh-1120
public void getAttributeNamesAndRemove() {
ExpiringSession session = this.repository.createSession();
session.setAttribute("attribute1", "value1");
session.setAttribute("attribute2", "value2");
for (String attributeName : session.getAttributeNames()) {
session.removeAttribute(attributeName);
}
assertThat(session.getAttributeNames()).isEmpty();
}
}

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2014-2018 the original author or authors.
* Copyright 2014-2016 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.
@@ -85,18 +85,6 @@ public class MapSessionTests {
assertThat(this.session.isExpired(now)).isTrue();
}
@Test // gh-1120
public void getAttributeNamesAndRemove() {
this.session.setAttribute("attribute1", "value1");
this.session.setAttribute("attribute2", "value2");
for (String attributeName : this.session.getAttributeNames()) {
this.session.removeAttribute(attributeName);
}
assertThat(this.session.getAttributeNames()).isEmpty();
}
static class CustomSession implements ExpiringSession {
public long getCreationTime() {

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2014-2018 the original author or authors.
* Copyright 2014-2016 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.
@@ -59,7 +59,6 @@ import static org.mockito.BDDMockito.given;
import static org.mockito.Matchers.any;
import static org.mockito.Matchers.anyLong;
import static org.mockito.Matchers.anyString;
import static org.mockito.Matchers.eq;
import static org.mockito.Mockito.atLeastOnce;
import static org.mockito.Mockito.never;
import static org.mockito.Mockito.reset;
@@ -530,104 +529,6 @@ public class RedisOperationsSessionRepositoryTests {
verify(this.defaultSerializer).deserialize(body);
}
@Test
public void onMessageDeletedSessionFound() throws Exception {
String deletedId = "deleted-id";
given(this.redisOperations.boundHashOps(getKey(deletedId)))
.willReturn(this.boundHashOperations);
Map map = map(RedisOperationsSessionRepository.MAX_INACTIVE_ATTR, 0,
RedisOperationsSessionRepository.LAST_ACCESSED_ATTR,
System.currentTimeMillis() - TimeUnit.MINUTES.toMillis(5));
given(this.boundHashOperations.entries()).willReturn(map);
String channel = "__keyevent@0__:del";
String body = "spring:session:sessions:expires:" + deletedId;
DefaultMessage message = new DefaultMessage(channel.getBytes("UTF-8"), body.getBytes("UTF-8"));
this.redisRepository.setApplicationEventPublisher(this.publisher);
this.redisRepository.onMessage(message, "".getBytes("UTF-8"));
verify(this.redisOperations).boundHashOps(eq(getKey(deletedId)));
verify(this.boundHashOperations).entries();
verify(this.publisher).publishEvent(this.event.capture());
assertThat(this.event.getValue().getSessionId()).isEqualTo(deletedId);
verifyZeroInteractions(this.defaultSerializer);
verifyZeroInteractions(this.publisher);
verifyZeroInteractions(this.redisOperations);
verifyZeroInteractions(this.boundHashOperations);
}
@Test
public void onMessageDeletedSessionNotFound() throws Exception {
String deletedId = "deleted-id";
given(this.redisOperations.boundHashOps(getKey(deletedId)))
.willReturn(this.boundHashOperations);
given(this.boundHashOperations.entries()).willReturn(map());
String channel = "__keyevent@0__:del";
String body = "spring:session:sessions:expires:" + deletedId;
DefaultMessage message = new DefaultMessage(channel.getBytes("UTF-8"), body.getBytes("UTF-8"));
this.redisRepository.setApplicationEventPublisher(this.publisher);
this.redisRepository.onMessage(message, "".getBytes("UTF-8"));
verify(this.redisOperations).boundHashOps(eq(getKey(deletedId)));
verify(this.boundHashOperations).entries();
verifyZeroInteractions(this.defaultSerializer);
verifyZeroInteractions(this.publisher);
verifyZeroInteractions(this.redisOperations);
verifyZeroInteractions(this.boundHashOperations);
}
@Test
public void onMessageExpiredSessionFound() throws Exception {
String expiredId = "expired-id";
given(this.redisOperations.boundHashOps(getKey(expiredId)))
.willReturn(this.boundHashOperations);
Map map = map(RedisOperationsSessionRepository.MAX_INACTIVE_ATTR, 1,
RedisOperationsSessionRepository.LAST_ACCESSED_ATTR,
System.currentTimeMillis() - TimeUnit.MINUTES.toMillis(5));
given(this.boundHashOperations.entries()).willReturn(map);
String channel = "__keyevent@0__:expired";
String body = "spring:session:sessions:expires:" + expiredId;
DefaultMessage message = new DefaultMessage(channel.getBytes("UTF-8"), body.getBytes("UTF-8"));
this.redisRepository.setApplicationEventPublisher(this.publisher);
this.redisRepository.onMessage(message, "".getBytes("UTF-8"));
verify(this.redisOperations).boundHashOps(eq(getKey(expiredId)));
verify(this.boundHashOperations).entries();
verify(this.publisher).publishEvent(this.event.capture());
assertThat(this.event.getValue().getSessionId()).isEqualTo(expiredId);
verifyZeroInteractions(this.defaultSerializer);
verifyZeroInteractions(this.publisher);
verifyZeroInteractions(this.redisOperations);
verifyZeroInteractions(this.boundHashOperations);
}
@Test
public void onMessageExpiredSessionNotFound() throws Exception {
String expiredId = "expired-id";
given(this.redisOperations.boundHashOps(getKey(expiredId)))
.willReturn(this.boundHashOperations);
given(this.boundHashOperations.entries()).willReturn(map());
String channel = "__keyevent@0__:expired";
String body = "spring:session:sessions:expires:" + expiredId;
DefaultMessage message = new DefaultMessage(channel.getBytes("UTF-8"), body.getBytes("UTF-8"));
this.redisRepository.setApplicationEventPublisher(this.publisher);
this.redisRepository.onMessage(message, "".getBytes("UTF-8"));
verify(this.redisOperations).boundHashOps(eq(getKey(expiredId)));
verify(this.boundHashOperations).entries();
verifyZeroInteractions(this.defaultSerializer);
verifyZeroInteractions(this.publisher);
verifyZeroInteractions(this.redisOperations);
verifyZeroInteractions(this.boundHashOperations);
}
@Test
public void resolvePrincipalIndex() {
PrincipalNameResolver resolver = RedisOperationsSessionRepository.PRINCIPAL_NAME_RESOLVER;
@@ -805,19 +706,6 @@ public class RedisOperationsSessionRepositoryTests {
this.redisRepository.setRedisFlushMode(null);
}
@Test // gh-1120
public void getAttributeNamesAndRemove() {
RedisSession session = this.redisRepository.new RedisSession(this.cached);
session.setAttribute("attribute1", "value1");
session.setAttribute("attribute2", "value2");
for (String attributeName : session.getAttributeNames()) {
session.removeAttribute(attributeName);
}
assertThat(session.getAttributeNames()).isEmpty();
}
private String getKey(String id) {
return "spring:session:sessions:" + id;
}

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2014-2018 the original author or authors.
* Copyright 2014-2016 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.
@@ -22,7 +22,6 @@ import java.util.Map;
import java.util.concurrent.TimeUnit;
import com.hazelcast.core.IMap;
import com.hazelcast.map.EntryProcessor;
import com.hazelcast.query.impl.predicates.EqualPredicate;
import org.junit.Before;
import org.junit.Rule;
@@ -41,7 +40,6 @@ import org.springframework.session.hazelcast.HazelcastSessionRepository.Hazelcas
import static org.assertj.core.api.Assertions.assertThat;
import static org.mockito.BDDMockito.given;
import static org.mockito.Matchers.any;
import static org.mockito.Matchers.eq;
import static org.mockito.Matchers.isA;
import static org.mockito.Mockito.times;
@@ -106,8 +104,8 @@ public class HazelcastSessionRepositoryTests {
verifyZeroInteractions(this.sessions);
this.repository.save(session);
verify(this.sessions, times(1)).set(eq(session.getId()),
eq(session.getDelegate()), isA(Long.class), eq(TimeUnit.SECONDS));
verify(this.sessions, times(1)).put(eq(session.getId()), eq(session.getDelegate()),
isA(Long.class), eq(TimeUnit.SECONDS));
}
@Test
@@ -115,8 +113,8 @@ public class HazelcastSessionRepositoryTests {
this.repository.setHazelcastFlushMode(HazelcastFlushMode.IMMEDIATE);
HazelcastSession session = this.repository.createSession();
verify(this.sessions, times(1)).set(eq(session.getId()),
eq(session.getDelegate()), isA(Long.class), eq(TimeUnit.SECONDS));
verify(this.sessions, times(1)).put(eq(session.getId()), eq(session.getDelegate()),
isA(Long.class), eq(TimeUnit.SECONDS));
}
@Test
@@ -126,8 +124,8 @@ public class HazelcastSessionRepositoryTests {
verifyZeroInteractions(this.sessions);
this.repository.save(session);
verify(this.sessions, times(1)).set(eq(session.getId()),
eq(session.getDelegate()), isA(Long.class), eq(TimeUnit.SECONDS));
verify(this.sessions, times(1)).put(eq(session.getId()), eq(session.getDelegate()),
isA(Long.class), eq(TimeUnit.SECONDS));
}
@Test
@@ -136,10 +134,8 @@ public class HazelcastSessionRepositoryTests {
HazelcastSession session = this.repository.createSession();
session.setAttribute("testName", "testValue");
verify(this.sessions, times(1)).set(eq(session.getId()),
eq(session.getDelegate()), isA(Long.class), eq(TimeUnit.SECONDS));
verify(this.sessions, times(1)).executeOnKey(eq(session.getId()),
any(EntryProcessor.class));
verify(this.sessions, times(2)).put(eq(session.getId()), eq(session.getDelegate()),
isA(Long.class), eq(TimeUnit.SECONDS));
this.repository.save(session);
verifyZeroInteractions(this.sessions);
@@ -152,8 +148,8 @@ public class HazelcastSessionRepositoryTests {
verifyZeroInteractions(this.sessions);
this.repository.save(session);
verify(this.sessions, times(1)).set(eq(session.getId()),
eq(session.getDelegate()), isA(Long.class), eq(TimeUnit.SECONDS));
verify(this.sessions, times(1)).put(eq(session.getId()), eq(session.getDelegate()),
isA(Long.class), eq(TimeUnit.SECONDS));
}
@Test
@@ -162,10 +158,8 @@ public class HazelcastSessionRepositoryTests {
HazelcastSession session = this.repository.createSession();
session.removeAttribute("testName");
verify(this.sessions, times(1)).set(eq(session.getId()),
eq(session.getDelegate()), isA(Long.class), eq(TimeUnit.SECONDS));
verify(this.sessions, times(1)).executeOnKey(eq(session.getId()),
any(EntryProcessor.class));
verify(this.sessions, times(2)).put(eq(session.getId()), eq(session.getDelegate()),
isA(Long.class), eq(TimeUnit.SECONDS));
this.repository.save(session);
verifyZeroInteractions(this.sessions);
@@ -178,8 +172,8 @@ public class HazelcastSessionRepositoryTests {
verifyZeroInteractions(this.sessions);
this.repository.save(session);
verify(this.sessions, times(1)).set(eq(session.getId()),
eq(session.getDelegate()), isA(Long.class), eq(TimeUnit.SECONDS));
verify(this.sessions, times(1)).put(eq(session.getId()), eq(session.getDelegate()),
isA(Long.class), eq(TimeUnit.SECONDS));
}
@Test
@@ -188,10 +182,8 @@ public class HazelcastSessionRepositoryTests {
HazelcastSession session = this.repository.createSession();
session.setLastAccessedTime(System.currentTimeMillis());
verify(this.sessions, times(1)).set(eq(session.getId()),
eq(session.getDelegate()), isA(Long.class), eq(TimeUnit.SECONDS));
verify(this.sessions, times(1)).executeOnKey(eq(session.getId()),
any(EntryProcessor.class));
verify(this.sessions, times(2)).put(eq(session.getId()), eq(session.getDelegate()),
isA(Long.class), eq(TimeUnit.SECONDS));
this.repository.save(session);
verifyZeroInteractions(this.sessions);
@@ -204,8 +196,8 @@ public class HazelcastSessionRepositoryTests {
verifyZeroInteractions(this.sessions);
this.repository.save(session);
verify(this.sessions, times(1)).set(eq(session.getId()),
eq(session.getDelegate()), isA(Long.class), eq(TimeUnit.SECONDS));
verify(this.sessions, times(1)).put(eq(session.getId()), eq(session.getDelegate()),
isA(Long.class), eq(TimeUnit.SECONDS));
}
@Test
@@ -214,10 +206,8 @@ public class HazelcastSessionRepositoryTests {
HazelcastSession session = this.repository.createSession();
session.setMaxInactiveIntervalInSeconds(1);
verify(this.sessions, times(1)).set(eq(session.getId()),
eq(session.getDelegate()), isA(Long.class), eq(TimeUnit.SECONDS));
verify(this.sessions, times(1)).executeOnKey(eq(session.getId()),
any(EntryProcessor.class));
verify(this.sessions, times(2)).put(eq(session.getId()), eq(session.getDelegate()),
isA(Long.class), eq(TimeUnit.SECONDS));
this.repository.save(session);
verifyZeroInteractions(this.sessions);
@@ -227,8 +217,8 @@ public class HazelcastSessionRepositoryTests {
public void saveUnchangedFlushModeOnSave() {
HazelcastSession session = this.repository.createSession();
this.repository.save(session);
verify(this.sessions, times(1)).set(eq(session.getId()),
eq(session.getDelegate()), isA(Long.class), eq(TimeUnit.SECONDS));
verify(this.sessions, times(1)).put(eq(session.getId()), eq(session.getDelegate()),
isA(Long.class), eq(TimeUnit.SECONDS));
this.repository.save(session);
verifyZeroInteractions(this.sessions);
@@ -239,8 +229,8 @@ public class HazelcastSessionRepositoryTests {
this.repository.setHazelcastFlushMode(HazelcastFlushMode.IMMEDIATE);
HazelcastSession session = this.repository.createSession();
verify(this.sessions, times(1)).set(eq(session.getId()),
eq(session.getDelegate()), isA(Long.class), eq(TimeUnit.SECONDS));
verify(this.sessions, times(1)).put(eq(session.getId()), eq(session.getDelegate()),
isA(Long.class), eq(TimeUnit.SECONDS));
this.repository.save(session);
verifyZeroInteractions(this.sessions);
@@ -259,8 +249,8 @@ public class HazelcastSessionRepositoryTests {
@Test
public void getSessionExpired() {
MapSession expired = new MapSession();
expired.setLastAccessedTime(System.currentTimeMillis()
- (MapSession.DEFAULT_MAX_INACTIVE_INTERVAL_SECONDS * 1000 + 1000));
expired.setLastAccessedTime(System.currentTimeMillis() -
(MapSession.DEFAULT_MAX_INACTIVE_INTERVAL_SECONDS * 1000 + 1000));
given(this.sessions.get(eq(expired.getId()))).willReturn(expired);
HazelcastSession session = this.repository.getSession(expired.getId());
@@ -296,8 +286,8 @@ public class HazelcastSessionRepositoryTests {
public void findByIndexNameAndIndexValueUnknownIndexName() {
String indexValue = "testIndexValue";
Map<String, HazelcastSession> sessions = this.repository
.findByIndexNameAndIndexValue("testIndexName", indexValue);
Map<String, HazelcastSession> sessions = this.repository.findByIndexNameAndIndexValue(
"testIndexName", indexValue);
assertThat(sessions).isEmpty();
verifyZeroInteractions(this.sessions);
@@ -307,10 +297,8 @@ public class HazelcastSessionRepositoryTests {
public void findByIndexNameAndIndexValuePrincipalIndexNameNotFound() {
String principal = "username";
Map<String, HazelcastSession> sessions = this.repository
.findByIndexNameAndIndexValue(
FindByIndexNameSessionRepository.PRINCIPAL_NAME_INDEX_NAME,
principal);
Map<String, HazelcastSession> sessions = this.repository.findByIndexNameAndIndexValue(
FindByIndexNameSessionRepository.PRINCIPAL_NAME_INDEX_NAME, principal);
assertThat(sessions).isEmpty();
verify(this.sessions, times(1)).values(isA(EqualPredicate.class));
@@ -330,26 +318,11 @@ public class HazelcastSessionRepositoryTests {
saved.add(saved2);
given(this.sessions.values(isA(EqualPredicate.class))).willReturn(saved);
Map<String, HazelcastSession> sessions = this.repository
.findByIndexNameAndIndexValue(
FindByIndexNameSessionRepository.PRINCIPAL_NAME_INDEX_NAME,
principal);
Map<String, HazelcastSession> sessions = this.repository.findByIndexNameAndIndexValue(
FindByIndexNameSessionRepository.PRINCIPAL_NAME_INDEX_NAME, principal);
assertThat(sessions).hasSize(2);
verify(this.sessions, times(1)).values(isA(EqualPredicate.class));
}
@Test // gh-1120
public void getAttributeNamesAndRemove() {
HazelcastSession session = this.repository.createSession();
session.setAttribute("attribute1", "value1");
session.setAttribute("attribute2", "value2");
for (String attributeName : session.getAttributeNames()) {
session.removeAttribute(attributeName);
}
assertThat(session.getAttributeNames()).isEmpty();
}
}

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2014-2018 the original author or authors.
* Copyright 2014-2016 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.
@@ -412,7 +412,7 @@ public class JdbcOperationsSessionRepositoryTests {
@Test
public void getSessionExpired() {
JdbcOperationsSessionRepository.JdbcSession expired = this.repository.new JdbcSession();
MapSession expired = new MapSession();
expired.setLastAccessedTime(System.currentTimeMillis() -
(MapSession.DEFAULT_MAX_INACTIVE_INTERVAL_SECONDS * 1000 + 1000));
given(this.jdbcOperations.query(isA(String.class),
@@ -432,8 +432,7 @@ public class JdbcOperationsSessionRepositoryTests {
@Test
public void getSessionFound() {
JdbcOperationsSessionRepository.JdbcSession saved = this.repository.new JdbcSession(
new MapSession());
MapSession saved = new MapSession();
saved.setAttribute("savedName", "savedValue");
given(this.jdbcOperations.query(isA(String.class),
isA(PreparedStatementSetter.class), isA(ResultSetExtractor.class)))
@@ -494,12 +493,11 @@ public class JdbcOperationsSessionRepositoryTests {
String principal = "username";
Authentication authentication = new UsernamePasswordAuthenticationToken(principal,
"notused", AuthorityUtils.createAuthorityList("ROLE_USER"));
List<JdbcOperationsSessionRepository.JdbcSession> saved =
new ArrayList<JdbcOperationsSessionRepository.JdbcSession>(2);
JdbcOperationsSessionRepository.JdbcSession saved1 = this.repository.new JdbcSession();
List<MapSession> saved = new ArrayList<MapSession>(2);
MapSession saved1 = new MapSession();
saved1.setAttribute(SPRING_SECURITY_CONTEXT, authentication);
saved.add(saved1);
JdbcOperationsSessionRepository.JdbcSession saved2 = this.repository.new JdbcSession();
MapSession saved2 = new MapSession();
saved2.setAttribute(SPRING_SECURITY_CONTEXT, authentication);
saved.add(saved2);
given(this.jdbcOperations.query(isA(String.class),
@@ -525,19 +523,6 @@ public class JdbcOperationsSessionRepositoryTests {
verify(this.jdbcOperations, times(1)).update(startsWith("DELETE"), anyLong());
}
@Test // gh-1120
public void getAttributeNamesAndRemove() {
JdbcOperationsSessionRepository.JdbcSession session = this.repository.createSession();
session.setAttribute("attribute1", "value1");
session.setAttribute("attribute2", "value2");
for (String attributeName : session.getAttributeNames()) {
session.removeAttribute(attributeName);
}
assertThat(session.getAttributeNames()).isEmpty();
}
private void assertPropagationRequiresNew() {
ArgumentCaptor<TransactionDefinition> argument =
ArgumentCaptor.forClass(TransactionDefinition.class);

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2014-2018 the original author or authors.
* Copyright 2014-2016 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.
@@ -710,19 +710,19 @@ public class CookieHttpSessionStrategyTests {
}
private String createSessionCookieValue(long size) {
StringBuilder sb = new StringBuilder();
StringBuffer buffer = new StringBuffer();
for (long i = 0; i < size; i++) {
String hex = Long.toHexString(i);
sb.append(hex);
sb.append(" ");
sb.append(i);
buffer.append(hex);
buffer.append(" ");
buffer.append(i);
if (i < size - 1) {
sb.append(" ");
buffer.append(" ");
}
}
return sb.toString();
return buffer.toString();
}
@SuppressWarnings("deprecation")

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2014-2018 the original author or authors.
* Copyright 2014-2016 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.
@@ -568,27 +568,6 @@ public class SessionRepositoryFilterTests {
});
}
// gh-951
@Test
public void doFilterChangeSessionIdCopyAttributes() throws Exception {
// change the session id
doFilter(new DoInFilter() {
@Override
public void doFilter(HttpServletRequest wrappedRequest) {
HttpSession session = wrappedRequest.getSession();
session.setMaxInactiveInterval(300);
String originalSessionId = session.getId();
int originalMaxInactiveInterval = session.getMaxInactiveInterval();
String changeSessionId = ReflectionTestUtils.invokeMethod(wrappedRequest,
"changeSessionId");
assertThat(changeSessionId).isNotEqualTo(originalSessionId);
assertThat(session.getMaxInactiveInterval())
.isEqualTo(originalMaxInactiveInterval);
}
});
}
// gh-142, gh-153
@Test
public void doFilterIsRequestedValidSessionFalseInvalidId() throws Exception {
@@ -1175,22 +1154,6 @@ public class SessionRepositoryFilterTests {
});
}
@Test // gh-1243
public void doFilterInclude() throws Exception {
doFilter(new DoInFilter() {
@Override
public void doFilter(HttpServletRequest wrappedRequest,
HttpServletResponse wrappedResponse)
throws IOException, ServletException {
String id = wrappedRequest.getSession().getId();
wrappedRequest.getRequestDispatcher("/").include(wrappedRequest,
wrappedResponse);
assertThat(SessionRepositoryFilterTests.this.sessionRepository
.getSession(id)).isNotNull();
}
});
}
// --- MultiHttpSessionStrategyAdapter
@Test

View File

@@ -14,7 +14,16 @@
<ports>0</ports>
</outbound-ports>
<join>
<multicast enabled="false"/>
<multicast enabled="false">
</multicast>
<tcp-ip enabled="true">
<interface>127.0.0.1</interface>
<member-list>
<member>127.0.0.1</member>
</member-list>
</tcp-ip>
<aws enabled="false">
</aws>
</join>
</network>

View File

@@ -14,7 +14,16 @@
<ports>0</ports>
</outbound-ports>
<join>
<multicast enabled="false"/>
<multicast enabled="false">
</multicast>
<tcp-ip enabled="true">
<interface>127.0.0.1</interface>
<member-list>
<member>127.0.0.1</member>
</member-list>
</tcp-ip>
<aws enabled="false">
</aws>
</join>
</network>