Extend IdleTimeoutSessionExpirationPolicy.
Determine expiration timeout in terms of both fixed timeout and idle timeout. If the remaining idle timeout is less than the remaining fixed timeout then return Optional.empty(). Edit Javadoc. Resolves gh-5.
This commit is contained in:
@@ -17,6 +17,7 @@
|
||||
package org.springframework.session.data.gemfire.expiration.support;
|
||||
|
||||
import java.time.Duration;
|
||||
import java.util.Optional;
|
||||
|
||||
import org.springframework.lang.NonNull;
|
||||
import org.springframework.session.Session;
|
||||
@@ -25,34 +26,38 @@ import org.springframework.util.Assert;
|
||||
|
||||
/**
|
||||
* An implementation of the {@link SessionExpirationPolicy} interface that specifies an expiration policy based on
|
||||
* a fixed period of time. That is, the {@link Session} will timeout after a fixed {@link Duration} even if the
|
||||
* {@link Session} is still active.
|
||||
* a {@link Duration fixed duration of time}.
|
||||
*
|
||||
* In other words, the {@link Session} will timeout after a {@link Duration fixed duration of time} even if
|
||||
* the {@link Session} is still active (i.e. not idle).
|
||||
*
|
||||
* @author John Blum
|
||||
* @see java.time.Duration
|
||||
* @see org.springframework.session.Session
|
||||
* @see org.springframework.session.data.gemfire.expiration.SessionExpirationPolicy
|
||||
* @see org.springframework.session.data.gemfire.expiration.support.IdleTimeoutSessionExpirationPolicy
|
||||
* @since 2.1.0
|
||||
*/
|
||||
@SuppressWarnings("unused")
|
||||
public class FixedTimeoutSessionExpirationPolicy implements SessionExpirationPolicy {
|
||||
public class FixedTimeoutSessionExpirationPolicy extends IdleTimeoutSessionExpirationPolicy {
|
||||
|
||||
private final Duration fixedExpirationTimeout;
|
||||
private final Duration fixedTimeout;
|
||||
|
||||
/**
|
||||
* Constructs a new {@link FixedTimeoutSessionExpirationPolicy} initialized with the given
|
||||
* {@link Duration fixed expiration timeout}.
|
||||
* Constructs a new {@link FixedTimeoutSessionExpirationPolicy} initialized with
|
||||
* the given {@link Duration fixed, expiration timeout}.
|
||||
*
|
||||
* @param fixedExpirationTimeout {@link Duration} specifying the fixed length of time until
|
||||
* the {@link Session} expires.
|
||||
* @throws IllegalArgumentException if {@link Duration} is {@literal null}.
|
||||
* @param fixedTimeout {@link Duration fixed length of time} until the {@link Session} will expire.
|
||||
* @throws IllegalArgumentException if the {@link Duration fixed timeout} is {@literal null}.
|
||||
* @see java.time.Duration
|
||||
*/
|
||||
public FixedTimeoutSessionExpirationPolicy(@NonNull Duration fixedExpirationTimeout) {
|
||||
public FixedTimeoutSessionExpirationPolicy(@NonNull Duration fixedTimeout) {
|
||||
|
||||
Assert.notNull(fixedExpirationTimeout, "Fixed expiration timeout is required");
|
||||
super(null);
|
||||
|
||||
this.fixedExpirationTimeout = fixedExpirationTimeout;
|
||||
Assert.notNull(fixedTimeout, "Fixed expiration timeout is required");
|
||||
|
||||
this.fixedTimeout = fixedTimeout;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -61,19 +66,25 @@ public class FixedTimeoutSessionExpirationPolicy implements SessionExpirationPol
|
||||
* @return the configured {@link Duration fixed expiration timeout}.
|
||||
* @see java.time.Duration
|
||||
*/
|
||||
protected Duration getFixedExpirationTimeout() {
|
||||
return this.fixedExpirationTimeout;
|
||||
protected Duration getFixedTimeout() {
|
||||
return this.fixedTimeout;
|
||||
}
|
||||
|
||||
@NonNull @Override
|
||||
public Duration expireAfter(@NonNull Session session) {
|
||||
@Override
|
||||
public Optional<Duration> determineExpirationTimeout(@NonNull Session session) {
|
||||
|
||||
long currentTimeMinusCreationTime =
|
||||
Math.max(System.currentTimeMillis() - session.getCreationTime().toEpochMilli(), 0);
|
||||
Optional<Duration> idleTimeout = super.determineExpirationTimeout(session);
|
||||
|
||||
Duration expirationDuration =
|
||||
getFixedExpirationTimeout().minus(Duration.ofMillis(currentTimeMinusCreationTime));
|
||||
Duration fixedExpirationTimeout = getFixedTimeout().minus(computeTimeSinceCreation(session));
|
||||
|
||||
return expirationDuration.isNegative() ? Duration.ZERO : expirationDuration;
|
||||
return idleTimeout.filter(it -> it.compareTo(fixedExpirationTimeout) <= 0).isPresent()
|
||||
? Optional.empty() : Optional.of(fixedExpirationTimeout);
|
||||
}
|
||||
|
||||
private Duration computeTimeSinceCreation(@NonNull Session session) {
|
||||
|
||||
long timeSinceCreation = Math.max(System.currentTimeMillis() - session.getCreationTime().toEpochMilli(), 0L);
|
||||
|
||||
return Duration.ofMillis(timeSinceCreation);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -34,6 +34,8 @@ import org.springframework.session.Session;
|
||||
* Unit tests for {@link FixedTimeoutSessionExpirationPolicy}.
|
||||
*
|
||||
* @author John Blum
|
||||
* @see java.time.Duration
|
||||
* @see java.time.Instant
|
||||
* @see org.junit.Test
|
||||
* @see org.mockito.Mockito
|
||||
* @see org.springframework.session.Session
|
||||
@@ -45,17 +47,18 @@ public class FixedTimeoutSessionExpirationPolicyUnitTests {
|
||||
@Test
|
||||
public void constructsFixedTimeoutSessionExpirationPolicy() {
|
||||
|
||||
Duration fixedExpirationTimeout = Duration.ofSeconds(60);
|
||||
Duration fixedExpirationTimeout = Duration.ofSeconds(60L);
|
||||
|
||||
FixedTimeoutSessionExpirationPolicy sessionExpirationPolicy =
|
||||
new FixedTimeoutSessionExpirationPolicy(fixedExpirationTimeout);
|
||||
|
||||
assertThat(sessionExpirationPolicy).isNotNull();
|
||||
assertThat(sessionExpirationPolicy.getFixedExpirationTimeout()).isEqualTo(fixedExpirationTimeout);
|
||||
assertThat(sessionExpirationPolicy.getFixedTimeout()).isEqualTo(fixedExpirationTimeout);
|
||||
assertThat(sessionExpirationPolicy.getIdleTimeout().orElse(null)).isNull();
|
||||
}
|
||||
|
||||
@Test(expected = IllegalArgumentException.class)
|
||||
public void constructsFixedTimeoutSessionExpirationPolicyWithNullDuration() {
|
||||
public void constructsFixedTimeoutSessionExpirationPolicyWithNullFixedTimeout() {
|
||||
|
||||
try {
|
||||
new FixedTimeoutSessionExpirationPolicy(null);
|
||||
@@ -70,43 +73,167 @@ public class FixedTimeoutSessionExpirationPolicyUnitTests {
|
||||
}
|
||||
|
||||
@Test
|
||||
public void expireAfterReturnsFutureDuration() {
|
||||
public void determineExpirationTimeoutWithNoIdleTimeoutReturnsExpiredDuration() {
|
||||
|
||||
Duration expirationTimeout = Duration.ofSeconds(30);
|
||||
Duration fixedTimeout = Duration.ofSeconds(30L);
|
||||
|
||||
FixedTimeoutSessionExpirationPolicy sessionExpirationPolicy =
|
||||
new FixedTimeoutSessionExpirationPolicy(expirationTimeout);
|
||||
new FixedTimeoutSessionExpirationPolicy(fixedTimeout);
|
||||
|
||||
assertThat(sessionExpirationPolicy.getFixedTimeout()).isEqualTo(fixedTimeout);
|
||||
assertThat(sessionExpirationPolicy.getIdleTimeout().orElse(null)).isNull();
|
||||
|
||||
Session mockSession = mock(Session.class);
|
||||
|
||||
when(mockSession.getCreationTime())
|
||||
.thenReturn(Instant.ofEpochMilli(System.currentTimeMillis() - Duration.ofSeconds(15).toMillis()));
|
||||
.thenReturn(Instant.ofEpochMilli(System.currentTimeMillis() - Duration.ofSeconds(60L).toMillis()));
|
||||
|
||||
Duration expireAfter = sessionExpirationPolicy.expireAfter(mockSession);
|
||||
Duration expirationTimeout = sessionExpirationPolicy.determineExpirationTimeout(mockSession).orElse(null);
|
||||
|
||||
assertThat(expireAfter).isNotNull();
|
||||
assertThat(expireAfter.getSeconds()).isLessThanOrEqualTo(15);
|
||||
assertThat(expirationTimeout).isNotNull();
|
||||
assertThat(expirationTimeout).isLessThan(Duration.ZERO);
|
||||
|
||||
verify(mockSession, times(1)).getCreationTime();
|
||||
verify(mockSession, never()).getLastAccessedTime();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void expireAfterReturnsZero() {
|
||||
public void determineExpirationTimeoutWithNoIdleTimeoutReturnsNonExpiredDuration() {
|
||||
|
||||
Duration expirationTimeout = Duration.ofSeconds(30);
|
||||
Duration fixedTimeout = Duration.ofSeconds(30L);
|
||||
|
||||
FixedTimeoutSessionExpirationPolicy sessionExpirationPolicy =
|
||||
new FixedTimeoutSessionExpirationPolicy(expirationTimeout);
|
||||
new FixedTimeoutSessionExpirationPolicy(fixedTimeout);
|
||||
|
||||
assertThat(sessionExpirationPolicy.getFixedTimeout()).isEqualTo(fixedTimeout);
|
||||
assertThat(sessionExpirationPolicy.getIdleTimeout().orElse(null)).isNull();
|
||||
|
||||
Session mockSession = mock(Session.class);
|
||||
|
||||
when(mockSession.getCreationTime())
|
||||
.thenReturn(Instant.ofEpochMilli(System.currentTimeMillis() - Duration.ofSeconds(60).toMillis()));
|
||||
.thenReturn(Instant.ofEpochMilli(System.currentTimeMillis() - Duration.ofSeconds(15L).toMillis()));
|
||||
|
||||
Duration expireAfter = sessionExpirationPolicy.expireAfter(mockSession);
|
||||
Duration expirationTimeout = sessionExpirationPolicy.determineExpirationTimeout(mockSession).orElse(null);
|
||||
|
||||
assertThat(expireAfter).isEqualTo(Duration.ZERO);
|
||||
assertThat(expirationTimeout).isNotNull();
|
||||
assertThat(expirationTimeout).isGreaterThan(Duration.ZERO);
|
||||
|
||||
verify(mockSession, times(1)).getCreationTime();
|
||||
verify(mockSession, never()).getLastAccessedTime();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void determineExpirationTimeoutWithLongerIdleTimeoutReturnsExpiredDuration() {
|
||||
|
||||
Duration fixedTimeout = Duration.ofSeconds(60L);
|
||||
Duration idleTimeout = Duration.ofSeconds(30L);
|
||||
|
||||
FixedTimeoutSessionExpirationPolicy sessionExpirationPolicy =
|
||||
new FixedTimeoutSessionExpirationPolicy(fixedTimeout);
|
||||
|
||||
sessionExpirationPolicy.setExpirationTimeout(idleTimeout);
|
||||
|
||||
assertThat(sessionExpirationPolicy.getFixedTimeout()).isEqualTo(fixedTimeout);
|
||||
assertThat(sessionExpirationPolicy.getIdleTimeout().orElse(null)).isEqualTo(idleTimeout);
|
||||
|
||||
Session mockSession = mock(Session.class);
|
||||
|
||||
when(mockSession.getCreationTime())
|
||||
.thenReturn(Instant.ofEpochMilli(System.currentTimeMillis() - Duration.ofSeconds(90L).toMillis()));
|
||||
|
||||
when(mockSession.getLastAccessedTime())
|
||||
.thenReturn(Instant.ofEpochMilli(System.currentTimeMillis() - Duration.ofSeconds(15L).toMillis()));
|
||||
|
||||
Duration expirationTimeout = sessionExpirationPolicy.determineExpirationTimeout(mockSession).orElse(null);
|
||||
|
||||
assertThat(expirationTimeout).isNotNull();
|
||||
assertThat(expirationTimeout).isLessThan(Duration.ZERO);
|
||||
|
||||
verify(mockSession, times(1)).getCreationTime();
|
||||
verify(mockSession, times(1)).getLastAccessedTime();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void determineExpirationTimeoutWithLongerIdleTimeoutReturnsNonExpiredDuration() {
|
||||
|
||||
Duration fixedTimeout = Duration.ofSeconds(60L);
|
||||
Duration idleTimeout = Duration.ofSeconds(30L);
|
||||
|
||||
FixedTimeoutSessionExpirationPolicy sessionExpirationPolicy =
|
||||
new FixedTimeoutSessionExpirationPolicy(fixedTimeout);
|
||||
|
||||
sessionExpirationPolicy.setExpirationTimeout(idleTimeout);
|
||||
|
||||
assertThat(sessionExpirationPolicy.getFixedTimeout()).isEqualTo(fixedTimeout);
|
||||
assertThat(sessionExpirationPolicy.getIdleTimeout().orElse(null)).isEqualTo(idleTimeout);
|
||||
|
||||
Session mockSession = mock(Session.class);
|
||||
|
||||
when(mockSession.getCreationTime())
|
||||
.thenReturn(Instant.ofEpochMilli(System.currentTimeMillis() - Duration.ofSeconds(45L).toMillis()));
|
||||
|
||||
when(mockSession.getLastAccessedTime())
|
||||
.thenReturn(Instant.ofEpochMilli(System.currentTimeMillis() - Duration.ofSeconds(10L).toMillis()));
|
||||
|
||||
Duration expirationTimeout = sessionExpirationPolicy.determineExpirationTimeout(mockSession).orElse(null);
|
||||
|
||||
assertThat(expirationTimeout).isNotNull();
|
||||
assertThat(expirationTimeout).isGreaterThan(Duration.ZERO);
|
||||
|
||||
verify(mockSession, times(1)).getCreationTime();
|
||||
verify(mockSession, times(1)).getLastAccessedTime();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void determineExpirationTimeoutWithShorterTimeoutReturnsNoDuration() {
|
||||
|
||||
Duration fixedTimeout = Duration.ofSeconds(60L);
|
||||
Duration idleTimeout = Duration.ofSeconds(30L);
|
||||
|
||||
FixedTimeoutSessionExpirationPolicy sessionExpirationPolicy =
|
||||
new FixedTimeoutSessionExpirationPolicy(fixedTimeout);
|
||||
|
||||
sessionExpirationPolicy.setExpirationTimeout(idleTimeout);
|
||||
|
||||
assertThat(sessionExpirationPolicy.getFixedTimeout()).isEqualTo(fixedTimeout);
|
||||
assertThat(sessionExpirationPolicy.getIdleTimeout().orElse(null)).isEqualTo(idleTimeout);
|
||||
|
||||
Session mockSession = mock(Session.class);
|
||||
|
||||
when(mockSession.getCreationTime())
|
||||
.thenReturn(Instant.ofEpochMilli(System.currentTimeMillis() - Duration.ofSeconds(30L).toMillis()));
|
||||
|
||||
when(mockSession.getLastAccessedTime())
|
||||
.thenReturn(Instant.ofEpochMilli(System.currentTimeMillis() - Duration.ofSeconds(15L).toMillis()));
|
||||
|
||||
Duration expirationTimeout = sessionExpirationPolicy.determineExpirationTimeout(mockSession).orElse(null);
|
||||
|
||||
assertThat(expirationTimeout).isNull();
|
||||
|
||||
verify(mockSession, times(1)).getCreationTime();
|
||||
verify(mockSession, times(1)).getLastAccessedTime();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void expirationTimeoutIsNotGreaterThanFixedTimeout() {
|
||||
|
||||
Duration fixedTimeout = Duration.ofSeconds(30L);
|
||||
|
||||
FixedTimeoutSessionExpirationPolicy sessionExpirationPolicy =
|
||||
new FixedTimeoutSessionExpirationPolicy(fixedTimeout);
|
||||
|
||||
assertThat(sessionExpirationPolicy.getFixedTimeout()).isEqualTo(fixedTimeout);
|
||||
assertThat(sessionExpirationPolicy.getIdleTimeout().orElse(null)).isNull();
|
||||
|
||||
Session mockSession = mock(Session.class);
|
||||
|
||||
when(mockSession.getCreationTime())
|
||||
.thenReturn(Instant.ofEpochMilli(System.currentTimeMillis() + Duration.ofSeconds(30).toMillis()));
|
||||
|
||||
Duration expirationTimeout = sessionExpirationPolicy.determineExpirationTimeout(mockSession).orElse(null);
|
||||
|
||||
assertThat(expirationTimeout).isNotNull();
|
||||
assertThat(expirationTimeout).isEqualTo(fixedTimeout);
|
||||
|
||||
verify(mockSession, times(1)).getCreationTime();
|
||||
verify(mockSession, never()).getLastAccessedTime();
|
||||
|
||||
Reference in New Issue
Block a user