[java-plugin-shibd] branch dev/StateMgmtWIP updated: Start removing old code and add discovery unit tests.
Codeberg
noreply at shibboleth.net
Mon Apr 27 19:00:17 UTC 2026
This is an automated email from the git hooks/post-receive script.
codeberg pushed a commit to branch dev/StateMgmtWIP
in repository java-plugin-shibd.
View the commit online:
https://codeberg.org/Shibboleth/java-plugin-shibd/commit/79b96851e838ca91b287f0e60d8ccaf0d8ec40d5
The following commit(s) were added to refs/heads/dev/StateMgmtWIP by this push:
new 79b9685 Start removing old code and add discovery unit tests.
79b9685 is described below
commit 79b96851e838ca91b287f0e60d8ccaf0d8ec40d5
Author: Scott Cantor <scott at restingparrotsoftware.com>
AuthorDate: Mon Apr 27 14:58:57 2026 -0400
Start removing old code and add discovery unit tests.
---
.../idp/flows/sp/initiator/disco/disco-beans.xml | 5 +-
.../net/shibboleth/sp/conf/agents-system.xml | 17 --
.../sp/flows/SessionInitiatorFlowTest.java | 72 +++++++
...SPEnvironmentApplicationContextInitializer.java | 3 +
.../main/java/net/shibboleth/sp/Application.java | 11 --
.../sp/profile/AbstractStateTokenManager.java | 114 -----------
.../shibboleth/sp/profile/StateTokenManager.java | 73 -------
.../net/shibboleth/sp/impl/BasicApplication.java | 36 +---
.../sp/impl/CookieStateTokenManager.java | 183 ------------------
.../sp/impl/PassthroughStateTokenManager.java | 70 -------
.../sp/impl/StorageServiceStateTokenManager.java | 139 --------------
.../sp/profile/impl/IssueCorrelationCookie.java | 202 -------------------
.../sp/profile/impl/MapResourceToStateToken.java | 156 ---------------
.../sp/profile/impl/MapStateTokenToResource.java | 134 -------------
.../sp/profile/impl/ProcessCorrelationCookie.java | 2 +-
.../impl/InitializeAgentRequestContextTest.java | 18 +-
.../sp/impl/CookieStateTokenManagerTest.java | 151 ---------------
.../sp/impl/PassthroughStateTokenManagerTest.java | 69 -------
.../impl/StorageServiceStateTokenManagerTest.java | 80 --------
.../sp/profile/impl/BaseAgentRequestTest.java | 6 -
.../profile/impl/IssueCorrelationCookieTest.java | 163 ----------------
.../profile/impl/MapResourceToStateTokenTest.java | 213 ---------------------
.../profile/impl/ProcessCorrelationCookieTest.java | 2 +-
23 files changed, 87 insertions(+), 1832 deletions(-)
diff --git a/sp-conf-impl/src/main/resources/META-INF/net/shibboleth/idp/flows/sp/initiator/disco/disco-beans.xml b/sp-conf-impl/src/main/resources/META-INF/net/shibboleth/idp/flows/sp/initiator/disco/disco-beans.xml
index 84c31d4..42cacb4 100644
--- a/sp-conf-impl/src/main/resources/META-INF/net/shibboleth/idp/flows/sp/initiator/disco/disco-beans.xml
+++ b/sp-conf-impl/src/main/resources/META-INF/net/shibboleth/idp/flows/sp/initiator/disco/disco-beans.xml
@@ -20,8 +20,9 @@
class="net.shibboleth.sp.profile.impl.PrepareDiscoveryStateDataContext" scope="prototype" />
<bean id="PreserveStateData"
- class="net.shibboleth.sp.profile.impl.PreserveStateDataAction" scope="prototype"
- p:errorFatal="%{sp.stateToken.errorsFatal:false}" />
+ class="net.shibboleth.sp.profile.PreserveStateDataAction" scope="prototype"
+ p:errorFatal="%{sp.stateToken.errorsFatal:false}"
+ p:createOutputObjects="true" />
<bean id="IssueDiscoveryRequest"
class="net.shibboleth.sp.profile.impl.IssueDiscoveryRequest" scope="prototype"
diff --git a/sp-conf-impl/src/main/resources/net/shibboleth/sp/conf/agents-system.xml b/sp-conf-impl/src/main/resources/net/shibboleth/sp/conf/agents-system.xml
index f24a6cc..5669657 100644
--- a/sp-conf-impl/src/main/resources/net/shibboleth/sp/conf/agents-system.xml
+++ b/sp-conf-impl/src/main/resources/net/shibboleth/sp/conf/agents-system.xml
@@ -63,28 +63,11 @@
p:unverifiedConfiguration-ref="DefaultUnverifiedRelyingPartyConfiguration"
p:relyingPartyConfigurations-ref="shibboleth.sp.RelyingPartyOverrides"
p:discoveryServiceLookupStrategy="#{getObject('%{sp.discoveryURLFunction:DefaultDiscoveryServiceStrategy}'.trim())}"
- p:stateTokenManager-ref="#{'%{sp.stateToken.Manager:shibboleth.sp.CookieStateTokenManager}'.trim()}"
- p:stateManager-ref="shibboleth.sp.CookieStateManager" />
- <!--
- // TODO: make this property-driven once we retire the older interface
-
p:stateManager-ref="#{'%{sp.stateToken.Manager:shibboleth.sp.CookieStateManager}'.trim()}" />
- -->
<bean id="shibboleth.sp.Application" class="net.shibboleth.sp.impl.BasicApplication" abstract="true"
p:metricName="net.shibboleth.sp.relyingparty.configurations" />
- <bean id="shibboleth.sp.PassthroughStateTokenManager" class="net.shibboleth.sp.impl.PassthroughStateTokenManager" lazy-init="true" />
-
- <!-- Deprecated, will be removed once we redo the flows. -->
-
- <bean id="shibboleth.sp.StorageStateTokenManager" class="net.shibboleth.sp.impl.StorageServiceStateTokenManager" lazy-init="true"
- p:storageService-ref="#{'%{sp.stateToken.StorageService:shibboleth.StorageService}'.trim()}" />
-
- <bean id="shibboleth.sp.CookieStateTokenManager" class="net.shibboleth.sp.impl.CookieStateTokenManager" lazy-init="true"
- p:cookieManager-ref="shibboleth.sp.RemotedCookieManager"
- p:cookiePrefix="#{'%{sp.stateToken.cookiePrefix:__Host-shibsp_state_}'.trim()}" />
-
<!-- State Managers -->
<bean id="shibboleth.sp.StateManager" abstract="true"
diff --git a/sp-conf-impl/src/test/java/net/shibboleth/sp/flows/SessionInitiatorFlowTest.java b/sp-conf-impl/src/test/java/net/shibboleth/sp/flows/SessionInitiatorFlowTest.java
index 5ca67a4..37eaf3c 100644
--- a/sp-conf-impl/src/test/java/net/shibboleth/sp/flows/SessionInitiatorFlowTest.java
+++ b/sp-conf-impl/src/test/java/net/shibboleth/sp/flows/SessionInitiatorFlowTest.java
@@ -21,11 +21,17 @@ import javax.annotation.Nonnull;
import org.opensaml.profile.action.EventIds;
import org.springframework.webflow.executor.FlowExecutionResult;
+import org.testng.Assert;
import org.testng.annotations.Test;
+import com.google.common.escape.Escaper;
+import com.google.common.net.UrlEscapers;
+
import net.shibboleth.idp.authn.AuthnEventIds;
import net.shibboleth.sp.ddf.DDF;
import net.shibboleth.sp.messaging.RemotedHttpServletRequest;
+import net.shibboleth.sp.messaging.RemotedHttpServletResponse;
+import net.shibboleth.sp.profile.InitiatorConstants;
import net.shibboleth.sp.profile.SPConstants;
/**
@@ -35,6 +41,12 @@ public class SessionInitiatorFlowTest extends AbstractSPFlowTest {
/** Flow ID. */
@Nonnull public static final String FLOW_ID = "sp/session-initiator";
+
+ /** Discovery service. */
+ @Nonnull public static final String DISCO_URL = "https://ds.example.org/DS";
+
+ /** Return URL for discovery. */
+ @Nonnull public static final String DISCO_RETURN_URL = "https://sp.example.org/Login?DS=1";
protected SessionInitiatorFlowTest() {
super(FLOW_ID);
@@ -91,4 +103,64 @@ public class SessionInitiatorFlowTest extends AbstractSPFlowTest {
assertFlowExecutionOutcome(result.getOutcome());
assertOutputMessageEvent(result, AuthnEventIds.NO_POTENTIAL_FLOW);
}
+
+ /**
+ * Test flow with no initiator subflows installed but discovery triggered and no target resource.
+ * @throws IOException
+ */
+ @Test
+ public void testDiscoveryNoTarget() throws IOException {
+ setDefaultAuth();
+
+ final Escaper esc = UrlEscapers.urlFormParameterEscaper();
+
+ final DDF input = new DDF(null).structure();
+ input.addmember(SPConstants.APPLICATION).string(APPLICATION_ID);
+ input.addmember(InitiatorConstants.DISCOVERY_RETURN_URL).string(esc.escape(DISCO_RETURN_URL));
+ input.addmember(RemotedHttpServletRequest.STRUCTURE_NAME).structure();
+ setRequest("POST", input);
+
+ final FlowExecutionResult result = flowExecutor.launchExecution(FLOW_ID, null, externalContext);
+ assertFlowExecutionResult(result, FLOW_ID);
+ assertFlowExecutionOutcome(result.getOutcome());
+
+ final DDF output = assertOutputMessageSuccess(result);
+ final String url = new String(
+ output.getmember(RemotedHttpServletResponse.STRUCTURE_NAME).getmember(RemotedHttpServletResponse.REDIRECT).unsafe_string(),
+ StandardCharsets.UTF_8);
+ assert url != null;
+
+ Assert.assertEquals(url, DISCO_URL + "?return=" + esc.escape(DISCO_RETURN_URL) + "&entityID=" + esc.escape("https://sp.example.org"));
+ }
+
+ /**
+ * Test flow with no initiator subflows installed but discovery triggered and a target resource.
+ * @throws IOException
+ */
+ @Test
+ public void testDiscoveryWithTarget() throws IOException {
+ setDefaultAuth();
+
+ final Escaper esc = UrlEscapers.urlFormParameterEscaper();
+
+ final DDF input = new DDF(null).structure();
+ input.addmember(SPConstants.APPLICATION).string(APPLICATION_ID);
+ input.addmember(InitiatorConstants.DISCOVERY_RETURN_URL).string(esc.escape(DISCO_RETURN_URL));
+ input.addmember(RemotedHttpServletRequest.STRUCTURE_NAME).structure();
+ input.addmember(SPConstants.TARGET).unsafe_string("https://sp.example.org".getBytes(StandardCharsets.UTF_8));
+ setRequest("POST", input);
+
+ final FlowExecutionResult result = flowExecutor.launchExecution(FLOW_ID, null, externalContext);
+ assertFlowExecutionResult(result, FLOW_ID);
+ assertFlowExecutionOutcome(result.getOutcome());
+
+ final DDF output = assertOutputMessageSuccess(result);
+ final String url = new String(
+ output.getmember(RemotedHttpServletResponse.STRUCTURE_NAME).getmember(RemotedHttpServletResponse.REDIRECT).unsafe_string(),
+ StandardCharsets.UTF_8);
+ assert url != null;
+
+ Assert.assertTrue(url.startsWith(DISCO_URL + "?return=" + esc.escape(DISCO_RETURN_URL + "&state=")));
+ }
+
}
\ No newline at end of file
diff --git a/sp-conf-impl/src/test/java/net/shibboleth/sp/flows/TestSPEnvironmentApplicationContextInitializer.java b/sp-conf-impl/src/test/java/net/shibboleth/sp/flows/TestSPEnvironmentApplicationContextInitializer.java
index c602e84..21bd025 100644
--- a/sp-conf-impl/src/test/java/net/shibboleth/sp/flows/TestSPEnvironmentApplicationContextInitializer.java
+++ b/sp-conf-impl/src/test/java/net/shibboleth/sp/flows/TestSPEnvironmentApplicationContextInitializer.java
@@ -37,6 +37,9 @@ public class TestSPEnvironmentApplicationContextInitializer extends TestEnvironm
// Avoids some complex mocking for the default StateManager bean.
mock.setProperty("sp.stateToken.sealed", "false");
+ // Set to allow disco flow to run.
+ mock.setProperty("sp.discoveryURL", "https://ds.example.org/DS");
+
mock.setProperty("sp.storageService", "shibboleth.StorageService");
mock.setProperty("sp.session.storageService", "shibboleth.StorageService");
mock.setProperty("idp.additionalProperties",
diff --git a/sp-server-api/src/main/java/net/shibboleth/sp/Application.java b/sp-server-api/src/main/java/net/shibboleth/sp/Application.java
index 34901c9..e8e14d8 100644
--- a/sp-server-api/src/main/java/net/shibboleth/sp/Application.java
+++ b/sp-server-api/src/main/java/net/shibboleth/sp/Application.java
@@ -30,7 +30,6 @@ import net.shibboleth.idp.attribute.transcoding.AttributeTranscoderRegistry;
import net.shibboleth.profile.relyingparty.RelyingPartyConfigurationResolver;
import net.shibboleth.shared.annotation.constraint.NotEmpty;
import net.shibboleth.shared.service.ReloadableService;
-import net.shibboleth.sp.profile.StateTokenManager;
import net.shibboleth.sp.state.StateManager;
/**
@@ -102,16 +101,6 @@ public interface Application extends RelyingPartyConfigurationResolver {
* @return ordered list of unprefixed flow IDs
*/
@Nonnull List<String> getLogoutInitiators(@Nullable final ProfileRequestContext profileRequestContext);
-
- /**
- * Gets the {@link StateTokenManager} to use for thie application.
- *
- * @return the manager to use
- *
- * @deprecated
- */
- @Deprecated
- @Nonnull StateTokenManager getStateTokenManager();
/**
* Gets the {@link StateManager} to use for thie application.
diff --git a/sp-server-api/src/main/java/net/shibboleth/sp/profile/AbstractStateTokenManager.java b/sp-server-api/src/main/java/net/shibboleth/sp/profile/AbstractStateTokenManager.java
deleted file mode 100644
index 5580661..0000000
--- a/sp-server-api/src/main/java/net/shibboleth/sp/profile/AbstractStateTokenManager.java
+++ /dev/null
@@ -1,114 +0,0 @@
-/*
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package net.shibboleth.sp.profile;
-
-import java.time.Duration;
-
-import javax.annotation.Nonnull;
-
-import net.shibboleth.shared.annotation.constraint.NonnullAfterInit;
-import net.shibboleth.shared.component.AbstractIdentifiableInitializableComponent;
-import net.shibboleth.shared.component.ComponentInitializationException;
-import net.shibboleth.shared.logic.Constraint;
-import net.shibboleth.shared.security.IdentifierGenerationStrategy;
-import net.shibboleth.shared.security.IdentifierGenerationStrategy.ProviderType;
-
-/**
- * Base class for {@link StateTokenManager} implementations.
- *
- * @deprecated
- */
- at Deprecated
-public abstract class AbstractStateTokenManager extends AbstractIdentifiableInitializableComponent
- implements StateTokenManager {
-
- /** Identifier generation. */
- @NonnullAfterInit private IdentifierGenerationStrategy identifierStrategy;
-
- /** Expiration for state token. */
- @Nonnull private Duration expiration;
-
- /**
- * Constructor.
- */
- @SuppressWarnings("null")
- public AbstractStateTokenManager() {
- expiration = Duration.ofMinutes(30);
- }
-
- /**
- * Get {@link IdentifierGenerationStrategy} to use.
- *
- * @return identifier generator strategy
- */
- @NonnullAfterInit public IdentifierGenerationStrategy getIdentifierGenerationStrategy() {
- return identifierStrategy;
- }
-
- /**
- * Set {@link IdentifierGenerationStrategy} to use.
- *
- * <p>Defaults to a secure random source that produces 16 byte values.</p>
- *
- * @param strategy identifier generator strategy
- */
- public void setIdentifierGenerationStrategy(@Nonnull final IdentifierGenerationStrategy strategy) {
- checkSetterPreconditions();
-
- identifierStrategy = Constraint.isNotNull(strategy, "IdentifierGenerationStrategy cannot be null");
- }
-
- /**
- * Get the expiration limit for state tokens.
- *
- * @return expiration limit
- */
- @Nonnull public Duration getExpiration() {
- return expiration;
- }
-
- /**
- * Set the expiration limit for state tokens.
- *
- * <p>Defaults to PT30M.</p>
- *
- * @param exp expiration limit
- */
- public void setExpiration(@Nonnull final Duration exp) {
- checkSetterPreconditions();
-
- expiration = Constraint.isNotNull(exp, "Expiration cannot be null");
- }
-
- /** {@inheritDoc} */
- @Override
- protected void doInitialize() throws ComponentInitializationException {
- super.doInitialize();
-
- if (identifierStrategy == null) {
- identifierStrategy = IdentifierGenerationStrategy.getInstance(ProviderType.SECURE);
- }
- }
-
- /**
- * Generate a state token.
- *
- * @return a new state token
- */
- @Nonnull protected String generateToken() {
- return identifierStrategy.generateIdentifier(false);
- }
-
-}
\ No newline at end of file
diff --git a/sp-server-api/src/main/java/net/shibboleth/sp/profile/StateTokenManager.java b/sp-server-api/src/main/java/net/shibboleth/sp/profile/StateTokenManager.java
deleted file mode 100644
index f542405..0000000
--- a/sp-server-api/src/main/java/net/shibboleth/sp/profile/StateTokenManager.java
+++ /dev/null
@@ -1,73 +0,0 @@
-/*
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package net.shibboleth.sp.profile;
-
-import java.io.IOException;
-
-import javax.annotation.Nonnull;
-import javax.annotation.Nullable;
-
-import net.shibboleth.sp.Agent;
-import net.shibboleth.sp.Application;
-
-/**
- * Interface to a service that manages "state" tokens, used in most SSO protocols
- * to manage stateful request/response correlation and to limit exposure of the
- * resource URLs accessed by clients to allow recovery of the URL for final redirection.
- *
- * <p>SAML refers to this notion as <em>RelayState</em>, while OpenID Connect just refers to it
- * as <em>state</em>.</p>
- *
- * <p>There are multiple possible implementations of this concept, some involving cookies.</p>
- *
- * <p>The value type is a byte array to accomodate non-Unicode data from agents.</p>
- *
- * @deprecated
- */
- at Deprecated
-public interface StateTokenManager {
-
- /**
- * Preserves a value by transforming it into a state token.
- *
- * @param agent agent owning the state
- * @param application application owning the state
- * @param value input value to preserve
- *
- * @return state token representing value
- *
- * @throws IOException if creation of token fails
- */
- @Nonnull String preserveToStateToken(@Nonnull final Agent agent, @Nonnull final Application application,
- @Nonnull final byte[] value) throws IOException;
-
- /**
- * Recovers a value from a state token.
- *
- * <p>In most implementations, the state token mapping should be cleared on successful use of this
- * method.</p>
- *
- * @param agent agent owning the state
- * @param application application owning the state
- * @param token state token
- *
- * @return the recovered value, or null if unable to recover without underlying cause
- *
- * @throws IOException if recovery from token fails
- */
- @Nullable byte[] recoverFromStateToken(@Nonnull final Agent agent, @Nonnull final Application application,
- @Nonnull final String token) throws IOException;
-
-}
\ No newline at end of file
diff --git a/sp-server-impl/src/main/java/net/shibboleth/sp/impl/BasicApplication.java b/sp-server-impl/src/main/java/net/shibboleth/sp/impl/BasicApplication.java
index 5f01f6f..379d41a 100644
--- a/sp-server-impl/src/main/java/net/shibboleth/sp/impl/BasicApplication.java
+++ b/sp-server-impl/src/main/java/net/shibboleth/sp/impl/BasicApplication.java
@@ -58,7 +58,6 @@ import net.shibboleth.shared.service.ReloadableService;
import net.shibboleth.sp.Agent;
import net.shibboleth.sp.Application;
import net.shibboleth.sp.ProtocolSupportService;
-import net.shibboleth.sp.profile.StateTokenManager;
import net.shibboleth.sp.state.StateManager;
import net.shibboleth.spring.security.CredentialHolder;
@@ -97,9 +96,6 @@ public class BasicApplication extends BasicRelyingPartyConfiguration implements
/** Logout initiator list lookup strategy. */
@NonnullAfterInit private Function<ProfileRequestContext,List<String>> logoutInitiatorLookupStrategy;
- /** State token management. */
- @Nullable private StateTokenManager stateTokenManager;
-
/** State management. */
@Nullable private StateManager stateManager;
@@ -382,35 +378,7 @@ public class BasicApplication extends BasicRelyingPartyConfiguration implements
logoutInitiatorLookupStrategy = Constraint.isNotNull(strategy,
"Logout initiators lookup strategy cannot be null");
}
-
- /** {@inheritDoc} */
- @Nonnull public StateTokenManager getStateTokenManager() {
- checkComponentActive();
- if (stateTokenManager != null) {
- return stateTokenManager;
- }
-
- if (parent != null && allowInheritance) {
- return parent.getStateTokenManager();
- }
-
- throw new ConstraintViolationException("StateTokenManager cannot be null");
- }
-
- /**
- * Set the {@link StateTokenManager} to use.
- *
- * @param manager state token manager
- *
- * @deprecated
- */
- @Deprecated
- public void setStateTokenManager(@Nonnull final StateTokenManager manager) {
- checkSetterPreconditions();
- stateTokenManager = Constraint.isNotNull(manager, "StateTokenManager cannot be null");
- }
-
/** {@inheritDoc} */
@Nonnull public StateManager getStateManager() {
checkComponentActive();
@@ -644,9 +612,7 @@ public class BasicApplication extends BasicRelyingPartyConfiguration implements
return;
}
- if (stateTokenManager == null) {
- throw new ComponentInitializationException("StateTokenManager cannot be null");
- } else if (stateManager == null) {
+ if (stateManager == null) {
throw new ComponentInitializationException("StateManager cannot be null");
} else if (transcodingRegistry == null) {
throw new ComponentInitializationException("AttributeTranscoderRegistry cannot be null");
diff --git a/sp-server-impl/src/main/java/net/shibboleth/sp/impl/CookieStateTokenManager.java b/sp-server-impl/src/main/java/net/shibboleth/sp/impl/CookieStateTokenManager.java
deleted file mode 100644
index ab832d3..0000000
--- a/sp-server-impl/src/main/java/net/shibboleth/sp/impl/CookieStateTokenManager.java
+++ /dev/null
@@ -1,183 +0,0 @@
-/*
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package net.shibboleth.sp.impl;
-
-import java.io.IOException;
-import java.security.InvalidAlgorithmParameterException;
-import java.security.NoSuchAlgorithmException;
-import java.time.Instant;
-
-import javax.annotation.Nonnull;
-import javax.annotation.Nullable;
-
-import org.slf4j.Logger;
-
-import net.shibboleth.shared.annotation.constraint.NonnullAfterInit;
-import net.shibboleth.shared.annotation.constraint.NotEmpty;
-import net.shibboleth.shared.codec.Base64Support;
-import net.shibboleth.shared.codec.DecodingException;
-import net.shibboleth.shared.codec.EncodingException;
-import net.shibboleth.shared.component.ComponentInitializationException;
-import net.shibboleth.shared.logic.Constraint;
-import net.shibboleth.shared.net.CookieManager;
-import net.shibboleth.shared.primitive.LoggerFactory;
-import net.shibboleth.shared.primitive.StringSupport;
-import net.shibboleth.shared.security.IdentifierGenerationStrategy;
-import net.shibboleth.shared.security.IdentifierGenerationStrategy.ProviderType;
-import net.shibboleth.shared.security.RandomIdentifierParameterSpec;
-import net.shibboleth.sp.Agent;
-import net.shibboleth.sp.Application;
-import net.shibboleth.sp.profile.AbstractStateTokenManager;
-import net.shibboleth.sp.profile.StateTokenManager;
-
-/**
- * {@link StateTokenManager} implemented using cookies.
- *
- * @deprecated
- */
- at Deprecated
-public class CookieStateTokenManager extends AbstractStateTokenManager {
-
- /** Default cookie prefix. */
- @Nonnull @NotEmpty public static String DEFAULT_PREFIX = "_shibsp_state_";
-
- /** Class logger. */
- @Nonnull private Logger log = LoggerFactory.getLogger(CookieStateTokenManager.class);
-
- /** Cookie manager. */
- @NonnullAfterInit private CookieManager cookieManager;
-
- /** Fixed prefix for cookie names. */
- @Nonnull @NotEmpty private String cookiePrefix;
-
- /** Constructor. */
- public CookieStateTokenManager() {
- cookiePrefix = DEFAULT_PREFIX;
- }
-
- /**
- * Set the fixed prefix to use for the cookies.
- *
- * <p>Defaults to "_shibsp_state".</p>
- *
- * @param prefix cookie prefix
- */
- public void setCookiePrefix(@Nonnull @NotEmpty final String prefix) {
- checkSetterPreconditions();
-
- cookiePrefix = Constraint.isNotNull(StringSupport.trimOrNull(prefix), "Cookie prefix cannot be null or empty");
- }
-
- /**
- * Set the {@link CookieManager} to use.
- *
- * @param manager instance to use
- */
- public void setCookieManager(@Nonnull final CookieManager manager) {
- checkSetterPreconditions();
-
- cookieManager = Constraint.isNotNull(manager, "CookieManager cannot be null");
- }
-
- /** {@inheritDoc} */
- @Override
- protected void doInitialize() throws ComponentInitializationException {
- super.doInitialize();
-
- if (cookieManager == null) {
- throw new ComponentInitializationException("CookieManager cannot be null");
- }
-
- if (getIdentifierGenerationStrategy() == null) {
- final RandomIdentifierParameterSpec spec = new RandomIdentifierParameterSpec(null, 6, null);
- try {
- setIdentifierGenerationStrategy(IdentifierGenerationStrategy.getInstance(ProviderType.SECURE, spec));
- } catch (final InvalidAlgorithmParameterException | NoSuchAlgorithmException e) {
- throw new ComponentInitializationException(e);
- }
- }
- }
-
- /** {@inheritDoc} */
- @Nonnull public String preserveToStateToken(@Nonnull final Agent agent, @Nonnull final Application application,
- @Nonnull final byte[] value) throws IOException {
-
- cookieManager.purgeStaleCookies(cookiePrefix);
-
- final Instant ts = Instant.now();
- assert ts != null;
-
- final String key = Long.toString(ts.toEpochMilli()) + '_' + generateToken();
- final String name = getCookieName(application, key);
- try {
- cookieManager.addCookie(name, Base64Support.encodeURLSafe(value), (int) getExpiration().toSeconds());
- } catch (final EncodingException e) {
- throw new IOException(e);
- }
-
- log.trace("Created state token mapping from '{}' to value '{}'", name, value);
-
- return key;
- }
-
- /** {@inheritDoc} */
- @Nullable public byte[] recoverFromStateToken(@Nonnull final Agent agent, @Nonnull final Application application,
- @Nonnull final String token) throws IOException {
-
- if (token.isEmpty()) {
- log.warn("Invalid state token: '{}'", token);
- return null;
- }
-
- final String cookieName = getCookieName(application, token);
- final String cookieValue = cookieManager.getCookieValue(cookieName, null);
-
- if (cookieValue != null) {
- log.trace("Recovered state token mapping from '{}' to value '{}'", token, cookieValue);
- cookieManager.unsetCookie(cookieName);
- try {
- return Base64Support.decodeURLSafe(cookieValue);
- } catch (final DecodingException e) {
- throw new IOException(e);
- }
- }
-
- log.warn("No cookie found matching state token: '{}'", token);
- return null;
- }
-
- /**
- * Computes the name of a new state cookie.
- *
- * @param application the application
- * @param uniquePortion unique portion of name
- *
- * @return cookie name
- */
- @Nonnull public String getCookieName(@Nonnull final Application application, @Nonnull final String uniquePortion) {
-
- // Format is prefix_appId_timestamp_random
- // The timestamp allows them to be sorted for staleness.
-
- final StringBuilder builder = new StringBuilder(cookiePrefix);
- builder.append('_')
- .append(application.getId())
- .append('_')
- .append(uniquePortion);
-
- return builder.toString();
- }
-
-}
\ No newline at end of file
diff --git a/sp-server-impl/src/main/java/net/shibboleth/sp/impl/PassthroughStateTokenManager.java b/sp-server-impl/src/main/java/net/shibboleth/sp/impl/PassthroughStateTokenManager.java
deleted file mode 100644
index c00b485..0000000
--- a/sp-server-impl/src/main/java/net/shibboleth/sp/impl/PassthroughStateTokenManager.java
+++ /dev/null
@@ -1,70 +0,0 @@
-/*
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package net.shibboleth.sp.impl;
-
-import java.io.IOException;
-
-import javax.annotation.Nonnull;
-import javax.annotation.Nullable;
-
-import org.slf4j.Logger;
-
-import net.shibboleth.shared.codec.Base64Support;
-import net.shibboleth.shared.codec.DecodingException;
-import net.shibboleth.shared.codec.EncodingException;
-import net.shibboleth.shared.component.AbstractIdentifiableInitializableComponent;
-import net.shibboleth.shared.primitive.LoggerFactory;
-import net.shibboleth.sp.Agent;
-import net.shibboleth.sp.Application;
-import net.shibboleth.sp.profile.StateTokenManager;
-
-/**
- * {@link StateTokenManager} implemented as a simple pass-through that doesn't mask the data.
- *
- * @deprecated
- */
- at Deprecated
-public class PassthroughStateTokenManager extends AbstractIdentifiableInitializableComponent
- implements StateTokenManager {
-
- /** Class logger. */
- @Nonnull private Logger log = LoggerFactory.getLogger(PassthroughStateTokenManager.class);
-
- /** {@inheritDoc} */
- @Override
- @Nonnull public String preserveToStateToken(@Nonnull final Agent agent, @Nonnull final Application application,
- @Nonnull final byte[] value) throws IOException {
-
- try {
- return Base64Support.encodeURLSafe(value);
- } catch (final EncodingException e) {
- throw new IOException(e);
- }
- }
-
- /** {@inheritDoc} */
- @Override
- @Nullable public byte[] recoverFromStateToken(@Nonnull final Agent agent, @Nonnull final Application application,
- @Nonnull final String token) throws IOException {
-
- try {
- return Base64Support.decodeURLSafe(token);
- } catch (final DecodingException e) {
- log.warn("Unable to Base64-decode state token: {}", token);
- return null;
- }
- }
-
-}
\ No newline at end of file
diff --git a/sp-server-impl/src/main/java/net/shibboleth/sp/impl/StorageServiceStateTokenManager.java b/sp-server-impl/src/main/java/net/shibboleth/sp/impl/StorageServiceStateTokenManager.java
deleted file mode 100644
index d89a6c1..0000000
--- a/sp-server-impl/src/main/java/net/shibboleth/sp/impl/StorageServiceStateTokenManager.java
+++ /dev/null
@@ -1,139 +0,0 @@
-/*
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package net.shibboleth.sp.impl;
-
-import java.io.IOException;
-import java.time.Instant;
-
-import javax.annotation.Nonnull;
-import javax.annotation.Nullable;
-
-import org.opensaml.storage.StorageRecord;
-import org.opensaml.storage.StorageService;
-import org.slf4j.Logger;
-
-import net.shibboleth.shared.annotation.constraint.NonnullAfterInit;
-import net.shibboleth.shared.codec.Base64Support;
-import net.shibboleth.shared.codec.DecodingException;
-import net.shibboleth.shared.codec.EncodingException;
-import net.shibboleth.shared.component.ComponentInitializationException;
-import net.shibboleth.shared.logic.Constraint;
-import net.shibboleth.shared.primitive.LoggerFactory;
-import net.shibboleth.sp.Agent;
-import net.shibboleth.sp.Application;
-import net.shibboleth.sp.profile.AbstractStateTokenManager;
-import net.shibboleth.sp.profile.StateTokenManager;
-
-/**
- * {@link StateTokenManager} implemented with a {@link StorageService}.
- *
- * @deprecated
- */
- at Deprecated
-public class StorageServiceStateTokenManager extends AbstractStateTokenManager {
-
- /** Class logger. */
- @Nonnull private Logger log = LoggerFactory.getLogger(StorageServiceStateTokenManager.class);
-
- /** Storage back-end. */
- @NonnullAfterInit private StorageService storageService;
-
- /**
- * Set {@link StorageService} to use.
- *
- * @param storage storage service
- */
- public void setStorageService(@Nonnull final StorageService storage) {
- checkSetterPreconditions();
-
- storageService = Constraint.isNotNull(storage, "StorageService cannot be null");
- }
-
- /** {@inheritDoc} */
- @Override
- protected void doInitialize() throws ComponentInitializationException {
- super.doInitialize();
-
- if (storageService == null) {
- throw new ComponentInitializationException("StorageService cannot be null");
- } else if (!storageService.getCapabilities().isServerSide()) {
- throw new ComponentInitializationException("StorageService cannot be client-side");
- }
- }
-
- /** {@inheritDoc} */
- @Override
- @Nonnull public String preserveToStateToken(@Nonnull final Agent agent, @Nonnull final Application application,
- @Nonnull final byte[] value) throws IOException {
-
- final String context = getContext(agent, application);
- final String key = generateToken();
-
- String encoded;
- try {
- encoded = Base64Support.encode(value, false);
- } catch (final EncodingException e) {
- throw new IOException(e);
- }
-
- if (storageService.create(context, key, encoded, Instant.now().plus(getExpiration()).toEpochMilli())) {
- log.trace("Created state token mapping ('{}', '{}') to value '{}'", context, key, encoded);
- return key;
- }
-
- // Should only happen if the randomizer failed...
- throw new IOException("Unable to create storage record for state token");
- }
-
- /** {@inheritDoc} */
- @Override
- @Nullable public byte[] recoverFromStateToken(@Nonnull final Agent agent, @Nonnull final Application application,
- @Nonnull final String token) throws IOException {
-
- final String context = getContext(agent, application);
- final StorageRecord<String> record = storageService.read(context, token);
- if (record != null) {
- log.trace("Recovered state token mapping ('{}', '{}') to value '{}'", context, token, record.getValue());
- try {
- storageService.delete(context, token);
- } catch (final IOException e) {
- log.warn("Unable to delete state token ('{}', '{}') from storage", context, token, e);
- }
- try {
- return Base64Support.decode(record.getValue());
- } catch (final DecodingException e) {
- throw new IOException(e);
- }
- }
-
- return null;
- }
-
- /**
- * Compute the storage context to use.
- *
- * @param agent calling agent
- * @param application calling application
- *
- * @return storage context for request
- */
- @SuppressWarnings("null")
- @Nonnull private String getContext(@Nonnull final Agent agent, @Nonnull final Application application) {
- final StringBuilder builder = new StringBuilder(StorageServiceStateTokenManager.class.getName());
- builder.append('!').append(agent.getId()).append('!').append(application.getId());
- return builder.toString();
- }
-
-}
\ No newline at end of file
diff --git a/sp-server-impl/src/main/java/net/shibboleth/sp/profile/impl/IssueCorrelationCookie.java b/sp-server-impl/src/main/java/net/shibboleth/sp/profile/impl/IssueCorrelationCookie.java
deleted file mode 100644
index 28bc140..0000000
--- a/sp-server-impl/src/main/java/net/shibboleth/sp/profile/impl/IssueCorrelationCookie.java
+++ /dev/null
@@ -1,202 +0,0 @@
-/*
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package net.shibboleth.sp.profile.impl;
-
-import java.util.function.Function;
-
-import javax.annotation.Nonnull;
-
-import org.opensaml.profile.action.ActionSupport;
-import org.opensaml.profile.action.EventIds;
-import org.opensaml.profile.context.ProfileRequestContext;
-import org.slf4j.Logger;
-
-import com.google.common.escape.Escaper;
-import com.google.common.net.UrlEscapers;
-
-import net.shibboleth.shared.annotation.constraint.NonnullAfterInit;
-import net.shibboleth.shared.annotation.constraint.NonnullBeforeExec;
-import net.shibboleth.shared.annotation.constraint.NotEmpty;
-import net.shibboleth.shared.component.ComponentInitializationException;
-import net.shibboleth.shared.logic.Constraint;
-import net.shibboleth.shared.net.CookieManager;
-import net.shibboleth.shared.primitive.LoggerFactory;
-import net.shibboleth.shared.primitive.StringSupport;
-import net.shibboleth.sp.context.AgentRequestContext;
-import net.shibboleth.sp.ddf.DDF;
-import net.shibboleth.sp.messaging.RemotedHttpServletRequestResponseContext;
-import net.shibboleth.sp.profile.AbstractApplicationAction;
-import net.shibboleth.sp.profile.SPConstants;
-
-/**
- * Action that issues a cookie used to record state about a request for
- * later enforcement/evaluation.
- *
- * @event {@link EventIds#PROCEED_EVENT_ID}
- * @event {@link EventIds#INVALID_MESSAGE}
- *
- * @deprecated
- */
- at Deprecated
-public class IssueCorrelationCookie extends AbstractApplicationAction {
-
- /** Default cookie prefix. */
- @Nonnull @NotEmpty static public String DEFAULT_COOKIE_PREFIX = "shibsp_req_";
-
- /** Class logger. */
- @Nonnull private Logger log = LoggerFactory.getLogger(IssueCorrelationCookie.class);
-
- /** Cookie manager. */
- @NonnullAfterInit private CookieManager cookieManager;
-
- /** Cookie prefix. */
- @Nonnull private String cookiePrefix;
-
- /** Whether an error constructing a correlation cookie is fatal. */
- private boolean errorFatal;
-
- /** Lookup strategy for request message ID. */
- @NonnullAfterInit private Function<ProfileRequestContext,String> requestIDLookupStrategy;
-
- /** State token vakue used in cookie name. */
- @NonnullBeforeExec private String stateToken;
-
- /** Request ID. */
- @NonnullBeforeExec private String requestID;
-
- /** Constructor. */
- public IssueCorrelationCookie() {
- cookiePrefix = DEFAULT_COOKIE_PREFIX;
- }
-
- /**
- * Sets the {@link CookieManager} to use.
- *
- * @param manager cookie manager instance
- */
- public void setCookieManager(@Nonnull final CookieManager manager) {
- checkSetterPreconditions();
-
- cookieManager = Constraint.isNotNull(manager, "CookieManager cannot be null");
- }
-
- /**
- * Sets the cookie prefix.
- *
- * <p>Defaults to {@link #DEFAULT_COOKIE_PREFIX}.</p>
- *
- * @param prefix cookie prefix
- */
- public void setCookiePrefix(@Nonnull @NotEmpty final String prefix) {
- checkSetterPreconditions();
-
- cookiePrefix = Constraint.isNotNull(StringSupport.trimOrNull(prefix), "Cookie prefix cannot be null or empty");
- }
-
- /**
- * Sets whether an error computing a state token should result in a fatal event.
- *
- * <p>Defaults to false.</p>
- *
- * @param flag flag to set
- */
- public void setErrorFatal(final boolean flag) {
- checkSetterPreconditions();
-
- errorFatal = flag;
- }
-
- /**
- * Sets the lookup strategy for obtaining the request message's ID.
- *
- * @param strategy lookup strategy
- */
- public void setRequestIDLookupStrategy(@Nonnull final Function<ProfileRequestContext,String> strategy) {
- checkSetterPreconditions();
-
- requestIDLookupStrategy = Constraint.isNotNull(strategy, "Request ID lookup strategy cannot be null");
- }
-
- /** {@inheritDoc} */
- @Override
- protected void doInitialize() throws ComponentInitializationException {
- super.doInitialize();
-
- if (cookieManager == null) {
- throw new ComponentInitializationException("CookieManager cannot be null");
- } else if (requestIDLookupStrategy == null) {
- throw new ComponentInitializationException("Request ID lookup strategy cannot be null");
- }
- }
-
- /** {@inheritDoc} */
- @Override
- protected boolean doPreExecute(@Nonnull final ProfileRequestContext profileRequestContext) {
- if (!super.doPreExecute(profileRequestContext)) {
- return false;
- }
-
- requestID = requestIDLookupStrategy.apply(profileRequestContext);
-
- if (requestID == null) {
- log.debug("{} No request message ID available, skipping creation of correlation cookie", getLogPrefix());
- return false;
- }
-
- final DDF input = ensureAgentRequestContext().getInput();
- if (input != null) {
- stateToken = input.getmember(SPConstants.STATE).string();
- }
-
- if (stateToken == null) {
- if (requestID != null) {
- if (errorFatal) {
- log.warn("{} Input was missing {} parameter", getLogPrefix(), SPConstants.STATE);
- ActionSupport.buildEvent(profileRequestContext, EventIds.INVALID_MESSAGE);
- } else {
- log.debug("{} Input was missing {} parameter, skipping creation of correlation cookie", getLogPrefix(),
- SPConstants.STATE);
- }
- }
- return false;
- }
-
- return true;
- }
-
- /** {@inheritDoc} */
- @Override
- protected void doExecute(@Nonnull final ProfileRequestContext profileRequestContext) {
-
- ensureOutputObjects();
- final AgentRequestContext agentRequestContext = ensureAgentRequestContext();
-
- // We do the crazy stuff to accomodate the cookies being set or unset.
- try {
- RemotedHttpServletRequestResponseContext.loadCurrent(agentRequestContext.getRemotedHttpServletRequest(),
- agentRequestContext.getRemotedHttpServletResponse());
-
- cookieManager.purgeStaleCookies(cookiePrefix);
-
- log.debug("{} Tracking request ID {} against state token {}", getLogPrefix(), requestID, stateToken);
-
- final Escaper escaper = UrlEscapers.urlFormParameterEscaper();
- cookieManager.addCookie(cookiePrefix + escaper.escape(stateToken), escaper.escape(requestID));
- } finally {
- RemotedHttpServletRequestResponseContext.clearCurrent();
- }
- }
-
-}
\ No newline at end of file
diff --git a/sp-server-impl/src/main/java/net/shibboleth/sp/profile/impl/MapResourceToStateToken.java b/sp-server-impl/src/main/java/net/shibboleth/sp/profile/impl/MapResourceToStateToken.java
deleted file mode 100644
index d09afca..0000000
--- a/sp-server-impl/src/main/java/net/shibboleth/sp/profile/impl/MapResourceToStateToken.java
+++ /dev/null
@@ -1,156 +0,0 @@
-/*
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package net.shibboleth.sp.profile.impl;
-
-import java.io.IOException;
-
-import javax.annotation.Nonnull;
-
-import org.opensaml.profile.action.ActionSupport;
-import org.opensaml.profile.action.EventIds;
-import org.opensaml.profile.context.ProfileRequestContext;
-import org.slf4j.Logger;
-
-import net.shibboleth.shared.annotation.constraint.NonnullBeforeExec;
-import net.shibboleth.shared.primitive.LoggerFactory;
-import net.shibboleth.sp.context.AgentRequestContext;
-import net.shibboleth.sp.ddf.DDF;
-import net.shibboleth.sp.messaging.RemotedHttpServletRequestResponseContext;
-import net.shibboleth.sp.profile.AbstractApplicationAction;
-import net.shibboleth.sp.profile.SPConstants;
-
-/**
- * Action that maps a target/resource URL into a state token.
- *
- * <p>The existence of a {@link SPConstants#STATE} member will cause the action
- * to be skipped, while the absence of {@link SPConstants#TARGET} will result in
- * conditional failure.</p>
- *
- * <p>Errors may be ignored or result in an {@link EventIds#IO_ERROR} event.</p>
- *
- * @event {@link EventIds#PROCEED_EVENT_ID}
- * @event {@link EventIds#INVALID_MESSAGE}
- * @event {@link EventIds#IO_ERROR}
- */
-public class MapResourceToStateToken extends AbstractApplicationAction {
-
- /** Class logger. */
- @Nonnull private Logger log = LoggerFactory.getLogger(MapResourceToStateToken.class);
-
- /** Whether an error constructing a state token is fatal. */
- private boolean errorFatal;
-
- /** Whether to require target parameter in the absence of a state token. */
- private boolean targetRequired;
-
- /** Agent input. */
- @NonnullBeforeExec private DDF input;
-
- /** Target resource to operate on. */
- @NonnullBeforeExec private byte[] target;
-
- /** Constructor. */
- public MapResourceToStateToken() {
- targetRequired = true;
- }
-
- /**
- * Sets whether an error computing a state token should result in a fatal event.
- *
- * <p>Defaults to false.</p>
- *
- * @param flag flag to set
- */
- public void setErrorFatal(final boolean flag) {
- checkSetterPreconditions();
-
- errorFatal = flag;
- }
-
- /**
- * Sets whether the {@link SPConstants#TARGET} parameter is required if no state token
- * exists already.
- *
- * <p>Defaults to true.</p>
- *
- * @param flag flag to set
- */
- public void setTargetRequired(final boolean flag) {
- checkSetterPreconditions();
-
- targetRequired = flag;
- }
-
- /** {@inheritDoc} */
- @Override
- protected boolean doPreExecute(@Nonnull final ProfileRequestContext profileRequestContext) {
- if (!super.doPreExecute(profileRequestContext)) {
- return false;
- }
-
- input = ensureAgentRequestContext().getInput();
- if (input == null) {
- log.debug("{} Input message was absent", getLogPrefix());
- return false;
- }
-
- if (input.getmember(SPConstants.STATE).isstring()) {
- log.debug("{} Input message already contains {} parameter", getLogPrefix(), SPConstants.STATE);
- return false;
- }
-
- target = input.getmember(SPConstants.TARGET).unsafe_string();
- if (target == null) {
- if (targetRequired) {
- log.warn("{} Input message did not contain {} member", getLogPrefix(), SPConstants.TARGET);
- ActionSupport.buildEvent(profileRequestContext, EventIds.INVALID_MESSAGE);
- }
- return false;
- }
-
- ensureAgentRequestContext().setTargetURL(target);
- return true;
- }
-
- /** {@inheritDoc} */
- @Override
- protected void doExecute(@Nonnull final ProfileRequestContext profileRequestContext) {
-
- ensureOutputObjects();
-
- final AgentRequestContext agentRequestContext = ensureAgentRequestContext();
-
- // We do the crazy stuff to accomodate cookie-backed state management.
- try {
- RemotedHttpServletRequestResponseContext.loadCurrent(agentRequestContext.getRemotedHttpServletRequest(),
- agentRequestContext.getRemotedHttpServletResponse());
-
- try {
- final String token = ensureApplication().getStateTokenManager().preserveToStateToken(
- ensureAgent(), ensureApplication(), target);
- input.addmember(SPConstants.STATE).string(token);
- log.debug("{} Target resource preserved to state token: {}", getLogPrefix(), token);
- } catch (final IOException e) {
- log.warn("{} Exception preserving target resource to state token", getLogPrefix(), e);
- if (errorFatal) {
- ActionSupport.buildEvent(profileRequestContext, EventIds.IO_ERROR);
- }
- }
- } finally {
- RemotedHttpServletRequestResponseContext.clearCurrent();
- }
- }
-
-}
\ No newline at end of file
diff --git a/sp-server-impl/src/main/java/net/shibboleth/sp/profile/impl/MapStateTokenToResource.java b/sp-server-impl/src/main/java/net/shibboleth/sp/profile/impl/MapStateTokenToResource.java
deleted file mode 100644
index 99ae50b..0000000
--- a/sp-server-impl/src/main/java/net/shibboleth/sp/profile/impl/MapStateTokenToResource.java
+++ /dev/null
@@ -1,134 +0,0 @@
-/*
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package net.shibboleth.sp.profile.impl;
-
-import java.io.IOException;
-import java.util.function.Function;
-
-import javax.annotation.Nonnull;
-
-import org.opensaml.profile.action.EventIds;
-import org.opensaml.profile.context.ProfileRequestContext;
-import org.slf4j.Logger;
-
-import net.shibboleth.shared.annotation.constraint.NonnullAfterInit;
-import net.shibboleth.shared.component.ComponentInitializationException;
-import net.shibboleth.shared.logic.Constraint;
-import net.shibboleth.shared.primitive.LoggerFactory;
-import net.shibboleth.sp.context.AgentRequestContext;
-import net.shibboleth.sp.ddf.DDF;
-import net.shibboleth.sp.messaging.RemotedHttpServletRequestResponseContext;
-import net.shibboleth.sp.profile.AbstractApplicationAction;
-import net.shibboleth.sp.profile.SPConstants;
-
-/**
- * Action that maps a state token into a target/resource URL.
- *
- * <p>The state token comes from a pluggable function.</p>
- *
- * <p>The existence of {@link AgentRequestContext#getTargetURL()} will cause the action
- * to be skipped but the absence of a state token will not result in failure.</p>
- *
- * <p>As a side effect for downstream actions, the state token will be added to the
- * input message in a {@link SPConstants#STATE} field.</p>
- *
- * @event {@link EventIds#PROCEED_EVENT_ID}
- * @event {@link EventIds#INVALID_MESSAGE}
- * @event {@link EventIds#IO_ERROR}
- */
-public class MapStateTokenToResource extends AbstractApplicationAction {
-
- /** Class logger. */
- @Nonnull private Logger log = LoggerFactory.getLogger(MapStateTokenToResource.class);
-
- /** Lookup strategy for state token. */
- @NonnullAfterInit private Function<ProfileRequestContext,String> stateTokenLookupStrategy;
-
- /**
- * Sets the lookup strategy to obtain the protocol specific state token.
- *
- * @param strategy lookup strategy
- */
- public void setStateTokenLookupStrategy(@Nonnull final Function<ProfileRequestContext,String> strategy) {
- checkSetterPreconditions();
- stateTokenLookupStrategy = Constraint.isNotNull(strategy, "State token lookup strategy cannot be null");
- }
-
- /** {@inheritDoc} */
- @Override
- protected void doInitialize() throws ComponentInitializationException {
- super.doInitialize();
-
- if (stateTokenLookupStrategy == null) {
- throw new ComponentInitializationException("State token lookup strategy cannot be null");
- }
- }
-
- /** {@inheritDoc} */
- @Override
- protected boolean doPreExecute(@Nonnull final ProfileRequestContext profileRequestContext) {
- if (!super.doPreExecute(profileRequestContext)) {
- return false;
- }
-
- if (ensureAgentRequestContext().getTargetURL() != null) {
- log.debug("{} Target URL already populated, skipping state token processing", getLogPrefix());
- return false;
- }
-
- return true;
- }
-
- /** {@inheritDoc} */
- @Override
- protected void doExecute(@Nonnull final ProfileRequestContext profileRequestContext) {
-
- ensureOutputObjects();
-
- final AgentRequestContext agentRequestContext = ensureAgentRequestContext();
-
- // We do the crazy stuff to accomodate cookie-backed state management
- // (and to get the relevant state token in the first place).
- try {
- RemotedHttpServletRequestResponseContext.loadCurrent(agentRequestContext.getRemotedHttpServletRequest(),
- agentRequestContext.getRemotedHttpServletResponse());
-
- final String token = stateTokenLookupStrategy.apply(profileRequestContext);
- if (token == null) {
- log.debug("{} No state token returned from lookup strategy, nothing to do", getLogPrefix());
- return;
- }
-
- final DDF input = agentRequestContext.getInput();
- if (input != null) {
- input.addmember(SPConstants.STATE).string(token);
- }
-
- final byte[] target = ensureApplication().getStateTokenManager().recoverFromStateToken(
- ensureAgent(), ensureApplication(), token);
- if (target != null) {
- agentRequestContext.setTargetURL(target);
- log.debug("{} Requested resource recovered from state token: {}", getLogPrefix(), target);
- } else {
- log.warn("{} Unable to recover requested resource from state token", getLogPrefix());
- }
- } catch (final IOException e) {
- log.warn("{} Exception recovering requested resource from state token", getLogPrefix(), e);
- } finally {
- RemotedHttpServletRequestResponseContext.clearCurrent();
- }
- }
-
-}
\ No newline at end of file
diff --git a/sp-server-impl/src/main/java/net/shibboleth/sp/profile/impl/ProcessCorrelationCookie.java b/sp-server-impl/src/main/java/net/shibboleth/sp/profile/impl/ProcessCorrelationCookie.java
index 5e7275b..7b63d65 100644
--- a/sp-server-impl/src/main/java/net/shibboleth/sp/profile/impl/ProcessCorrelationCookie.java
+++ b/sp-server-impl/src/main/java/net/shibboleth/sp/profile/impl/ProcessCorrelationCookie.java
@@ -74,7 +74,7 @@ public class ProcessCorrelationCookie extends AbstractApplicationAction {
/** Constructor. */
public ProcessCorrelationCookie() {
- cookiePrefix = IssueCorrelationCookie.DEFAULT_COOKIE_PREFIX;
+ cookiePrefix = "shibsp_req_";
}
/**
diff --git a/sp-server-impl/src/test/java/net/shibboleth/sp/authn/impl/InitializeAgentRequestContextTest.java b/sp-server-impl/src/test/java/net/shibboleth/sp/authn/impl/InitializeAgentRequestContextTest.java
index ea93a8a..5a9c685 100644
--- a/sp-server-impl/src/test/java/net/shibboleth/sp/authn/impl/InitializeAgentRequestContextTest.java
+++ b/sp-server-impl/src/test/java/net/shibboleth/sp/authn/impl/InitializeAgentRequestContextTest.java
@@ -34,7 +34,6 @@ import net.shibboleth.shared.component.ComponentInitializationException;
import net.shibboleth.shared.testing.MockReloadableService;
import net.shibboleth.sp.context.AgentRequestContext;
import net.shibboleth.sp.impl.BasicAgent;
-import net.shibboleth.sp.impl.PassthroughStateTokenManager;
import net.shibboleth.sp.impl.ProtocolSupportServiceManager;
import net.shibboleth.sp.state.impl.StorageServiceStateManager;
import net.shibboleth.sp.testing.MockAgentResolver;
@@ -62,21 +61,16 @@ public class InitializeAgentRequestContextTest {
agent.setAttributeFilter(new MockReloadableService<>(null));
agent.setAttributeTranscoderRegistry(new MockReloadableService<>(null));
- final PassthroughStateTokenManager manager = new PassthroughStateTokenManager();
- manager.setId("test");
- manager.initialize();
- agent.setStateTokenManager(manager);
-
final MemoryStorageService storage = new MemoryStorageService();
storage.setId("test");
storage.initialize();
- final StorageServiceStateManager manager2 = new StorageServiceStateManager();
- manager2.setId("test");
- manager2.setObjectMapper(new JsonMapper());
- manager2.setStorageService(storage);
- manager2.initialize();
- agent.setStateManager(manager2);
+ final StorageServiceStateManager manager = new StorageServiceStateManager();
+ manager.setId("test");
+ manager.setObjectMapper(new JsonMapper());
+ manager.setStorageService(storage);
+ manager.initialize();
+ agent.setStateManager(manager);
agent.initialize();
diff --git a/sp-server-impl/src/test/java/net/shibboleth/sp/impl/CookieStateTokenManagerTest.java b/sp-server-impl/src/test/java/net/shibboleth/sp/impl/CookieStateTokenManagerTest.java
deleted file mode 100644
index 2952d7a..0000000
--- a/sp-server-impl/src/test/java/net/shibboleth/sp/impl/CookieStateTokenManagerTest.java
+++ /dev/null
@@ -1,151 +0,0 @@
-/*
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package net.shibboleth.sp.impl;
-
-import java.io.IOException;
-import java.time.Instant;
-import java.util.ArrayList;
-import java.util.List;
-
-import javax.annotation.Nonnull;
-
-import org.springframework.mock.web.MockHttpServletRequest;
-import org.springframework.mock.web.MockHttpServletResponse;
-import org.testng.Assert;
-import org.testng.annotations.AfterClass;
-import org.testng.annotations.BeforeClass;
-import org.testng.annotations.BeforeMethod;
-import org.testng.annotations.Test;
-
-import jakarta.servlet.http.Cookie;
-import jakarta.servlet.http.HttpServletRequest;
-import jakarta.servlet.http.HttpServletResponse;
-import net.shibboleth.shared.component.ComponentInitializationException;
-import net.shibboleth.shared.net.CookieManager;
-import net.shibboleth.shared.net.CookieManager.SameSiteValue;
-import net.shibboleth.shared.primitive.NonnullSupplier;
-import net.shibboleth.sp.profile.impl.BaseApplicationActionTest;
-
-/**
- * Unit tests for {@link CookieStateTokenManager}.
- */
- at SuppressWarnings("javadoc")
-public class CookieStateTokenManagerTest extends BaseApplicationActionTest {
-
- private CookieManager cookieManager;
- private CookieStateTokenManager stateManager;
-
- private MockHttpServletRequest request;
- private MockHttpServletResponse response;
-
- @BeforeClass
- public void setUp() throws ComponentInitializationException {
-
- cookieManager = new CookieManager();
- cookieManager.setCookiePath("/");
- cookieManager.setSameSite(SameSiteValue.None);
- cookieManager.setCookieLimit(10);
- cookieManager.setHttpServletRequestSupplier(new NonnullSupplier<HttpServletRequest>() {
- @Nonnull public HttpServletRequest get() {
- assert request != null;
- return request;
- }
- });
- cookieManager.setHttpServletResponseSupplier(new NonnullSupplier<HttpServletResponse>() {
- @Nonnull public HttpServletResponse get() {
- assert response != null;
- return response;
- }
- });
- cookieManager.initialize();
-
- stateManager = new CookieStateTokenManager();
- stateManager.setId("test");
- stateManager.setCookieManager(cookieManager);
-
- stateManager.initialize();
- }
-
- @AfterClass
- public void tearDown() {
- stateManager.destroy();
- cookieManager.destroy();
- }
-
- @BeforeMethod
- public void beforeMethod() throws ComponentInitializationException {
- super.beforeMethod();
-
- request = new MockHttpServletRequest();
- response = new MockHttpServletResponse();
- }
-
- @Test
- public void testMissing() throws IOException {
- request.setCookies(new Cookie(getCookieName(), "foo"));
-
- Assert.assertNull(stateManager.recoverFromStateToken(agent, application, "foo"));
- }
-
- @Test
- public void testPurge() throws IOException, InterruptedException {
-
- final List<Cookie> cookies = new ArrayList<>(12);
- for (int i = 0; i < 12; ++i) {
- cookies.add(new Cookie(getCookieName(), "foo" + i));
- Thread.sleep(250);
- }
- request.setCookies(cookies.toArray(new Cookie[12]));
-
- final String token = stateManager.preserveToStateToken(agent, application, "foo".getBytes());
- assert token != null;
-
- final Cookie[] respCookies = response.getCookies();
- Assert.assertEquals(respCookies.length, 3);
- Assert.assertEquals(respCookies[0].getMaxAge(), 0);
- Assert.assertEquals(respCookies[1].getMaxAge(), 0);
- Assert.assertEquals(respCookies[2].getMaxAge(), stateManager.getExpiration().toSeconds());
- }
-
- @Test
- public void testMapRecover() throws IOException {
-
- final String token = stateManager.preserveToStateToken(agent, application, "foo".getBytes());
- assert token != null;
-
- // Move token set on response to request.
- request = new MockHttpServletRequest();
- request.setCookies(response.getCookies());
- response = new MockHttpServletResponse();
-
- final byte[] original = stateManager.recoverFromStateToken(agent, application, token);
- Assert.assertEquals(original, "foo".getBytes());
-
- // Check that old token is unset.
- final Cookie[] cookies = response.getCookies();
- Assert.assertEquals(cookies.length, 1);
- Assert.assertEquals(cookies[0].getName(), CookieStateTokenManager.DEFAULT_PREFIX + '_' + "test" + '_' + token);
- Assert.assertEquals(cookies[0].getValue(), null);
- Assert.assertEquals(cookies[0].getMaxAge(), 0);
- Assert.assertEquals(cookies[0].getAttribute("SameSite"), SameSiteValue.None.getValue());
- }
-
- @Nonnull private String getCookieName() {
- final Instant now = Instant.now();
- final String rand = stateManager.getIdentifierGenerationStrategy().generateIdentifier(false);
- return stateManager.getCookieName(application, now.toEpochMilli() + '_' + rand);
- }
-
-}
\ No newline at end of file
diff --git a/sp-server-impl/src/test/java/net/shibboleth/sp/impl/PassthroughStateTokenManagerTest.java b/sp-server-impl/src/test/java/net/shibboleth/sp/impl/PassthroughStateTokenManagerTest.java
deleted file mode 100644
index c78bfcb..0000000
--- a/sp-server-impl/src/test/java/net/shibboleth/sp/impl/PassthroughStateTokenManagerTest.java
+++ /dev/null
@@ -1,69 +0,0 @@
-/*
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package net.shibboleth.sp.impl;
-
-import java.io.IOException;
-
-import org.testng.Assert;
-import org.testng.annotations.AfterClass;
-import org.testng.annotations.BeforeClass;
-import org.testng.annotations.BeforeMethod;
-import org.testng.annotations.Test;
-
-import net.shibboleth.shared.component.ComponentInitializationException;
-import net.shibboleth.sp.profile.impl.BaseApplicationActionTest;
-
-/**
- * Unit tests for {@link PassthroughStateTokenManager}.
- */
- at SuppressWarnings("javadoc")
-public class PassthroughStateTokenManagerTest extends BaseApplicationActionTest {
-
- private PassthroughStateTokenManager stateManager;
-
- @BeforeClass
- public void setUp() throws ComponentInitializationException {
-
- stateManager = new PassthroughStateTokenManager();
- stateManager.setId("test");
- stateManager.initialize();
- }
-
- @AfterClass
- public void tearDown() {
- stateManager.destroy();
- }
-
- @BeforeMethod
- public void beforeMethod() throws ComponentInitializationException {
- super.beforeMethod();
- }
-
- @Test
- public void testInvalid() throws IOException {
- Assert.assertNull(stateManager.recoverFromStateToken(agent, application, "123"));
- }
-
- @Test
- public void testMapRecover() throws IOException {
-
- final String token = stateManager.preserveToStateToken(agent, application, "foo".getBytes());
- assert token != null;
-
- final byte[] original = stateManager.recoverFromStateToken(agent, application, token);
- Assert.assertEquals(original, "foo".getBytes());
- }
-
-}
\ No newline at end of file
diff --git a/sp-server-impl/src/test/java/net/shibboleth/sp/impl/StorageServiceStateTokenManagerTest.java b/sp-server-impl/src/test/java/net/shibboleth/sp/impl/StorageServiceStateTokenManagerTest.java
deleted file mode 100644
index e9f1a0c..0000000
--- a/sp-server-impl/src/test/java/net/shibboleth/sp/impl/StorageServiceStateTokenManagerTest.java
+++ /dev/null
@@ -1,80 +0,0 @@
-/*
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package net.shibboleth.sp.impl;
-
-import java.io.IOException;
-import java.time.Duration;
-
-import org.opensaml.storage.impl.MemoryStorageService;
-import org.testng.Assert;
-import org.testng.annotations.AfterClass;
-import org.testng.annotations.BeforeClass;
-import org.testng.annotations.BeforeMethod;
-import org.testng.annotations.Test;
-
-import net.shibboleth.shared.component.ComponentInitializationException;
-import net.shibboleth.sp.profile.impl.BaseApplicationActionTest;
-
-/**
- * Unit tests for {@link StorageServiceStateTokenManager}.
- */
- at SuppressWarnings("javadoc")
-public class StorageServiceStateTokenManagerTest extends BaseApplicationActionTest {
-
- private MemoryStorageService storageService;
- private StorageServiceStateTokenManager stateManager;
-
- @BeforeClass
- public void setUp() throws ComponentInitializationException {
- storageService = new MemoryStorageService();
- storageService.setId("test");
- storageService.setCleanupInterval(Duration.ZERO);
- storageService.initialize();
-
- stateManager = new StorageServiceStateTokenManager();
- stateManager.setStorageService(storageService);
- stateManager.setId("test");
- stateManager.initialize();
- }
-
- @AfterClass
- public void tearDown() {
- stateManager.destroy();
- storageService.destroy();
- }
-
- @BeforeMethod
- public void beforeMethod() throws ComponentInitializationException {
- super.beforeMethod();
- }
-
- @Test
- public void testMissing() throws IOException {
- Assert.assertNull(stateManager.recoverFromStateToken(agent, application, "foo"));
- }
-
- @Test
- public void testMapRecover() throws IOException {
-
- final String token = stateManager.preserveToStateToken(agent, application, "foo".getBytes());
- assert token != null;
-
- final byte[] original = stateManager.recoverFromStateToken(agent, application, token);
- Assert.assertEquals(original, "foo".getBytes());
-
- Assert.assertNull(stateManager.recoverFromStateToken(agent, application, token));
- }
-
-}
\ No newline at end of file
diff --git a/sp-server-impl/src/test/java/net/shibboleth/sp/profile/impl/BaseAgentRequestTest.java b/sp-server-impl/src/test/java/net/shibboleth/sp/profile/impl/BaseAgentRequestTest.java
index 91bdae5..4ff1a39 100644
--- a/sp-server-impl/src/test/java/net/shibboleth/sp/profile/impl/BaseAgentRequestTest.java
+++ b/sp-server-impl/src/test/java/net/shibboleth/sp/profile/impl/BaseAgentRequestTest.java
@@ -27,7 +27,6 @@ import net.shibboleth.shared.component.ComponentInitializationException;
import net.shibboleth.shared.testing.MockReloadableService;
import net.shibboleth.sp.context.AgentRequestContext;
import net.shibboleth.sp.impl.BasicAgent;
-import net.shibboleth.sp.impl.PassthroughStateTokenManager;
import net.shibboleth.sp.impl.ProtocolSupportServiceManager;
import net.shibboleth.sp.state.impl.StorageServiceStateManager;
@@ -57,11 +56,6 @@ public abstract class BaseAgentRequestTest extends OpenSAMLInitBaseTestCase {
agent.setAttributeFilter(new MockReloadableService<>(null));
agent.setAttributeTranscoderRegistry(new MockReloadableService<>(null));
- final PassthroughStateTokenManager manager = new PassthroughStateTokenManager();
- manager.setId("test");
- manager.initialize();
- agent.setStateTokenManager(manager);
-
final MemoryStorageService storage = new MemoryStorageService();
storage.setId("test");
storage.initialize();
diff --git a/sp-server-impl/src/test/java/net/shibboleth/sp/profile/impl/IssueCorrelationCookieTest.java b/sp-server-impl/src/test/java/net/shibboleth/sp/profile/impl/IssueCorrelationCookieTest.java
deleted file mode 100644
index 9a89f89..0000000
--- a/sp-server-impl/src/test/java/net/shibboleth/sp/profile/impl/IssueCorrelationCookieTest.java
+++ /dev/null
@@ -1,163 +0,0 @@
-/*
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package net.shibboleth.sp.profile.impl;
-
-import java.util.ArrayList;
-import java.util.List;
-import java.util.function.Function;
-
-import javax.annotation.Nonnull;
-
-import org.opensaml.profile.action.EventIds;
-import org.opensaml.profile.context.ProfileRequestContext;
-import org.springframework.mock.web.MockHttpServletRequest;
-import org.springframework.mock.web.MockHttpServletResponse;
-import org.springframework.webflow.execution.Event;
-import org.testng.Assert;
-import org.testng.annotations.AfterMethod;
-import org.testng.annotations.BeforeMethod;
-import org.testng.annotations.DataProvider;
-import org.testng.annotations.Test;
-
-import jakarta.servlet.http.Cookie;
-import net.shibboleth.idp.profile.testing.ActionTestingSupport;
-import net.shibboleth.shared.annotation.constraint.NotEmpty;
-import net.shibboleth.shared.codec.DecodingException;
-import net.shibboleth.shared.component.ComponentInitializationException;
-import net.shibboleth.shared.net.CookieManager;
-import net.shibboleth.shared.net.CookieManager.SameSiteValue;
-import net.shibboleth.shared.primitive.NonnullSupplier;
-import net.shibboleth.sp.ddf.DDF;
-import net.shibboleth.sp.profile.SPConstants;
-
-/**
- * Unit test for {@link IssueCorrelationCookie} action.
- */
- at SuppressWarnings("javadoc")
-public class IssueCorrelationCookieTest extends BaseApplicationActionTest {
-
- @Nonnull @NotEmpty private final static String TEST_STATE = "foo";
- @Nonnull @NotEmpty private final static String TEST_ID = "123456789";
-
- private String requestId;
-
- private DDF input;
- private MockHttpServletRequest request;
- private MockHttpServletResponse response;
-
- private CookieManager cookieManager;
- private IssueCorrelationCookie action;
-
- /**
- * Set up test.
- *
- * @throws ComponentInitializationException
- */
- @BeforeMethod
- public void setUp() throws ComponentInitializationException {
- super.beforeMethod();
-
- request = new MockHttpServletRequest();
- response = new MockHttpServletResponse();
-
- cookieManager = new CookieManager();
- cookieManager.setHttpServletRequestSupplier(NonnullSupplier.of(request));
- cookieManager.setHttpServletResponseSupplier(NonnullSupplier.of(response));
- cookieManager.setCookieLimit(10);
- cookieManager.setSameSite(SameSiteValue.None);
- cookieManager.setMaxAge(-1);
- cookieManager.initialize();
-
- action = new IssueCorrelationCookie();
- action.setCookieManager(cookieManager);
- action.setRequestIDLookupStrategy(new Function<>() {
- public String apply(ProfileRequestContext t) {
- return requestId;
- }
- });
-
- action.setErrorFatal(true);
- action.initialize();
-
- input = new DDF(null).structure();
- arc.setInput(input);
- }
-
- /**
- * Tear down test.
- */
- @AfterMethod
- public void tearDown() {
- action.destroy();
- cookieManager.destroy();
- }
-
- @DataProvider
- Object[][] correlationData() {
- return new Object[][] {
- new Object[] { null, TEST_ID},
- new Object[] { TEST_STATE, null},
- new Object[] { TEST_STATE, TEST_ID},
- };
- }
-
- @Test(dataProvider="correlationData")
- public void testAction(final String state, final String id) {
- evaluateAction(state, id);
- }
-
- private void evaluateAction(final String state, final String id) {
- requestId = id;
- if (state != null) {
- input.addmember(SPConstants.STATE).string(state);
- }
-
- final Event event = action.execute(src);
-
- if (state != null) {
- ActionTestingSupport.assertProceedEvent(event);
- } else {
- ActionTestingSupport.assertEvent(event, EventIds.INVALID_MESSAGE);
- return;
- }
-
- if (id == null) {
- Assert.assertEquals(response.getCookies().length, 0);
- return;
- }
-
- final Cookie cookie = response.getCookie(IssueCorrelationCookie.DEFAULT_COOKIE_PREFIX + state);
- assert cookie != null;
- Assert.assertEquals(cookie.getValue(), requestId);
- Assert.assertEquals(cookie.getMaxAge(), -1);
- Assert.assertEquals(cookie.getAttribute("SameSite"), SameSiteValue.None.getValue());
- }
-
- @Test
- public void testPurge() throws ComponentInitializationException, DecodingException, InterruptedException {
-
- final List<Cookie> cookies = new ArrayList<>(12);
- for (int i = 0; i < 12; ++i) {
- cookies.add(new Cookie(IssueCorrelationCookie.DEFAULT_COOKIE_PREFIX + i, "foo" + i));
- Thread.sleep(250);
- }
- request.setCookies(cookies.toArray(new Cookie[12]));
-
- evaluateAction(TEST_STATE, TEST_ID);
-
- Assert.assertEquals(response.getCookies().length, 3);
- }
-
-}
\ No newline at end of file
diff --git a/sp-server-impl/src/test/java/net/shibboleth/sp/profile/impl/MapResourceToStateTokenTest.java b/sp-server-impl/src/test/java/net/shibboleth/sp/profile/impl/MapResourceToStateTokenTest.java
deleted file mode 100644
index a38e959..0000000
--- a/sp-server-impl/src/test/java/net/shibboleth/sp/profile/impl/MapResourceToStateTokenTest.java
+++ /dev/null
@@ -1,213 +0,0 @@
-/*
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package net.shibboleth.sp.profile.impl;
-
-import java.io.IOException;
-import java.nio.charset.StandardCharsets;
-import java.time.Duration;
-
-import javax.annotation.Nonnull;
-
-import org.opensaml.profile.action.EventIds;
-import org.opensaml.storage.impl.MemoryStorageService;
-import org.springframework.mock.web.MockHttpServletRequest;
-import org.springframework.mock.web.MockHttpServletResponse;
-import org.springframework.webflow.execution.Event;
-import org.testng.Assert;
-import org.testng.annotations.AfterMethod;
-import org.testng.annotations.BeforeMethod;
-import org.testng.annotations.Test;
-
-import net.shibboleth.idp.profile.testing.ActionTestingSupport;
-import net.shibboleth.shared.annotation.constraint.NotEmpty;
-import net.shibboleth.shared.codec.Base64Support;
-import net.shibboleth.shared.codec.DecodingException;
-import net.shibboleth.shared.component.ComponentInitializationException;
-import net.shibboleth.shared.net.CookieManager;
-import net.shibboleth.shared.primitive.NonnullSupplier;
-import net.shibboleth.sp.ddf.DDF;
-import net.shibboleth.sp.impl.CookieStateTokenManager;
-import net.shibboleth.sp.impl.PassthroughStateTokenManager;
-import net.shibboleth.sp.impl.StorageServiceStateTokenManager;
-import net.shibboleth.sp.profile.SPConstants;
-
-/**
- * Unit test for {@link MapResourceToStateToken} action.
- */
- at SuppressWarnings("javadoc")
-public class MapResourceToStateTokenTest extends BaseApplicationActionTest {
-
- /** Test request URL. */
- @Nonnull @NotEmpty private final static String TEST_URL = "https://sp.example.org/cgi-bin/test.cgi";
-
- /** Test query string. */
- @Nonnull @NotEmpty private final static String TEST_QUERY = TEST_URL + "?foo=bar%20baz&frobnitz=zorkmid";
-
- private MapResourceToStateToken action;
-
- /**
- * Set up test.
- *
- * @throws ComponentInitializationException
- */
- @BeforeMethod
- public void setUp() throws ComponentInitializationException {
- super.beforeMethod();
-
- action = new MapResourceToStateToken();
- action.initialize();
- }
-
- /**
- * Tear down test.
- */
- @AfterMethod
- public void tearDown() {
- action.destroy();
- }
-
- @Test
- public void testNoTarget() {
- final DDF input = new DDF(null).structure();
- arc.setInput(input);
-
- final Event event = action.execute(src);
- ActionTestingSupport.assertEvent(event, EventIds.INVALID_MESSAGE);
- }
-
- @Test
- public void testStateExists() {
- final DDF input = new DDF(null).structure();
- input.addmember(SPConstants.STATE).string("foo");
- arc.setInput(input);
-
- final Event event = action.execute(src);
- ActionTestingSupport.assertProceedEvent(event);
-
- Assert.assertEquals(input.getmember(SPConstants.STATE).string(), "foo");
- }
-
- @Test
- public void testPassthroughURL() throws ComponentInitializationException, DecodingException {
-
- final PassthroughStateTokenManager manager = new PassthroughStateTokenManager();
- manager.setId("test");
- manager.initialize();
-
- application.setStateTokenManager(manager);
- application.initialize();
-
- final DDF input = new DDF(null).structure();
- input.addmember(SPConstants.TARGET).unsafe_string(TEST_URL.getBytes(StandardCharsets.UTF_8));
- arc.setInput(input);
-
- final Event event = action.execute(src);
- ActionTestingSupport.assertProceedEvent(event);
-
- final String token = input.getmember(SPConstants.STATE).string();
- assert token != null;
-
- Assert.assertEquals(Base64Support.decodeURLSafe(token), TEST_URL.getBytes());
- }
-
- @Test
- public void testPassthroughURLAndQuery() throws ComponentInitializationException, DecodingException {
-
- final PassthroughStateTokenManager manager = new PassthroughStateTokenManager();
- manager.setId("test");
- manager.initialize();
-
- application.setStateTokenManager(manager);
- application.initialize();
-
- final DDF input = new DDF(null).structure();
- input.addmember(SPConstants.TARGET).unsafe_string(TEST_QUERY.getBytes());
- arc.setInput(input);
-
- final Event event = action.execute(src);
- ActionTestingSupport.assertProceedEvent(event);
-
- final String token = input.getmember(SPConstants.STATE).string();
- assert token != null;
-
- Assert.assertEquals(Base64Support.decodeURLSafe(token), TEST_QUERY.getBytes(StandardCharsets.UTF_8));
- }
-
- @Test
- public void testStorageURL() throws ComponentInitializationException, DecodingException, IOException {
-
- final MemoryStorageService storage = new MemoryStorageService();
- storage.setId("test");
- storage.setCleanupInterval(Duration.ZERO);
- storage.initialize();
-
- final StorageServiceStateTokenManager manager = new StorageServiceStateTokenManager();
- manager.setId("test");
- manager.setStorageService(storage);
- manager.initialize();
-
- application.setStateTokenManager(manager);
- application.initialize();
-
- final DDF input = new DDF(null).structure();
- input.addmember(SPConstants.TARGET).unsafe_string(TEST_URL.getBytes(StandardCharsets.UTF_8));
- arc.setInput(input);
-
- final Event event = action.execute(src);
- ActionTestingSupport.assertProceedEvent(event);
-
- final String token = input.getmember(SPConstants.STATE).string();
- assert token != null;
-
- final byte[] value = manager.recoverFromStateToken(agent, application, token);
- Assert.assertEquals(value, TEST_URL.getBytes(StandardCharsets.UTF_8));
- }
-
- @Test
- public void testCookieURL() throws ComponentInitializationException, DecodingException, IOException {
-
- final MockHttpServletRequest request = new MockHttpServletRequest();
- final MockHttpServletResponse response = new MockHttpServletResponse();
-
- final CookieManager cookieManager = new CookieManager();
- cookieManager.setHttpServletRequestSupplier(NonnullSupplier.of(request));
- cookieManager.setHttpServletResponseSupplier(NonnullSupplier.of(response));
- cookieManager.initialize();
-
- final CookieStateTokenManager manager = new CookieStateTokenManager();
- manager.setId("test");
- manager.setCookieManager(cookieManager);
- manager.initialize();
-
- application.setStateTokenManager(manager);
- application.initialize();
-
- final DDF input = new DDF(null).structure();
- input.addmember(SPConstants.TARGET).unsafe_string(TEST_URL.getBytes(StandardCharsets.UTF_8));
- arc.setInput(input);
-
- final Event event = action.execute(src);
- ActionTestingSupport.assertProceedEvent(event);
-
- final String token = input.getmember(SPConstants.STATE).string();
- assert token != null;
-
- request.setCookies(response.getCookies());
-
- final byte[] value = manager.recoverFromStateToken(agent, application, token);
- Assert.assertEquals(value, TEST_URL.getBytes(StandardCharsets.UTF_8));
- }
-
-}
\ No newline at end of file
diff --git a/sp-server-impl/src/test/java/net/shibboleth/sp/profile/impl/ProcessCorrelationCookieTest.java b/sp-server-impl/src/test/java/net/shibboleth/sp/profile/impl/ProcessCorrelationCookieTest.java
index 9c24163..f6e9c0f 100644
--- a/sp-server-impl/src/test/java/net/shibboleth/sp/profile/impl/ProcessCorrelationCookieTest.java
+++ b/sp-server-impl/src/test/java/net/shibboleth/sp/profile/impl/ProcessCorrelationCookieTest.java
@@ -114,7 +114,7 @@ public class ProcessCorrelationCookieTest extends BaseApplicationActionTest {
if (createCookie && token != null) {
final Escaper escaper = UrlEscapers.urlFormParameterEscaper();
- final Cookie cookie = new Cookie(IssueCorrelationCookie.DEFAULT_COOKIE_PREFIX + escaper.escape(token), id);
+ final Cookie cookie = new Cookie("shibsp_req_" + escaper.escape(token), id);
request.setCookies(cookie);
}
--
To stop receiving notification emails like this one, please contact
the administrator of this repository.
More information about the commits
mailing list