Compare commits
117 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
144d3d4103 | ||
|
|
fc9bb33414 | ||
|
|
ec4a0cb9ff | ||
|
|
e5274b6eae | ||
|
|
3db2e13d7e | ||
|
|
774e6df063 | ||
|
|
6911bd359b | ||
|
|
ddae03c79e | ||
|
|
bba095f276 | ||
|
|
61937a9251 | ||
|
|
3885b7e7ff | ||
|
|
bea569c3c8 | ||
|
|
7f1434cc4c | ||
|
|
cd8f87e0a9 | ||
|
|
95f41a7024 | ||
|
|
d245cc1a36 | ||
|
|
695f2f1509 | ||
|
|
3940a22d5e | ||
|
|
eb4ce12915 | ||
|
|
46bac131d0 | ||
|
|
9675278729 | ||
|
|
f0c216d9d5 | ||
|
|
cb6f7fdfa6 | ||
|
|
b50a4e247e | ||
|
|
6b3d78ac09 | ||
|
|
c0bd38c46f | ||
|
|
2262600b21 | ||
|
|
0c11a4297a | ||
|
|
b778d97dc7 | ||
|
|
d0887fe40d | ||
|
|
1a94d742b1 | ||
|
|
c433b01ee5 | ||
|
|
a3195f1f4b | ||
|
|
467ecaaeff | ||
|
|
4a18242d95 | ||
|
|
e44cd45668 | ||
|
|
7f0de8126e | ||
|
|
d75b03f594 | ||
|
|
ca0fea3a54 | ||
|
|
92af786e6b | ||
|
|
d271a4ad1d | ||
|
|
04c1908378 | ||
|
|
f0e187fbd7 | ||
|
|
2d3001a24e | ||
|
|
f2d1badd60 | ||
|
|
6a6d60d8f8 | ||
|
|
b2cb3f6a3a | ||
|
|
d7ae5785eb | ||
|
|
96eb40439c | ||
|
|
8ed0999ad3 | ||
|
|
b2d2335d73 | ||
|
|
f597c5a824 | ||
|
|
212eca306c | ||
|
|
a64e6d1a9c | ||
|
|
598715f219 | ||
|
|
4d90fcc7a8 | ||
|
|
4f57c6c6c1 | ||
|
|
c210a4a3cf | ||
|
|
a1380d722b | ||
|
|
c029922bf4 | ||
|
|
6b55f3f7d2 | ||
|
|
6668e41b0a | ||
|
|
304e32eef5 | ||
|
|
288c622012 | ||
|
|
3827ae1e72 | ||
|
|
9067f8235d | ||
|
|
19928e6b7f | ||
|
|
1df1a76069 | ||
|
|
17e397212d | ||
|
|
39503a21a7 | ||
|
|
ebbc10b2b4 | ||
|
|
9a51cb9ca7 | ||
|
|
5e0ee5077a | ||
|
|
526c6ee012 | ||
|
|
ff4045acbd | ||
|
|
2d359986d3 | ||
|
|
6424910c83 | ||
|
|
49e3a1c7cd | ||
|
|
3b8258f233 | ||
|
|
a2b30eb54b | ||
|
|
4c2581d432 | ||
|
|
25aec99357 | ||
|
|
1c9dfa6638 | ||
|
|
466e2cf102 | ||
|
|
eb0f292c20 | ||
|
|
43fda301e2 | ||
|
|
4a06b38c5f | ||
|
|
6a78101db5 | ||
|
|
b5ea6c752d | ||
|
|
46633274d5 | ||
|
|
038287b2cc | ||
|
|
32c053271c | ||
|
|
802e0e714b | ||
|
|
6263f6e927 | ||
|
|
5671037c39 | ||
|
|
3d44467275 | ||
|
|
94221c70a9 | ||
|
|
dd3a571494 | ||
|
|
e4fe53abf8 | ||
|
|
7b65d7930b | ||
|
|
0f8326516b | ||
|
|
2aec28289e | ||
|
|
af7a5a208f | ||
|
|
e9924d27a1 | ||
|
|
f0820c8038 | ||
|
|
7d680ff3ef | ||
|
|
6d9885455b | ||
|
|
06104c348d | ||
|
|
090742350c | ||
|
|
a290b11019 | ||
|
|
eabad84ba8 | ||
|
|
4e33b7740c | ||
|
|
f8967c4c13 | ||
|
|
245e634bea | ||
|
|
7a2914323f | ||
|
|
6e04d903ae | ||
|
|
d8c3a4dd61 |
4
.gitignore
vendored
4
.gitignore
vendored
@@ -10,5 +10,5 @@ target
|
||||
out
|
||||
.springBeans
|
||||
*.rdb
|
||||
!eclispe/.checkstyle
|
||||
.checkstyle
|
||||
.checkstyle
|
||||
!etc/eclipse/.checkstyle
|
||||
|
||||
@@ -40,5 +40,5 @@ appropriate to the circumstances. Maintainers are obligated to maintain confiden
|
||||
with regard to the reporter of an incident.
|
||||
|
||||
This Code of Conduct is adapted from the
|
||||
http://contributor-covenant.org[Contributor Covenant], version 1.3.0, available at
|
||||
http://contributor-covenant.org/version/1/3/0/[contributor-covenant.org/version/1/3/0/]
|
||||
https://contributor-covenant.org[Contributor Covenant], version 1.3.0, available at
|
||||
https://contributor-covenant.org/version/1/3/0/[contributor-covenant.org/version/1/3/0/]
|
||||
|
||||
@@ -10,8 +10,8 @@ By participating, you are expected to uphold this code. Please report unaccepta
|
||||
== Using GitHub issues
|
||||
|
||||
We use GitHub issues to track bugs and enhancements. If you have a general usage question
|
||||
please ask on http://stackoverflow.com[Stack Overflow]. The Spring Session team and the
|
||||
broader community monitor the http://stackoverflow.com/tags/spring-session[`spring-session`]
|
||||
please ask on https://stackoverflow.com[Stack Overflow]. The Spring Session team and the
|
||||
broader community monitor the https://stackoverflow.com/tags/spring-session[`spring-session`]
|
||||
tag.
|
||||
|
||||
If you are reporting a bug, please help to speed up problem diagnosis by providing as much
|
||||
|
||||
@@ -19,8 +19,8 @@ By participating, you are expected to uphold this code. Please report unaccepta
|
||||
|
||||
= Spring Session Project Site
|
||||
|
||||
You can find the documentation, issue management, support, samples, and guides for using Spring Session at http://projects.spring.io/spring-session/
|
||||
You can find the documentation, issue management, support, samples, and guides for using Spring Session at https://projects.spring.io/spring-session/
|
||||
|
||||
= License
|
||||
|
||||
Spring Session is Open Source software released under the http://www.apache.org/licenses/LICENSE-2.0.html[Apache 2.0 license].
|
||||
Spring Session is Open Source software released under the https://www.apache.org/licenses/LICENSE-2.0.html[Apache 2.0 license].
|
||||
|
||||
20
build.gradle
20
build.gradle
@@ -3,6 +3,7 @@ buildscript {
|
||||
maven { url "https://repo.spring.io/plugins-release" }
|
||||
}
|
||||
dependencies {
|
||||
classpath 'io.spring.gradle:dependency-management-plugin:0.6.1.RELEASE'
|
||||
classpath("com.bmuschko:gradle-tomcat-plugin:2.2.5")
|
||||
classpath("org.springframework.build.gradle:propdeps-plugin:0.0.7")
|
||||
classpath("io.spring.gradle:spring-io-plugin:0.0.4.RELEASE")
|
||||
@@ -13,16 +14,17 @@ buildscript {
|
||||
}
|
||||
|
||||
plugins {
|
||||
id "org.sonarqube" version "1.2"
|
||||
id "org.sonarqube" version "2.1"
|
||||
}
|
||||
|
||||
group = 'org.springframework.session'
|
||||
|
||||
ext.springBootVersion = '1.3.2.RELEASE'
|
||||
ext.springBootVersion = '1.4.7.RELEASE'
|
||||
ext.IDE_GRADLE = "$rootDir/gradle/ide.gradle"
|
||||
ext.JAVA_GRADLE = "$rootDir/gradle/java.gradle"
|
||||
ext.SPRING3_GRADLE = "$rootDir/gradle/spring3.gradle"
|
||||
ext.MAVEN_GRADLE = "$rootDir/gradle/publish-maven.gradle"
|
||||
ext.BOM_GRADLE = "$rootDir/gradle/bom.gradle"
|
||||
ext.SAMPLE_GRADLE = "$rootDir/gradle/sample.gradle"
|
||||
ext.TOMCAT_GRADLE = "$rootDir/gradle/tomcat.gradle"
|
||||
ext.TOMCAT_6_GRADLE = "$rootDir/gradle/tomcat6.gradle"
|
||||
@@ -49,12 +51,14 @@ sonarqube {
|
||||
}
|
||||
}
|
||||
|
||||
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')
|
||||
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')
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -16,6 +16,10 @@ liveReload {
|
||||
docRoot asciidoctor.sourceDir.canonicalPath
|
||||
}
|
||||
|
||||
repositories {
|
||||
maven { url 'http://dist.gemstone.com/maven/release' }
|
||||
}
|
||||
|
||||
asciidoctorj {
|
||||
|
||||
}
|
||||
@@ -27,18 +31,20 @@ dependencies {
|
||||
project(':spring-session-data-mongo'),
|
||||
"org.springframework.data:spring-data-gemfire:$springDataGemFireVersion",
|
||||
"org.springframework.data:spring-data-redis:$springDataRedisVersion",
|
||||
"org.springframework.data:spring-data-gemfire:$springDataGemFireVersion",
|
||||
"org.springframework:spring-webmvc:${springVersion}",
|
||||
"org.springframework:spring-websocket:${springVersion}",
|
||||
"org.springframework:spring-messaging:${springVersion}",
|
||||
"org.springframework:spring-jdbc:${springVersion}",
|
||||
"org.springframework.security:spring-security-config:${springSecurityVersion}",
|
||||
"org.springframework.security:spring-security-web:${springSecurityVersion}",
|
||||
"org.springframework.security:spring-security-test:${springSecurityVersion}",
|
||||
'junit:junit:4.11',
|
||||
'org.mockito:mockito-core:1.9.5',
|
||||
"junit:junit:$junitVersion",
|
||||
"org.mockito:mockito-core:$mockitoVersion",
|
||||
"org.springframework:spring-test:$springVersion",
|
||||
"org.assertj:assertj-core:$assertjVersion",
|
||||
"com.hazelcast:hazelcast:$hazelcastVersion",
|
||||
"redis.clients:jedis:2.4.1",
|
||||
"biz.paluch.redis:lettuce:$lettuceVersion",
|
||||
"javax.servlet:javax.servlet-api:$servletApiVersion"
|
||||
}
|
||||
|
||||
@@ -53,6 +59,7 @@ asciidoctor {
|
||||
'download-url' : "https://github.com/spring-projects/spring-session/archive/${ghTag}.zip",
|
||||
'spring-session-version' : version,
|
||||
'spring-version' : springVersion,
|
||||
'lettuce-version' : lettuceVersion,
|
||||
'hazelcast-version' : hazelcastVersion,
|
||||
'docs-itest-dir' : rootProject.projectDir.path + '/docs/src/integration-test/java/',
|
||||
'docs-test-dir' : rootProject.projectDir.path + '/docs/src/test/java/',
|
||||
|
||||
@@ -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-redis</artifactId>
|
||||
<artifactId>spring-boot-starter-data-redis</artifactId>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
----
|
||||
@@ -93,7 +93,7 @@ spring.redis.password=secret
|
||||
spring.redis.port=6379
|
||||
----
|
||||
|
||||
For more information, refer to http://docs.spring.io/spring-boot/docs/current/reference/htmlsingle/#boot-features-connecting-to-redis[Connecting to Redis] portion of the Spring Boot documentation.
|
||||
For more information, refer to https://docs.spring.io/spring-boot/docs/current/reference/htmlsingle/#boot-features-connecting-to-redis[Connecting to Redis] portion of the Spring Boot documentation.
|
||||
|
||||
[[boot-servlet-configuration]]
|
||||
== Servlet Container Initialization
|
||||
@@ -117,7 +117,7 @@ You can run the sample by obtaining the {download-url}[source code] and invoking
|
||||
|
||||
[NOTE]
|
||||
====
|
||||
For the sample to work, you must http://redis.io/download[install Redis 2.8+] on localhost and run it with the default port (6379).
|
||||
For the sample to work, you must https://redis.io/download[install Redis 2.8+] on localhost and run it with the default port (6379).
|
||||
Alternatively, you can update the `JedisConnectionFactory` to point to a Redis server.
|
||||
====
|
||||
|
||||
@@ -153,7 +153,7 @@ If you like, you can easily remove the session using redis-cli. For example, on
|
||||
|
||||
$ redis-cli keys '*' | xargs redis-cli del
|
||||
|
||||
TIP: The Redis documentation has instructions for http://redis.io/topics/quickstart[installing redis-cli].
|
||||
TIP: The Redis documentation has instructions for https://redis.io/topics/quickstart[installing redis-cli].
|
||||
|
||||
Alternatively, you can also delete the explicit key. Enter the following into your terminal ensuring to replace `7e8383a4-082c-4ffe-a4bc-c40fd3363c5e` with the value of your SESSION cookie:
|
||||
|
||||
|
||||
@@ -27,7 +27,7 @@ This allows sharing a session across domains and applications.
|
||||
If the regular expression does not match, no domain is set and the existing domain will be used.
|
||||
If the regular expression matches, the first https://docs.oracle.com/javase/tutorial/essential/regex/groups.html[grouping] will be used as the domain.
|
||||
This means that a request to https://child.example.com will set the domain to example.com.
|
||||
However, a request to http://localhost:8080/ or http://192.168.1.100:8080/ will leave the cookie unset and thus still work in development without any changes necessary for production.
|
||||
However, a request to http://localhost:8080/ or https://192.168.1.100:8080/ will leave the cookie unset and thus still work in development without any changes necessary for production.
|
||||
|
||||
[WARNING]
|
||||
====
|
||||
@@ -78,8 +78,8 @@ You can run the sample by obtaining the {download-url}[source code] and invoking
|
||||
|
||||
[NOTE]
|
||||
====
|
||||
For the sample to work, you must http://redis.io/download[install Redis 2.8+] on localhost and run it with the default port (6379).
|
||||
Alternatively, you can update the `JedisConnectionFactory` to point to a Redis server.
|
||||
For the sample to work, you must https://redis.io/download[install Redis 2.8+] on localhost and run it with the default port (6379).
|
||||
Alternatively, you can update the `LettuceConnectionFactory` to point to a Redis server.
|
||||
====
|
||||
|
||||
----
|
||||
|
||||
@@ -6,8 +6,6 @@ This guide describes how to use Spring Session to find sessions by username.
|
||||
|
||||
NOTE: The completed guide can be found in the <<findbyusername-sample, findbyusername application>>.
|
||||
|
||||
NOTE: This feature will likely be refactored in the next release to account for https://github.com/spring-projects/spring-session/issues/301[#301]
|
||||
|
||||
|
||||
[[findbyusername-assumptions]]
|
||||
== Assumptions
|
||||
@@ -33,10 +31,10 @@ Consider the following scenario:
|
||||
Wouldn't it be nice if we could allow the user to invalidate the session at the library from any device they authenticate with?
|
||||
This sample demonstrates how this is possible.
|
||||
|
||||
[[findbyprincipalnamesessionrepository]]
|
||||
[[findbyindexnamesessionrepository]]
|
||||
== FindByIndexNameSessionRepository
|
||||
|
||||
In order to look up a user by their username, you must first choose a `SessionRepository` that implements <<index.doc#api-findbyprincipalnamesessionrepository,FindByIndexNameSessionRepository>>.
|
||||
In order to look up a user by their username, you must first choose a `SessionRepository` that implements link:../#api-findbyindexnamesessionrepository[FindByIndexNameSessionRepository].
|
||||
Our sample application assumes that the Redis support is already setup, so we are ready to go.
|
||||
|
||||
== Mapping the username
|
||||
@@ -110,7 +108,7 @@ You can run the sample by obtaining the {download-url}[source code] and invoking
|
||||
|
||||
[NOTE]
|
||||
====
|
||||
For the sample to work, you must http://redis.io/download[install Redis 2.8+] on localhost and run it with the default port (6379).
|
||||
For the sample to work, you must https://redis.io/download[install Redis 2.8+] on localhost and run it with the default port (6379).
|
||||
Alternatively, you can update the `JedisConnectionFactory` to point to a Redis server.
|
||||
====
|
||||
|
||||
|
||||
@@ -70,7 +70,7 @@ spring:
|
||||
port: 6397
|
||||
----
|
||||
|
||||
For more information, refer to http://docs.spring.io/spring-boot/docs/current/reference/htmlsingle/#boot-features-connecting-to-redis[Connecting to Redis] portion of the Spring Boot documentation.
|
||||
For more information, refer to https://docs.spring.io/spring-boot/docs/current/reference/htmlsingle/#boot-features-connecting-to-redis[Connecting to Redis] portion of the Spring Boot documentation.
|
||||
|
||||
[[grails3-sample]]
|
||||
== Grails 3 Sample Application
|
||||
@@ -84,7 +84,7 @@ You can run the sample by obtaining the {download-url}[source code] and invoking
|
||||
|
||||
[NOTE]
|
||||
====
|
||||
For the sample to work, you must http://redis.io/download[install Redis 2.8+] on localhost and run it with the default port (6379).
|
||||
For the sample to work, you must https://redis.io/download[install Redis 2.8+] on localhost and run it with the default port (6379).
|
||||
Alternatively, you can update the `JedisConnectionFactory` to point to a Redis server.
|
||||
====
|
||||
|
||||
@@ -120,10 +120,13 @@ If you like, you can easily remove the session using redis-cli. For example, on
|
||||
|
||||
$ redis-cli keys '*' | xargs redis-cli del
|
||||
|
||||
TIP: The Redis documentation has instructions for http://redis.io/topics/quickstart[installing redis-cli].
|
||||
TIP: The Redis documentation has instructions for https://redis.io/topics/quickstart[installing redis-cli].
|
||||
|
||||
Alternatively, you can also delete the explicit key. Enter the following into your terminal ensuring to replace `7e8383a4-082c-4ffe-a4bc-c40fd3363c5e` with the value of your SESSION cookie:
|
||||
|
||||
$ 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
|
||||
|
||||
@@ -64,6 +64,8 @@ Ensure you have the following in your pom.xml:
|
||||
----
|
||||
endif::[]
|
||||
|
||||
// tag::config[]
|
||||
|
||||
[[security-spring-configuration]]
|
||||
== Spring Configuration
|
||||
|
||||
@@ -79,17 +81,19 @@ include::{docs-test-dir}docs/http/HazelcastHttpSessionConfig.java[tags=config]
|
||||
<1> The `@EnableHazelcastHttpSession` annotation creates a Spring Bean with the name of `springSessionRepositoryFilter` that implements Filter.
|
||||
The filter is what is in charge of replacing the `HttpSession` implementation to be backed by Spring Session.
|
||||
In this instance Spring Session is backed by Hazelcast.
|
||||
<2> We create a `HazelcastInstance` that connects Spring Session to Hazelcast.
|
||||
<2> In order to support retrieval of sessions by principal name index, appropriate `ValueExtractor` needs to be registered.
|
||||
Spring Session provides `PrincipalNameExtractor` for this purpose.
|
||||
<3> We create a `HazelcastInstance` that connects Spring Session to Hazelcast.
|
||||
By default, an embedded instance of Hazelcast is started and connected to by the application.
|
||||
For more information on configuring Hazelcast, refer to the http://docs.hazelcast.org/docs/latest/manual/html-single/index.html#hazelcast-configuration[reference documentation].
|
||||
For more information on configuring Hazelcast, refer to the https://docs.hazelcast.org/docs/latest/manual/html-single/index.html#hazelcast-configuration[reference documentation].
|
||||
|
||||
== Servlet Container Initialization
|
||||
|
||||
Our <<security-spring-configuration,Spring Configuration>> created a Spring Bean named `springSessionRepositoryFilter` that implements `Filter`.
|
||||
The `springSessionRepositoryFilter` bean is responsible for replacing the `HttpSession` with a custom implementation that is backed by Spring Session.
|
||||
|
||||
In order for our `Filter` to do its magic, Spring needs to load our `Config` class.
|
||||
Since our application is already loading Spring configuration using our `SecurityInitializer` class, we can simply add our Config class to it.
|
||||
In order for our `Filter` to do its magic, Spring needs to load our `SessionConfig` class.
|
||||
Since our application is already loading Spring configuration using our `SecurityInitializer` class, we can simply add our `SessionConfig` class to it.
|
||||
|
||||
.src/main/java/sample/SecurityInitializer.java
|
||||
[source,java]
|
||||
@@ -113,7 +117,7 @@ NOTE: The name of our class (Initializer) does not matter. What is important is
|
||||
|
||||
By extending `AbstractHttpSessionApplicationInitializer` we ensure that the Spring Bean by the name `springSessionRepositoryFilter` is registered with our Servlet Container for every request before Spring Security's `springSecurityFilterChain`.
|
||||
|
||||
|
||||
// end::config[]
|
||||
|
||||
[[hazelcast-spring-security-sample]]
|
||||
== Hazelcast Spring Security Sample Application
|
||||
@@ -126,7 +130,7 @@ You can run the sample by obtaining the {download-url}[source code] and invoking
|
||||
====
|
||||
Hazelcast will run in embedded mode with your application by default, but if you want to connect
|
||||
to a stand alone instance instead, you can configure it by following the instructions in the
|
||||
http://docs.hazelcast.org/docs/latest/manual/html-single/index.html#hazelcast-configuration[reference documentation].
|
||||
https://docs.hazelcast.org/docs/latest/manual/html-single/index.html#hazelcast-configuration[reference documentation].
|
||||
====
|
||||
|
||||
----
|
||||
@@ -157,9 +161,9 @@ Go ahead and view the cookies (click for help with https://developer.chrome.com/
|
||||
|
||||
=== Interact with the data store
|
||||
|
||||
If you like, you can remove the session using http://docs.hazelcast.org/docs/latest/manual/html-single/index.html#hazelcast-java-client[a Java client],
|
||||
http://docs.hazelcast.org/docs/latest/manual/html-single/index.html#other-client-implementations[one of the other clients], or the
|
||||
http://docs.hazelcast.org/docs/latest/manual/html-single/index.html#management-center[management center].
|
||||
If you like, you can remove the session using https://docs.hazelcast.org/docs/latest/manual/html-single/index.html#hazelcast-java-client[a Java client],
|
||||
https://docs.hazelcast.org/docs/latest/manual/html-single/index.html#other-client-implementations[one of the other clients], or the
|
||||
https://docs.hazelcast.org/docs/latest/manual/html-single/index.html#management-center[management center].
|
||||
|
||||
==== Using the console
|
||||
|
||||
@@ -168,7 +172,7 @@ For example, using the management center console after connecting to your Hazelc
|
||||
default> ns spring:session:sessions
|
||||
spring:session:sessions> m.clear
|
||||
|
||||
TIP: The Hazelcast documentation has instructions for http://docs.hazelcast.org/docs/latest/manual/html-single/index.html#executing-console-commands[the console].
|
||||
TIP: The Hazelcast documentation has instructions for https://docs.hazelcast.org/docs/latest/manual/html-single/index.html#executing-console-commands[the console].
|
||||
|
||||
Alternatively, you can also delete the explicit key. Enter the following into the console ensuring to replace `7e8383a4-082c-4ffe-a4bc-c40fd3363c5e` with the value of your SESSION cookie:
|
||||
|
||||
@@ -179,7 +183,7 @@ Now visit the application at http://localhost:8080/ and observe that we are no l
|
||||
==== Using the REST API
|
||||
|
||||
As described in the other clients section of the documentation, there is a
|
||||
http://docs.hazelcast.org/docs/latest/manual/html-single/index.html#rest-client[REST API]
|
||||
https://docs.hazelcast.org/docs/latest/manual/html-single/index.html#rest-client[REST API]
|
||||
provided by the Hazelcast node(s).
|
||||
|
||||
For example, you could delete an individual key as follows (replacing `7e8383a4-082c-4ffe-a4bc-c40fd3363c5e` with the value of your SESSION cookie):
|
||||
@@ -188,4 +192,4 @@ For example, you could delete an individual key as follows (replacing `7e8383a4-
|
||||
|
||||
TIP: The port number of the Hazelcast node will be printed to the console on startup. Replace `xxxxx` above with the port number.
|
||||
|
||||
Now observe that you are no longer authenticated with this session.
|
||||
Now observe that you are no longer authenticated with this session.
|
||||
|
||||
@@ -89,16 +89,17 @@ We start with the _Spring Boot_ application for configuring and bootstrapping a
|
||||
include::{samples-dir}httpsession-gemfire-boot/src/main/java/sample/server/GemFireServer.java[tags=class]
|
||||
----
|
||||
|
||||
<1> The `@EnableGemFireHttpSession` annotation is used on the GemFire Server mainly to define the corresponding
|
||||
<1> The `@EnableGemFireHttpSession` annotation is used on the GemFire Server to mainly define the corresponding
|
||||
Region (e.g. `ClusteredSpringSessions`, the default) in which Session state information will be stored
|
||||
and managed by GemFire. As well, we have specified an arbitrary expiration attribute (i.e. `maxInactiveIntervalInSeconds`)
|
||||
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` allowing us to configure certain aspects of the GemFire Server using
|
||||
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 setup a Cache Server instance running in the GemFire Server to listen for connections from cache clients.
|
||||
The Cache Server `Socket` will be used to connect our GemFire client cache, _Spring Boot_ web application to the server.
|
||||
<2> Next, we define a few `Properties` that allow us to configure certain aspects of the GemFire Server using
|
||||
https://gemfire.docs.pivotal.io/docs-gemfire/latest/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,
|
||||
_Spring Boot_ web application to the server.
|
||||
|
||||
The sample also makes use of a `PropertySourcesPlaceholderConfigurer` bean in order to externalize the sample application
|
||||
configuration to affect GemFire and application configuration/behavior from the command-line (e.g. such as GemFire's
|
||||
@@ -106,9 +107,9 @@ configuration to affect GemFire and application configuration/behavior from the
|
||||
|
||||
=== Spring Boot-based GemFire cache client Web application
|
||||
|
||||
Now, we create the _Spring Boot_ web application (a GemFire cache client), exposing our Web service
|
||||
using Spring MVC along with _Spring Session_ backed by GemFire, connected to our _Spring Boot_-based GemFire Server,
|
||||
in order to manage Session state in a cluster/replicated-enabled fashion.
|
||||
Now, we create our _Spring Boot_ Web application exposing our Web service with Spring MVC, running as a
|
||||
GemFire cache client connected to our _Spring Boot_-based GemFire Server, using Spring Session backed by GemFire
|
||||
to manage Session state in a clustered, replicated fashion.
|
||||
|
||||
[source,java]
|
||||
----
|
||||
@@ -116,28 +117,29 @@ include::{samples-dir}httpsession-gemfire-boot/src/main/java/sample/client/Appli
|
||||
----
|
||||
|
||||
<1> Here, again, we use the `@EnableGemFireHttpSession` annotation to not only configure the GemFire cache client,
|
||||
but also to override the (HTTP) Web application container's `HttpSession` and replace it with a Session implementation
|
||||
backed by _Spring Session_ in conjunction with GemFire. Also notice, we did not define any Session expiration timeout
|
||||
with the `maxInactiveIntervalInSeconds` attribute this time. That is because the Session expiration is managed
|
||||
by GemFire, which will appropriately notify the cache client when the Session times out. Again, we have just resorted
|
||||
to using the default Region, `ClusteredSpringSessions`. Of course, we can change the Region name, but we must do so
|
||||
on both the client and the server. That is a GemFire requirement, not a _Spring Session Data GemFire_ requirement.
|
||||
<2> Similary to the server configuration, we set a few basic GemFire System `Properties` on the client.
|
||||
<3> Although, this time, an instance of `ClientCache` is created with the `ClientCacheFactoryBean` from _Spring Data GemFire_.
|
||||
<4> However, in order to connect to the GemFire Server we must define a GemFire `Pool` bean containing pre-populated
|
||||
connections to the server. Whenever a client Region entry operation corresponding to a Session update occurs,
|
||||
but to also override the (HTTP) Web application container's `HttpSession` and replace it with a Session implementation
|
||||
backed by _Spring Session_ and GemFire. Also notice, we did not define any Session expiration timeout with the
|
||||
`maxInactiveIntervalInSeconds` attribute this time. That is because the Session expiration is managed by GemFire,
|
||||
on the server, which will appropriately notify the cache client when the Session times out. Again, we have just
|
||||
resorted to using the default named Region, `ClusteredSpringSessions`. Of course, we can change the Region name,
|
||||
but we must do so on both the client and the server. That is a GemFire requirement, not a
|
||||
_Spring Session Data GemFire_ requirement.
|
||||
<2> Similarly to the server configuration, we set a few basic GemFire System `Properties` on the client.
|
||||
<3> Although, this time, an instance of `ClientCache` is created with the `ClientCacheFactoryBean`
|
||||
from _Spring Data GemFire_.
|
||||
<4> However, in order to connect to the GemFire Server we must define a GemFire `Pool` bean containing a
|
||||
pool of connections to the server. Whenever a client Region entry operation corresponding to a Session update occurs,
|
||||
the client-side Region will use an existing, pooled connection to route the operation to the server.
|
||||
<5> The following _Spring_ `BeanPostProcessor` (along with some utility methods) are only needed for testing purposes
|
||||
and is not required by any production code. Specifically, the `BeanPostProcessor` along with the code referenced in *6*
|
||||
and are not required by any production code. Specifically, the `BeanPostProcessor` along with the code referenced in *6*
|
||||
is useful in integration test cases where the client and server processes are forked by the test framework. It is pretty
|
||||
easy to figure out that a race condition is imminent without proper coordination between the client and the server,
|
||||
therefore, the BPP and `ClientMembershipListener` help sync the interaction between the client and the server
|
||||
on startup during automated testing.
|
||||
<6> See <5> above.
|
||||
<7> Navigates the Web application to the home page (`index.html`), which uses **Thymeleaf** templates for server-side
|
||||
<6> Navigates the Web application to the home page (`index.html`), which uses **Thymeleaf** templates for server-side
|
||||
pages.
|
||||
<8> Heartbeat web service endpoint (useful for manual testing purposes).
|
||||
<9> Web service endpoint for adding a Session attributes defined by the user using the Web application UI. In addition,
|
||||
<7> Heartbeat Web service endpoint (useful for manual testing purposes).
|
||||
<8> Web service endpoint allowing the user to add a Session attribute using the Web application UI. In addition,
|
||||
the webapp stores an additional Session attribute (`requestCount`) to keep track of how many HTTP requests the user
|
||||
has sent during the current "session".
|
||||
|
||||
@@ -147,23 +149,25 @@ TIP: In typical GemFire deployments, where the cluster includes potentially hund
|
||||
(servers), it is more common for clients to connect to one or more GemFire Locators running in the cluster. A Locator
|
||||
passes meta-data to clients about the servers available, their load and which servers have the client's data of interest,
|
||||
which is particularly important in direct, single-hop data access and latency-sensitive operations. See more details
|
||||
about the http://gemfire.docs.pivotal.io/docs-gemfire/latest/topologies_and_comm/cs_configuration/chapter_overview.html[Client/Server Topology in GemFire's User Guide].
|
||||
about the https://gemfire.docs.pivotal.io/docs-gemfire/latest/topologies_and_comm/cs_configuration/chapter_overview.html[Client/Server Topology in GemFire's User Guide].
|
||||
|
||||
NOTE: For more information on configuring _Spring Data GemFire_, refer to the http://docs.spring.io/spring-data-gemfire/docs/current/reference/html/[reference guide].
|
||||
NOTE: For more information on configuring _Spring Data GemFire_, refer to the https://docs.spring.io/spring-data-gemfire/docs/current/reference/html/[reference guide].
|
||||
|
||||
The `@EnableGemFireHttpSession` annotation enables a developer to configure certain aspects of both _Spring Session_
|
||||
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://gemfire.docs.pivotal.io/docs-gemfire/latest/javadocs/japi/com/gemstone/gemfire/cache/client/ClientRegionShortcut.html[ClientRegionShortcut]
|
||||
* `clientRegionShort` - specifies GemFire's https://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]
|
||||
(default is `PROXY`). This attribute is only used when configuring client Region.
|
||||
* `serverRegionShort` - specifies GemFire's http://gemfire.docs.pivotal.io/docs-gemfire/latest/developing/management_all_region_types/chapter_overview.html[data management policy]
|
||||
using a GemFire http://data-docs-samples.cfapps.io/docs-gemfire/latest/javadocs/japi/com/gemstone/gemfire/cache/RegionShortcut.html[RegionShortcut]
|
||||
* `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`.
|
||||
* `serverRegionShort` - specifies GemFire's https://gemfire.docs.pivotal.io/docs-gemfire/latest/developing/management_all_region_types/chapter_overview.html[data management policy]
|
||||
using a GemFire https://data-docs-samples.cfapps.io/docs-gemfire/latest/javadocs/japi/com/gemstone/gemfire/cache/RegionShortcut.html[RegionShortcut]
|
||||
(default is `PARTITION`). This attribute is only used when configuring server Regions, or when a p2p topology is employed.
|
||||
|
||||
NOTE: It is important to note that the GemFire client Region name must match a server Region by the same name if
|
||||
NOTE: It is important to remember that the GemFire client Region name must match a server Region by the same name if
|
||||
the client Region is a `PROXY` or `CACHING_PROXY`. Client and server Region names are not required to match if
|
||||
the client Region used to store Spring Sessions is `LOCAL`. However, keep in mind that your session state will not
|
||||
be propagated to the server and you lose all the benefits of using GemFire to store and manage distributed, replicated
|
||||
@@ -226,7 +230,10 @@ 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/latest/getting_started/installation/install_intro.html[Installing Pivotal GemFire].
|
||||
see https://gemfire.docs.pivotal.io/docs-gemfire/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`.
|
||||
|
||||
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:
|
||||
@@ -255,7 +262,7 @@ NEXT_STEP_NAME : END
|
||||
gfsh>remove --region=/ClusteredSpringSessions --key="70002719-3c54-4c20-82c3-e7faa6b718f3"
|
||||
....
|
||||
|
||||
NOTE: The _GemFire User Guide_ has more detailed instructions on using http://gemfire.docs.pivotal.io/docs-gemfire/latest/tools_modules/gfsh/chapter_overview.html[gfsh].
|
||||
NOTE: The _GemFire User Guide_ has more detailed instructions on using https://gemfire.docs.pivotal.io/docs-gemfire/latest/tools_modules/gfsh/chapter_overview.html[gfsh].
|
||||
|
||||
Now visit the application at http://localhost:8080/ again and observe that the attribute we added is no longer displayed.
|
||||
|
||||
|
||||
@@ -83,35 +83,35 @@ Add the following Spring Configuration:
|
||||
include::{samples-dir}httpsession-gemfire-clientserver-xml/src/main/webapp/WEB-INF/spring/session-client.xml[tags=beans]
|
||||
----
|
||||
|
||||
<1> First, a `Properties` bean is created to reference GemFire configuration common to both the client and server,
|
||||
stored in the `META-INF/spring/application.properties` file.
|
||||
<2> The `application.properties` are used along with the `PropertySourcesPlaceholderConfigurer` bean to replace
|
||||
placeholders in the Spring XML configuration meta-data with property values.
|
||||
<3> Spring annotation configuration support is enabled with `<context:annotation-config/>` element so that any
|
||||
<1> Spring annotation configuration support is enabled with `<context:annotation-config/>` element so that any
|
||||
Spring beans declared in the XML config that are annotated with either Spring or Standard Java annotations supported
|
||||
by Spring will be configured appropriately.
|
||||
<4> `GemFireHttpSessionConfiguration` is registered to enable Spring Session functionality.
|
||||
<5> Then, a Spring `BeanPostProcessor` is registered to determine whether a GemFire Server at the designated host/port
|
||||
is running, blocking client startup until the server is available.
|
||||
<6> Next, we include a `Properties` bean to configure certain aspects of the GemFire client cache using
|
||||
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 sample application-specific System property, defaulting
|
||||
<2> The `META-INF/spring/application.properties` file are used along with the `PropertySourcesPlaceholderConfigurer`
|
||||
bean to replace placeholders in the Spring XML configuration meta-data with the approrpriate property values.
|
||||
<3> Then the `GemFireCacheSeverReadyBeanPostProcessor`is registered to determine whether a GemFire Server
|
||||
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
|
||||
https://gemfire.docs.pivotal.io/docs-gemfire/latest/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.
|
||||
<7> Finally, we create the GemFire client cache and configure a Pool of client connections to talk to the GemFire Server
|
||||
in our Client/Server topology. In our configuration, we use sensible settings for timeouts, number of connections
|
||||
and so on. Also, our `Pool` has been configured to connect directly to a server.
|
||||
<5> Then we create a instance of a GemFire `ClientCache` initialized with our `gemfireProperties`.
|
||||
<6> We configure a Pool of client connections to talk to the GemFire Server in our Client/Server topology.
|
||||
In our configuration, we use sensible settings for timeouts, number of connections and so on. Also, our `Pool`
|
||||
has been configured to connect directly to a server.
|
||||
<7> Finally, the `GemFireHttpSessionConfiguration` is registered to enable Spring Session functionality.
|
||||
|
||||
TIP: In typical GemFire deployments, where the cluster includes potentially hundreds of GemFire data nodes (servers),
|
||||
it is more common for clients to connect to one or more GemFire Locators running in the cluster. A Locator passes meta-data
|
||||
to clients about the servers available, load and which servers have the client's data of interest, which is particularly
|
||||
important for single-hop, direct data access. See more details about the http://gemfire.docs.pivotal.io/docs-gemfire/latest/topologies_and_comm/cs_configuration/chapter_overview.html[Client/Server Topology in GemFire's User Guide].
|
||||
important for single-hop, direct data access. See more details about the https://gemfire.docs.pivotal.io/docs-gemfire/latest/topologies_and_comm/cs_configuration/chapter_overview.html[Client/Server Topology in GemFire's User Guide].
|
||||
|
||||
NOTE: For more information on configuring _Spring Data GemFire_, refer to the http://docs.spring.io/spring-data-gemfire/docs/current/reference/html/[reference guide].
|
||||
NOTE: For more information on configuring _Spring Data GemFire_, refer to the https://docs.spring.io/spring-data-gemfire/docs/current/reference/html/[reference guide].
|
||||
|
||||
=== Server Configuration
|
||||
|
||||
Now, we have only covered one side of the equation. We also need a GemFire Server for our client to talk to and pass
|
||||
session state information up to the server to manage.
|
||||
We have only covered one side of the equation. We also need a GemFire Server for our client to talk to and send
|
||||
session state information to the server to manage.
|
||||
|
||||
In this sample, we will use the following GemFire Server Java Configuration:
|
||||
|
||||
@@ -124,15 +124,16 @@ include::{samples-dir}httpsession-gemfire-clientserver-xml/src/main/resources/ME
|
||||
Spring beans declared in the XML config that are annotated with either Spring or Standard Java annotations supported
|
||||
by Spring will be configured appropriately.
|
||||
<2> A `PropertySourcesPlaceholderConfigurer` is registered to replace placeholders in our Spring XML configuration
|
||||
meta-data with property values from `META-INF/spring/application.properties`.
|
||||
<3> We enable the same Spring Session functionality that we used on the client by registering an instance of `GemFireHttpSessionConfiguration`,
|
||||
except that we set the session expiration timeout to **30 seconds**. We will explain later what this means.
|
||||
<4> Next, we configure the GemFire Server using GemFire System properties very much like our P2P samples.
|
||||
meta-data with property values in the `META-INF/spring/application.properties` file.
|
||||
<3> Next, we configure the GemFire Server using GemFire System Properties very much like our P2P samples.
|
||||
With the `mcast-port` set to 0 and no `locators` property specified, our server will be standalone. We also allow a
|
||||
JMX client (e.g. _Gfsh_) to connect to our server with the use of the GemFire-specific JMX System properties.
|
||||
<5> Then, we create an instance of the GemFire peer cache using our GemFire System properties.
|
||||
<6> And finally, we also setup a GemFire `CacheServer` instance running on *localhost*, listening on port **11235**,
|
||||
to accept our client connection.
|
||||
<4> Then we create an instance of a GemFire peer `Cache` initialized with our GemFire System Properties.
|
||||
<5> We also setup a GemFire `CacheServer` instance running on *localhost*, listening to port **11235**,
|
||||
ready to accept our client connection.
|
||||
<6> Finally, we enable the same Spring Session functionality we used on the client by registering an instance of
|
||||
`GemFireHttpSessionConfiguration`, except that we set the session expiration timeout to **30 seconds**.
|
||||
We will explain later what this means.
|
||||
|
||||
The GemFire Server configuration gets bootstrapped with the following:
|
||||
|
||||
@@ -166,7 +167,7 @@ include::{samples-dir}httpsession-gemfire-clientserver-xml/src/main/webapp/WEB-I
|
||||
include::{samples-dir}httpsession-gemfire-clientserver-xml/src/main/webapp/WEB-INF/web.xml[tags=listeners]
|
||||
----
|
||||
|
||||
The http://docs.spring.io/spring/docs/current/spring-framework-reference/htmlsingle/#context-create[ContextLoaderListener]
|
||||
The https://docs.spring.io/spring/docs/current/spring-framework-reference/htmlsingle/#context-create[ContextLoaderListener]
|
||||
reads the `contextConfigLocation` context parameter value and picks up our _session-client.xml_ configuration file.
|
||||
|
||||
Finally, we need to ensure that our Servlet Container (i.e. Tomcat) uses our `springSessionRepositoryFilter`
|
||||
@@ -180,7 +181,7 @@ The following snippet performs this last step for us:
|
||||
include::{samples-dir}httpsession-gemfire-clientserver-xml/src/main/webapp/WEB-INF/web.xml[tags=springSessionRepositoryFilter]
|
||||
----
|
||||
|
||||
The http://docs.spring.io/spring-framework/docs/current/javadoc-api/org/springframework/web/filter/DelegatingFilterProxy.html[DelegatingFilterProxy]
|
||||
The https://docs.spring.io/spring-framework/docs/current/javadoc-api/org/springframework/web/filter/DelegatingFilterProxy.html[DelegatingFilterProxy]
|
||||
will look up a bean by the name of `springSessionRepositoryFilter` and cast it to a `Filter`. For every request that `DelegatingFilterProxy`
|
||||
is invoked, the `springSessionRepositoryFilter` will be invoked.
|
||||
// end::config[]
|
||||
@@ -233,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 http://gemfire.docs.pivotal.io/docs-gemfire/latest/getting_started/installation/install_intro.html[Installing Pivotal GemFire].
|
||||
see https://gemfire.docs.pivotal.io/gemfire/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:
|
||||
@@ -262,7 +263,7 @@ NEXT_STEP_NAME : END
|
||||
gfsh>remove --region=/ClusteredSpringSessions --key="70002719-3c54-4c20-82c3-e7faa6b718f3"
|
||||
....
|
||||
|
||||
NOTE: The _GemFire User Guide_ has more detailed instructions on using http://gemfire.docs.pivotal.io/docs-gemfire/latest/tools_modules/gfsh/chapter_overview.html[gfsh].
|
||||
NOTE: The _GemFire User Guide_ has more detailed instructions on using https://gemfire.docs.pivotal.io/docs-gemfire/latest/tools_modules/gfsh/chapter_overview.html[gfsh].
|
||||
|
||||
Now visit the application at http://localhost:8080/ again and observe that the attribute we added is no longer displayed.
|
||||
|
||||
|
||||
@@ -84,49 +84,47 @@ include::{samples-dir}httpsession-gemfire-clientserver/src/main/java/sample/Clie
|
||||
----
|
||||
|
||||
<1> The `@EnableGemFireHttpSession` annotation creates a Spring bean named `springSessionRepositoryFilter` that
|
||||
implements `Filter`. The filter is what replaces the `HttpSession` with an implementation backed by Spring Session.
|
||||
In this instance, Spring Session is backed by GemFire.
|
||||
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/reference/topics/gemfire_properties.html[GemFire's System properties].
|
||||
<3> Then, we configure a `Pool` of client connections to talk to the GemFire Server in our Client/Server topology. In our
|
||||
using https://gemfire.docs.pivotal.io/docs-gemfire/latest/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://gemfire.docs.pivotal.io/docs-gemfire/latest/javadocs/japi/com/gemstone/gemfire/cache/client/PoolFactory.html[PoolFactory API].
|
||||
<4> After configuring a `Pool`, we create an instance of the GemFire client cache using the GemFire `Properties`
|
||||
and `Pool` to communicate with the server and perform cache data access operations.
|
||||
<5> Finally, we include a Spring `BeanPostProcessor` to block the client until our GemFire Server is up and running,
|
||||
https://data-docs-samples.cfapps.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.
|
||||
|
||||
The `gemfireCacheServerReadyBeanPostProcessor` is necessary in order to coordinate the client and server in
|
||||
an automated fashion during testing, but unnecessary in situations where the GemFire cluster is already presently
|
||||
running, such as in production. This `BeanPostProcessor` implements 2 approaches to ensure our server has adequate
|
||||
time to startup.
|
||||
running, such as in production.
|
||||
|
||||
The first approach uses a timed wait, checking at periodic intervals to determine whether a client `Socket` connection
|
||||
can be made to the server's `CacheServer` endpoint.
|
||||
|
||||
The second approach uses a GemFire http://gemfire.docs.pivotal.io/docs-gemfire/latest/javadocs/japi/com/gemstone/gemfire/management/membership/ClientMembershipListener.html[ClientMembershipListener]
|
||||
The `BeanPostProcessor` uses a GemFire https://data-docs-samples.cfapps.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. Either one of these approaches are sufficient
|
||||
by themselves, but both are demonstrated here to illustrate how this might work and to give you ideas, or other options
|
||||
in practice.
|
||||
`postProcessAfterInitialization` callback to block the client.
|
||||
|
||||
TIP: In typical GemFire deployments, where the cluster includes potentially hundreds of GemFire data nodes (servers),
|
||||
it is more common for clients to connect to one or more GemFire Locators running in the cluster. A Locator passes meta-data
|
||||
to clients about the servers available, load and which servers have the client's data of interest, which is particularly
|
||||
important for single-hop, direct data access. See more details about the http://gemfire.docs.pivotal.io/docs-gemfire/latest/topologies_and_comm/cs_configuration/chapter_overview.html[Client/Server Topology in GemFire's User Guide].
|
||||
important for single-hop, direct data access. See more details about the https://gemfire.docs.pivotal.io/docs-gemfire/latest/topologies_and_comm/cs_configuration/chapter_overview.html[Client/Server Topology in GemFire's User Guide].
|
||||
|
||||
NOTE: For more information on configuring _Spring Data GemFire_, refer to the http://docs.spring.io/spring-data-gemfire/docs/current/reference/html/[reference guide].
|
||||
NOTE: For more information on configuring _Spring Data GemFire_, refer to the https://docs.spring.io/spring-data-gemfire/docs/current/reference/html/[reference guide].
|
||||
|
||||
The `@EnableGemFireHttpSession` annotation enables a developer to configure certain aspects of both Spring Session
|
||||
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 http://gemfire.docs.pivotal.io/docs-gemfire/latest/developing/management_all_region_types/chapter_overview.html[data management policies]
|
||||
with a GemFire http://gemfire.docs.pivotal.io/docs-gemfire/latest/javadocs/japi/com/gemstone/gemfire/cache/client/ClientRegionShortcut.html[ClientRegionShortcut]
|
||||
(default is `PROXY`).
|
||||
* `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 https://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]
|
||||
(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`.
|
||||
* `serverRegionShort` - specifies GemFire's https://gemfire.docs.pivotal.io/docs-gemfire/latest/developing/management_all_region_types/chapter_overview.html[data management policy]
|
||||
using a GemFire https://data-docs-samples.cfapps.io/docs-gemfire/latest/javadocs/japi/com/gemstone/gemfire/cache/RegionShortcut.html[RegionShortcut]
|
||||
(default is `PARTITION`). This attribute is only used when configuring server Regions, or when a p2p topology is employed.
|
||||
|
||||
NOTE: It is important to note that the GemFire client Region name must match a server Region by the same name if
|
||||
the client Region is a `PROXY` or `CACHING_PROXY`. Names are not required to match if the client Region used to
|
||||
@@ -134,13 +132,13 @@ store Spring Sessions is `LOCAL`, however, keep in mind that your session state
|
||||
and you lose all benefits of using GemFire to store and manage distributed, replicated session state information
|
||||
in a cluster.
|
||||
|
||||
NOTE: `serverRegionShort` is ignored in a client/server cache configuration and only applies when a peer-to-peer (P2P) topology,
|
||||
and more specifically, a GemFire peer cache is used.
|
||||
NOTE: `serverRegionShort` is ignored in a client/server cache configuration and only applies when
|
||||
a peer-to-peer (P2P) topology, and more specifically, a GemFire peer cache is used.
|
||||
|
||||
=== Server Configuration
|
||||
|
||||
Now, we have only covered one side of the equation. We also need a GemFire Server for our client to talk to and pass
|
||||
session state up to the server to manage.
|
||||
We have only covered one side of the equation. We also need a GemFire Server for our client to talk to and send
|
||||
session state to the server to manage.
|
||||
|
||||
In this sample, we will use the following GemFire Server Java Configuration:
|
||||
|
||||
@@ -149,15 +147,15 @@ In this sample, we will use the following GemFire Server Java Configuration:
|
||||
include::{samples-dir}httpsession-gemfire-clientserver/src/main/java/sample/ServerConfig.java[tags=class]
|
||||
----
|
||||
|
||||
<1> On the server, we also configure Spring Session using the `@EnableGemFireHttpSession` annotation. For one, this
|
||||
ensures that the Region names on both the client and server match (in this sample, we use the default "_ClusteredSpringSessions_").
|
||||
<1> On the server, we also configure Spring Session using the `@EnableGemFireHttpSession` annotation. This ensures
|
||||
the Region names on both the client and server match (in this sample, we use the default "_ClusteredSpringSessions_").
|
||||
We have also set the session timeout to **30 seconds**. Later, we will see how this timeout is used.
|
||||
<2> Next, we configure the GemFire Server using GemFire System properties very much like our P2P samples.
|
||||
<2> Next, we configure the GemFire Server using GemFire System Properties very much like our P2P samples.
|
||||
With the `mcast-port` set to 0 and no `locators` property specified, our server will be standalone. We also allow a
|
||||
JMX client (e.g. _Gfsh_) to connect to our server with the use of the GemFire-specific JMX System properties.
|
||||
<3> Then, we create an instance of the GemFire peer cache using our GemFire System properties.
|
||||
<4> We also setup a GemFire `CacheServer` instance running on **localhost**, listening on port **12480**,
|
||||
to accept our client connection.
|
||||
<3> Then, we create an instance of a GemFire peer `Cache` initialized with our GemFire System Properties.
|
||||
<4> We also setup a GemFire `CacheServer` instance running on **localhost**, listening to port **12480**,
|
||||
ready to accept our client connection.
|
||||
<5> Finally, we declare a `main` method as an entry point for launching and running our GemFire Server
|
||||
from the command-line.
|
||||
|
||||
@@ -235,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 http://gemfire.docs.pivotal.io/docs-gemfire/latest/getting_started/installation/install_intro.html[Installing Pivotal GemFire].
|
||||
see https://gemfire.docs.pivotal.io/gemfire/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:
|
||||
@@ -264,7 +262,7 @@ NEXT_STEP_NAME : END
|
||||
gfsh>remove --region=/ClusteredSpringSessions --key="70002719-3c54-4c20-82c3-e7faa6b718f3"
|
||||
....
|
||||
|
||||
NOTE: The _GemFire User Guide_ has more detailed instructions on using http://gemfire.docs.pivotal.io/docs-gemfire/latest/tools_modules/gfsh/chapter_overview.html[gfsh].
|
||||
NOTE: The _GemFire User Guide_ has more detailed instructions on using https://gemfire.docs.pivotal.io/docs-gemfire/latest/tools_modules/gfsh/chapter_overview.html[gfsh].
|
||||
|
||||
Now visit the application at http://localhost:8080/ again and observe that the attribute we added is no longer displayed.
|
||||
|
||||
|
||||
@@ -100,7 +100,7 @@ Spring Session sample application.
|
||||
TIP: Additionally, we have configured this data node (server) as a GemFire Manager as well using GemFire-specific
|
||||
JMX System properties that enable JMX client (e.g. _Gfsh_) to connect to this running data node.
|
||||
|
||||
NOTE: For more information on configuring _Spring Data GemFire_, refer to the http://docs.spring.io/spring-data-gemfire/docs/current/reference/html/[reference guide].
|
||||
NOTE: For more information on configuring _Spring Data GemFire_, refer to the https://docs.spring.io/spring-data-gemfire/docs/current/reference/html/[reference guide].
|
||||
|
||||
== XML Servlet Container Initialization
|
||||
|
||||
@@ -118,7 +118,7 @@ include::{samples-dir}httpsession-gemfire-p2p-xml/src/main/webapp/WEB-INF/web.xm
|
||||
include::{samples-dir}httpsession-gemfire-p2p-xml/src/main/webapp/WEB-INF/web.xml[tags=listeners]
|
||||
----
|
||||
|
||||
The http://docs.spring.io/spring/docs/current/spring-framework-reference/htmlsingle/#context-create[ContextLoaderListener]
|
||||
The https://docs.spring.io/spring/docs/current/spring-framework-reference/htmlsingle/#context-create[ContextLoaderListener]
|
||||
reads the `contextConfigLocation` context parameter value and picks up our _session.xml_ configuration file.
|
||||
|
||||
Finally, we need to ensure that our Servlet Container (i.e. Tomcat) uses our `springSessionRepositoryFilter`
|
||||
@@ -132,7 +132,7 @@ The following snippet performs this last step for us:
|
||||
include::{samples-dir}httpsession-gemfire-p2p-xml/src/main/webapp/WEB-INF/web.xml[tags=springSessionRepositoryFilter]
|
||||
----
|
||||
|
||||
The http://docs.spring.io/spring-framework/docs/current/javadoc-api/org/springframework/web/filter/DelegatingFilterProxy.html[DelegatingFilterProxy]
|
||||
The https://docs.spring.io/spring-framework/docs/current/javadoc-api/org/springframework/web/filter/DelegatingFilterProxy.html[DelegatingFilterProxy]
|
||||
will look up a bean by the name of `springSessionRepositoryFilter` and cast it to a `Filter`. For every request that `DelegatingFilterProxy`
|
||||
is invoked, the `springSessionRepositoryFilter` will be invoked.
|
||||
// end::config[]
|
||||
@@ -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/docs-gemfire/latest/getting_started/installation/install_intro.html[Installing Pivotal GemFire].
|
||||
see https://gemfire.docs.pivotal.io/gemfire/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:
|
||||
@@ -205,6 +205,6 @@ NEXT_STEP_NAME : END
|
||||
gfsh>remove --region=/ClusteredSpringSessions --key="70002719-3c54-4c20-82c3-e7faa6b718f3"
|
||||
....
|
||||
|
||||
NOTE: The _GemFire User Guide_ has more detailed instructions on using http://gemfire.docs.pivotal.io/docs-gemfire/latest/tools_modules/gfsh/chapter_overview.html[gfsh].
|
||||
NOTE: The _GemFire User Guide_ has more detailed instructions on using https://gemfire.docs.pivotal.io/docs-gemfire/latest/tools_modules/gfsh/chapter_overview.html[gfsh].
|
||||
|
||||
Now visit the application at http://localhost:8080/ and observe that the attribute we added is no longer displayed.
|
||||
|
||||
@@ -96,15 +96,15 @@ Spring Session sample application.
|
||||
TIP: Additionally, we have configured this data node (server) as a GemFire Manager as well using GemFire-specific
|
||||
JMX System properties that enable JMX client (e.g. _Gfsh_) to connect to this running data node.
|
||||
|
||||
NOTE: For more information on configuring _Spring Data GemFire_, refer to the http://docs.spring.io/spring-data-gemfire/docs/current/reference/html/[reference guide].
|
||||
NOTE: For more information on configuring _Spring Data GemFire_, refer to the https://docs.spring.io/spring-data-gemfire/docs/current/reference/html/[reference guide].
|
||||
|
||||
The `@EnableGemFireHttpSession` annotation enables a developer to configure certain aspects of Spring Session
|
||||
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 http://gemfire.docs.pivotal.io/docs-gemfire/latest/javadocs/japi/com/gemstone/gemfire/cache/RegionShortcut.html[RegionShortcut]
|
||||
* `serverRegionShort` - specifies GemFire https://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]
|
||||
(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 http://gemfire.docs.pivotal.io/docs-gemfire/latest/getting_started/installation/install_intro.html[Installing Pivotal GemFire].
|
||||
see https://gemfire.docs.pivotal.io/gemfire/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:
|
||||
@@ -204,6 +204,6 @@ NEXT_STEP_NAME : END
|
||||
gfsh>remove --region=/ClusteredSpringSessions --key="70002719-3c54-4c20-82c3-e7faa6b718f3"
|
||||
....
|
||||
|
||||
NOTE: The _GemFire User Guide_ has more detailed instructions on using http://gemfire.docs.pivotal.io/docs-gemfire/latest/tools_modules/gfsh/chapter_overview.html[gfsh].
|
||||
NOTE: The _GemFire User Guide_ has more detailed instructions on using https://gemfire.docs.pivotal.io/docs-gemfire/latest/tools_modules/gfsh/chapter_overview.html[gfsh].
|
||||
|
||||
Now visit the application at http://localhost:8080/ and observe that the attribute we added is no longer displayed.
|
||||
|
||||
@@ -95,7 +95,7 @@ spring.datasource.username=myapp
|
||||
spring.datasource.password=secret
|
||||
----
|
||||
|
||||
For more information, refer to http://docs.spring.io/spring-boot/docs/current/reference/htmlsingle/#boot-features-configure-datasource[Configure a DataSource] portion of the Spring Boot documentation.
|
||||
For more information, refer to https://docs.spring.io/spring-boot/docs/current/reference/htmlsingle/#boot-features-configure-datasource[Configure a DataSource] portion of the Spring Boot documentation.
|
||||
|
||||
[[httpsession-jdbc-boot-servlet-configuration]]
|
||||
== Servlet Container Initialization
|
||||
|
||||
@@ -87,7 +87,7 @@ In this instance Spring Session is backed by a relational database.
|
||||
We configure the H2 database to create database tables using the SQL script which is included in Spring Session.
|
||||
<3> We create a `transactionManager` that manages transactions for previously configured `dataSource`.
|
||||
|
||||
For additional information on how to configure data access related concerns, please refer to the http://docs.spring.io/spring/docs/current/spring-framework-reference/html/spring-data-tier.html[Spring Framework Reference Documentation].
|
||||
For additional information on how to configure data access related concerns, please refer to the https://docs.spring.io/spring/docs/current/spring-framework-reference/html/spring-data-tier.html[Spring Framework Reference Documentation].
|
||||
|
||||
== XML Servlet Container Initialization
|
||||
|
||||
@@ -105,7 +105,7 @@ include::{samples-dir}httpsession-xml/src/main/webapp/WEB-INF/web.xml[tags=conte
|
||||
include::{samples-dir}httpsession-xml/src/main/webapp/WEB-INF/web.xml[tags=listeners]
|
||||
----
|
||||
|
||||
The http://docs.spring.io/spring/docs/current/spring-framework-reference/htmlsingle/#context-create[ContextLoaderListener] reads the contextConfigLocation and picks up our session.xml configuration.
|
||||
The https://docs.spring.io/spring/docs/current/spring-framework-reference/htmlsingle/#context-create[ContextLoaderListener] reads the contextConfigLocation and picks up our session.xml configuration.
|
||||
|
||||
Last we need to ensure that our Servlet Container (i.e. Tomcat) uses our `springSessionRepositoryFilter` for every request.
|
||||
The following snippet performs this last step for us:
|
||||
@@ -116,7 +116,7 @@ The following snippet performs this last step for us:
|
||||
include::{samples-dir}httpsession-xml/src/main/webapp/WEB-INF/web.xml[tags=springSessionRepositoryFilter]
|
||||
----
|
||||
|
||||
The http://docs.spring.io/spring-framework/docs/current/javadoc-api/org/springframework/web/filter/DelegatingFilterProxy.html[DelegatingFilterProxy] will look up a Bean by the name of `springSessionRepositoryFilter` and cast it to a `Filter`.
|
||||
The https://docs.spring.io/spring-framework/docs/current/javadoc-api/org/springframework/web/filter/DelegatingFilterProxy.html[DelegatingFilterProxy] will look up a Bean by the name of `springSessionRepositoryFilter` and cast it to a `Filter`.
|
||||
For every request that `DelegatingFilterProxy` is invoked, the `springSessionRepositoryFilter` will be invoked.
|
||||
|
||||
// end::config[]
|
||||
|
||||
@@ -85,7 +85,7 @@ In this instance Spring Session is backed by a relational database.
|
||||
We configure the H2 database to create database tables using the SQL script which is included in Spring Session.
|
||||
<3> We create a `transactionManager` that manages transactions for previously configured `dataSource`.
|
||||
|
||||
For additional information on how to configure data access related concerns, please refer to the http://docs.spring.io/spring/docs/current/spring-framework-reference/html/spring-data-tier.html[Spring Framework Reference Documentation].
|
||||
For additional information on how to configure data access related concerns, please refer to the https://docs.spring.io/spring/docs/current/spring-framework-reference/html/spring-data-tier.html[Spring Framework Reference Documentation].
|
||||
|
||||
== Java Servlet Container Initialization
|
||||
|
||||
|
||||
@@ -23,6 +23,11 @@ If you are using Maven, ensure to add the following dependencies:
|
||||
<version>{spring-session-version}</version>
|
||||
<type>pom</type>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>biz.paluch.redis</groupId>
|
||||
<artifactId>lettuce</artifactId>
|
||||
<version>{lettuce-version}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.springframework</groupId>
|
||||
<artifactId>spring-web</artifactId>
|
||||
@@ -85,7 +90,7 @@ The filter is what is in charge of replacing the `HttpSession` implementation to
|
||||
In this instance Spring Session is backed by Redis.
|
||||
<2> We create a `RedisConnectionFactory` that connects Spring Session to the Redis Server.
|
||||
We configure the connection to connect to localhost on the default port (6379)
|
||||
For more information on configuring Spring Data Redis, refer to the http://docs.spring.io/spring-data/data-redis/docs/current/reference/html/[reference documentation].
|
||||
For more information on configuring Spring Data Redis, refer to the https://docs.spring.io/spring-data/data-redis/docs/current/reference/html/[reference documentation].
|
||||
|
||||
== XML Servlet Container Initialization
|
||||
|
||||
@@ -103,7 +108,7 @@ include::{samples-dir}httpsession-xml/src/main/webapp/WEB-INF/web.xml[tags=conte
|
||||
include::{samples-dir}httpsession-xml/src/main/webapp/WEB-INF/web.xml[tags=listeners]
|
||||
----
|
||||
|
||||
The http://docs.spring.io/spring/docs/current/spring-framework-reference/htmlsingle/#context-create[ContextLoaderListener] reads the contextConfigLocation and picks up our session.xml configuration.
|
||||
The https://docs.spring.io/spring/docs/current/spring-framework-reference/htmlsingle/#context-create[ContextLoaderListener] reads the contextConfigLocation and picks up our session.xml configuration.
|
||||
|
||||
Last we need to ensure that our Servlet Container (i.e. Tomcat) uses our `springSessionRepositoryFilter` for every request.
|
||||
The following snippet performs this last step for us:
|
||||
@@ -114,7 +119,7 @@ The following snippet performs this last step for us:
|
||||
include::{samples-dir}httpsession-xml/src/main/webapp/WEB-INF/web.xml[tags=springSessionRepositoryFilter]
|
||||
----
|
||||
|
||||
The http://docs.spring.io/spring-framework/docs/current/javadoc-api/org/springframework/web/filter/DelegatingFilterProxy.html[DelegatingFilterProxy] will look up a Bean by the name of `springSessionRepositoryFilter` and cast it to a `Filter`.
|
||||
The https://docs.spring.io/spring-framework/docs/current/javadoc-api/org/springframework/web/filter/DelegatingFilterProxy.html[DelegatingFilterProxy] will look up a Bean by the name of `springSessionRepositoryFilter` and cast it to a `Filter`.
|
||||
For every request that `DelegatingFilterProxy` is invoked, the `springSessionRepositoryFilter` will be invoked.
|
||||
|
||||
// end::config[]
|
||||
@@ -128,8 +133,8 @@ You can run the sample by obtaining the {download-url}[source code] and invoking
|
||||
|
||||
[NOTE]
|
||||
====
|
||||
For the sample to work, you must http://redis.io/download[install Redis 2.8+] on localhost and run it with the default port (6379).
|
||||
Alternatively, you can update the `JedisConnectionFactory` to point to a Redis server.
|
||||
For the sample to work, you must https://redis.io/download[install Redis 2.8+] on localhost and run it with the default port (6379).
|
||||
Alternatively, you can update the `LettuceConnectionFactory` to point to a Redis server.
|
||||
====
|
||||
|
||||
----
|
||||
@@ -165,7 +170,7 @@ If you like, you can easily remove the session using redis-cli. For example, on
|
||||
|
||||
$ redis-cli keys '*' | xargs redis-cli del
|
||||
|
||||
TIP: The Redis documentation has instructions for http://redis.io/topics/quickstart[installing redis-cli].
|
||||
TIP: The Redis documentation has instructions for https://redis.io/topics/quickstart[installing redis-cli].
|
||||
|
||||
Alternatively, you can also delete the explicit key. Enter the following into your terminal ensuring to replace `7e8383a4-082c-4ffe-a4bc-c40fd3363c5e` with the value of your SESSION cookie:
|
||||
|
||||
|
||||
@@ -23,6 +23,11 @@ If you are using Maven, ensure to add the following dependencies:
|
||||
<version>{spring-session-version}</version>
|
||||
<type>pom</type>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>biz.paluch.redis</groupId>
|
||||
<artifactId>lettuce</artifactId>
|
||||
<version>{lettuce-version}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.springframework</groupId>
|
||||
<artifactId>spring-web</artifactId>
|
||||
@@ -83,7 +88,7 @@ The filter is what is in charge of replacing the `HttpSession` implementation to
|
||||
In this instance Spring Session is backed by Redis.
|
||||
<2> We create a `RedisConnectionFactory` that connects Spring Session to the Redis Server.
|
||||
We configure the connection to connect to localhost on the default port (6379)
|
||||
For more information on configuring Spring Data Redis, refer to the http://docs.spring.io/spring-data/data-redis/docs/current/reference/html/[reference documentation].
|
||||
For more information on configuring Spring Data Redis, refer to the https://docs.spring.io/spring-data/data-redis/docs/current/reference/html/[reference documentation].
|
||||
|
||||
== Java Servlet Container Initialization
|
||||
|
||||
@@ -120,8 +125,8 @@ You can run the sample by obtaining the {download-url}[source code] and invoking
|
||||
|
||||
[NOTE]
|
||||
====
|
||||
For the sample to work, you must http://redis.io/download[install Redis 2.8+] on localhost and run it with the default port (6379).
|
||||
Alternatively, you can update the `JedisConnectionFactory` to point to a Redis server.
|
||||
For the sample to work, you must https://redis.io/download[install Redis 2.8+] on localhost and run it with the default port (6379).
|
||||
Alternatively, you can update the `LettuceConnectionFactory` to point to a Redis server.
|
||||
====
|
||||
|
||||
----
|
||||
@@ -157,7 +162,7 @@ If you like, you can easily remove the session using redis-cli. For example, on
|
||||
|
||||
$ redis-cli keys '*' | xargs redis-cli del
|
||||
|
||||
TIP: The Redis documentation has instructions for http://redis.io/topics/quickstart[installing redis-cli].
|
||||
TIP: The Redis documentation has instructions for https://redis.io/topics/quickstart[installing redis-cli].
|
||||
|
||||
Alternatively, you can also delete the explicit key. Enter the following into your terminal ensuring to replace `7e8383a4-082c-4ffe-a4bc-c40fd3363c5e` with the value of your SESSION cookie:
|
||||
|
||||
|
||||
@@ -100,7 +100,7 @@ spring.data.mongodb.port=27018
|
||||
spring.data.mongodb.database=prod
|
||||
----
|
||||
|
||||
For more information, refer to http://docs.spring.io/spring-boot/docs/current/reference/htmlsingle/#boot-features-connecting-to-mongodb[Connecting to MongoDB] portion of the Spring Boot documentation.
|
||||
For more information, refer to https://docs.spring.io/spring-boot/docs/current/reference/htmlsingle/#boot-features-connecting-to-mongodb[Connecting to MongoDB] portion of the Spring Boot documentation.
|
||||
|
||||
[[boot-servlet-configuration]]
|
||||
== Servlet Container Initialization
|
||||
|
||||
@@ -23,6 +23,11 @@ If you are using Maven, ensure to add the following dependencies:
|
||||
<version>{spring-session-version}</version>
|
||||
<type>pom</type>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>biz.paluch.redis</groupId>
|
||||
<artifactId>lettuce</artifactId>
|
||||
<version>{lettuce-version}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.springframework</groupId>
|
||||
<artifactId>spring-web</artifactId>
|
||||
@@ -83,7 +88,7 @@ The filter is what is in charge of replacing the `HttpSession` implementation to
|
||||
In this instance Spring Session is backed by Redis.
|
||||
<2> We create a `RedisConnectionFactory` that connects Spring Session to the Redis Server.
|
||||
We configure the connection to connect to localhost on the default port (6379)
|
||||
For more information on configuring Spring Data Redis, refer to the http://docs.spring.io/spring-data/data-redis/docs/current/reference/html/[reference documentation].
|
||||
For more information on configuring Spring Data Redis, refer to the https://docs.spring.io/spring-data/data-redis/docs/current/reference/html/[reference documentation].
|
||||
<3> We customize Spring Session's HttpSession integration to use HTTP headers to convey the current session information instead of cookies.
|
||||
|
||||
== Servlet Container Initialization
|
||||
@@ -121,8 +126,8 @@ You can run the sample by obtaining the {download-url}[source code] and invoking
|
||||
|
||||
[NOTE]
|
||||
====
|
||||
For the sample to work, you must http://redis.io/download[install Redis 2.8+] on localhost and run it with the default port (6379).
|
||||
Alternatively, you can update the `JedisConnectionFactory` to point to a Redis server.
|
||||
For the sample to work, you must https://redis.io/download[install Redis 2.8+] on localhost and run it with the default port (6379).
|
||||
Alternatively, you can update the `LettuceConnectionFactory` to point to a Redis server.
|
||||
====
|
||||
|
||||
----
|
||||
@@ -203,7 +208,7 @@ Now remove the session using redis-cli. For example, on a Linux based system you
|
||||
|
||||
$ redis-cli keys '*' | xargs redis-cli del
|
||||
|
||||
TIP: The Redis documentation has instructions for http://redis.io/topics/quickstart[installing redis-cli].
|
||||
TIP: The Redis documentation has instructions for https://redis.io/topics/quickstart[installing redis-cli].
|
||||
|
||||
Alternatively, you can also delete the explicit key. Enter the following into your terminal ensuring to replace `7e8383a4-082c-4ffe-a4bc-c40fd3363c5e` with the value of your SESSION cookie:
|
||||
|
||||
|
||||
@@ -19,15 +19,20 @@ If you are using Maven, ensure to add the following dependencies:
|
||||
<!-- ... -->
|
||||
|
||||
<dependency>
|
||||
<groupId>org.springframework.session</groupId>
|
||||
<artifactId>spring-session-data-redis</artifactId>
|
||||
<version>{spring-session-version}</version>
|
||||
<type>pom</type>
|
||||
<groupId>org.springframework.session</groupId>
|
||||
<artifactId>spring-session-data-redis</artifactId>
|
||||
<version>{spring-session-version}</version>
|
||||
<type>pom</type>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.springframework</groupId>
|
||||
<artifactId>spring-web</artifactId>
|
||||
<version>{spring-version}</version>
|
||||
<groupId>biz.paluch.redis</groupId>
|
||||
<artifactId>lettuce</artifactId>
|
||||
<version>{lettuce-version}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.springframework</groupId>
|
||||
<artifactId>spring-web</artifactId>
|
||||
<version>{spring-version}</version>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
----
|
||||
@@ -82,7 +87,7 @@ The filter is what is in charge of replacing the `HttpSession` implementation to
|
||||
In this instance Spring Session is backed by Redis.
|
||||
<2> We create a `RedisConnectionFactory` that connects Spring Session to the Redis Server.
|
||||
We configure the connection to connect to localhost on the default port (6379)
|
||||
For more information on configuring Spring Data Redis, refer to the http://docs.spring.io/spring-data/data-redis/docs/current/reference/html/[reference documentation].
|
||||
For more information on configuring Spring Data Redis, refer to the https://docs.spring.io/spring-data/data-redis/docs/current/reference/html/[reference documentation].
|
||||
|
||||
== Servlet Container Initialization
|
||||
|
||||
@@ -125,8 +130,8 @@ You can run the sample by obtaining the {download-url}[source code] and invoking
|
||||
|
||||
[NOTE]
|
||||
====
|
||||
For the sample to work, you must http://redis.io/download[install Redis 2.8+] on localhost and run it with the default port (6379).
|
||||
Alternatively, you can update the `JedisConnectionFactory` to point to a Redis server.
|
||||
For the sample to work, you must https://redis.io/download[install Redis 2.8+] on localhost and run it with the default port (6379).
|
||||
Alternatively, you can update the `LettuceConnectionFactory` to point to a Redis server.
|
||||
====
|
||||
|
||||
----
|
||||
@@ -159,7 +164,7 @@ If you like, you can easily remove the session using redis-cli. For example, on
|
||||
|
||||
$ redis-cli keys '*' | xargs redis-cli del
|
||||
|
||||
TIP: The Redis documentation has instructions for http://redis.io/topics/quickstart[installing redis-cli].
|
||||
TIP: The Redis documentation has instructions for https://redis.io/topics/quickstart[installing redis-cli].
|
||||
|
||||
Alternatively, you can also delete the explicit key. Enter the following into your terminal ensuring to replace `7e8383a4-082c-4ffe-a4bc-c40fd3363c5e` with the value of your SESSION cookie:
|
||||
|
||||
|
||||
@@ -19,8 +19,8 @@ You can run the sample by obtaining the {download-url}[source code] and invoking
|
||||
|
||||
[NOTE]
|
||||
====
|
||||
For the sample to work, you must http://redis.io/download[install Redis 2.8+] on localhost and run it with the default port (6379).
|
||||
Alternatively, you can update the `JedisConnectionFactory` to point to a Redis server.
|
||||
For the sample to work, you must https://redis.io/download[install Redis 2.8+] on localhost and run it with the default port (6379).
|
||||
Alternatively, you can update the `LettuceConnectionFactory` to point to a Redis server.
|
||||
====
|
||||
|
||||
----
|
||||
@@ -140,7 +140,7 @@ For example, if the URL is http://localhost:8080/?_s=1 this alias would be used.
|
||||
|
||||
The nice thing about specifying the session alias in the URL is that we can have multiple tabs open with different active sessions.
|
||||
The bad thing is that we need to include the session alias in every URL of our application.
|
||||
Fortunately, Spring Session will automatically include the session alias in any URL that passes through http://docs.oracle.com/javaee/6/api/javax/servlet/http/HttpServletResponse.html#encodeURL(java.lang.String)[HttpServletResponse#encodeURL(java.lang.String)]
|
||||
Fortunately, Spring Session will automatically include the session alias in any URL that passes through https://docs.oracle.com/javaee/6/api/javax/servlet/http/HttpServletResponse.html#encodeURL(java.lang.String)[HttpServletResponse#encodeURL(java.lang.String)]
|
||||
|
||||
This means that if you are using standard tag libraries the session alias is automatically included in the URL.
|
||||
For example, if we are currently using the session with the alias of *1*, then the following:
|
||||
|
||||
@@ -84,8 +84,8 @@ include::{samples-dir}websocket/src/main/java/sample/config/WebSecurityConfig.ja
|
||||
|
||||
[NOTE]
|
||||
====
|
||||
For the sample to work, you must http://redis.io/download[install Redis 2.8+] on localhost and run it with the default port (6379).
|
||||
Alternatively, you can update the `JedisConnectionFactory` to point to a Redis server.
|
||||
For the sample to work, you must https://redis.io/download[install Redis 2.8+] on localhost and run it with the default port (6379).
|
||||
Alternatively, you can update the `LettuceConnectionFactory` to point to a Redis server.
|
||||
====
|
||||
|
||||
----
|
||||
|
||||
@@ -1,3 +1,4 @@
|
||||
|
||||
= Spring Session
|
||||
Rob Winch, Vedran Pavić, Jakub Kubrynski
|
||||
:doctype: book
|
||||
@@ -22,15 +23,21 @@ Additional features include:
|
||||
|
||||
* <<websocket,WebSocket>> - provides the ability to keep the `HttpSession` alive when receiving WebSocket messages
|
||||
|
||||
== What's New in 1.2
|
||||
== What's New in 1.3
|
||||
|
||||
Below are the highlights of what is new in Spring Session 1.2. You can find a complete list of what's new in https://github.com/spring-projects/spring-session/issues?utf8=%E2%9C%93&q=milestone%3A%221.2.0+RC1%22[1.2.0 RC1] by referring to the changelog.
|
||||
Below are the highlights of what is new in Spring Session 1.3. You can find a complete list of what's new by referring to the changelogs of
|
||||
https://github.com/spring-projects/spring-session/milestone/6?closed=1[1.3.0.M1],
|
||||
https://github.com/spring-projects/spring-session/milestone/18?closed=1[1.3.0.M2],
|
||||
https://github.com/spring-projects/spring-session/milestone/16?closed=1[1.3.0.RC1], and
|
||||
https://github.com/spring-projects/spring-session/milestone/19?closed=1[1.3.0.RELEASE].
|
||||
|
||||
* Added <<httpsession-jdbc,JdbcOperationsSessionRepository>> (See https://github.com/spring-projects/spring-session/issues/364[#364]).
|
||||
* Added <<httpsession-mongo,MongoOperationsSessionRepository>> (See https://github.com/spring-projects/spring-session/pull/371[#371]).
|
||||
* SessionRepositoryFilter caches null session lookup (See https://github.com/spring-projects/spring-session/issues/423[#423])
|
||||
* link:guides/grails3.html[Grails 3 Sample & Guide]
|
||||
* Improved Workspace Setup (See https://github.com/spring-projects/spring-session/pull/417[#417])
|
||||
* First class support for https://docs.spring.io/spring-session/docs/1.3.0.RELEASE/reference/html5/#httpsession-hazelcast[Hazelcast]
|
||||
* First class support for https://docs.spring.io/spring-session/docs/1.3.0.RELEASE/reference/html5/#spring-security-concurrent-sessions-how[Spring Security's concurrent session management]
|
||||
* Added https://github.com/maseev/spring-session-orientdb[OrientDB Community Extension]
|
||||
* https://github.com/spring-projects/spring-session/tree/1.3.0.RELEASE/samples/httpsession-redis-json[GenericJackson2JsonRedisSerializer sample] with Spring Security's new Jackson Support
|
||||
* Guides now https://github.com/spring-projects/spring-session/pull/652[use Lettuce]
|
||||
* `spring.session.cleanup.cron.expression` can be used to override the cleanup task’s cron expression
|
||||
* Lots of performance improvements and bug fixes
|
||||
|
||||
[[samples]]
|
||||
== Samples and Guides (Start Here)
|
||||
@@ -185,14 +192,14 @@ 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/topologies_and_comm/multi_site_configuration/chapter_overview.html[WAN functionality].
|
||||
Additionally, GemFire supports site-to-site replication using https://gemfire.docs.pivotal.io/docs-gemfire/latest/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].
|
||||
of this document. More details on GemFire WAN functionality can be found https://docs.spring.io/spring-data-gemfire/docs/current/reference/html/#bootstrap:gateway[here].
|
||||
|
||||
[[httpsession-gemfire-clientserver]]
|
||||
==== GemFire Client-Server
|
||||
|
||||
The http://gemfire.docs.pivotal.io/docs-gemfire/latest/topologies_and_comm/cs_configuration/chapter_overview.html[Client-Server]
|
||||
The https://gemfire.docs.pivotal.io/docs-gemfire/latest/topologies_and_comm/cs_configuration/chapter_overview.html[Client-Server]
|
||||
topology will probably be the more common configuration preference for users when using GemFire as a provider in
|
||||
Spring Session since a GemFire server will have significantly different and unique JVM heap requirements when compared
|
||||
to the application. Using a client-server topology enables an application to manage (e.g. replicate) application state
|
||||
@@ -234,14 +241,14 @@ include::guides/httpsession-gemfire-clientserver-xml.adoc[tags=config,leveloffse
|
||||
==== GemFire Peer-To-Peer (P2P)
|
||||
|
||||
Perhaps less common would be to configure the Spring Session application as a peer member in the GemFire cluster using
|
||||
the http://gemfire.docs.pivotal.io/docs-gemfire/latest/topologies_and_comm/p2p_configuration/chapter_overview.html[Peer-To-Peer (P2P)] topology.
|
||||
the https://gemfire.docs.pivotal.io/docs-gemfire/latest/topologies_and_comm/p2p_configuration/chapter_overview.html[Peer-To-Peer (P2P)] topology.
|
||||
In this configuration, a Spring Session application would be an actual data node (server) in the GemFire cluster,
|
||||
and **not** a cache client as before.
|
||||
|
||||
One advantage to this approach is the proximity of the application to the application's state (i.e. it's data). However,
|
||||
there are other effective means of accomplishing similar data dependent computations, such as using GemFire's
|
||||
http://gemfire.docs.pivotal.io/docs-gemfire/latest/developing/function_exec/chapter_overview.html[Function Execution].
|
||||
Any of GemFire's other http://gemfire.docs.pivotal.io/docs-gemfire/latest/getting_started/product_intro.html[features]
|
||||
https://gemfire.docs.pivotal.io/docs-gemfire/latest/developing/function_exec/chapter_overview.html[Function Execution].
|
||||
Any of GemFire's other https://gemfire.docs.pivotal.io/docs-gemfire/latest/getting_started/product_intro.html[features]
|
||||
can be used when GemFire is serving as a provider in Spring Session.
|
||||
|
||||
P2P is very useful for both testing purposes as well as smaller, more focused and self-contained applications,
|
||||
@@ -368,6 +375,18 @@ There is also a constructor taking `Serializer` and `Deserializer` objects, allo
|
||||
You can create your own session converter by extending `AbstractMongoSessionConverter` class.
|
||||
The implementation will be used for serializing, deserializing your objects and for providing queries to access the session.
|
||||
|
||||
[[httpsession-hazelcast]]
|
||||
=== HttpSession with Hazelcast
|
||||
|
||||
Using Spring Session with `HttpSession` is enabled by adding a Servlet Filter before anything that uses the `HttpSession`.
|
||||
|
||||
This section describes how to use Hazelcast to back `HttpSession` using Java based configuration.
|
||||
|
||||
NOTE: The <<samples, Hazelcast Spring Sample>> provides a working sample on how to integrate Spring Session and `HttpSession` using Java configuration.
|
||||
You can read the basic steps for integration below, but you are encouraged to follow along with the detailed Hazelcast Spring Guide when integrating with your own application.
|
||||
|
||||
include::guides/hazelcast-spring.adoc[tags=config,leveloffset=+2]
|
||||
|
||||
[[httpsession-how]]
|
||||
=== How HttpSession Integration Works
|
||||
|
||||
@@ -505,17 +524,49 @@ Before using WebSocket integration, you should be sure that you have <<httpsessi
|
||||
|
||||
include::guides/websocket.adoc[tags=config,leveloffset=+2]
|
||||
|
||||
[[spring-security-concurrent-sessions]]
|
||||
[[spring-security]]
|
||||
== Spring Security Integration
|
||||
|
||||
Spring Session provides integration with Spring Security.
|
||||
|
||||
[[spring-security-rememberme]]
|
||||
=== Spring Security Remember-Me Support
|
||||
|
||||
Spring Session provides integration with https://docs.spring.io/spring-security/site/docs/4.2.x/reference/htmlsingle/#remember-me[Spring Security's Remember-Me Authentication].
|
||||
The support will:
|
||||
|
||||
* Change the session expiration length
|
||||
* Ensure the session cookie expires at `Integer.MAX_VALUE`.
|
||||
The cookie expiration is set to the largest possible value because the cookie is only set when the session is created.
|
||||
If it were set to the same value as the session expiration, then the session would get renewed when the user used it but the cookie expiration would not be updated causing the expiration to be fixed.
|
||||
|
||||
To configure Spring Session with Spring Security in Java Configuration use the following as a guide:
|
||||
|
||||
[source,java,indent=0]
|
||||
----
|
||||
include::{docs-test-dir}docs/security/RememberMeSecurityConfiguration.java[tags=http-rememberme]
|
||||
}
|
||||
|
||||
include::{docs-test-dir}docs/security/RememberMeSecurityConfiguration.java[tags=rememberme-bean]
|
||||
----
|
||||
|
||||
An XML based configuration would look something like this:
|
||||
|
||||
[source,xml,indent=0]
|
||||
----
|
||||
include::{docs-test-resources-dir}docs/security/RememberMeSecurityConfigurationXmlTests-context.xml[tags=config]
|
||||
----
|
||||
|
||||
|
||||
[[spring-security-concurrent-sessions]]
|
||||
=== Spring Security Concurrent Session Control
|
||||
|
||||
|
||||
Spring Session provides integration with Spring Security to support its concurrent session control.
|
||||
This allows limiting the number of active sessions that a single user can have concurrently, but unlike the default
|
||||
Spring Security support this will also work in a clustered environment. This is done by providing a custom
|
||||
implementation of Spring Security's `SessionRegistry` interface.
|
||||
|
||||
[[spring-security-concurrent-sessions-how]]
|
||||
=== Configuring Spring Security's concurrent session management
|
||||
|
||||
When using Spring Security's Java config DSL, you can configure the custom `SessionRegistry` through the
|
||||
`SessionManagementConfigurer` like this:
|
||||
[source,java,indent=0]
|
||||
@@ -647,44 +698,6 @@ It is important to note that no infrastructure for session expirations is config
|
||||
This is because things like session expiration are highly implementation dependent.
|
||||
This means if you require cleaning up expired sessions, you are responsible for cleaning up the expired sessions.
|
||||
|
||||
[[api-enablehazelcasthttpsession]]
|
||||
=== EnableHazelcastHttpSession
|
||||
|
||||
If you wish to use http://hazelcast.org/[Hazelcast] as your backing source for the `SessionRepository`, then the `@EnableHazelcastHttpSession` annotation
|
||||
can be added to an `@Configuration` class. This extends the functionality provided by the `@EnableSpringHttpSession` annotation but makes the `SessionRepository` for you in Hazelcast.
|
||||
You must provide a single `HazelcastInstance` bean for the configuration to work.
|
||||
For example:
|
||||
|
||||
[source,java,indent=0]
|
||||
----
|
||||
include::{docs-test-dir}docs/http/HazelcastHttpSessionConfig.java[tags=config]
|
||||
----
|
||||
|
||||
This will configure Hazelcast in embedded mode with default configuration.
|
||||
See the http://docs.hazelcast.org/docs/latest/manual/html-single/index.html#hazelcast-configuration[Hazelcast documentation] for
|
||||
detailed information on configuration options for Hazelcast.
|
||||
|
||||
[[api-enablehazelcasthttpsession-storage]]
|
||||
==== Storage Details
|
||||
|
||||
Sessions will be stored in a distributed `Map` in Hazelcast using a <<api-mapsessionrepository,MapSessionRepository>>.
|
||||
The `Map` interface methods will be used to `get()` and `put()` Sessions.
|
||||
The expiration of a session in the `Map` is handled by Hazelcast's support for setting the time to live on an entry when it is `put()` into the `Map`. Entries (sessions) that have been idle longer than the time to live will be automatically removed from the `Map`.
|
||||
|
||||
You shouldn't need to configure any settings such as `max-idle-seconds` or `time-to-live-seconds` for the `Map` within the Hazelcast configuration.
|
||||
|
||||
[[api-enablehazelcasthttpsession-customize]]
|
||||
==== Basic Customization
|
||||
You can use the following attributes on `@EnableHazelcastHttpSession` to customize the configuration:
|
||||
|
||||
* **maxInactiveIntervalInSeconds** - the amount of time before the session will expire in seconds. Default is 1800 seconds (30 minutes)
|
||||
* **sessionMapName** - the name of the distributed `Map` that will be used in Hazelcast to store the session data.
|
||||
|
||||
[[api-enablehazelcasthttpsession-events]]
|
||||
==== Session Events
|
||||
Using a `MapListener` to respond to entries being added, evicted, and removed from the distributed `Map`, these events will trigger
|
||||
publishing SessionCreatedEvent, SessionExpiredEvent, and SessionDeletedEvent events respectively using the `ApplicationEventPublisher`.
|
||||
|
||||
[[api-redisoperationssessionrepository]]
|
||||
=== RedisOperationsSessionRepository
|
||||
|
||||
@@ -724,7 +737,7 @@ You can customize the serialization by creating a Bean named `springSessionDefau
|
||||
|
||||
`RedisOperationsSessionRepository` is subscribed to receive events from redis using a `RedisMessageListenerContainer`.
|
||||
You can customize the way those events are dispatched, by creating a Bean named `springSessionRedisTaskExecutor` and/or a Bean `springSessionRedisSubscriptionExecutor`.
|
||||
More details on configuring redis task executors can be found http://docs.spring.io/spring-data-redis/docs/current/reference/html/#redis:pubsub:subscribe:containers[here].
|
||||
More details on configuring redis task executors can be found https://docs.spring.io/spring-data-redis/docs/current/reference/html/#redis:pubsub:subscribe:containers[here].
|
||||
|
||||
[[api-redisoperationssessionrepository-storage]]
|
||||
==== Storage Details
|
||||
@@ -803,7 +816,7 @@ The `SessionRepository.getSession(String)` method ensures that no expired sessio
|
||||
This means there is no need to check the expiration before using a session.
|
||||
====
|
||||
|
||||
Spring Session relies on the delete and expired http://redis.io/topics/notifications[keyspace notifications] from Redis to fire a <<api-redisoperationssessionrepository-sessiondestroyedevent,SessionDeletedEvent>> and <<api-redisoperationssessionrepository-sessiondestroyedevent,SessionExpiredEvent>> respectively.
|
||||
Spring Session relies on the delete and expired https://redis.io/topics/notifications[keyspace notifications] from Redis to fire a <<api-redisoperationssessionrepository-sessiondestroyedevent,SessionDeletedEvent>> and <<api-redisoperationssessionrepository-sessiondestroyedevent,SessionExpiredEvent>> respectively.
|
||||
It is the `SessionDeletedEvent` or `SessionExpiredEvent` that ensures resources associated with the Session are cleaned up.
|
||||
For example, when using Spring Session's WebSocket support the Redis expired or delete event is what triggers any WebSocket connections associated with the session to be closed.
|
||||
|
||||
@@ -816,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 they 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 the 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.
|
||||
For additional details see https://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 they 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 the 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.
|
||||
@@ -833,7 +846,7 @@ EXPIRE spring:session:expirations1439245080000 2100
|
||||
----
|
||||
|
||||
The background task will then use these mappings to explicitly request each key.
|
||||
By accessing they key, rather than deleting it, we ensure that Redis deletes the key for us only if the TTL is expired.
|
||||
By accessing the key, rather than deleting it, we ensure that Redis deletes the key for us only if the TTL is expired.
|
||||
|
||||
[NOTE]
|
||||
====
|
||||
@@ -853,7 +866,7 @@ This is necessary to ensure resources associated with the `Session` are properly
|
||||
|
||||
For example, when integrating with WebSockets the `SessionDestroyedEvent` is in charge of closing any active WebSocket connections.
|
||||
|
||||
Firing `SessionDeletedEvent` or `SessionExpiredEvent` is made available through the `SessionMessageListener` which listens to http://redis.io/topics/notifications[Redis Keyspace events].
|
||||
Firing `SessionDeletedEvent` or `SessionExpiredEvent` is made available through the `SessionMessageListener` which listens to https://redis.io/topics/notifications[Redis Keyspace events].
|
||||
In order for this to work, Redis Keyspace events for Generic commands and Expired events needs to be enabled.
|
||||
For example:
|
||||
|
||||
@@ -892,7 +905,7 @@ If registered as a MessageListener (default), then `RedisOperationsSessionReposi
|
||||
[[api-redisoperationssessionrepository-cli]]
|
||||
==== Viewing the Session in Redis
|
||||
|
||||
After http://redis.io/topics/quickstart[installing redis-cli], you can inspect the values in Redis http://redis.io/commands#hash[using the redis-cli].
|
||||
After https://redis.io/topics/quickstart[installing redis-cli], you can inspect the values in Redis https://redis.io/commands#hash[using the redis-cli].
|
||||
For example, enter the following into a terminal:
|
||||
|
||||
[source,bash]
|
||||
@@ -997,9 +1010,9 @@ Session attribute a value that is not `Comparable` and the Session is saved to G
|
||||
|
||||
NOTE: Any Session attribute that is not indexed may store non-`Comparable` values.
|
||||
|
||||
To learn more about GemFire's Range-based Indexes, see http://gemfire.docs.pivotal.io/docs-gemfire/latest/developing/query_index/creating_map_indexes.html[Creating Indexes on Map Fields].
|
||||
To learn more about GemFire's Range-based Indexes, see https://gemfire.docs.pivotal.io/docs-gemfire/latest/developing/query_index/creating_map_indexes.html[Creating Indexes on Map Fields].
|
||||
|
||||
To learn more about GemFire Indexing in general, see http://gemfire.docs.pivotal.io/docs-gemfire/latest/developing/query_index/query_index.html[Working with Indexes].
|
||||
To learn more about GemFire Indexing in general, see https://gemfire.docs.pivotal.io/docs-gemfire/latest/developing/query_index/query_index.html[Working with Indexes].
|
||||
|
||||
|
||||
[[api-mapsessionrepository]]
|
||||
@@ -1053,7 +1066,7 @@ A typical example of how to create a new instance can be seen below:
|
||||
include::{indexdoc-tests}[tags=new-jdbcoperationssessionrepository]
|
||||
----
|
||||
|
||||
For additional information on how to create and configure `JdbcTemplate` and `PlatformTransactionManager`, refer to the http://docs.spring.io/spring/docs/current/spring-framework-reference/html/spring-data-tier.html[Spring Framework Reference Documentation].
|
||||
For additional information on how to create and configure `JdbcTemplate` and `PlatformTransactionManager`, refer to the https://docs.spring.io/spring/docs/current/spring-framework-reference/html/spring-data-tier.html[Spring Framework Reference Documentation].
|
||||
|
||||
[[api-jdbcoperationssessionrepository-config]]
|
||||
==== EnableJdbcHttpSession
|
||||
@@ -1104,6 +1117,54 @@ include::{session-main-resources-dir}org/springframework/session/jdbc/schema-mys
|
||||
All JDBC operations in `JdbcOperationsSessionRepository` are executed in a transactional manner.
|
||||
Transactions are executed with propagation set to `REQUIRES_NEW` in order to avoid unexpected behavior due to interference with existing transactions (for example, executing `save` operation in a thread that already participates in a read-only transaction).
|
||||
|
||||
[[api-hazelcastsessionrepository]]
|
||||
=== HazelcastSessionRepository
|
||||
|
||||
`HazelcastSessionRepository` is a `SessionRepository` implementation that stores sessions in Hazelcast's distributed `IMap`.
|
||||
In a web environment, this is typically used in combination with `SessionRepositoryFilter`.
|
||||
|
||||
[[api-hazelcastsessionrepository-new]]
|
||||
==== Instantiating a HazelcastSessionRepository
|
||||
|
||||
A typical example of how to create a new instance can be seen below:
|
||||
|
||||
[source,java,indent=0]
|
||||
----
|
||||
include::{indexdoc-tests}[tags=new-hazelcastsessionrepository]
|
||||
----
|
||||
|
||||
For additional information on how to create and configure Hazelcast instance, refer to the https://docs.hazelcast.org/docs/latest/manual/html-single/index.html#hazelcast-configuration[Hazelcast documentation].
|
||||
|
||||
[[api-enablehazelcasthttpsession]]
|
||||
==== EnableHazelcastHttpSession
|
||||
|
||||
If you wish to use https://hazelcast.org/[Hazelcast] as your backing source for the `SessionRepository`, then the `@EnableHazelcastHttpSession` annotation
|
||||
can be added to an `@Configuration` class. This extends the functionality provided by the `@EnableSpringHttpSession` annotation but makes the `SessionRepository` for you in Hazelcast.
|
||||
You must provide a single `HazelcastInstance` bean for the configuration to work.
|
||||
Complete configuration example can be found in the <<samples>>
|
||||
|
||||
[[api-enablehazelcasthttpsession-storage]]
|
||||
==== Storage Details
|
||||
|
||||
Sessions will be stored in a distributed `IMap` in Hazelcast using a <<api-mapsessionrepository,MapSessionRepository>>.
|
||||
The `IMap` interface methods will be used to `get()` and `put()` Sessions.
|
||||
Additionally, `values()` method is used to support `FindByIndexNameSessionRepository#findByIndexNameAndIndexValue` operation, together with appropriate `ValueExtractor` that needs to be registered with Hazelcast. Refer to <<samples, Hazelcast Spring Sample>> for more details on this configuration.
|
||||
The expiration of a session in the `IMap` is handled by Hazelcast's support for setting the time to live on an entry when it is `put()` into the `IMap`. Entries (sessions) that have been idle longer than the time to live will be automatically removed from the `IMap`.
|
||||
|
||||
You shouldn't need to configure any settings such as `max-idle-seconds` or `time-to-live-seconds` for the `IMap` within the Hazelcast configuration.
|
||||
|
||||
[[api-enablehazelcasthttpsession-customize]]
|
||||
==== Basic Customization
|
||||
You can use the following attributes on `@EnableHazelcastHttpSession` to customize the configuration:
|
||||
|
||||
* **maxInactiveIntervalInSeconds** - the amount of time before the session will expire in seconds. Default is 1800 seconds (30 minutes)
|
||||
* **sessionMapName** - the name of the distributed `Map` that will be used in Hazelcast to store the session data.
|
||||
|
||||
[[api-enablehazelcasthttpsession-events]]
|
||||
==== Session Events
|
||||
Using a `MapListener` to respond to entries being added, evicted, and removed from the distributed `Map`, these events will trigger
|
||||
publishing SessionCreatedEvent, SessionExpiredEvent, and SessionDeletedEvent events respectively using the `ApplicationEventPublisher`.
|
||||
|
||||
[[community]]
|
||||
== Spring Session Community
|
||||
|
||||
@@ -1113,7 +1174,7 @@ Please find additional information below.
|
||||
[[community-support]]
|
||||
=== Support
|
||||
|
||||
You can get help by asking questions on http://stackoverflow.com/questions/tagged/spring-session[StackOverflow with the tag spring-session].
|
||||
You can get help by asking questions on https://stackoverflow.com/questions/tagged/spring-session[StackOverflow with the tag spring-session].
|
||||
Similarly we encourage helping others by answering questions on StackOverflow.
|
||||
|
||||
[[community-source]]
|
||||
@@ -1134,7 +1195,21 @@ We appreciate https://help.github.com/articles/using-pull-requests/[Pull Request
|
||||
[[community-license]]
|
||||
=== License
|
||||
|
||||
Spring Session is Open Source software released under the http://www.apache.org/licenses/LICENSE-2.0.html[Apache 2.0 license].
|
||||
Spring Session is Open Source software released under the https://www.apache.org/licenses/LICENSE-2.0.html[Apache 2.0 license].
|
||||
|
||||
[[community-extensions]]
|
||||
=== Community Extensions
|
||||
|
||||
|===
|
||||
| Name | Location
|
||||
|
||||
| Spring Session OrientDB
|
||||
| https://github.com/maseev/spring-session-orientdb
|
||||
|
||||
| Spring Session Infinispan
|
||||
| https://infinispan.org/docs/dev/user_guide/user_guide.html#externalizing_session_using_spring_session
|
||||
|
||||
|===
|
||||
|
||||
[[minimum-requirements]]
|
||||
== Minimum Requirements
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
@@ -14,10 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
/**
|
||||
* Mix-in classes to provide Jackson serialization support.
|
||||
*
|
||||
* @author Jitendra Singh
|
||||
* @since 4.2
|
||||
*/
|
||||
package org.springframework.security.web.jackson2;
|
||||
package docs;
|
||||
|
||||
public class Docs {
|
||||
}
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
@@ -16,17 +16,23 @@
|
||||
|
||||
package docs;
|
||||
|
||||
import com.hazelcast.config.Config;
|
||||
import com.hazelcast.core.Hazelcast;
|
||||
import com.hazelcast.core.HazelcastInstance;
|
||||
import com.hazelcast.core.IMap;
|
||||
import org.junit.Test;
|
||||
|
||||
import org.springframework.data.redis.connection.jedis.JedisConnectionFactory;
|
||||
import org.springframework.data.redis.connection.lettuce.LettuceConnectionFactory;
|
||||
import org.springframework.jdbc.core.JdbcTemplate;
|
||||
import org.springframework.jdbc.datasource.DataSourceTransactionManager;
|
||||
import org.springframework.mock.web.MockServletContext;
|
||||
import org.springframework.session.ExpiringSession;
|
||||
import org.springframework.session.MapSession;
|
||||
import org.springframework.session.MapSessionRepository;
|
||||
import org.springframework.session.Session;
|
||||
import org.springframework.session.SessionRepository;
|
||||
import org.springframework.session.data.redis.RedisOperationsSessionRepository;
|
||||
import org.springframework.session.hazelcast.HazelcastSessionRepository;
|
||||
import org.springframework.session.jdbc.JdbcOperationsSessionRepository;
|
||||
import org.springframework.session.web.http.SessionRepositoryFilter;
|
||||
import org.springframework.transaction.PlatformTransactionManager;
|
||||
@@ -104,7 +110,7 @@ public class IndexDocTests {
|
||||
@SuppressWarnings("unused")
|
||||
public void newRedisOperationsSessionRepository() {
|
||||
// tag::new-redisoperationssessionrepository[]
|
||||
JedisConnectionFactory factory = new JedisConnectionFactory();
|
||||
LettuceConnectionFactory factory = new LettuceConnectionFactory();
|
||||
SessionRepository<? extends ExpiringSession> repository = new RedisOperationsSessionRepository(
|
||||
factory);
|
||||
// end::new-redisoperationssessionrepository[]
|
||||
@@ -135,6 +141,25 @@ public class IndexDocTests {
|
||||
// end::new-jdbcoperationssessionrepository[]
|
||||
}
|
||||
|
||||
@Test
|
||||
@SuppressWarnings("unused")
|
||||
public void newHazelcastSessionRepository() {
|
||||
// tag::new-hazelcastsessionrepository[]
|
||||
|
||||
Config config = new Config();
|
||||
|
||||
// ... configure Hazelcast ...
|
||||
|
||||
HazelcastInstance hazelcastInstance = Hazelcast.newHazelcastInstance(config);
|
||||
|
||||
IMap<String, MapSession> sessions = hazelcastInstance
|
||||
.getMap("spring:session:sessions");
|
||||
|
||||
HazelcastSessionRepository repository =
|
||||
new HazelcastSessionRepository(sessions);
|
||||
// end::new-hazelcastsessionrepository[]
|
||||
}
|
||||
|
||||
@Test
|
||||
public void runSpringHttpSessionConfig() {
|
||||
AnnotationConfigWebApplicationContext context = new AnnotationConfigWebApplicationContext();
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
@@ -17,21 +17,37 @@
|
||||
package docs.http;
|
||||
|
||||
import com.hazelcast.config.Config;
|
||||
import com.hazelcast.config.MapAttributeConfig;
|
||||
import com.hazelcast.config.MapIndexConfig;
|
||||
import com.hazelcast.core.Hazelcast;
|
||||
import com.hazelcast.core.HazelcastInstance;
|
||||
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.session.hazelcast.HazelcastSessionRepository;
|
||||
import org.springframework.session.hazelcast.PrincipalNameExtractor;
|
||||
import org.springframework.session.hazelcast.config.annotation.web.http.EnableHazelcastHttpSession;
|
||||
|
||||
//tag::config[]
|
||||
@EnableHazelcastHttpSession // <1>
|
||||
@Configuration
|
||||
public class HazelcastHttpSessionConfig {
|
||||
|
||||
@Bean
|
||||
public HazelcastInstance embeddedHazelcast() {
|
||||
Config hazelcastConfig = new Config();
|
||||
return Hazelcast.newHazelcastInstance(hazelcastConfig); // <2>
|
||||
public HazelcastInstance hazelcastInstance() {
|
||||
MapAttributeConfig attributeConfig = new MapAttributeConfig()
|
||||
.setName(HazelcastSessionRepository.PRINCIPAL_NAME_ATTRIBUTE)
|
||||
.setExtractor(PrincipalNameExtractor.class.getName());
|
||||
|
||||
Config config = new Config();
|
||||
|
||||
config.getMapConfig("spring:session:sessions") // <2>
|
||||
.addMapAttributeConfig(attributeConfig)
|
||||
.addMapIndexConfig(new MapIndexConfig(
|
||||
HazelcastSessionRepository.PRINCIPAL_NAME_ATTRIBUTE, false));
|
||||
|
||||
return Hazelcast.newHazelcastInstance(config); // <3>
|
||||
}
|
||||
|
||||
}
|
||||
// end::config[]
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -0,0 +1,78 @@
|
||||
/*
|
||||
* 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
|
||||
*
|
||||
* https://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 docs.security;
|
||||
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
|
||||
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
|
||||
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.session.MapSessionRepository;
|
||||
import org.springframework.session.config.annotation.web.http.EnableSpringHttpSession;
|
||||
import org.springframework.session.security.web.authentication.SpringSessionRememberMeServices;
|
||||
|
||||
/**
|
||||
* @author rwinch
|
||||
*/
|
||||
@EnableWebSecurity
|
||||
@EnableSpringHttpSession
|
||||
public class RememberMeSecurityConfiguration extends WebSecurityConfigurerAdapter {
|
||||
|
||||
// @formatter:off
|
||||
// tag::http-rememberme[]
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
http
|
||||
// ... additional configuration ...
|
||||
.rememberMe()
|
||||
.rememberMeServices(rememberMeServices());
|
||||
// end::http-rememberme[]
|
||||
|
||||
http
|
||||
.formLogin().and()
|
||||
.authorizeRequests()
|
||||
.anyRequest().authenticated();
|
||||
}
|
||||
|
||||
// tag::rememberme-bean[]
|
||||
@Bean
|
||||
public SpringSessionRememberMeServices rememberMeServices() {
|
||||
SpringSessionRememberMeServices rememberMeServices =
|
||||
new SpringSessionRememberMeServices();
|
||||
// optionally customize
|
||||
rememberMeServices.setAlwaysRemember(true);
|
||||
return rememberMeServices;
|
||||
}
|
||||
// end::rememberme-bean[]
|
||||
// @formatter:on
|
||||
|
||||
@Override
|
||||
@Bean
|
||||
public InMemoryUserDetailsManager userDetailsService() {
|
||||
InMemoryUserDetailsManager uds = new InMemoryUserDetailsManager();
|
||||
uds.createUser(
|
||||
User.withUsername("user").password("password").roles("USER").build());
|
||||
return uds;
|
||||
}
|
||||
|
||||
@Bean
|
||||
MapSessionRepository sessionRepository() {
|
||||
return new MapSessionRepository();
|
||||
}
|
||||
}
|
||||
// end::class[]
|
||||
@@ -0,0 +1,88 @@
|
||||
/*
|
||||
* 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.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* https://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 docs.security;
|
||||
|
||||
import java.util.concurrent.TimeUnit;
|
||||
|
||||
import javax.servlet.http.Cookie;
|
||||
|
||||
import org.junit.Before;
|
||||
import org.junit.Test;
|
||||
import org.junit.runner.RunWith;
|
||||
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.session.ExpiringSession;
|
||||
import org.springframework.session.SessionRepository;
|
||||
import org.springframework.session.web.http.SessionRepositoryFilter;
|
||||
import org.springframework.test.context.ContextConfiguration;
|
||||
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
|
||||
import org.springframework.test.context.web.WebAppConfiguration;
|
||||
import org.springframework.test.web.servlet.MockMvc;
|
||||
import org.springframework.test.web.servlet.MvcResult;
|
||||
import org.springframework.test.web.servlet.setup.MockMvcBuilders;
|
||||
import org.springframework.web.context.WebApplicationContext;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
import static org.springframework.security.test.web.servlet.request.SecurityMockMvcRequestBuilders.formLogin;
|
||||
import static org.springframework.security.test.web.servlet.setup.SecurityMockMvcConfigurers.springSecurity;
|
||||
|
||||
/**
|
||||
* @author rwinch
|
||||
*/
|
||||
@RunWith(SpringJUnit4ClassRunner.class)
|
||||
@ContextConfiguration(classes = RememberMeSecurityConfiguration.class)
|
||||
@WebAppConfiguration
|
||||
@SuppressWarnings("rawtypes")
|
||||
public class RememberMeSecurityConfigurationTests<T extends ExpiringSession> {
|
||||
@Autowired
|
||||
WebApplicationContext context;
|
||||
@Autowired
|
||||
SessionRepositoryFilter springSessionRepositoryFilter;
|
||||
@Autowired
|
||||
SessionRepository<T> sessions;
|
||||
|
||||
MockMvc mockMvc;
|
||||
|
||||
@Before
|
||||
public void setup() {
|
||||
// @formatter:off
|
||||
this.mockMvc = MockMvcBuilders
|
||||
.webAppContextSetup(this.context)
|
||||
.addFilters(this.springSessionRepositoryFilter)
|
||||
.apply(springSecurity())
|
||||
.build();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
@Test
|
||||
public void authenticateWhenSpringSessionRememberMeEnabledThenCookieMaxAgeAndSessionExpirationSet()
|
||||
throws Exception {
|
||||
// @formatter:off
|
||||
MvcResult result = this.mockMvc
|
||||
.perform(formLogin())
|
||||
.andReturn();
|
||||
// @formatter:on
|
||||
|
||||
Cookie cookie = result.getResponse().getCookie("SESSION");
|
||||
assertThat(cookie.getMaxAge()).isEqualTo(Integer.MAX_VALUE);
|
||||
T session = this.sessions.getSession(cookie.getValue());
|
||||
assertThat(session.getMaxInactiveIntervalInSeconds())
|
||||
.isEqualTo((int) TimeUnit.DAYS.toSeconds(30));
|
||||
|
||||
}
|
||||
}
|
||||
// end::class[]
|
||||
@@ -0,0 +1,88 @@
|
||||
/*
|
||||
* 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.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* https://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 docs.security;
|
||||
|
||||
import java.util.concurrent.TimeUnit;
|
||||
|
||||
import javax.servlet.http.Cookie;
|
||||
|
||||
import org.junit.Before;
|
||||
import org.junit.Test;
|
||||
import org.junit.runner.RunWith;
|
||||
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.session.ExpiringSession;
|
||||
import org.springframework.session.SessionRepository;
|
||||
import org.springframework.session.web.http.SessionRepositoryFilter;
|
||||
import org.springframework.test.context.ContextConfiguration;
|
||||
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
|
||||
import org.springframework.test.context.web.WebAppConfiguration;
|
||||
import org.springframework.test.web.servlet.MockMvc;
|
||||
import org.springframework.test.web.servlet.MvcResult;
|
||||
import org.springframework.test.web.servlet.setup.MockMvcBuilders;
|
||||
import org.springframework.web.context.WebApplicationContext;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
import static org.springframework.security.test.web.servlet.request.SecurityMockMvcRequestBuilders.formLogin;
|
||||
import static org.springframework.security.test.web.servlet.setup.SecurityMockMvcConfigurers.springSecurity;
|
||||
|
||||
/**
|
||||
* @author rwinch
|
||||
*/
|
||||
@RunWith(SpringJUnit4ClassRunner.class)
|
||||
@ContextConfiguration
|
||||
@WebAppConfiguration
|
||||
@SuppressWarnings("rawtypes")
|
||||
public class RememberMeSecurityConfigurationXmlTests<T extends ExpiringSession> {
|
||||
@Autowired
|
||||
WebApplicationContext context;
|
||||
@Autowired
|
||||
SessionRepositoryFilter springSessionRepositoryFilter;
|
||||
@Autowired
|
||||
SessionRepository<T> sessions;
|
||||
|
||||
MockMvc mockMvc;
|
||||
|
||||
@Before
|
||||
public void setup() {
|
||||
// @formatter:off
|
||||
this.mockMvc = MockMvcBuilders
|
||||
.webAppContextSetup(this.context)
|
||||
.addFilters(this.springSessionRepositoryFilter)
|
||||
.apply(springSecurity())
|
||||
.build();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
@Test
|
||||
public void authenticateWhenSpringSessionRememberMeEnabledThenCookieMaxAgeAndSessionExpirationSet()
|
||||
throws Exception {
|
||||
// @formatter:off
|
||||
MvcResult result = this.mockMvc
|
||||
.perform(formLogin())
|
||||
.andReturn();
|
||||
// @formatter:on
|
||||
|
||||
Cookie cookie = result.getResponse().getCookie("SESSION");
|
||||
assertThat(cookie.getMaxAge()).isEqualTo(Integer.MAX_VALUE);
|
||||
T session = this.sessions.getSession(cookie.getValue());
|
||||
assertThat(session.getMaxInactiveIntervalInSeconds())
|
||||
.isEqualTo((int) TimeUnit.DAYS.toSeconds(30));
|
||||
|
||||
}
|
||||
}
|
||||
// end::class[]
|
||||
@@ -1,11 +1,11 @@
|
||||
/*
|
||||
* Copyright 2014-2016 the original author or authors.
|
||||
* Copyright 2014-2019 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
* https://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,
|
||||
@@ -21,7 +21,6 @@ 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;
|
||||
|
||||
@@ -33,7 +32,7 @@ import org.springframework.session.security.SpringSessionBackedSessionRegistry;
|
||||
public class SecurityConfiguration extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Autowired
|
||||
FindByIndexNameSessionRepository<ExpiringSession> sessionRepository;
|
||||
private FindByIndexNameSessionRepository sessionRepository;
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
@@ -45,7 +44,8 @@ public class SecurityConfiguration extends WebSecurityConfigurerAdapter {
|
||||
}
|
||||
|
||||
@Bean
|
||||
SpringSessionBackedSessionRegistry sessionRegistry() {
|
||||
@SuppressWarnings("unchecked")
|
||||
public SpringSessionBackedSessionRegistry sessionRegistry() {
|
||||
return new SpringSessionBackedSessionRegistry(this.sessionRepository);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -4,9 +4,9 @@
|
||||
xmlns:context="http://www.springframework.org/schema/context"
|
||||
xmlns:p="http://www.springframework.org/schema/p"
|
||||
xmlns:util="http://www.springframework.org/schema/util"
|
||||
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
|
||||
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd
|
||||
http://www.springframework.org/schema/util http://www.springframework.org/schema/util/spring-util-4.1.xsd">
|
||||
xsi:schemaLocation="http://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd
|
||||
http://www.springframework.org/schema/context https://www.springframework.org/schema/context/spring-context.xsd
|
||||
http://www.springframework.org/schema/util https://www.springframework.org/schema/util/spring-util-4.1.xsd">
|
||||
|
||||
<context:annotation-config/>
|
||||
|
||||
|
||||
@@ -4,9 +4,9 @@
|
||||
xmlns:context="http://www.springframework.org/schema/context"
|
||||
xmlns:p="http://www.springframework.org/schema/p"
|
||||
xmlns:util="http://www.springframework.org/schema/util"
|
||||
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
|
||||
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd
|
||||
http://www.springframework.org/schema/util http://www.springframework.org/schema/util/spring-util-4.1.xsd">
|
||||
xsi:schemaLocation="http://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd
|
||||
http://www.springframework.org/schema/context https://www.springframework.org/schema/context/spring-context.xsd
|
||||
http://www.springframework.org/schema/util https://www.springframework.org/schema/util/spring-util-4.1.xsd">
|
||||
|
||||
<!-- tag::config[] -->
|
||||
<bean class="org.springframework.security.web.session.HttpSessionEventPublisher"/>
|
||||
|
||||
@@ -0,0 +1,28 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<beans xmlns="http://www.springframework.org/schema/beans"
|
||||
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||
xmlns:security="http://www.springframework.org/schema/security"
|
||||
xmlns:p="http://www.springframework.org/schema/p"
|
||||
xsi:schemaLocation="http://www.springframework.org/schema/security https://www.springframework.org/schema/security/spring-security.xsd
|
||||
http://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd">
|
||||
|
||||
<!-- tag::config[] -->
|
||||
<security:http>
|
||||
<!-- ... -->
|
||||
<security:form-login />
|
||||
<security:remember-me services-ref="rememberMeServices"/>
|
||||
</security:http>
|
||||
|
||||
<bean id="rememberMeServices"
|
||||
class="org.springframework.session.security.web.authentication.SpringSessionRememberMeServices"
|
||||
p:alwaysRemember="true"/>
|
||||
<!-- end::config[] -->
|
||||
|
||||
|
||||
<security:user-service>
|
||||
<security:user name="user" password="password" authorities="ROLE_USER"/>
|
||||
</security:user-service>
|
||||
|
||||
<bean class="org.springframework.session.config.annotation.web.http.SpringHttpSessionConfiguration"/>
|
||||
<bean id="springSessionRepository" class="org.springframework.session.MapSessionRepository"/>
|
||||
</beans>
|
||||
@@ -2,14 +2,14 @@
|
||||
<beans xmlns="http://www.springframework.org/schema/beans"
|
||||
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||
xmlns:security="http://www.springframework.org/schema/security"
|
||||
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
|
||||
http://www.springframework.org/schema/security http://www.springframework.org/schema/security/spring-security.xsd">
|
||||
xsi:schemaLocation="http://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd
|
||||
http://www.springframework.org/schema/security https://www.springframework.org/schema/security/spring-security.xsd">
|
||||
|
||||
<!-- tag::config[] -->
|
||||
<security:http>
|
||||
<!-- other config goes here... -->
|
||||
<security:session-management>
|
||||
<security:concurrency-control max-sessions="2" session-registry-ref="sessionRegistry"
|
||||
<security:concurrency-control max-sessions="2" session-registry-ref="sessionRegistry"/>
|
||||
</security:session-management>
|
||||
</security:http>
|
||||
|
||||
@@ -19,4 +19,4 @@
|
||||
</bean>
|
||||
<!-- end::config[] -->
|
||||
|
||||
</beans>
|
||||
</beans>
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
<?xml version="1.0"?>
|
||||
<!DOCTYPE module PUBLIC "-//Puppy Crawl//DTD Check Configuration 1.3//EN"
|
||||
"http://www.puppycrawl.com/dtds/configuration_1_3.dtd">
|
||||
"https://www.puppycrawl.com/dtds/configuration_1_3.dtd">
|
||||
<module name="Checker">
|
||||
<!-- Suppressions -->
|
||||
<module name="SuppressionFilter">
|
||||
@@ -75,7 +75,7 @@
|
||||
<module name="AvoidStarImport"/>
|
||||
<module name="AvoidStaticImport">
|
||||
<property name="excludes"
|
||||
value="org.assertj.core.api.Assertions.*, org.mockito.Mockito.*, org.mockito.BDDMockito.*, org.mockito.AdditionalMatchers.*, org.mockito.Matchers.*, org.springframework.test.web.servlet.request.MockMvcRequestBuilders.*, org.springframework.test.web.servlet.result.MockMvcResultHandlers.*, org.springframework.test.web.servlet.result.MockMvcResultMatchers.*, org.springframework.security.test.web.servlet.request.SecurityMockMvcRequestPostProcessors.*, org.springframework.security.test.web.servlet.setup.SecurityMockMvcConfigurers.*, org.springframework.hateoas.mvc.ControllerLinkBuilder.linkTo"/>
|
||||
value="org.assertj.core.api.Assertions.*, org.mockito.Mockito.*, org.mockito.BDDMockito.*, org.mockito.AdditionalMatchers.*, org.mockito.Matchers.*, org.springframework.test.web.servlet.request.MockMvcRequestBuilders.*, org.springframework.test.web.servlet.result.MockMvcResultHandlers.*, org.springframework.test.web.servlet.result.MockMvcResultMatchers.*, org.springframework.security.test.web.servlet.request.SecurityMockMvcRequestPostProcessors.*, org.springframework.security.test.web.servlet.setup.SecurityMockMvcConfigurers.*, org.springframework.security.test.web.servlet.request.SecurityMockMvcRequestBuilders.*, org.springframework.hateoas.mvc.ControllerLinkBuilder.linkTo"/>
|
||||
</module>
|
||||
<module name="IllegalImport"/>
|
||||
<module name="RedundantImport"/>
|
||||
@@ -5,7 +5,7 @@
|
||||
^\Q * you may not use this file except in compliance with the License.\E$
|
||||
^\Q * You may obtain a copy of the License at\E$
|
||||
^\Q *\E$
|
||||
^\Q * http://www.apache.org/licenses/LICENSE-2.0\E$
|
||||
^\Q * https://www.apache.org/licenses/LICENSE-2.0\E$
|
||||
^\Q *\E$
|
||||
^\Q * Unless required by applicable law or agreed to in writing, software\E$
|
||||
^\Q * distributed under the License is distributed on an "AS IS" BASIS,\E$
|
||||
@@ -1,6 +1,6 @@
|
||||
<?xml version="1.0"?>
|
||||
<!DOCTYPE suppressions PUBLIC "-//Puppy Crawl//DTD Suppressions 1.1//EN"
|
||||
"http://www.puppycrawl.com/dtds/suppressions_1_1.dtd">
|
||||
"https://www.puppycrawl.com/dtds/suppressions_1_1.dtd">
|
||||
<suppressions>
|
||||
<suppress files=".+Application\.java" checks="HideUtilityClassConstructor"/>
|
||||
<suppress files=".+Configuration\.java" checks="HideUtilityClassConstructor"/>
|
||||
@@ -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 Boot Java Conventions
|
||||
formatter_profile=Spring Session Java Conventions
|
||||
formatter_settings_version=12
|
||||
org.eclipse.jdt.ui.exception.name=e
|
||||
org.eclipse.jdt.ui.gettersetter.use.is=true
|
||||
@@ -1,29 +1,31 @@
|
||||
bootstrapVersion=2.3.2
|
||||
commonsPoolVersion=2.4.2
|
||||
jacksonVersion=2.6.5
|
||||
jacksonVersion=2.8.8
|
||||
jspApiVersion=2.0
|
||||
servletApiVersion=3.0.1
|
||||
jstlelVersion=1.2.5
|
||||
version=1.3.0.M1
|
||||
springDataRedisVersion=1.7.1.RELEASE
|
||||
version=1.3.6.BUILD-SNAPSHOT
|
||||
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.5.4
|
||||
springDataGeodeVersion=1.0.0.APACHE-GEODE-INCUBATING-M2
|
||||
hazelcastVersion=3.6.8
|
||||
seleniumVersion=2.52.0
|
||||
springSecurityVersion=4.0.3.RELEASE
|
||||
springVersion=4.2.5.RELEASE
|
||||
httpClientVersion=4.5.1
|
||||
jedisVersion=2.8.1
|
||||
h2Version=1.4.192
|
||||
springDataMongoVersion=1.9.1.RELEASE
|
||||
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.1.RELEASE
|
||||
springDataGemFireVersion=1.8.11.RELEASE
|
||||
assertjVersion=2.5.0
|
||||
spockVersion=1.0-groovy-2.4
|
||||
webjarsTaglibVersion=0.3
|
||||
jstlVersion=1.2.1
|
||||
groovyVersion=2.4.4
|
||||
groovyVersion=2.4.11
|
||||
|
||||
3
gradle/bom.gradle
Normal file
3
gradle/bom.gradle
Normal file
@@ -0,0 +1,3 @@
|
||||
sonarqube {
|
||||
skipProject = true
|
||||
}
|
||||
@@ -45,6 +45,9 @@ task cleanEclipseJdtUi(type: Delete) {
|
||||
delete project.file(".settings/org.eclipse.wst.common.project.facet.core.xml")
|
||||
}
|
||||
|
||||
task eclipseConfiguration(dependsOn: [eclipseCheckstyle, eclipseSettings, eclipseWstComponent]) {
|
||||
}
|
||||
|
||||
tasks["eclipseJdt"].dependsOn(eclipseJdtPrepare)
|
||||
tasks["cleanEclipse"].dependsOn(cleanEclipseJdtUi)
|
||||
tasks["eclipse"].dependsOn(eclipseCheckstyle, eclipseSettings, eclipseWstComponent)
|
||||
tasks["eclipse"].dependsOn(eclipseConfiguration)
|
||||
@@ -14,7 +14,7 @@ group = 'org.springframework.session'
|
||||
sourceCompatibility = 1.5
|
||||
targetCompatibility = 1.5
|
||||
|
||||
ext.springIoVersion = project.hasProperty('platformVersion') ? platformVersion : 'latest.integration'
|
||||
ext.springIoVersion = project.hasProperty('platformVersion') ? platformVersion : 'Brussels-BUILD-SNAPSHOT'
|
||||
|
||||
ext.spockDependencies = [
|
||||
dependencies.create("org.spockframework:spock-core:$spockVersion") {
|
||||
@@ -78,7 +78,7 @@ task integrationTest(type: Test, dependsOn: jar) {
|
||||
check.dependsOn integrationTest
|
||||
|
||||
checkstyle {
|
||||
configFile = rootProject.file('config/checkstyle/checkstyle.xml')
|
||||
configFile = rootProject.file('etc/checkstyle/checkstyle.xml')
|
||||
configProperties.configDir = configFile.parentFile
|
||||
toolVersion = '6.16.1'
|
||||
}
|
||||
|
||||
@@ -21,12 +21,12 @@ def customizePom(pom, gradleProject) {
|
||||
url = "https://github.com/spring-projects/spring-session"
|
||||
organization {
|
||||
name = "Spring IO"
|
||||
url = "http://projects.spring.io/spring-session"
|
||||
url = "https://projects.spring.io/spring-session"
|
||||
}
|
||||
licenses {
|
||||
license {
|
||||
name "The Apache Software License, Version 2.0"
|
||||
url "http://www.apache.org/licenses/LICENSE-2.0.txt"
|
||||
url "https://www.apache.org/licenses/LICENSE-2.0.txt"
|
||||
distribution "repo"
|
||||
}
|
||||
}
|
||||
|
||||
@@ -9,6 +9,9 @@ configurations.spring3TestRuntime {
|
||||
&& details.requested.name != 'spring-messaging') {
|
||||
details.useVersion '3.2.14.RELEASE'
|
||||
}
|
||||
if (details.requested.name == 'spring-data-redis') {
|
||||
details.useVersion springDataRedisSpring3Version
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
BIN
gradle/wrapper/gradle-wrapper.jar
vendored
BIN
gradle/wrapper/gradle-wrapper.jar
vendored
Binary file not shown.
4
gradle/wrapper/gradle-wrapper.properties
vendored
4
gradle/wrapper/gradle-wrapper.properties
vendored
@@ -1,6 +1,6 @@
|
||||
#Tue Nov 25 20:57:10 CST 2014
|
||||
#Mon Jan 29 18:35:20 CET 2018
|
||||
distributionBase=GRADLE_USER_HOME
|
||||
distributionPath=wrapper/dists
|
||||
zipStoreBase=GRADLE_USER_HOME
|
||||
zipStorePath=wrapper/dists
|
||||
distributionUrl=https\://services.gradle.org/distributions/gradle-2.10-bin.zip
|
||||
distributionUrl=https\://services.gradle.org/distributions/gradle-3.5.1-bin.zip
|
||||
|
||||
74
gradlew
vendored
74
gradlew
vendored
@@ -1,4 +1,4 @@
|
||||
#!/usr/bin/env bash
|
||||
#!/usr/bin/env sh
|
||||
|
||||
##############################################################################
|
||||
##
|
||||
@@ -6,12 +6,30 @@
|
||||
##
|
||||
##############################################################################
|
||||
|
||||
# Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
|
||||
DEFAULT_JVM_OPTS="-Xmx1024M -XX:MaxPermSize=512M"
|
||||
# Attempt to set APP_HOME
|
||||
# Resolve links: $0 may be a link
|
||||
PRG="$0"
|
||||
# Need this for relative symlinks.
|
||||
while [ -h "$PRG" ] ; do
|
||||
ls=`ls -ld "$PRG"`
|
||||
link=`expr "$ls" : '.*-> \(.*\)$'`
|
||||
if expr "$link" : '/.*' > /dev/null; then
|
||||
PRG="$link"
|
||||
else
|
||||
PRG=`dirname "$PRG"`"/$link"
|
||||
fi
|
||||
done
|
||||
SAVED="`pwd`"
|
||||
cd "`dirname \"$PRG\"`/" >/dev/null
|
||||
APP_HOME="`pwd -P`"
|
||||
cd "$SAVED" >/dev/null
|
||||
|
||||
APP_NAME="Gradle"
|
||||
APP_BASE_NAME=`basename "$0"`
|
||||
|
||||
# Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
|
||||
DEFAULT_JVM_OPTS=""
|
||||
|
||||
# Use the maximum available, or set MAX_FD != -1 to use that value.
|
||||
MAX_FD="maximum"
|
||||
|
||||
@@ -30,6 +48,7 @@ die ( ) {
|
||||
cygwin=false
|
||||
msys=false
|
||||
darwin=false
|
||||
nonstop=false
|
||||
case "`uname`" in
|
||||
CYGWIN* )
|
||||
cygwin=true
|
||||
@@ -40,31 +59,11 @@ case "`uname`" in
|
||||
MINGW* )
|
||||
msys=true
|
||||
;;
|
||||
NONSTOP* )
|
||||
nonstop=true
|
||||
;;
|
||||
esac
|
||||
|
||||
# For Cygwin, ensure paths are in UNIX format before anything is touched.
|
||||
if $cygwin ; then
|
||||
[ -n "$JAVA_HOME" ] && JAVA_HOME=`cygpath --unix "$JAVA_HOME"`
|
||||
fi
|
||||
|
||||
# Attempt to set APP_HOME
|
||||
# Resolve links: $0 may be a link
|
||||
PRG="$0"
|
||||
# Need this for relative symlinks.
|
||||
while [ -h "$PRG" ] ; do
|
||||
ls=`ls -ld "$PRG"`
|
||||
link=`expr "$ls" : '.*-> \(.*\)$'`
|
||||
if expr "$link" : '/.*' > /dev/null; then
|
||||
PRG="$link"
|
||||
else
|
||||
PRG=`dirname "$PRG"`"/$link"
|
||||
fi
|
||||
done
|
||||
SAVED="`pwd`"
|
||||
cd "`dirname \"$PRG\"`/" >&-
|
||||
APP_HOME="`pwd -P`"
|
||||
cd "$SAVED" >&-
|
||||
|
||||
CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar
|
||||
|
||||
# Determine the Java command to use to start the JVM.
|
||||
@@ -90,7 +89,7 @@ location of your Java installation."
|
||||
fi
|
||||
|
||||
# Increase the maximum file descriptors if we can.
|
||||
if [ "$cygwin" = "false" -a "$darwin" = "false" ] ; then
|
||||
if [ "$cygwin" = "false" -a "$darwin" = "false" -a "$nonstop" = "false" ] ; then
|
||||
MAX_FD_LIMIT=`ulimit -H -n`
|
||||
if [ $? -eq 0 ] ; then
|
||||
if [ "$MAX_FD" = "maximum" -o "$MAX_FD" = "max" ] ; then
|
||||
@@ -114,6 +113,7 @@ fi
|
||||
if $cygwin ; then
|
||||
APP_HOME=`cygpath --path --mixed "$APP_HOME"`
|
||||
CLASSPATH=`cygpath --path --mixed "$CLASSPATH"`
|
||||
JAVACMD=`cygpath --unix "$JAVACMD"`
|
||||
|
||||
# We build the pattern for arguments to be converted via cygpath
|
||||
ROOTDIRSRAW=`find -L / -maxdepth 1 -mindepth 1 -type d 2>/dev/null`
|
||||
@@ -154,11 +154,19 @@ if $cygwin ; then
|
||||
esac
|
||||
fi
|
||||
|
||||
# Split up the JVM_OPTS And GRADLE_OPTS values into an array, following the shell quoting and substitution rules
|
||||
function splitJvmOpts() {
|
||||
JVM_OPTS=("$@")
|
||||
# Escape application args
|
||||
save ( ) {
|
||||
for i do printf %s\\n "$i" | sed "s/'/'\\\\''/g;1s/^/'/;\$s/\$/' \\\\/" ; done
|
||||
echo " "
|
||||
}
|
||||
eval splitJvmOpts $DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS
|
||||
JVM_OPTS[${#JVM_OPTS[*]}]="-Dorg.gradle.appname=$APP_BASE_NAME"
|
||||
APP_ARGS=$(save "$@")
|
||||
|
||||
exec "$JAVACMD" "${JVM_OPTS[@]}" -classpath "$CLASSPATH" org.gradle.wrapper.GradleWrapperMain "$@"
|
||||
# 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"
|
||||
|
||||
# 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
|
||||
cd "$(dirname "$0")"
|
||||
fi
|
||||
|
||||
exec "$JAVACMD" "$@"
|
||||
|
||||
14
gradlew.bat
vendored
14
gradlew.bat
vendored
@@ -8,14 +8,14 @@
|
||||
@rem Set local scope for the variables with windows NT shell
|
||||
if "%OS%"=="Windows_NT" setlocal
|
||||
|
||||
@rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
|
||||
set DEFAULT_JVM_OPTS=-Xmx1024M -XX:MaxPermSize=512M
|
||||
|
||||
set DIRNAME=%~dp0
|
||||
if "%DIRNAME%" == "" set DIRNAME=.
|
||||
set APP_BASE_NAME=%~n0
|
||||
set APP_HOME=%DIRNAME%
|
||||
|
||||
@rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
|
||||
set DEFAULT_JVM_OPTS=
|
||||
|
||||
@rem Find java.exe
|
||||
if defined JAVA_HOME goto findJavaFromJavaHome
|
||||
|
||||
@@ -46,10 +46,9 @@ echo location of your Java installation.
|
||||
goto fail
|
||||
|
||||
:init
|
||||
@rem Get command-line arguments, handling Windowz variants
|
||||
@rem Get command-line arguments, handling Windows variants
|
||||
|
||||
if not "%OS%" == "Windows_NT" goto win9xME_args
|
||||
if "%@eval[2+2]" == "4" goto 4NT_args
|
||||
|
||||
:win9xME_args
|
||||
@rem Slurp the command line arguments.
|
||||
@@ -60,11 +59,6 @@ set _SKIP=2
|
||||
if "x%~1" == "x" goto execute
|
||||
|
||||
set CMD_LINE_ARGS=%*
|
||||
goto execute
|
||||
|
||||
:4NT_args
|
||||
@rem Get arguments from the 4NT Shell from JP Software
|
||||
set CMD_LINE_ARGS=%$
|
||||
|
||||
:execute
|
||||
@rem Setup the command line
|
||||
|
||||
@@ -7,25 +7,26 @@ buildscript {
|
||||
}
|
||||
}
|
||||
|
||||
apply plugin: 'spring-boot'
|
||||
apply plugin: 'org.springframework.boot'
|
||||
|
||||
apply from: JAVA_GRADLE
|
||||
apply from: SAMPLE_GRADLE
|
||||
|
||||
group = 'samples'
|
||||
|
||||
ext['spring-security.version'] = springSecurityVersion
|
||||
|
||||
dependencies {
|
||||
compile project(':spring-session'),
|
||||
"org.springframework.boot:spring-boot-starter-redis",
|
||||
"org.springframework.boot:spring-boot-starter-data-redis",
|
||||
"org.springframework.boot:spring-boot-starter-web",
|
||||
"org.springframework.boot:spring-boot-starter-thymeleaf",
|
||||
"org.springframework.boot:spring-boot-starter-security",
|
||||
"nz.net.ultraq.thymeleaf:thymeleaf-layout-dialect",
|
||||
"org.thymeleaf.extras:thymeleaf-extras-conditionalcomments",
|
||||
"org.webjars:bootstrap:$bootstrapVersion",
|
||||
"org.webjars:html5shiv:$html5ShivVersion",
|
||||
"org.webjars:webjars-locator",
|
||||
"org.springframework.security:spring-security-web:$springSecurityVersion",
|
||||
"org.springframework.security:spring-security-config:$springSecurityVersion"
|
||||
"org.webjars:webjars-locator"
|
||||
|
||||
testCompile "org.springframework.boot:spring-boot-starter-test"
|
||||
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
<html xmlns:th="http://www.thymeleaf.org" xmlns:layout="http://www.ultraq.net.nz/thymeleaf/layout" layout:decorator="layout">
|
||||
<html xmlns:th="https://www.thymeleaf.org" xmlns:layout="https://github.com/ultraq/thymeleaf-layout-dialect" layout:decorator="layout">
|
||||
<head>
|
||||
<title>Secured Content</title>
|
||||
</head>
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
<!DOCTYPE html SYSTEM "http://www.thymeleaf.org/dtd/xhtml1-strict-thymeleaf-spring4-3.dtd">
|
||||
<!DOCTYPE html SYSTEM "https://www.thymeleaf.org/dtd/xhtml1-strict-thymeleaf-spring4-3.dtd">
|
||||
<html xmlns="http://www.w3.org/1999/xhtml"
|
||||
xmlns:th="http://www.thymeleaf.org"
|
||||
xmlns:layout="http://www.ultraq.net.nz/thymeleaf/layout">
|
||||
xmlns:th="https://www.thymeleaf.org"
|
||||
xmlns:layout="https://github.com/ultraq/thymeleaf-layout-dialect">
|
||||
<head>
|
||||
<title layout:title-pattern="$DECORATOR_TITLE - $CONTENT_TITLE">Spring Session Sample</title>
|
||||
<link rel="icon" type="image/x-icon" th:href="@{/resources/img/favicon.ico}" href="../static/img/favicon.ico"/>
|
||||
@@ -115,7 +115,7 @@
|
||||
|
||||
<div id="footer">
|
||||
<div class="container">
|
||||
<p class="muted credit">Visit the <a href="http://spring.io/spring-security">Spring Security</a> site for more <a href="https://github.com/spring-projects/spring-security/blob/master/samples/">samples</a>.</p>
|
||||
<p class="muted credit">Visit the <a href="https://spring.io/spring-security">Spring Security</a> site for more <a href="https://github.com/spring-projects/spring-security/blob/master/samples/">samples</a>.</p>
|
||||
</div>
|
||||
</div>
|
||||
</body>
|
||||
|
||||
@@ -3,8 +3,11 @@ apply from: TOMCAT_7_GRADLE
|
||||
apply from: SAMPLE_GRADLE
|
||||
|
||||
dependencies {
|
||||
compile project(':spring-session-data-redis'),
|
||||
"org.springframework:spring-web:$springVersion",
|
||||
compile(project(':spring-session-data-redis')) {
|
||||
exclude module: 'jedis'
|
||||
}
|
||||
compile "org.springframework:spring-web:$springVersion",
|
||||
"biz.paluch.redis:lettuce:$lettuceVersion",
|
||||
"org.webjars:bootstrap:$bootstrapVersion",
|
||||
"org.webjars:webjars-taglib:$webjarsTaglibVersion",
|
||||
jstlDependencies
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
@@ -17,7 +17,7 @@
|
||||
package sample;
|
||||
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.data.redis.connection.jedis.JedisConnectionFactory;
|
||||
import org.springframework.data.redis.connection.lettuce.LettuceConnectionFactory;
|
||||
import org.springframework.session.data.redis.config.annotation.web.http.EnableRedisHttpSession;
|
||||
import org.springframework.session.web.http.CookieSerializer;
|
||||
import org.springframework.session.web.http.DefaultCookieSerializer;
|
||||
@@ -26,8 +26,8 @@ import org.springframework.session.web.http.DefaultCookieSerializer;
|
||||
public class Config {
|
||||
|
||||
@Bean
|
||||
public JedisConnectionFactory connectionFactory() {
|
||||
return new JedisConnectionFactory();
|
||||
public LettuceConnectionFactory connectionFactory() {
|
||||
return new LettuceConnectionFactory();
|
||||
}
|
||||
|
||||
// tag::cookie-serializer[]
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
Demonstrates using Spring Session to lookup a user's session by the username.
|
||||
The sample provides a hook to add the current username to the session (required for finding the user) by providing a custom implementation of Spring Security's `AuthenticationSuccessHandler`.
|
||||
|
||||
NOTE: This product includes GeoLite2 data created by MaxMind, available from http://www.maxmind.com
|
||||
NOTE: This product includes GeoLite2 data created by MaxMind, available from https://www.maxmind.com
|
||||
@@ -7,25 +7,26 @@ buildscript {
|
||||
}
|
||||
}
|
||||
|
||||
apply plugin: 'spring-boot'
|
||||
apply plugin: 'org.springframework.boot'
|
||||
|
||||
apply from: JAVA_GRADLE
|
||||
apply from: SAMPLE_GRADLE
|
||||
|
||||
group = 'samples'
|
||||
|
||||
ext['spring-security.version'] = springSecurityVersion
|
||||
|
||||
dependencies {
|
||||
compile project(':spring-session'),
|
||||
"org.springframework.boot:spring-boot-starter-redis",
|
||||
"org.springframework.boot:spring-boot-starter-data-redis",
|
||||
"org.springframework.boot:spring-boot-starter-web",
|
||||
"org.springframework.boot:spring-boot-starter-security",
|
||||
"org.springframework.boot:spring-boot-starter-thymeleaf",
|
||||
"nz.net.ultraq.thymeleaf:thymeleaf-layout-dialect",
|
||||
"org.thymeleaf.extras:thymeleaf-extras-conditionalcomments",
|
||||
"org.webjars:bootstrap:$bootstrapVersion",
|
||||
"org.webjars:html5shiv:$html5ShivVersion",
|
||||
"org.webjars:webjars-locator",
|
||||
"org.springframework.security:spring-security-web:$springSecurityVersion",
|
||||
"org.springframework.security:spring-security-config:$springSecurityVersion",
|
||||
"com.maxmind.geoip2:geoip2:2.3.1",
|
||||
"org.apache.httpcomponents:httpclient"
|
||||
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* 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
|
||||
* https://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,
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user