Picketlink SVN: r1095 - in product/trunk/picketlink-core/src/test: resources and 1 other directory.
by picketlink-commits@lists.jboss.org
Author: anil.saldhana(a)jboss.com
Date: 2011-07-19 09:32:09 -0400 (Tue, 19 Jul 2011)
New Revision: 1095
Removed:
product/trunk/picketlink-core/src/test/java/org/picketlink/test/identity/federation/bindings/workflow/PingFederateResponseTestCase.java.bak
product/trunk/picketlink-core/src/test/resources/responseIDP/
Log:
remove the ping response test
Deleted: product/trunk/picketlink-core/src/test/java/org/picketlink/test/identity/federation/bindings/workflow/PingFederateResponseTestCase.java.bak
===================================================================
--- product/trunk/picketlink-core/src/test/java/org/picketlink/test/identity/federation/bindings/workflow/PingFederateResponseTestCase.java.bak 2011-07-18 22:04:21 UTC (rev 1094)
+++ product/trunk/picketlink-core/src/test/java/org/picketlink/test/identity/federation/bindings/workflow/PingFederateResponseTestCase.java.bak 2011-07-19 13:32:09 UTC (rev 1095)
@@ -1,138 +0,0 @@
-/*
- * JBoss, Home of Professional Open Source.
- * Copyright 2008, Red Hat Middleware LLC, and individual contributors
- * as indicated by the @author tags. See the copyright.txt file in the
- * distribution for a full listing of individual contributors.
- *
- * This is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Lesser General Public License as
- * published by the Free Software Foundation; either version 2.1 of
- * the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public
- * License along with this software; if not, write to the Free
- * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
- * 02110-1301 USA, or see the FSF site: http://www.fsf.org.
- */
-package org.picketlink.test.identity.federation.bindings.workflow;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertNotNull;
-import static org.junit.Assert.assertTrue;
-
-import java.io.ByteArrayOutputStream;
-import java.io.File;
-import java.io.FileInputStream;
-import java.io.IOException;
-import java.io.InputStream;
-import java.io.PrintWriter;
-import java.net.URL;
-import java.util.List;
-import java.util.Map;
-
-import org.apache.catalina.deploy.LoginConfig;
-import org.junit.Test;
-import org.picketlink.identity.federation.bindings.tomcat.sp.SPPostFormAuthenticator;
-import org.picketlink.identity.federation.web.constants.GeneralConstants;
-import org.picketlink.identity.federation.web.util.PostBindingUtil;
-import org.picketlink.test.identity.federation.bindings.mock.MockCatalinaContext;
-import org.picketlink.test.identity.federation.bindings.mock.MockCatalinaContextClassLoader;
-import org.picketlink.test.identity.federation.bindings.mock.MockCatalinaRequest;
-import org.picketlink.test.identity.federation.bindings.mock.MockCatalinaResponse;
-import org.picketlink.test.identity.federation.bindings.mock.MockCatalinaSession;
-
-/**
- * Validating PicketLink SP Handling of
- * a response from Ping Federate IDP.
- *
- * @author Anil.Saldhana(a)redhat.com
- * @since Feb 22, 2011
- */
-public class PingFederateResponseTestCase
-{
- private final String profile = "saml2/post";
-
- private final ClassLoader tcl = Thread.currentThread().getContextClassLoader();
-
- @SuppressWarnings("unchecked")
- @Test
- public void testSP() throws Exception
- {
- MockCatalinaSession session = new MockCatalinaSession();
- //First we go to the employee application
- MockCatalinaContextClassLoader mclSPEmp = setupTCL(profile + "/ping");
- Thread.currentThread().setContextClassLoader(mclSPEmp);
- SPPostFormAuthenticator spEmpl = new SPPostFormAuthenticator();
-
- MockCatalinaContext context = new MockCatalinaContext();
- spEmpl.setContainer(context);
- spEmpl.testStart();
-
- MockCatalinaRequest catalinaRequest = new MockCatalinaRequest();
- catalinaRequest.setSession(session);
- catalinaRequest.setContext(context);
-
- String idpResponse = PostBindingUtil.base64Encode(new String(readIDPResponse()));
-
- catalinaRequest.setParameter(GeneralConstants.SAML_RESPONSE_KEY, idpResponse);
-
- MockCatalinaResponse catalinaResponse = new MockCatalinaResponse();
- ByteArrayOutputStream baos = new ByteArrayOutputStream();
- catalinaResponse.setWriter(new PrintWriter(baos));
-
- LoginConfig loginConfig = new LoginConfig();
- assertTrue(spEmpl.authenticate(catalinaRequest, catalinaResponse, loginConfig));
-
- Map<String, List<Object>> sessionMap = (Map<String, List<Object>>) session
- .getAttribute(GeneralConstants.SESSION_ATTRIBUTE_MAP);
- assertNotNull(sessionMap);
- assertEquals("asptest_email", sessionMap.get("email").get(0));
- assertEquals("asptest_zipcode", sessionMap.get("zipcode").get(0));
- }
-
- private byte[] readIDPResponse() throws IOException
- {
- File file = new File(tcl.getResource("responseIDP/pingidp.xml").getPath());
- InputStream is = new FileInputStream(file);
- assertNotNull(is);
-
- long length = file.length();
-
- // Create the byte array to hold the data
- byte[] bytes = new byte[(int) length];
-
- // Read in the bytes
- int offset = 0;
- int numRead = 0;
- while (offset < bytes.length && (numRead = is.read(bytes, offset, bytes.length - offset)) >= 0)
- {
- offset += numRead;
- }
-
- // Ensure all the bytes have been read in
- if (offset < bytes.length)
- {
- throw new IOException("Could not completely read file " + file.getName());
- }
-
- // Close the input stream and return bytes
- is.close();
- return bytes;
- }
-
- private MockCatalinaContextClassLoader setupTCL(String resource)
- {
- URL[] urls = new URL[]
- {tcl.getResource(resource)};
-
- MockCatalinaContextClassLoader mcl = new MockCatalinaContextClassLoader(urls);
- mcl.setDelegate(tcl);
- mcl.setProfile(resource);
- return mcl;
- }
-}
\ No newline at end of file
13 years, 5 months
Picketlink SVN: r1093 - product.
by picketlink-commits@lists.jboss.org
Author: anil.saldhana(a)jboss.com
Date: 2011-07-18 16:12:59 -0400 (Mon, 18 Jul 2011)
New Revision: 1093
Added:
product/trunk/
Log:
PL product branch
13 years, 5 months
Picketlink SVN: r1092 - /.
by picketlink-commits@lists.jboss.org
Author: anil.saldhana(a)jboss.com
Date: 2011-07-18 16:12:47 -0400 (Mon, 18 Jul 2011)
New Revision: 1092
Added:
product/
Log:
PL product branch
13 years, 5 months
Picketlink SVN: r1091 - in federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core: wstrust/plugins/saml and 1 other directory.
by picketlink-commits@lists.jboss.org
Author: sguilhen(a)redhat.com
Date: 2011-07-14 18:24:22 -0400 (Thu, 14 Jul 2011)
New Revision: 1091
Added:
federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/wstrust/plugins/saml/SAML11TokenProvider.java
Modified:
federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/sts/AbstractSecurityTokenProvider.java
Log:
Fixed logic in AbstractSecurityTokenProvider that prevented the revocation registries from being loaded.
Modified: federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/sts/AbstractSecurityTokenProvider.java
===================================================================
--- federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/sts/AbstractSecurityTokenProvider.java 2011-07-14 15:04:56 UTC (rev 1090)
+++ federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/sts/AbstractSecurityTokenProvider.java 2011-07-14 22:24:22 UTC (rev 1091)
@@ -107,66 +107,64 @@
pae.printStackTrace();
}
}
+ }
+ if (this.tokenRegistry == null)
+ tokenRegistry = new DefaultTokenRegistry();
- if (this.tokenRegistry == null)
- tokenRegistry = new DefaultTokenRegistry();
-
- // check if a revocation registry option has been set.
- String registryOption = this.properties.get(REVOCATION_REGISTRY);
- if (registryOption == null)
+ // check if a revocation registry option has been set.
+ String registryOption = this.properties.get(REVOCATION_REGISTRY);
+ if (registryOption == null)
+ {
+ if (logger.isDebugEnabled())
+ logger.debug("Revocation registry option not specified: cancelled ids will not be persisted!");
+ }
+ else
+ {
+ // if a file is to be used as registry, check if the user has specified the file name.
+ if ("FILE".equalsIgnoreCase(registryOption))
{
- if (logger.isDebugEnabled())
- logger.debug("Revocation registry option not specified: cancelled ids will not be persisted!");
+ String registryFile = this.properties.get(REVOCATION_REGISTRY_FILE);
+ if (registryFile != null)
+ this.revocationRegistry = new FileBasedRevocationRegistry(registryFile);
+ else
+ this.revocationRegistry = new FileBasedRevocationRegistry();
}
+ // another option is to use the default JPA registry to store the revoked ids.
+ else if ("JPA".equalsIgnoreCase(registryOption))
+ {
+ String configuration = this.properties.get(REVOCATION_REGISTRY_JPA_CONFIG);
+ if (configuration != null)
+ this.revocationRegistry = new JPABasedRevocationRegistry(configuration);
+ else
+ this.revocationRegistry = new JPABasedRevocationRegistry();
+ }
+ // the user has specified its own registry implementation class.
else
{
- // if a file is to be used as registry, check if the user has specified the file name.
- if ("FILE".equalsIgnoreCase(registryOption))
+ try
{
- String registryFile = this.properties.get(REVOCATION_REGISTRY_FILE);
- if (registryFile != null)
- this.revocationRegistry = new FileBasedRevocationRegistry(registryFile);
- else
- this.revocationRegistry = new FileBasedRevocationRegistry();
- }
- // another option is to use the default JPA registry to store the revoked ids.
- else if ("JPA".equalsIgnoreCase(registryOption))
- {
- String configuration = this.properties.get(REVOCATION_REGISTRY_JPA_CONFIG);
- if (configuration != null)
- this.revocationRegistry = new JPABasedRevocationRegistry(configuration);
- else
- this.revocationRegistry = new JPABasedRevocationRegistry();
- }
- // the user has specified its own registry implementation class.
- else
- {
- try
+ Class<?> clazz = SecurityActions.loadClass(getClass(), registryOption);
+ if (clazz != null)
{
- Class<?> clazz = SecurityActions.loadClass(getClass(), registryOption);
- if (clazz != null)
+ Object object = clazz.newInstance();
+ if (object instanceof RevocationRegistry)
+ this.revocationRegistry = (RevocationRegistry) object;
+ else
{
- Object object = clazz.newInstance();
- if (object instanceof RevocationRegistry)
- this.revocationRegistry = (RevocationRegistry) object;
- else
- {
- logger.warn(registryOption
- + " is not an instance of RevocationRegistry - using default registry");
- }
+ logger.warn(registryOption
+ + " is not an instance of RevocationRegistry - using default registry");
}
}
- catch (Exception pae)
- {
- logger.warn("Error instantiating revocation registry class - using default registry");
- pae.printStackTrace();
- }
}
+ catch (Exception pae)
+ {
+ logger.warn("Error instantiating revocation registry class - using default registry");
+ pae.printStackTrace();
+ }
}
-
- if (this.revocationRegistry == null)
- this.revocationRegistry = new DefaultRevocationRegistry();
}
- }
+ if (this.revocationRegistry == null)
+ this.revocationRegistry = new DefaultRevocationRegistry();
+ }
}
\ No newline at end of file
Added: federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/wstrust/plugins/saml/SAML11TokenProvider.java
===================================================================
--- federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/wstrust/plugins/saml/SAML11TokenProvider.java (rev 0)
+++ federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/wstrust/plugins/saml/SAML11TokenProvider.java 2011-07-14 22:24:22 UTC (rev 1091)
@@ -0,0 +1,383 @@
+package org.picketlink.identity.federation.core.wstrust.plugins.saml;
+
+import java.net.URI;
+import java.security.Principal;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import javax.xml.namespace.QName;
+
+import org.apache.log4j.Logger;
+import org.picketlink.identity.federation.core.exceptions.ProcessingException;
+import org.picketlink.identity.federation.core.interfaces.ProtocolContext;
+import org.picketlink.identity.federation.core.interfaces.SecurityTokenProvider;
+import org.picketlink.identity.federation.core.saml.v1.SAML11Constants;
+import org.picketlink.identity.federation.core.saml.v2.common.IDGenerator;
+import org.picketlink.identity.federation.core.saml.v2.constants.JBossSAMLConstants;
+import org.picketlink.identity.federation.core.saml.v2.util.AssertionUtil;
+import org.picketlink.identity.federation.core.sts.AbstractSecurityTokenProvider;
+import org.picketlink.identity.federation.core.wstrust.SecurityToken;
+import org.picketlink.identity.federation.core.wstrust.StandardSecurityToken;
+import org.picketlink.identity.federation.core.wstrust.WSTrustConstants;
+import org.picketlink.identity.federation.core.wstrust.WSTrustRequestContext;
+import org.picketlink.identity.federation.core.wstrust.WSTrustUtil;
+import org.picketlink.identity.federation.core.wstrust.wrappers.Lifetime;
+import org.picketlink.identity.federation.saml.v1.assertion.SAML11AssertionType;
+import org.picketlink.identity.federation.saml.v1.assertion.SAML11AudienceRestrictionCondition;
+import org.picketlink.identity.federation.saml.v1.assertion.SAML11AuthenticationStatementType;
+import org.picketlink.identity.federation.saml.v1.assertion.SAML11ConditionsType;
+import org.picketlink.identity.federation.saml.v1.assertion.SAML11NameIdentifierType;
+import org.picketlink.identity.federation.saml.v1.assertion.SAML11StatementAbstractType;
+import org.picketlink.identity.federation.saml.v1.assertion.SAML11SubjectConfirmationType;
+import org.picketlink.identity.federation.saml.v1.assertion.SAML11SubjectType;
+import org.picketlink.identity.federation.ws.policy.AppliesTo;
+import org.picketlink.identity.federation.ws.trust.RequestedReferenceType;
+import org.picketlink.identity.federation.ws.trust.StatusType;
+import org.picketlink.identity.federation.ws.wss.secext.KeyIdentifierType;
+import org.picketlink.identity.xmlsec.w3.xmldsig.KeyInfoType;
+import org.w3c.dom.Element;
+
+public class SAML11TokenProvider extends AbstractSecurityTokenProvider
+{
+ protected static Logger logger = Logger.getLogger(SAML11TokenProvider.class);
+
+ /*
+ * (non-Javadoc)
+ *
+ * @seeorg.picketlink.identity.federation.core.interfaces.SecurityTokenProvider#cancelToken(org.picketlink.identity.
+ * federation.core.interfaces.ProtocolContext)
+ */
+ @Override
+ public void cancelToken(ProtocolContext context) throws ProcessingException
+ {
+ if (!(context instanceof WSTrustRequestContext))
+ return;
+
+ WSTrustRequestContext wstContext = (WSTrustRequestContext) context;
+
+ // get the SAML assertion that will be canceled.
+ Element token = wstContext.getRequestSecurityToken().getCancelTargetElement();
+ if (token == null)
+ throw new ProcessingException("Invalid cancel request: missing required CancelTarget");
+ Element assertionElement = (Element) token.getFirstChild();
+ if (!this.isSAMLAssertion(assertionElement))
+ throw new ProcessingException("CancelTarget doesn't not contain a SAMLV1.1 assertion");
+
+ // get the assertion ID and add it to the canceled assertions set.
+ String assertionId = assertionElement.getAttribute("AssertionID");
+ this.revocationRegistry.revokeToken(SAMLUtil.SAML11_TOKEN_TYPE, assertionId);
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see
+ * org.picketlink.identity.federation.core.interfaces.SecurityTokenProvider#issueToken(org.picketlink.identity.federation
+ * .core.interfaces.ProtocolContext)
+ */
+ @Override
+ public void issueToken(ProtocolContext context) throws ProcessingException
+ {
+ if (!(context instanceof WSTrustRequestContext))
+ return;
+
+ WSTrustRequestContext wstContext = (WSTrustRequestContext) context;
+ // generate an id for the new assertion.
+ String assertionID = IDGenerator.create("ID_");
+
+ // lifetime and audience restrictions.
+ Lifetime lifetime = wstContext.getRequestSecurityToken().getLifetime();
+ SAML11AudienceRestrictionCondition restriction = null;
+ AppliesTo appliesTo = wstContext.getRequestSecurityToken().getAppliesTo();
+ if (appliesTo != null)
+ {
+ restriction = new SAML11AudienceRestrictionCondition();
+ restriction.add(URI.create(WSTrustUtil.parseAppliesTo(appliesTo)));
+ }
+ SAML11ConditionsType conditions = new SAML11ConditionsType();
+ conditions.setNotBefore(lifetime.getCreated());
+ conditions.setNotOnOrAfter(lifetime.getExpires());
+ conditions.add(restriction);
+
+ // the assertion principal (default is caller principal)
+ Principal principal = wstContext.getCallerPrincipal();
+
+ String confirmationMethod = null;
+ KeyInfoType keyInfoType = null;
+ // if there is a on-behalf-of principal, we have the sender vouches confirmation method.
+ if (wstContext.getOnBehalfOfPrincipal() != null)
+ {
+ principal = wstContext.getOnBehalfOfPrincipal();
+ confirmationMethod = SAMLUtil.SAML11_SENDER_VOUCHES_URI;
+ }
+ // if there is a proof-of-possession token in the context, we have the holder of key confirmation method.
+ else if (wstContext.getProofTokenInfo() != null)
+ {
+ confirmationMethod = SAMLUtil.SAML11_HOLDER_OF_KEY_URI;
+ keyInfoType = wstContext.getProofTokenInfo();
+ }
+ else
+ confirmationMethod = SAMLUtil.SAML11_BEARER_URI;
+
+ SAML11SubjectConfirmationType subjectConfirmation = new SAML11SubjectConfirmationType();
+ subjectConfirmation.addConfirmationMethod(URI.create(confirmationMethod));
+ // TODO: set the key info.
+
+ // create a subject using the caller principal or on-behalf-of principal.
+ String subjectName = principal == null ? "ANONYMOUS" : principal.getName();
+ SAML11NameIdentifierType nameId = new SAML11NameIdentifierType(subjectName);
+ nameId.setFormat(URI.create(SAML11Constants.FORMAT_UNSPECIFIED));
+ SAML11SubjectType subject = new SAML11SubjectType();
+ subject.setChoice(new SAML11SubjectType.SAML11SubjectTypeChoice(nameId));
+ subject.setSubjectConfirmation(subjectConfirmation);
+
+ // add the subject to an auth statement.
+ SAML11AuthenticationStatementType authStatement = new SAML11AuthenticationStatementType(URI
+ .create("urn:picketlink:auth"), lifetime.getCreated());
+ authStatement.setSubject(subject);
+
+ // TODO: add attribute statements.
+
+ // create the SAML assertion.
+ SAML11AssertionType assertion = new SAML11AssertionType(assertionID, lifetime.getCreated());
+ assertion.add(authStatement);
+ assertion.setConditions(conditions);
+ assertion.setIssuer(wstContext.getTokenIssuer());
+
+ // convert the constructed assertion to element.
+ Element assertionElement = null;
+ try
+ {
+ assertionElement = SAMLUtil.toElement(assertion);
+ }
+ catch (Exception e)
+ {
+ throw new ProcessingException("Failed to marshall SAMLV1.1 assertion", e);
+ }
+ SecurityToken token = new StandardSecurityToken(wstContext.getRequestSecurityToken().getTokenType().toString(),
+ assertionElement, assertionID);
+ wstContext.setSecurityToken(token);
+
+ // set the SAML assertion attached reference.
+ KeyIdentifierType keyIdentifier = WSTrustUtil.createKeyIdentifier(SAMLUtil.SAML11_VALUE_TYPE, "#" + assertionID);
+ Map<QName, String> attributes = new HashMap<QName, String>();
+ attributes.put(new QName(WSTrustConstants.WSSE11_NS, "TokenType", WSTrustConstants.WSSE.PREFIX_11),
+ SAMLUtil.SAML11_TOKEN_TYPE);
+ RequestedReferenceType attachedReference = WSTrustUtil.createRequestedReference(keyIdentifier, attributes);
+ wstContext.setAttachedReference(attachedReference);
+
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see
+ * org.picketlink.identity.federation.core.interfaces.SecurityTokenProvider#renewToken(org.picketlink.identity.federation
+ * .core.interfaces.ProtocolContext)
+ */
+ @Override
+ public void renewToken(ProtocolContext context) throws ProcessingException
+ {
+ if (!(context instanceof WSTrustRequestContext))
+ return;
+
+ WSTrustRequestContext wstContext = (WSTrustRequestContext) context;
+ // get the specified assertion that must be renewed.
+ Element token = wstContext.getRequestSecurityToken().getRenewTargetElement();
+ if (token == null)
+ throw new ProcessingException("Invalid renew request: missing required RenewTarget");
+ Element oldAssertionElement = (Element) token.getFirstChild();
+ if (!this.isSAMLAssertion(oldAssertionElement))
+ throw new ProcessingException("RenewTarget doesn't not contain a SAMLV1.1 assertion");
+
+ // get the JAXB representation of the old assertion.
+ SAML11AssertionType oldAssertion = null;
+ try
+ {
+ oldAssertion = SAMLUtil.saml11FromElement(oldAssertionElement);
+ }
+ catch (Exception je)
+ {
+ throw new ProcessingException("Error unmarshalling assertion", je);
+ }
+
+ // canceled assertions cannot be renewed.
+ if (this.revocationRegistry.isRevoked(SAMLUtil.SAML11_TOKEN_TYPE, oldAssertion.getID()))
+ throw new ProcessingException("SAMLV1.1 Assertion with id " + oldAssertion.getID()
+ + " has been canceled and cannot be renewed");
+
+ // adjust the lifetime for the renewed assertion.
+ SAML11ConditionsType conditions = oldAssertion.getConditions();
+ conditions.setNotBefore(wstContext.getRequestSecurityToken().getLifetime().getCreated());
+ conditions.setNotOnOrAfter(wstContext.getRequestSecurityToken().getLifetime().getExpires());
+
+ // create a new unique ID for the renewed assertion.
+ String assertionID = IDGenerator.create("ID_");
+
+ // get the list of all assertion statements - should include the auth statement that contains the subject.
+ List<SAML11StatementAbstractType> statements = new ArrayList<SAML11StatementAbstractType>();
+ statements.addAll(oldAssertion.getStatements());
+
+ // create the new assertion.
+ SAML11AssertionType newAssertion = new SAML11AssertionType(assertionID, conditions.getNotBefore());
+ newAssertion.addAllStatements(statements);
+ newAssertion.setConditions(conditions);
+ newAssertion.setIssuer(wstContext.getTokenIssuer());
+
+ // create a security token with the new assertion.
+ Element assertionElement = null;
+ try
+ {
+ assertionElement = SAMLUtil.toElement(newAssertion);
+ }
+ catch (Exception e)
+ {
+ throw new ProcessingException("Failed to marshall SAMLV1.1 assertion", e);
+ }
+ SecurityToken securityToken = new StandardSecurityToken(wstContext.getRequestSecurityToken().getTokenType()
+ .toString(), assertionElement, assertionID);
+ wstContext.setSecurityToken(securityToken);
+
+ // set the SAML assertion attached reference.
+ KeyIdentifierType keyIdentifier = WSTrustUtil.createKeyIdentifier(SAMLUtil.SAML11_VALUE_TYPE, "#" + assertionID);
+ Map<QName, String> attributes = new HashMap<QName, String>();
+ attributes.put(new QName(WSTrustConstants.WSSE11_NS, "TokenType"), SAMLUtil.SAML11_TOKEN_TYPE);
+ RequestedReferenceType attachedReference = WSTrustUtil.createRequestedReference(keyIdentifier, attributes);
+ wstContext.setAttachedReference(attachedReference);
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see
+ * org.picketlink.identity.federation.core.interfaces.SecurityTokenProvider#validateToken(org.picketlink.identity
+ * .federation.core.interfaces.ProtocolContext)
+ */
+ @Override
+ public void validateToken(ProtocolContext context) throws ProcessingException
+ {
+ if (!(context instanceof WSTrustRequestContext))
+ return;
+
+ WSTrustRequestContext wstContext = (WSTrustRequestContext) context;
+ if (logger.isTraceEnabled())
+ logger.trace("SAML V1.1 token validation started");
+
+ // get the SAML assertion that must be validated.
+ Element token = wstContext.getRequestSecurityToken().getValidateTargetElement();
+ if (token == null)
+ throw new ProcessingException("Bad validate request: missing required ValidateTarget");
+
+ String code = WSTrustConstants.STATUS_CODE_VALID;
+ String reason = "SAMLV1.1 Assertion successfuly validated";
+
+ SAML11AssertionType assertion = null;
+ Element assertionElement = (Element) token.getFirstChild();
+ if (!this.isSAMLAssertion(assertionElement))
+ {
+ code = WSTrustConstants.STATUS_CODE_INVALID;
+ reason = "Validation failure: supplied token is not a SAMLV1.1 Assertion";
+ }
+ else
+ {
+ try
+ {
+ assertion = SAMLUtil.saml11FromElement(assertionElement);
+ }
+ catch (Exception e)
+ {
+ throw new ProcessingException("Unmarshalling error:", e);
+ }
+ }
+
+ // check if the assertion has been canceled before.
+ if (this.revocationRegistry.isRevoked(SAMLUtil.SAML11_TOKEN_TYPE, assertion.getID()))
+ {
+ code = WSTrustConstants.STATUS_CODE_INVALID;
+ reason = "Validation failure: assertion with id " + assertion.getID() + " has been canceled";
+ }
+
+ // check the assertion lifetime.
+ try
+ {
+ if (AssertionUtil.hasExpired(assertion))
+ {
+ code = WSTrustConstants.STATUS_CODE_INVALID;
+ reason = "Validation failure: assertion expired or used before its lifetime period";
+ }
+ }
+ catch (Exception ce)
+ {
+ code = WSTrustConstants.STATUS_CODE_INVALID;
+ reason = "Validation failure: unable to verify assertion lifetime: " + ce.getMessage();
+ }
+
+ // construct the status and set it on the request context.
+ StatusType status = new StatusType();
+ status.setCode(code);
+ status.setReason(reason);
+ wstContext.setStatus(status);
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see org.picketlink.identity.federation.core.interfaces.SecurityTokenProvider#family()
+ */
+ @Override
+ public String family()
+ {
+ return SecurityTokenProvider.FAMILY_TYPE.WS_TRUST.toString();
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see org.picketlink.identity.federation.core.interfaces.SecurityTokenProvider#getSupportedQName()
+ */
+ @Override
+ public QName getSupportedQName()
+ {
+ return new QName(tokenType(), JBossSAMLConstants.ASSERTION.get());
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see org.picketlink.identity.federation.core.interfaces.SecurityTokenProvider#supports(java.lang.String)
+ */
+ @Override
+ public boolean supports(String namespace)
+ {
+ return WSTrustConstants.BASE_NAMESPACE.equals(namespace);
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see org.picketlink.identity.federation.core.interfaces.SecurityTokenProvider#tokenType()
+ */
+ @Override
+ public String tokenType()
+ {
+ return SAMLUtil.SAML11_TOKEN_TYPE;
+ }
+
+ /**
+ * <p>
+ * Checks whether the specified element is a SAMLV1.1 assertion or not.
+ * </p>
+ *
+ * @param element
+ * the {@code Element} being verified.
+ * @return {@code true} if the element is a SAMLV1.1 assertion; {@code false} otherwise.
+ */
+ private boolean isSAMLAssertion(Element element)
+ {
+ return element == null ? false : "Assertion".equals(element.getLocalName())
+ && SAML11Constants.ASSERTION_11_NSURI.equals(element.getNamespaceURI());
+ }
+
+}
13 years, 5 months
Picketlink SVN: r1090 - in integration-tests/trunk/picketlink-sts-tests: src/test/java/org/picketlink/test/integration/sts and 1 other directory.
by picketlink-commits@lists.jboss.org
Author: sguilhen(a)redhat.com
Date: 2011-07-14 11:04:56 -0400 (Thu, 14 Jul 2011)
New Revision: 1090
Modified:
integration-tests/trunk/picketlink-sts-tests/.classpath
integration-tests/trunk/picketlink-sts-tests/src/test/java/org/picketlink/test/integration/sts/PicketLinkSTSIntegrationUnitTestCase.java
Log:
PLFED-205: Added SAMLv1.1 scenarios to the integration tests
Modified: integration-tests/trunk/picketlink-sts-tests/.classpath
===================================================================
--- integration-tests/trunk/picketlink-sts-tests/.classpath 2011-07-14 15:04:04 UTC (rev 1089)
+++ integration-tests/trunk/picketlink-sts-tests/.classpath 2011-07-14 15:04:56 UTC (rev 1090)
@@ -111,6 +111,5 @@
<classpathentry kind="var" path="M2_REPO/xml-apis/xml-apis/1.0.b2/xml-apis-1.0.b2.jar" sourcepath="M2_REPO/xml-apis/xml-apis/1.0.b2/xml-apis-1.0.b2-sources.jar"/>
<classpathentry kind="var" path="M2_REPO/org/apache/xmlsec/1.4.3/xmlsec-1.4.3.jar"/>
<classpathentry kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER"/>
- <classpathentry kind="lib" path="/picketlink-saml-jbas6/target/jboss-6.0.0.Final/lib/jboss-system.jar"/>
<classpathentry kind="output" path="target/classes"/>
</classpath>
Modified: integration-tests/trunk/picketlink-sts-tests/src/test/java/org/picketlink/test/integration/sts/PicketLinkSTSIntegrationUnitTestCase.java
===================================================================
--- integration-tests/trunk/picketlink-sts-tests/src/test/java/org/picketlink/test/integration/sts/PicketLinkSTSIntegrationUnitTestCase.java 2011-07-14 15:04:04 UTC (rev 1089)
+++ integration-tests/trunk/picketlink-sts-tests/src/test/java/org/picketlink/test/integration/sts/PicketLinkSTSIntegrationUnitTestCase.java 2011-07-14 15:04:56 UTC (rev 1090)
@@ -17,6 +17,10 @@
*/
package org.picketlink.test.integration.sts;
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertNotNull;
+import static org.junit.Assert.assertTrue;
+
import java.io.ByteArrayInputStream;
import java.io.InputStream;
import java.math.BigInteger;
@@ -39,11 +43,20 @@
import org.junit.Test;
import org.picketlink.identity.federation.api.wstrust.WSTrustClient;
import org.picketlink.identity.federation.api.wstrust.WSTrustClient.SecurityInfo;
+import org.picketlink.identity.federation.core.saml.v1.SAML11Constants;
import org.picketlink.identity.federation.core.util.Base64;
import org.picketlink.identity.federation.core.wstrust.WSTrustConstants;
import org.picketlink.identity.federation.core.wstrust.WSTrustUtil;
import org.picketlink.identity.federation.core.wstrust.plugins.saml.SAMLUtil;
import org.picketlink.identity.federation.core.wstrust.wrappers.RequestSecurityToken;
+import org.picketlink.identity.federation.saml.v1.assertion.SAML11AssertionType;
+import org.picketlink.identity.federation.saml.v1.assertion.SAML11AuthenticationStatementType;
+import org.picketlink.identity.federation.saml.v1.assertion.SAML11ConditionAbstractType;
+import org.picketlink.identity.federation.saml.v1.assertion.SAML11ConditionsType;
+import org.picketlink.identity.federation.saml.v1.assertion.SAML11NameIdentifierType;
+import org.picketlink.identity.federation.saml.v1.assertion.SAML11StatementAbstractType;
+import org.picketlink.identity.federation.saml.v1.assertion.SAML11SubjectConfirmationType;
+import org.picketlink.identity.federation.saml.v1.assertion.SAML11SubjectType;
import org.picketlink.identity.federation.saml.v2.assertion.AssertionType;
import org.picketlink.identity.federation.saml.v2.assertion.AudienceRestrictionType;
import org.picketlink.identity.federation.saml.v2.assertion.ConditionAbstractType;
@@ -94,6 +107,32 @@
/**
* <p>
+ * This tests sends a SAMLV1.1 security token request to PicketLinkSTS. This request should be handled by the {@code
+ * SAML1TokenProvider} and should result in a SAMLV1.1 assertion.
+ * </p>
+ *
+ * @throws Exception
+ * if an error occurs while running the test.
+ */
+ @Test
+ public void testIssueSAML11() throws Exception
+ {
+ Element assertionElement = client.issueToken(SAMLUtil.SAML11_TOKEN_TYPE);
+ Assert.assertNotNull("Invalid null assertion element", assertionElement);
+
+ // validate the contents of the SAML assertion.
+ SAML11AssertionType assertion = this.validateSAML11Assertion(assertionElement, "admin",
+ SAMLUtil.SAML11_BEARER_URI);
+
+ // in this scenario, the conditions section should NOT have an audience restriction.
+ SAML11ConditionsType conditionsType = assertion.getConditions();
+
+ List<SAML11ConditionAbstractType> conditions = conditionsType.get();
+ Assert.assertEquals("Unexpected restriction list size", 0, conditions.size());
+ }
+
+ /**
+ * <p>
* This tests sends a SAMLV2.0 security token request to PicketLinkSTS. This request should be handled by the
* standard {@code SAML20TokenProvider} and should result in a SAMLV2.0 assertion that looks like the following:
*
@@ -175,6 +214,39 @@
/**
* <p>
+ * This test requests a SAMLV1.1 assertion on behalf of another identity. The STS must issue an assertion for the
+ * identity contained in the {@code OnBehalfOf} section of the WS-Trust request (and not for the identity that sent
+ * the request).
+ * </p>
+ *
+ * @throws Exception
+ * if an error occurs while running the test.
+ */
+ @Test
+ public void testIssueSAML11OnBehalfOf() throws Exception
+ {
+ // issue a SAML 1.1 assertion for jduke.
+ Element assertionElement = client.issueTokenOnBehalfOf(null, SAMLUtil.SAML11_TOKEN_TYPE, new Principal()
+ {
+ @Override
+ public String getName()
+ {
+ return "jduke";
+ }
+ });
+ Assert.assertNotNull("Invalid null assertion element", assertionElement);
+
+ // this scenario results in the sender vouches confirmation method being used.
+ SAML11AssertionType assertion = this.validateSAML11Assertion(assertionElement, "jduke",
+ SAMLUtil.SAML11_SENDER_VOUCHES_URI);
+
+ // we haven't specified the service endpoint URI, so no restrictions should be visible.
+ SAML11ConditionsType conditions = assertion.getConditions();
+ Assert.assertEquals("Unexpected restriction list size", 0, conditions.get().size());
+ }
+
+ /**
+ * <p>
* This test requests a SAMLV2.0 assertion on behalf of another identity. The STS must issue an assertion for the
* identity contained in the {@code OnBehalfOf} section of the WS-Trust request (and not for the identity that sent
* the request).
@@ -362,6 +434,41 @@
/**
* <p>
+ * This test case first generates a SAMLV1.1 assertion and then sends a WS-Trust renew message to the STS to get the
+ * assertion renewed (i.e. get a new assertion with an updated lifetime).
+ * </p>
+ *
+ * @throws Exception
+ * if an error occurs while running the test.
+ */
+ @Test
+ public void testRenewSAML11() throws Exception
+ {
+ // issue a simple SAML assertion.
+ Element assertionElement = client.issueToken(SAMLUtil.SAML11_TOKEN_TYPE);
+ Assert.assertNotNull("Invalid null assertion element", assertionElement);
+ // validate the contents of the original assertion.
+ SAML11AssertionType originalAssertion = this.validateSAML11Assertion(assertionElement, "admin",
+ SAMLUtil.SAML11_BEARER_URI);
+
+ // now use the client API to renew the assertion.
+ Element renewedAssertionElement = client.renewToken(SAMLUtil.SAML11_TOKEN_TYPE, assertionElement);
+ Assert.assertNotNull("Invalid null assertion element", assertionElement);
+ // validate the contents of the renewed assertion.
+ SAML11AssertionType renewedAssertion = this.validateSAML11Assertion(renewedAssertionElement, "admin",
+ SAMLUtil.SAML11_BEARER_URI);
+
+ // assertions should have different ids and lifetimes.
+ Assert.assertFalse("Renewed assertion should have a unique id", originalAssertion.getID().equals(
+ renewedAssertion.getID()));
+ Assert.assertEquals(DatatypeConstants.LESSER, originalAssertion.getConditions().getNotBefore().compare(
+ renewedAssertion.getConditions().getNotBefore()));
+ Assert.assertEquals(DatatypeConstants.LESSER, originalAssertion.getConditions().getNotOnOrAfter().compare(
+ renewedAssertion.getConditions().getNotOnOrAfter()));
+ }
+
+ /**
+ * <p>
* This test case first generates a SAMLV2.0 assertion and then sends a WS-Trust renew message to the STS to get the
* assertion renewed (i.e. get a new assertion with an updated lifetime).
* </p>
@@ -397,6 +504,32 @@
/**
* <p>
+ * This test case first generates a SAMLV1.1 assertion and then sends a WS-Trust validate message to the STS to get
+ * the assertion validated, checking the validation results.
+ * </p>
+ *
+ * @throws Exception
+ * if an error occurs while running the test.
+ */
+ @Test
+ public void testValidateSAML11() throws Exception
+ {
+ // issue a simple SAML assertion.
+ Element assertionElement = client.issueToken(SAMLUtil.SAML11_TOKEN_TYPE);
+ Assert.assertNotNull("Invalid null assertion element", assertionElement);
+
+ // now use the client API to have the assertion validated by the STS.
+ boolean isValid = client.validateToken(assertionElement);
+ Assert.assertTrue("Found unexpected invalid assertion", isValid);
+
+ // now let's temper the SAML assertion and try to validate it again.
+ // assertionElement.setAttribute("Issuer", "ABC");
+ // isValid = client.validateToken(assertionElement);
+ // Assert.assertFalse("The assertion should be invalid", isValid);
+ }
+
+ /**
+ * <p>
* This test case first generates a SAMLV2.0 assertion and then sends a WS-Trust validate message to the STS to get
* the assertion validated, checking the validation results.
* </p>
@@ -423,6 +556,47 @@
/**
* <p>
+ * This test case first generates a SAMLV1.1 assertion and then sends a WS-Trust cancel message to the STS to cancel
+ * the assertion. A canceled assertion cannot be renewed or considered valid anymore.
+ * </p>
+ *
+ * @throws Exception
+ * if an error occurs while running the test.
+ */
+ @Test
+ public void testCancelSAML11() throws Exception
+ {
+ // issue a simple SAML assertion.
+ Element assertionElement = client.issueToken(SAMLUtil.SAML11_TOKEN_TYPE);
+ Assert.assertNotNull("Invalid null assertion element", assertionElement);
+
+ // before being canceled, the assertion shold be considered valid by the STS.
+ Assert.assertTrue("Found unexpected invalid assertion", client.validateToken(assertionElement));
+
+ // now use the client API to have the assertion canceled by the STS.
+ boolean canceled = client.cancelToken(assertionElement);
+ Assert.assertTrue(canceled);
+
+ // now that the assertion has been canceled, it should be considered invalid by the STS.
+ Assert.assertFalse("The assertion should be invalid", client.validateToken(assertionElement));
+
+ // trying to renew an invalid assertion should result in an exception being thrown.
+ try
+ {
+ client.renewToken(SAMLUtil.SAML11_TOKEN_TYPE, assertionElement);
+ Assert.fail("An exception should have been raised by the security token service");
+ }
+ catch (WebServiceException we)
+ {
+ Assert.assertEquals("Unexpected exception message",
+ "Exception in handling token request: SAMLV1.1 Assertion with id "
+ + assertionElement.getAttribute("AssertionID") + " has been canceled and cannot be renewed", we
+ .getMessage());
+ }
+ }
+
+ /**
+ * <p>
* This test case first generates a SAMLV2.0 assertion and then sends a WS-Trust cancel message to the STS to cancel
* the assertion. A canceled assertion cannot be renewed or considered valid anymore.
* </p>
@@ -485,6 +659,53 @@
}
}
+ private SAML11AssertionType validateSAML11Assertion(Element assertionElement, String assertionPrincipal,
+ String confirmationMethod) throws Exception
+ {
+ // unmarshall the SAMLV1.1 assertion.
+ SAML11AssertionType assertion = SAMLUtil.saml11FromElement(assertionElement);
+
+ // validate the assertion issuer.
+ Assert.assertNotNull("Invalid null assertion ID", assertion.getID());
+ Assert.assertEquals("Unexpected assertion issuer name", "PicketLinkSTS", assertion.getIssuer());
+
+ // validate the assertion auth statement.
+ List<SAML11StatementAbstractType> statements = assertion.getStatements();
+ assertTrue("At least one statement is expected in a SAMLV1.1 assertion", statements.size() > 0);
+ SAML11AuthenticationStatementType authStatement = null;
+ for (SAML11StatementAbstractType statement : statements)
+ {
+ if (statement instanceof SAML11AuthenticationStatementType)
+ {
+ authStatement = (SAML11AuthenticationStatementType) statement;
+ break;
+ }
+ }
+ assertNotNull("SAMLV1.1 assertion is missing the authentication statement", authStatement);
+
+ // validate the assertion subject.
+ Assert.assertNotNull("Unexpected null subject", authStatement.getSubject());
+ SAML11SubjectType subject = authStatement.getSubject();
+ SAML11NameIdentifierType nameID = subject.getChoice().getNameID();
+ assertEquals("Unexpected NameIdentifier format", SAML11Constants.FORMAT_UNSPECIFIED, nameID.getFormat()
+ .toString());
+ assertEquals("Unexpected NameIdentifier value", assertionPrincipal, nameID.getValue());
+
+ SAML11SubjectConfirmationType subjType = subject.getSubjectConfirmation();
+ assertEquals("Unexpected confirmation method", confirmationMethod, subjType.getConfirmationMethod().get(0)
+ .toString());
+
+ // validate the assertion conditions.
+ Assert.assertNotNull("Unexpected null conditions", assertion.getConditions());
+ Assert.assertNotNull(assertion.getConditions().getNotBefore());
+ Assert.assertNotNull(assertion.getConditions().getNotOnOrAfter());
+
+ // verify if the assertion has been signed.
+ Assert.assertNotNull("Assertion should have been signed", assertion.getSignature());
+
+ return assertion;
+ }
+
/**
* <p>
* Validates the contents of the specified SAML 2.0 assertion.
13 years, 5 months
Picketlink SVN: r1089 - in federation/trunk: picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/parsers/wst and 11 other directories.
by picketlink-commits@lists.jboss.org
Author: sguilhen(a)redhat.com
Date: 2011-07-14 11:04:04 -0400 (Thu, 14 Jul 2011)
New Revision: 1089
Modified:
federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/parsers/saml/SAML11AssertionParser.java
federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/parsers/wst/WSTCancelTargetParser.java
federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/parsers/wst/WSTRenewTargetParser.java
federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/parsers/wst/WSTValidateTargetParser.java
federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/saml/v1/SAML11Constants.java
federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/saml/v1/writers/SAML11AssertionWriter.java
federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/util/XMLSignatureUtil.java
federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/wstrust/StandardRequestHandler.java
federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/wstrust/WSTrustConstants.java
federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/wstrust/auth/STSIssuingLoginModule.java
federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/wstrust/plugins/saml/SAML20TokenProvider.java
federation/trunk/picketlink-fed-core/src/test/java/org/picketlink/test/identity/federation/core/parser/wst/WSTResponseAssertionHOKCertificateTestCase.java
federation/trunk/picketlink-fed-core/src/test/java/org/picketlink/test/identity/federation/core/parser/wst/WSTrustBatchIssueParsingTestCase.java
federation/trunk/picketlink-fed-core/src/test/java/org/picketlink/test/identity/federation/core/parser/wst/WSTrustBatchValidateParsingTestCase.java
federation/trunk/picketlink-fed-core/src/test/java/org/picketlink/test/identity/federation/core/parser/wst/WSTrustCancelTargetSamlTestCase.java
federation/trunk/picketlink-fed-core/src/test/java/org/picketlink/test/identity/federation/core/parser/wst/WSTrustIssueTestCase.java
federation/trunk/picketlink-fed-core/src/test/java/org/picketlink/test/identity/federation/core/parser/wst/WSTrustRenewTargetParsingTestCase.java
federation/trunk/picketlink-fed-core/src/test/java/org/picketlink/test/identity/federation/core/parser/wst/WSTrustValidateSamlTestCase.java
federation/trunk/picketlink-fed-core/src/test/java/org/picketlink/test/identity/federation/core/wstrust/PicketLinkSTSUnitTestCase.java
federation/trunk/picketlink-fed-core/src/test/resources/parser/wst/wst-batch-validate.xml
federation/trunk/picketlink-fed-core/src/test/resources/parser/wst/wst-cancel-saml.xml
federation/trunk/picketlink-fed-core/src/test/resources/parser/wst/wst-renew-saml.xml
federation/trunk/picketlink-fed-core/src/test/resources/parser/wst/wst-validate-saml.xml
federation/trunk/picketlink-fed-core/src/test/resources/sts/picketlink-sts.xml
federation/trunk/picketlink-webapps/picketlink-sts/src/main/resources/picketlink-sts.xml
Log:
PLFED-205: Added the SAML11TokenProvider to generate SAMLv1.1 assertions via WS-Trust
Modified: federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/parsers/saml/SAML11AssertionParser.java
===================================================================
--- federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/parsers/saml/SAML11AssertionParser.java 2011-07-13 19:35:11 UTC (rev 1088)
+++ federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/parsers/saml/SAML11AssertionParser.java 2011-07-14 15:04:04 UTC (rev 1089)
@@ -189,7 +189,7 @@
String majVersion = StaxParserUtil.getAttributeValue(majVersionAttribute);
StringUtil.match("1", majVersion);
- Attribute minVersionAttribute = nextElement.getAttributeByName(new QName(SAML11Constants.MAJOR_VERSION));
+ Attribute minVersionAttribute = nextElement.getAttributeByName(new QName(SAML11Constants.MINOR_VERSION));
String minVersion = StaxParserUtil.getAttributeValue(minVersionAttribute);
StringUtil.match("1", minVersion);
Modified: federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/parsers/wst/WSTCancelTargetParser.java
===================================================================
--- federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/parsers/wst/WSTCancelTargetParser.java 2011-07-13 19:35:11 UTC (rev 1088)
+++ federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/parsers/wst/WSTCancelTargetParser.java 2011-07-14 15:04:04 UTC (rev 1089)
@@ -27,11 +27,8 @@
import org.picketlink.identity.federation.core.exceptions.ParsingException;
import org.picketlink.identity.federation.core.parsers.ParserNamespaceSupport;
-import org.picketlink.identity.federation.core.parsers.saml.SAMLParser;
import org.picketlink.identity.federation.core.parsers.util.StaxParserUtil;
-import org.picketlink.identity.federation.core.saml.v2.constants.JBossSAMLConstants;
import org.picketlink.identity.federation.core.wstrust.WSTrustConstants;
-import org.picketlink.identity.federation.saml.v2.assertion.AssertionType;
import org.picketlink.identity.federation.ws.trust.CancelTargetType;
/**
@@ -53,25 +50,14 @@
{
throw new ParsingException("Unable to parse cancel token request: security token is null");
}
- String tag = StaxParserUtil.getStartElementName(startElement);
-
- if (tag.equals(JBossSAMLConstants.ASSERTION.get()))
+ // this is an unknown type - parse using the transformer.
+ try
{
- SAMLParser assertionParser = new SAMLParser();
- AssertionType assertion = (AssertionType) assertionParser.parse(xmlEventReader);
- cancelTarget.add(assertion);
+ cancelTarget.add(StaxParserUtil.getDOMElement(xmlEventReader));
}
- else
+ catch (Exception e)
{
- // this is an unknown type - parse using the transformer.
- try
- {
- cancelTarget.add(StaxParserUtil.getDOMElement(xmlEventReader));
- }
- catch (Exception e)
- {
- throw new ParsingException("Error parsing security token: " + e.getMessage(), e);
- }
+ throw new ParsingException("Error parsing security token: " + e.getMessage(), e);
}
return cancelTarget;
}
Modified: federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/parsers/wst/WSTRenewTargetParser.java
===================================================================
--- federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/parsers/wst/WSTRenewTargetParser.java 2011-07-13 19:35:11 UTC (rev 1088)
+++ federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/parsers/wst/WSTRenewTargetParser.java 2011-07-14 15:04:04 UTC (rev 1089)
@@ -23,11 +23,8 @@
import org.picketlink.identity.federation.core.exceptions.ParsingException;
import org.picketlink.identity.federation.core.parsers.ParserNamespaceSupport;
-import org.picketlink.identity.federation.core.parsers.saml.SAMLParser;
import org.picketlink.identity.federation.core.parsers.util.StaxParserUtil;
-import org.picketlink.identity.federation.core.saml.v2.constants.JBossSAMLConstants;
import org.picketlink.identity.federation.core.wstrust.WSTrustConstants;
-import org.picketlink.identity.federation.saml.v2.assertion.AssertionType;
import org.picketlink.identity.federation.ws.trust.RenewTargetType;
/**
@@ -51,25 +48,15 @@
{
throw new ParsingException("Unable to parse renew token request: security token is null");
}
- String tag = StaxParserUtil.getStartElementName(startElement);
- if (tag.equals(JBossSAMLConstants.ASSERTION.get()))
+ // this is an unknown type - parse using the transformer.
+ try
{
- SAMLParser assertionParser = new SAMLParser();
- AssertionType assertion = (AssertionType) assertionParser.parse(xmlEventReader);
- renewTargetType.add(assertion);
+ renewTargetType.add(StaxParserUtil.getDOMElement(xmlEventReader));
}
- else
+ catch (Exception e)
{
- // this is an unknown type - parse using the transformer.
- try
- {
- renewTargetType.add(StaxParserUtil.getDOMElement(xmlEventReader));
- }
- catch (Exception e)
- {
- throw new ParsingException("Error parsing security token: " + e.getMessage(), e);
- }
+ throw new ParsingException("Error parsing security token: " + e.getMessage(), e);
}
return renewTargetType;
}
Modified: federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/parsers/wst/WSTValidateTargetParser.java
===================================================================
--- federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/parsers/wst/WSTValidateTargetParser.java 2011-07-13 19:35:11 UTC (rev 1088)
+++ federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/parsers/wst/WSTValidateTargetParser.java 2011-07-14 15:04:04 UTC (rev 1089)
@@ -53,25 +53,15 @@
{
throw new ParsingException("Unable to parse validate token request: security token is null");
}
- String tag = StaxParserUtil.getStartElementName(startElement);
- if (tag.equals(JBossSAMLConstants.ASSERTION.get()))
+ // this is an unknown type - parse using the transformer.
+ try
{
- SAMLParser assertionParser = new SAMLParser();
- AssertionType assertion = (AssertionType) assertionParser.parse(xmlEventReader);
- validateTargetType.add(assertion);
+ validateTargetType.add(StaxParserUtil.getDOMElement(xmlEventReader));
}
- else
+ catch (Exception e)
{
- // this is an unknown type - parse using the transformer.
- try
- {
- validateTargetType.add(StaxParserUtil.getDOMElement(xmlEventReader));
- }
- catch (Exception e)
- {
- throw new ParsingException("Error parsing security token: " + e.getMessage(), e);
- }
+ throw new ParsingException("Error parsing security token: " + e.getMessage(), e);
}
return validateTargetType;
Modified: federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/saml/v1/SAML11Constants.java
===================================================================
--- federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/saml/v1/SAML11Constants.java 2011-07-13 19:35:11 UTC (rev 1088)
+++ federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/saml/v1/SAML11Constants.java 2011-07-14 15:04:04 UTC (rev 1089)
@@ -85,6 +85,8 @@
String FORMAT = "Format";
String FORMAT_EMAIL_ADDRESS = "urn:oasis:names:tc:SAML:1.1:nameid-format:emailAddress";
+
+ String FORMAT_UNSPECIFIED = "urn:oasis:names:tc:SAML:1.1:nameid-format:unspecified";
String IN_RESPONSE_TO = "InResponseTo";
Modified: federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/saml/v1/writers/SAML11AssertionWriter.java
===================================================================
--- federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/saml/v1/writers/SAML11AssertionWriter.java 2011-07-13 19:35:11 UTC (rev 1088)
+++ federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/saml/v1/writers/SAML11AssertionWriter.java 2011-07-14 15:04:04 UTC (rev 1089)
@@ -82,6 +82,7 @@
StaxUtil.writeDefaultNameSpace(writer, ns);
// Attributes
+// StaxUtil.writeAttribute(writer, JBossSAMLConstants.ID.get(), assertion.getID());
StaxUtil.writeAttribute(writer, SAML11Constants.ASSERTIONID, assertion.getID());
StaxUtil.writeAttribute(writer, SAML11Constants.MAJOR_VERSION, assertion.getMajorVersion() + "");
StaxUtil.writeAttribute(writer, SAML11Constants.MINOR_VERSION, assertion.getMinorVersion() + "");
Modified: federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/util/XMLSignatureUtil.java
===================================================================
--- federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/util/XMLSignatureUtil.java 2011-07-13 19:35:11 UTC (rev 1088)
+++ federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/util/XMLSignatureUtil.java 2011-07-14 15:04:04 UTC (rev 1089)
@@ -1,23 +1,19 @@
/*
- * JBoss, Home of Professional Open Source.
- * Copyright 2008, Red Hat Middleware LLC, and individual contributors
- * as indicated by the @author tags. See the copyright.txt file in the
- * distribution for a full listing of individual contributors.
- *
- * This is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Lesser General Public License as
- * published by the Free Software Foundation; either version 2.1 of
- * the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public
- * License along with this software; if not, write to the Free
- * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
- * 02110-1301 USA, or see the FSF site: http://www.fsf.org.
+ * JBoss, Home of Professional Open Source. Copyright 2008, Red Hat Middleware LLC, and individual contributors as
+ * indicated by the @author tags. See the copyright.txt file in the distribution for a full listing of individual
+ * contributors.
+ *
+ * This is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any
+ * later version.
+ *
+ * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied
+ * warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more
+ * details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License along with this software; if not, write to
+ * the Free Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA, or see the FSF site:
+ * http://www.fsf.org.
*/
package org.picketlink.identity.federation.core.util;
@@ -52,6 +48,7 @@
import javax.xml.crypto.dsig.keyinfo.KeyValue;
import javax.xml.crypto.dsig.spec.C14NMethodParameterSpec;
import javax.xml.crypto.dsig.spec.TransformParameterSpec;
+import javax.xml.namespace.QName;
import javax.xml.parsers.ParserConfigurationException;
import javax.xml.transform.Transformer;
import javax.xml.transform.TransformerException;
@@ -62,6 +59,7 @@
import org.picketlink.identity.federation.core.exceptions.ProcessingException;
import org.picketlink.identity.federation.core.saml.v2.constants.JBossSAMLURIConstants;
import org.picketlink.identity.federation.core.saml.v2.util.DocumentUtil;
+import org.picketlink.identity.federation.core.wstrust.WSTrustConstants;
import org.picketlink.identity.xmlsec.w3.xmldsig.SignatureType;
import org.w3c.dom.Document;
import org.w3c.dom.Node;
@@ -69,9 +67,9 @@
import org.xml.sax.SAXException;
/**
- * Utility for XML Signature
- * <b>Note:</b> You can change the canonicalization method type by using
- * the system property "picketlink.xmlsig.canonicalization"
+ * Utility for XML Signature <b>Note:</b> You can change the canonicalization method type by using the system property
+ * "picketlink.xmlsig.canonicalization"
+ *
* @author Anil.Saldhana(a)redhat.com
* @since Dec 15, 2008
*/
@@ -95,13 +93,13 @@
}
catch (Exception err)
{
- //JDK5
+ // JDK5
xsf = XMLSignatureFactory.getInstance("DOM", new org.jcp.xml.dsig.internal.dom.XMLDSigRI());
}
return xsf;
}
- //Set some system properties
+ // Set some system properties
static
{
SystemPropertiesUtil.ensure();
@@ -109,6 +107,7 @@
/**
* Set the canonicalization method type
+ *
* @param canonical
*/
public static void setCanonicalizationMethodType(String canonical)
@@ -118,8 +117,8 @@
}
/**
- * Precheck whether the document that will be validated
- * has the right signedinfo
+ * Precheck whether the document that will be validated has the right signedinfo
+ *
* @param doc
* @return
*/
@@ -131,18 +130,25 @@
/**
* Sign a node in a document
- * @param doc Document
- * @param parentOfNodeToBeSigned Parent Node of the node to be signed
- * @param signingKey Private Key
- * @param certificate X509 Certificate holding the public key
- * @param digestMethod (Example: DigestMethod.SHA1)
- * @param signatureMethod (Example: SignatureMethod.DSA_SHA1)
+ *
+ * @param doc
+ * Document
+ * @param parentOfNodeToBeSigned
+ * Parent Node of the node to be signed
+ * @param signingKey
+ * Private Key
+ * @param certificate
+ * X509 Certificate holding the public key
+ * @param digestMethod
+ * (Example: DigestMethod.SHA1)
+ * @param signatureMethod
+ * (Example: SignatureMethod.DSA_SHA1)
* @param referenceURI
* @return Document that contains the signed node
- * @throws XMLSignatureException
- * @throws MarshalException
- * @throws GeneralSecurityException
- * @throws ParserConfigurationException
+ * @throws XMLSignatureException
+ * @throws MarshalException
+ * @throws GeneralSecurityException
+ * @throws ParserConfigurationException
*/
public static Document sign(Document doc, Node parentOfNodeToBeSigned, PrivateKey signingKey,
X509Certificate certificate, String digestMethod, String signatureMethod, String referenceURI)
@@ -154,6 +160,7 @@
/**
* Sign a node in a document
+ *
* @param doc
* @param nodeToBeSigned
* @param keyPair
@@ -162,10 +169,10 @@
* @param signatureMethod
* @param referenceURI
* @return
- * @throws ParserConfigurationException
- * @throws XMLSignatureException
- * @throws MarshalException
- * @throws GeneralSecurityException
+ * @throws ParserConfigurationException
+ * @throws XMLSignatureException
+ * @throws MarshalException
+ * @throws GeneralSecurityException
*/
public static Document sign(Document doc, Node nodeToBeSigned, KeyPair keyPair, String digestMethod,
String signatureMethod, String referenceURI) throws ParserConfigurationException, GeneralSecurityException,
@@ -180,35 +187,50 @@
Node parentNode = nodeToBeSigned.getParentNode();
- //Let us create a new Document
+ // Let us create a new Document
Document newDoc = DocumentUtil.createDocument();
- //Import the node
+ // Import the node
Node signingNode = newDoc.importNode(nodeToBeSigned, true);
newDoc.appendChild(signingNode);
newDoc = sign(newDoc, keyPair, digestMethod, signatureMethod, referenceURI);
- //Now let us import this signed doc into the original document we got in the method call
+ // if the signed element is a SAMLv2.0 assertion we need to move the signature element to the position
+ // specified in the schema (before the assertion subject element).
+ if (nodeToBeSigned.getLocalName().equals("Assertion")
+ && WSTrustConstants.SAML2_ASSERTION_NS.equals(nodeToBeSigned.getNamespaceURI()))
+ {
+ Node signatureNode = DocumentUtil.getElement(newDoc, new QName(WSTrustConstants.DSIG_NS, "Signature"));
+ Node subjectNode = DocumentUtil.getElement(newDoc, new QName(WSTrustConstants.SAML2_ASSERTION_NS, "Subject"));
+ if (signatureNode != null && subjectNode != null)
+ {
+ newDoc.getDocumentElement().removeChild(signatureNode);
+ newDoc.getDocumentElement().insertBefore(signatureNode, subjectNode);
+ }
+ }
+
+ // Now let us import this signed doc into the original document we got in the method call
Node signedNode = doc.importNode(newDoc.getFirstChild(), true);
parentNode.replaceChild(signedNode, nodeToBeSigned);
- //doc.getDocumentElement().replaceChild(signedNode, nodeToBeSigned);
+ // doc.getDocumentElement().replaceChild(signedNode, nodeToBeSigned);
return doc;
}
/**
* Sign the root element
- * @param doc
+ *
+ * @param doc
* @param signingKey
* @param publicKey
* @param digestMethod
* @param signatureMethod
* @param referenceURI
- * @return
- * @throws GeneralSecurityException
- * @throws XMLSignatureException
- * @throws MarshalException
+ * @return
+ * @throws GeneralSecurityException
+ * @throws XMLSignatureException
+ * @throws MarshalException
*/
public static Document sign(Document doc, KeyPair keyPair, String digestMethod, String signatureMethod,
String referenceURI) throws GeneralSecurityException, MarshalException, XMLSignatureException
@@ -253,11 +275,12 @@
/**
* Validate a signed document with the given public key
+ *
* @param signedDoc
* @param publicKey
- * @return
- * @throws MarshalException
- * @throws XMLSignatureException
+ * @return
+ * @throws MarshalException
+ * @throws XMLSignatureException
*/
@SuppressWarnings("unchecked")
public static boolean validate(Document signedDoc, Key publicKey) throws MarshalException, XMLSignatureException
@@ -293,24 +316,27 @@
/**
* Marshall a SignatureType to output stream
+ *
* @param signature
- * @param os
- * @throws SAXException
- * @throws JAXBException
+ * @param os
+ * @throws SAXException
+ * @throws JAXBException
*/
public static void marshall(SignatureType signature, OutputStream os) throws JAXBException, SAXException
{
throw new RuntimeException("NYI");
- /*JAXBElement<SignatureType> jsig = objectFactory.createSignature(signature);
- Marshaller marshaller = JAXBUtil.getValidatingMarshaller(pkgName, schemaLocation);
- marshaller.marshal(jsig, os);*/
+ /*
+ * JAXBElement<SignatureType> jsig = objectFactory.createSignature(signature); Marshaller marshaller =
+ * JAXBUtil.getValidatingMarshaller(pkgName, schemaLocation); marshaller.marshal(jsig, os);
+ */
}
/**
* Marshall the signed document to an output stream
+ *
* @param signedDocument
* @param os
- * @throws TransformerException
+ * @throws TransformerException
*/
public static void marshall(Document signedDocument, OutputStream os) throws TransformerException
{
@@ -321,6 +347,7 @@
/**
* Given the X509Certificate in the keyinfo element, get a {@link X509Certificate}
+ *
* @param certificateString
* @return
* @throws ProcessingException
Modified: federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/wstrust/StandardRequestHandler.java
===================================================================
--- federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/wstrust/StandardRequestHandler.java 2011-07-13 19:35:11 UTC (rev 1088)
+++ federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/wstrust/StandardRequestHandler.java 2011-07-14 15:04:04 UTC (rev 1089)
@@ -394,7 +394,7 @@
// create a context and dispatch to the proper security token provider for renewal.
WSTrustRequestContext context = new WSTrustRequestContext(request, callerPrincipal);
-
+ context.setTokenIssuer(this.configuration.getSTSName());
// if the renew request was made on behalf of another identity, get the principal of that identity.
if (request.getOnBehalfOf() != null)
{
Modified: federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/wstrust/WSTrustConstants.java
===================================================================
--- federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/wstrust/WSTrustConstants.java 2011-07-13 19:35:11 UTC (rev 1088)
+++ federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/wstrust/WSTrustConstants.java 2011-07-14 15:04:04 UTC (rev 1089)
@@ -101,8 +101,6 @@
QName FAILED_AUTHENTICATION = new QName(WSSE_NS, "FailedAuthentication");
//Token Types
- String SAML2_TOKEN_TYPE = "http://docs.oasis-open.org/wss/oasis-wss-saml-token-profile-1.1#SAMLV2.0";
-
String RSTR_STATUS_TOKEN_TYPE = "http://docs.oasis-open.org/ws-sx/ws-trust/200512/RSTR/Status";
//Element Names
Modified: federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/wstrust/auth/STSIssuingLoginModule.java
===================================================================
--- federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/wstrust/auth/STSIssuingLoginModule.java 2011-07-13 19:35:11 UTC (rev 1088)
+++ federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/wstrust/auth/STSIssuingLoginModule.java 2011-07-14 15:04:04 UTC (rev 1089)
@@ -29,8 +29,8 @@
import javax.security.auth.login.LoginException;
import org.picketlink.identity.federation.core.wstrust.STSClient;
-import org.picketlink.identity.federation.core.wstrust.WSTrustConstants;
import org.picketlink.identity.federation.core.wstrust.WSTrustException;
+import org.picketlink.identity.federation.core.wstrust.plugins.saml.SAMLUtil;
import org.w3c.dom.Element;
/**
@@ -79,7 +79,7 @@
endpointURI = (String) options.get(ENDPOINT_ADDRESS); //base class
tokenType = (String) options.get(TOKEN_TYPE_OPTION);
if (tokenType == null)
- tokenType = WSTrustConstants.SAML2_TOKEN_TYPE;
+ tokenType = SAMLUtil.SAML2_TOKEN_TYPE;
}
/**
Modified: federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/wstrust/plugins/saml/SAML20TokenProvider.java
===================================================================
--- federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/wstrust/plugins/saml/SAML20TokenProvider.java 2011-07-13 19:35:11 UTC (rev 1088)
+++ federation/trunk/picketlink-fed-core/src/main/java/org/picketlink/identity/federation/core/wstrust/plugins/saml/SAML20TokenProvider.java 2011-07-14 15:04:04 UTC (rev 1089)
@@ -405,7 +405,7 @@
*/
public String tokenType()
{
- return WSTrustConstants.SAML2_TOKEN_TYPE;
+ return SAMLUtil.SAML2_TOKEN_TYPE;
}
/**
Modified: federation/trunk/picketlink-fed-core/src/test/java/org/picketlink/test/identity/federation/core/parser/wst/WSTResponseAssertionHOKCertificateTestCase.java
===================================================================
--- federation/trunk/picketlink-fed-core/src/test/java/org/picketlink/test/identity/federation/core/parser/wst/WSTResponseAssertionHOKCertificateTestCase.java 2011-07-13 19:35:11 UTC (rev 1088)
+++ federation/trunk/picketlink-fed-core/src/test/java/org/picketlink/test/identity/federation/core/parser/wst/WSTResponseAssertionHOKCertificateTestCase.java 2011-07-14 15:04:04 UTC (rev 1089)
@@ -33,6 +33,7 @@
import org.picketlink.identity.federation.core.parsers.wst.WSTrustParser;
import org.picketlink.identity.federation.core.saml.v2.util.XMLTimeUtil;
import org.picketlink.identity.federation.core.wstrust.WSTrustConstants;
+import org.picketlink.identity.federation.core.wstrust.plugins.saml.SAMLUtil;
import org.picketlink.identity.federation.core.wstrust.wrappers.RequestSecurityTokenResponse;
import org.picketlink.identity.federation.core.wstrust.wrappers.RequestSecurityTokenResponseCollection;
import org.picketlink.identity.federation.ws.addressing.EndpointReferenceType;
@@ -60,7 +61,7 @@
RequestSecurityTokenResponse rstr = coll.getRequestSecurityTokenResponses().get(0);
assertEquals("testcontext", rstr.getContext());
- assertEquals(WSTrustConstants.SAML2_TOKEN_TYPE, rstr.getTokenType().toASCIIString());
+ assertEquals(SAMLUtil.SAML2_TOKEN_TYPE, rstr.getTokenType().toASCIIString());
assertEquals(XMLTimeUtil.parse("2010-11-11T16:34:19.602Z"), rstr.getLifetime().getCreated());
assertEquals(XMLTimeUtil.parse("2010-11-11T18:34:19.602Z"), rstr.getLifetime().getExpires());
@@ -82,7 +83,7 @@
Map<QName, String> map = secRef.getOtherAttributes();
QName wsseTokenType = new QName(WSTrustConstants.WSSE11_NS, WSTrustConstants.TOKEN_TYPE,
WSTrustConstants.WSSE.PREFIX_11);
- assertEquals(WSTrustConstants.SAML2_TOKEN_TYPE, map.get(wsseTokenType));
+ assertEquals(SAMLUtil.SAML2_TOKEN_TYPE, map.get(wsseTokenType));
KeyIdentifierType keyId = (KeyIdentifierType) secRef.getAny().get(0);
assertEquals("#ID_5a15fc70-daa1-4808-b70e-9cbf6b8e4d4f", keyId.getValue());
Modified: federation/trunk/picketlink-fed-core/src/test/java/org/picketlink/test/identity/federation/core/parser/wst/WSTrustBatchIssueParsingTestCase.java
===================================================================
--- federation/trunk/picketlink-fed-core/src/test/java/org/picketlink/test/identity/federation/core/parser/wst/WSTrustBatchIssueParsingTestCase.java 2011-07-13 19:35:11 UTC (rev 1088)
+++ federation/trunk/picketlink-fed-core/src/test/java/org/picketlink/test/identity/federation/core/parser/wst/WSTrustBatchIssueParsingTestCase.java 2011-07-14 15:04:04 UTC (rev 1089)
@@ -34,6 +34,7 @@
import org.picketlink.identity.federation.core.saml.v2.util.DocumentUtil;
import org.picketlink.identity.federation.core.util.JAXPValidationUtil;
import org.picketlink.identity.federation.core.wstrust.WSTrustConstants;
+import org.picketlink.identity.federation.core.wstrust.plugins.saml.SAMLUtil;
import org.picketlink.identity.federation.core.wstrust.wrappers.RequestSecurityToken;
import org.picketlink.identity.federation.core.wstrust.wrappers.RequestSecurityTokenCollection;
import org.picketlink.identity.federation.core.wstrust.writers.WSTrustRequestWriter;
@@ -66,7 +67,7 @@
RequestSecurityToken rst1 = tokens.get(0);
assertEquals("context1", rst1.getContext());
assertEquals(WSTrustConstants.BATCH_ISSUE_REQUEST, rst1.getRequestType().toASCIIString());
- assertEquals(WSTrustConstants.SAML2_TOKEN_TYPE, rst1.getTokenType().toASCIIString());
+ assertEquals(SAMLUtil.SAML2_TOKEN_TYPE, rst1.getTokenType().toASCIIString());
RequestSecurityToken rst2 = tokens.get(1);
assertEquals("context2", rst2.getContext());
Modified: federation/trunk/picketlink-fed-core/src/test/java/org/picketlink/test/identity/federation/core/parser/wst/WSTrustBatchValidateParsingTestCase.java
===================================================================
--- federation/trunk/picketlink-fed-core/src/test/java/org/picketlink/test/identity/federation/core/parser/wst/WSTrustBatchValidateParsingTestCase.java 2011-07-13 19:35:11 UTC (rev 1088)
+++ federation/trunk/picketlink-fed-core/src/test/java/org/picketlink/test/identity/federation/core/parser/wst/WSTrustBatchValidateParsingTestCase.java 2011-07-14 15:04:04 UTC (rev 1089)
@@ -77,6 +77,8 @@
Document doc = DocumentUtil.getDocument(new ByteArrayInputStream(baos.toByteArray()));
baos.close();
+
+ System.out.println(DocumentUtil.asString(doc));
JAXPValidationUtil.validate(DocumentUtil.getNodeAsStream(doc));
}
Modified: federation/trunk/picketlink-fed-core/src/test/java/org/picketlink/test/identity/federation/core/parser/wst/WSTrustCancelTargetSamlTestCase.java
===================================================================
--- federation/trunk/picketlink-fed-core/src/test/java/org/picketlink/test/identity/federation/core/parser/wst/WSTrustCancelTargetSamlTestCase.java 2011-07-13 19:35:11 UTC (rev 1088)
+++ federation/trunk/picketlink-fed-core/src/test/java/org/picketlink/test/identity/federation/core/parser/wst/WSTrustCancelTargetSamlTestCase.java 2011-07-14 15:04:04 UTC (rev 1089)
@@ -36,6 +36,7 @@
import org.picketlink.identity.federation.core.saml.v2.util.DocumentUtil;
import org.picketlink.identity.federation.core.util.JAXPValidationUtil;
import org.picketlink.identity.federation.core.wstrust.WSTrustConstants;
+import org.picketlink.identity.federation.core.wstrust.plugins.saml.SAMLUtil;
import org.picketlink.identity.federation.core.wstrust.wrappers.RequestSecurityToken;
import org.picketlink.identity.federation.core.wstrust.writers.WSTrustRequestWriter;
import org.picketlink.identity.federation.saml.v2.assertion.AssertionType;
@@ -45,6 +46,7 @@
import org.picketlink.identity.federation.saml.v2.assertion.SubjectType;
import org.picketlink.identity.federation.ws.trust.CancelTargetType;
import org.w3c.dom.Document;
+import org.w3c.dom.Element;
/**
* Validate the WST Cancel Target for SAML assertions
@@ -66,7 +68,8 @@
CancelTargetType cancelTarget = requestToken.getCancelTarget();
- AssertionType assertion = (AssertionType) cancelTarget.getAny().get(0);
+ Element assertionElement = (Element) cancelTarget.getAny().get(0);
+ AssertionType assertion = SAMLUtil.fromElement(assertionElement);
validateAssertion(assertion);
//Now for the writing part
Modified: federation/trunk/picketlink-fed-core/src/test/java/org/picketlink/test/identity/federation/core/parser/wst/WSTrustIssueTestCase.java
===================================================================
--- federation/trunk/picketlink-fed-core/src/test/java/org/picketlink/test/identity/federation/core/parser/wst/WSTrustIssueTestCase.java 2011-07-13 19:35:11 UTC (rev 1088)
+++ federation/trunk/picketlink-fed-core/src/test/java/org/picketlink/test/identity/federation/core/parser/wst/WSTrustIssueTestCase.java 2011-07-14 15:04:04 UTC (rev 1089)
@@ -32,6 +32,7 @@
import org.picketlink.identity.federation.core.saml.v2.util.DocumentUtil;
import org.picketlink.identity.federation.core.util.JAXPValidationUtil;
import org.picketlink.identity.federation.core.wstrust.WSTrustConstants;
+import org.picketlink.identity.federation.core.wstrust.plugins.saml.SAMLUtil;
import org.picketlink.identity.federation.core.wstrust.wrappers.RequestSecurityToken;
import org.picketlink.identity.federation.core.wstrust.writers.WSTrustRequestWriter;
import org.w3c.dom.Document;
@@ -54,7 +55,7 @@
assertEquals("testcontext", requestToken.getContext());
assertEquals(WSTrustConstants.ISSUE_REQUEST, requestToken.getRequestType().toASCIIString());
- assertEquals(WSTrustConstants.SAML2_TOKEN_TYPE, requestToken.getTokenType().toASCIIString());
+ assertEquals(SAMLUtil.SAML2_TOKEN_TYPE, requestToken.getTokenType().toASCIIString());
//Now for the writing part
ByteArrayOutputStream baos = new ByteArrayOutputStream();
Modified: federation/trunk/picketlink-fed-core/src/test/java/org/picketlink/test/identity/federation/core/parser/wst/WSTrustRenewTargetParsingTestCase.java
===================================================================
--- federation/trunk/picketlink-fed-core/src/test/java/org/picketlink/test/identity/federation/core/parser/wst/WSTrustRenewTargetParsingTestCase.java 2011-07-13 19:35:11 UTC (rev 1088)
+++ federation/trunk/picketlink-fed-core/src/test/java/org/picketlink/test/identity/federation/core/parser/wst/WSTrustRenewTargetParsingTestCase.java 2011-07-14 15:04:04 UTC (rev 1089)
@@ -32,6 +32,7 @@
import org.picketlink.identity.federation.core.saml.v2.util.DocumentUtil;
import org.picketlink.identity.federation.core.util.JAXPValidationUtil;
import org.picketlink.identity.federation.core.wstrust.WSTrustConstants;
+import org.picketlink.identity.federation.core.wstrust.plugins.saml.SAMLUtil;
import org.picketlink.identity.federation.core.wstrust.wrappers.RequestSecurityToken;
import org.picketlink.identity.federation.core.wstrust.writers.WSTrustRequestWriter;
import org.picketlink.identity.federation.saml.v2.assertion.AssertionType;
@@ -39,6 +40,7 @@
import org.picketlink.identity.federation.saml.v2.assertion.SubjectType;
import org.picketlink.identity.federation.ws.trust.RenewTargetType;
import org.w3c.dom.Document;
+import org.w3c.dom.Element;
/**
* Validate the parsing of wst-batch-validate.xml
@@ -57,10 +59,11 @@
RequestSecurityToken requestToken = (RequestSecurityToken) parser.parse(configStream);
assertEquals("renewcontext", requestToken.getContext());
assertEquals(WSTrustConstants.RENEW_REQUEST, requestToken.getRequestType().toASCIIString());
- assertEquals(WSTrustConstants.SAML2_TOKEN_TYPE, requestToken.getTokenType().toASCIIString());
+ assertEquals(SAMLUtil.SAML2_TOKEN_TYPE, requestToken.getTokenType().toASCIIString());
RenewTargetType renewTarget = requestToken.getRenewTarget();
- AssertionType assertion = (AssertionType) renewTarget.getAny().get(0);
+ Element assertionElement = (Element) renewTarget.getAny().get(0);
+ AssertionType assertion = SAMLUtil.fromElement(assertionElement);
assertEquals("ID_654b6092-c725-40ea-8044-de453b59cb28", assertion.getID());
assertEquals("Test STS", assertion.getIssuer().getValue());
SubjectType subject = assertion.getSubject();
Modified: federation/trunk/picketlink-fed-core/src/test/java/org/picketlink/test/identity/federation/core/parser/wst/WSTrustValidateSamlTestCase.java
===================================================================
--- federation/trunk/picketlink-fed-core/src/test/java/org/picketlink/test/identity/federation/core/parser/wst/WSTrustValidateSamlTestCase.java 2011-07-13 19:35:11 UTC (rev 1088)
+++ federation/trunk/picketlink-fed-core/src/test/java/org/picketlink/test/identity/federation/core/parser/wst/WSTrustValidateSamlTestCase.java 2011-07-14 15:04:04 UTC (rev 1089)
@@ -32,11 +32,13 @@
import org.picketlink.identity.federation.core.saml.v2.util.DocumentUtil;
import org.picketlink.identity.federation.core.util.JAXPValidationUtil;
import org.picketlink.identity.federation.core.wstrust.WSTrustConstants;
+import org.picketlink.identity.federation.core.wstrust.plugins.saml.SAMLUtil;
import org.picketlink.identity.federation.core.wstrust.wrappers.RequestSecurityToken;
import org.picketlink.identity.federation.core.wstrust.writers.WSTrustRequestWriter;
import org.picketlink.identity.federation.saml.v2.assertion.AssertionType;
import org.picketlink.identity.federation.ws.trust.ValidateTargetType;
import org.w3c.dom.Document;
+import org.w3c.dom.Element;
/**
* Validate the parsing of wst-validate-saml.xml
@@ -58,7 +60,8 @@
assertEquals(WSTrustConstants.RSTR_STATUS_TOKEN_TYPE, rst1.getTokenType().toASCIIString());
ValidateTargetType validateTarget = rst1.getValidateTarget();
- AssertionType assertion = (AssertionType) validateTarget.getAny().get(0);
+ Element assertionElement = (Element) validateTarget.getAny().get(0);
+ AssertionType assertion = SAMLUtil.fromElement(assertionElement);
assertEquals("ID_654b6092-c725-40ea-8044-de453b59cb28", assertion.getID());
//Now for the writing part
Modified: federation/trunk/picketlink-fed-core/src/test/java/org/picketlink/test/identity/federation/core/wstrust/PicketLinkSTSUnitTestCase.java
===================================================================
--- federation/trunk/picketlink-fed-core/src/test/java/org/picketlink/test/identity/federation/core/wstrust/PicketLinkSTSUnitTestCase.java 2011-07-13 19:35:11 UTC (rev 1088)
+++ federation/trunk/picketlink-fed-core/src/test/java/org/picketlink/test/identity/federation/core/wstrust/PicketLinkSTSUnitTestCase.java 2011-07-14 15:04:04 UTC (rev 1089)
@@ -59,6 +59,7 @@
import org.picketlink.identity.federation.core.interfaces.SecurityTokenProvider;
import org.picketlink.identity.federation.core.parsers.sts.STSConfigParser;
import org.picketlink.identity.federation.core.parsers.wst.WSTrustParser;
+import org.picketlink.identity.federation.core.saml.v1.SAML11Constants;
import org.picketlink.identity.federation.core.saml.v2.common.IDGenerator;
import org.picketlink.identity.federation.core.saml.v2.constants.JBossSAMLConstants;
import org.picketlink.identity.federation.core.saml.v2.constants.JBossSAMLURIConstants;
@@ -73,6 +74,7 @@
import org.picketlink.identity.federation.core.wstrust.WSTrustException;
import org.picketlink.identity.federation.core.wstrust.WSTrustRequestHandler;
import org.picketlink.identity.federation.core.wstrust.WSTrustUtil;
+import org.picketlink.identity.federation.core.wstrust.plugins.saml.SAML11TokenProvider;
import org.picketlink.identity.federation.core.wstrust.plugins.saml.SAML20TokenProvider;
import org.picketlink.identity.federation.core.wstrust.plugins.saml.SAMLUtil;
import org.picketlink.identity.federation.core.wstrust.wrappers.BaseRequestSecurityTokenResponse;
@@ -81,6 +83,12 @@
import org.picketlink.identity.federation.core.wstrust.wrappers.RequestSecurityTokenResponse;
import org.picketlink.identity.federation.core.wstrust.wrappers.RequestSecurityTokenResponseCollection;
import org.picketlink.identity.federation.core.wstrust.writers.WSTrustRequestWriter;
+import org.picketlink.identity.federation.saml.v1.assertion.SAML11AssertionType;
+import org.picketlink.identity.federation.saml.v1.assertion.SAML11AuthenticationStatementType;
+import org.picketlink.identity.federation.saml.v1.assertion.SAML11NameIdentifierType;
+import org.picketlink.identity.federation.saml.v1.assertion.SAML11StatementAbstractType;
+import org.picketlink.identity.federation.saml.v1.assertion.SAML11SubjectConfirmationType;
+import org.picketlink.identity.federation.saml.v1.assertion.SAML11SubjectType;
import org.picketlink.identity.federation.saml.v2.assertion.AssertionType;
import org.picketlink.identity.federation.saml.v2.assertion.AudienceRestrictionType;
import org.picketlink.identity.federation.saml.v2.assertion.ConditionAbstractType;
@@ -157,9 +165,20 @@
* <RequestHandler>org.jboss.identity.federation.core.wstrust.StandardRequestHandler</RequestHandler>
* <TokenProviders>
* <TokenProvider ProviderClass="org.jboss.test.identity.federation.bindings.trust.SpecialTokenProvider"
- * TokenType="http://www.tokens.org/SpecialToken"/>
+ * TokenType="http://www.tokens.org/SpecialToken"
+ * TokenElement="SpecialToken"
+ * TokenElementNS="http://www.tokens.org">
+ * <Property Key="Property1" Value="Value1"/>
+ * <Property Key="Property2" Value="Value2"/>
+ * </TokenProvider>
+ * <TokenProvider ProviderClass="org.jboss.identity.federation.core.wstrust.SAML11TokenProvider"
+ * TokenType="http://docs.oasis-open.org/wss/oasis-wss-saml-token-profi...
+ * TokenElement="Assertion"
+ * TokenElementNS="urn:oasis:names:tc:SAML:1.0:assertion"/>
* <TokenProvider ProviderClass="org.jboss.identity.federation.core.wstrust.SAML20TokenProvider"
- * TokenType="http://docs.oasis-open.org/wss/oasis-wss-saml-token-profi...
+ * TokenType="http://docs.oasis-open.org/wss/oasis-wss-saml-token-profi...
+ * TokenElement="Assertion"
+ * TokenElementNS="urn:oasis:names:tc:SAML:2.0:assertion"/>/>
* </TokenProviders>
* <ServiceProviders>
* <ServiceProvider Endpoint="http://services.testcorp.org/provider1" TokenType="http://www.tokens.org/SpecialToken"
@@ -201,6 +220,9 @@
provider = config.getProviderForTokenType(SAMLUtil.SAML2_TOKEN_TYPE);
assertNotNull("Unexpected null token provider", provider);
assertTrue("Unexpected token provider type", provider instanceof SAML20TokenProvider);
+ provider = config.getProviderForTokenType(SAMLUtil.SAML11_TOKEN_TYPE);
+ assertNotNull("Unexpected null token provider", provider);
+ assertTrue("Unexpected token provider type", provider instanceof SAML11TokenProvider);
assertNull(config.getProviderForTokenType("unexistentType"));
// check the service provider -> token provider mapping.
@@ -222,23 +244,27 @@
JBossSAMLConstants.ASSERTION.get()));
assertNotNull("Unexpected null token provider", provider);
assertTrue("Unexpected token provider type", provider instanceof SAML20TokenProvider);
+ provider = config.getProviderForTokenElementNS(family, new QName(SAML11Constants.ASSERTION_11_NSURI,
+ JBossSAMLConstants.ASSERTION.get()));
+ assertNotNull("Unexpected null token provider", provider);
+ assertTrue("Unexpected token provider type", provider instanceof SAML11TokenProvider);
assertNull(config.getProviderForTokenElementNS(family, new QName("InvalidNamespace", "SpecialToken")));
// check the service provider -> token type mapping.
- assertEquals("Invalid token type for service provider 1", "http://www.tokens.org/SpecialToken",
- config.getTokenTypeForService("http://services.testcorp.org/provider1"));
- assertEquals("Invalid token type for service provider 2", SAMLUtil.SAML2_TOKEN_TYPE,
- config.getTokenTypeForService("http://services.testcorp.org/provider2"));
+ assertEquals("Invalid token type for service provider 1", "http://www.tokens.org/SpecialToken", config
+ .getTokenTypeForService("http://services.testcorp.org/provider1"));
+ assertEquals("Invalid token type for service provider 2", SAMLUtil.SAML2_TOKEN_TYPE, config
+ .getTokenTypeForService("http://services.testcorp.org/provider2"));
assertNull(config.getTokenTypeForService("http://invalid.service/service"));
// check the keystore configuration.
assertNotNull("Invalid null STS key pair", config.getSTSKeyPair());
assertNotNull("Invalid null STS public key", config.getSTSKeyPair().getPublic());
assertNotNull("Invalid null STS private key", config.getSTSKeyPair().getPrivate());
- assertNotNull("Invalid null validating key for service provider 1",
- config.getServiceProviderPublicKey("http://services.testcorp.org/provider1"));
- assertNotNull("Invalid null validating key for service provider 2",
- config.getServiceProviderPublicKey("http://services.testcorp.org/provider2"));
+ assertNotNull("Invalid null validating key for service provider 1", config
+ .getServiceProviderPublicKey("http://services.testcorp.org/provider1"));
+ assertNotNull("Invalid null validating key for service provider 2", config
+ .getServiceProviderPublicKey("http://services.testcorp.org/provider2"));
}
/**
@@ -276,6 +302,31 @@
/**
* <p>
+ * This tests sends a SAMLV2.0 security token request to PicketLinkSTS. This request should be handled by the {@code
+ * SAML11TokenProvider} and should result in a SAMLV1.1 assertion.
+ * </p>
+ *
+ * @throws Exception
+ * if an error occurs while running the test.
+ */
+ @Test
+ public void testInvokeSAML11() throws Exception
+ {
+ // create a simple token request, asking for a SAMLv1.1 token.
+ RequestSecurityToken request = this.createRequest("testcontext", WSTrustConstants.ISSUE_REQUEST,
+ SAMLUtil.SAML11_TOKEN_TYPE, null);
+ Source requestMessage = this.createSourceFromRequest(request);
+
+ // invoke the token service.
+ Source responseMessage = this.tokenService.invoke(requestMessage);
+ InputStream is = DocumentUtil.getSourceAsStream(responseMessage);
+ BaseRequestSecurityTokenResponse baseResponse = (BaseRequestSecurityTokenResponse) new WSTrustParser().parse(is);
+ // validate the security token response.
+ this.validateSAML11AssertionResponse(baseResponse, "testcontext", "jduke", SAMLUtil.SAML11_BEARER_URI);
+ }
+
+ /**
+ * <p>
* This tests sends a SAMLV2.0 security token request to PicketLinkSTS. This request should be handled by the
* standard {@code SAML20TokenProvider} and should result in a SAMLV2.0 assertion that looks like the following:
*
@@ -608,6 +659,78 @@
/**
* <p>
+ * This test case first generates a SAMLV1.1 assertion and then sends a WS-Trust validate message to the STS to get
+ * the assertion validated, checking the validation results.
+ * </p>
+ *
+ * @throws Exception
+ * if an error occurs while running the test.
+ */
+ @Test
+ public void testInvokeSAML11Validate() throws Exception
+ {
+ // create a simple token request.
+ RequestSecurityToken request = this.createRequest("testcontext", WSTrustConstants.ISSUE_REQUEST,
+ SAMLUtil.SAML11_TOKEN_TYPE, null);
+
+ Source requestMessage = this.createSourceFromRequest(request);
+
+ // invoke the token service.
+ Source responseMessage = this.tokenService.invoke(requestMessage);
+ WSTrustParser parser = new WSTrustParser();
+ BaseRequestSecurityTokenResponse baseResponse = (BaseRequestSecurityTokenResponse) parser.parse(DocumentUtil
+ .getSourceAsStream(responseMessage));
+
+ // validate the response and get the SAML assertion from the request.
+ this.validateSAML11AssertionResponse(baseResponse, "testcontext", "jduke", SAMLUtil.SAML11_BEARER_URI);
+ RequestSecurityTokenResponseCollection collection = (RequestSecurityTokenResponseCollection) baseResponse;
+ Element assertion = (Element) collection.getRequestSecurityTokenResponses().get(0).getRequestedSecurityToken()
+ .getAny().get(0);
+
+ // now construct a WS-Trust validate request with the generated assertion.
+ request = this.createRequest("validatecontext", WSTrustConstants.VALIDATE_REQUEST, WSTrustConstants.STATUS_TYPE,
+ null);
+ ValidateTargetType validateTarget = new ValidateTargetType();
+ validateTarget.add(assertion);
+ request.setValidateTarget(validateTarget);
+
+ // invoke the token service.
+ responseMessage = this.tokenService.invoke(this.createSourceFromRequest(request));
+ baseResponse = (BaseRequestSecurityTokenResponse) parser.parse(DocumentUtil.getSourceAsStream(responseMessage));
+
+ // validate the response contents.
+ assertNotNull("Unexpected null response", baseResponse);
+ assertTrue("Unexpected response type", baseResponse instanceof RequestSecurityTokenResponseCollection);
+ collection = (RequestSecurityTokenResponseCollection) baseResponse;
+ assertEquals("Unexpected number of responses", 1, collection.getRequestSecurityTokenResponses().size());
+ RequestSecurityTokenResponse response = collection.getRequestSecurityTokenResponses().get(0);
+ assertEquals("Unexpected response context", "validatecontext", response.getContext());
+ assertEquals("Unexpected token type", WSTrustConstants.STATUS_TYPE, response.getTokenType().toString());
+ StatusType status = response.getStatus();
+ assertNotNull("Unexpected null status", status);
+ assertEquals("Unexpected status code", WSTrustConstants.STATUS_CODE_VALID, status.getCode());
+ assertEquals("Unexpected status reason", "SAMLV1.1 Assertion successfuly validated", status.getReason());
+
+ // now let's temper the SAML assertion and try to validate it again.
+ // assertion.getAttributeNode("Issuer").setNodeValue("ABC");
+ // request.getValidateTarget().add(assertion);
+ // Source theRequest = this.createSourceFromRequest(request);
+ // responseMessage = this.tokenService.invoke(theRequest);
+ // collection = (RequestSecurityTokenResponseCollection) parser.parse(DocumentUtil
+ // .getSourceAsStream(responseMessage));
+ // assertEquals("Unexpected number of responses", 1, collection.getRequestSecurityTokenResponses().size());
+ // response = collection.getRequestSecurityTokenResponses().get(0);
+ // assertEquals("Unexpected response context", "validatecontext", response.getContext());
+ // assertEquals("Unexpected token type", WSTrustConstants.STATUS_TYPE, response.getTokenType().toString());
+ // status = response.getStatus();
+ // assertNotNull("Unexpected null status", status);
+ // assertEquals("Unexpected status code", WSTrustConstants.STATUS_CODE_INVALID, status.getCode());
+ // assertEquals("Unexpected status reason", "Validation failure: digital signature is invalid",
+ // status.getReason());
+ }
+
+ /**
+ * <p>
* This test case first generates a SAMLV2.0 assertion and then sends a WS-Trust validate message to the STS to get
* the assertion validated, checking the validation results.
* </p>
@@ -661,7 +784,7 @@
assertEquals("Unexpected status reason", "SAMLV2.0 Assertion successfuly validated", status.getReason());
// now let's temper the SAML assertion and try to validate it again.
- assertion.getFirstChild().getFirstChild().setNodeValue("Tempered Issuer");
+ assertion.setAttribute("Version", "X");
request.getValidateTarget().add(assertion);
Source theRequest = this.createSourceFromRequest(request);
responseMessage = this.tokenService.invoke(theRequest);
@@ -679,6 +802,65 @@
/**
* <p>
+ * This test case first generates a SAMLV1.1 assertion and then sends a WS-Trust renew message to the STS to get the
+ * assertion renewed (i.e. get a new assertion with an updated lifetime).
+ * </p>
+ *
+ * @throws Exception
+ * if an error occurs while running the test.
+ */
+ @Test
+ public void testInvokeSAML11Renew() throws Exception
+ {
+ // create a simple token request.
+ RequestSecurityToken request = this.createRequest("testcontext", WSTrustConstants.ISSUE_REQUEST,
+ SAMLUtil.SAML11_TOKEN_TYPE, null);
+
+ Source requestMessage = this.createSourceFromRequest(request);
+
+ // invoke the token service.
+ Source responseMessage = this.tokenService.invoke(requestMessage);
+ WSTrustParser parser = new WSTrustParser();
+ BaseRequestSecurityTokenResponse baseResponse = (BaseRequestSecurityTokenResponse) parser.parse(DocumentUtil
+ .getSourceAsStream(responseMessage));
+
+ // validate the response and get the SAML assertion from the request.
+ this.validateSAML11AssertionResponse(baseResponse, "testcontext", "jduke", SAMLUtil.SAML11_BEARER_URI);
+ RequestSecurityTokenResponseCollection collection = (RequestSecurityTokenResponseCollection) baseResponse;
+ Element assertionElement = (Element) collection.getRequestSecurityTokenResponses().get(0)
+ .getRequestedSecurityToken().getAny().get(0);
+
+ // now construct a WS-Trust renew request with the generated assertion.
+ request = this.createRequest("renewcontext", WSTrustConstants.RENEW_REQUEST, SAMLUtil.SAML11_TOKEN_TYPE, null);
+ RenewTargetType renewTarget = new RenewTargetType();
+ renewTarget.add(assertionElement);
+ request.setRenewTarget(renewTarget);
+
+ // invoke the token service.
+ responseMessage = this.tokenService.invoke(this.createSourceFromRequest(request));
+ baseResponse = (BaseRequestSecurityTokenResponse) parser.parse(DocumentUtil.getSourceAsStream(responseMessage));
+
+ // validate the renew response contents and get the renewed token.
+ this.validateSAML11AssertionResponse(baseResponse, "renewcontext", "jduke", SAMLUtil.SAML11_BEARER_URI);
+ collection = (RequestSecurityTokenResponseCollection) baseResponse;
+ Element renewedAssertionElement = (Element) collection.getRequestSecurityTokenResponses().get(0)
+ .getRequestedSecurityToken().getAny().get(0);
+
+ // compare the assertions, checking if the lifetime has been updated.
+ SAML11AssertionType originalAssertion = SAMLUtil.saml11FromElement(assertionElement);
+ SAML11AssertionType renewedAssertion = SAMLUtil.saml11FromElement(renewedAssertionElement);
+
+ // assertions should have different ids and lifetimes.
+ assertFalse("Renewed assertion should have a unique id", originalAssertion.getID().equals(
+ renewedAssertion.getID()));
+ assertEquals(DatatypeConstants.LESSER, originalAssertion.getConditions().getNotBefore().compare(
+ renewedAssertion.getConditions().getNotBefore()));
+ assertEquals(DatatypeConstants.LESSER, originalAssertion.getConditions().getNotOnOrAfter().compare(
+ renewedAssertion.getConditions().getNotOnOrAfter()));
+ }
+
+ /**
+ * <p>
* This test case first generates a SAMLV2.0 assertion and then sends a WS-Trust renew message to the STS to get the
* assertion renewed (i.e. get a new assertion with an updated lifetime).
* </p>
@@ -728,18 +910,107 @@
AssertionType renewedAssertion = SAMLUtil.fromElement(renewedAssertionElement);
// assertions should have different ids and lifetimes.
- assertFalse("Renewed assertion should have a unique id",
- originalAssertion.getID().equals(renewedAssertion.getID()));
- assertEquals(DatatypeConstants.LESSER,
- originalAssertion.getConditions().getNotBefore().compare(renewedAssertion.getConditions().getNotBefore()));
- assertEquals(
- DatatypeConstants.LESSER,
- originalAssertion.getConditions().getNotOnOrAfter()
- .compare(renewedAssertion.getConditions().getNotOnOrAfter()));
+ assertFalse("Renewed assertion should have a unique id", originalAssertion.getID().equals(
+ renewedAssertion.getID()));
+ assertEquals(DatatypeConstants.LESSER, originalAssertion.getConditions().getNotBefore().compare(
+ renewedAssertion.getConditions().getNotBefore()));
+ assertEquals(DatatypeConstants.LESSER, originalAssertion.getConditions().getNotOnOrAfter().compare(
+ renewedAssertion.getConditions().getNotOnOrAfter()));
}
/**
* <p>
+ * This test case first generates a SAMLV1.1 assertion and then sends a WS-Trust cancel message to the STS to cancel
+ * the assertion. A canceled assertion cannot be renewed or considered valid anymore.
+ * </p>
+ *
+ * @throws Exception
+ * if an error occurs while running the test.
+ */
+ @Test
+ public void testInvokeSAML11Cancel() throws Exception
+ {
+ // create a simple token request.
+ RequestSecurityToken request = this.createRequest("testcontext", WSTrustConstants.ISSUE_REQUEST,
+ SAMLUtil.SAML11_TOKEN_TYPE, null);
+
+ Source requestMessage = this.createSourceFromRequest(request);
+
+ // invoke the token service.
+ Source responseMessage = this.tokenService.invoke(requestMessage);
+ WSTrustParser parser = new WSTrustParser();
+ BaseRequestSecurityTokenResponse baseResponse = (BaseRequestSecurityTokenResponse) parser.parse(DocumentUtil
+ .getSourceAsStream(responseMessage));
+
+ // validate the response and get the SAML assertion from the request.
+ this.validateSAML11AssertionResponse(baseResponse, "testcontext", "jduke", SAMLUtil.SAML11_BEARER_URI);
+ RequestSecurityTokenResponseCollection collection = (RequestSecurityTokenResponseCollection) baseResponse;
+ Element assertion = (Element) collection.getRequestSecurityTokenResponses().get(0).getRequestedSecurityToken()
+ .getAny().get(0);
+
+ // now construct a WS-Trust cancel request with the generated assertion.
+ request = this.createRequest("cancelcontext", WSTrustConstants.CANCEL_REQUEST, null, null);
+ CancelTargetType cancelTarget = new CancelTargetType();
+ cancelTarget.add(assertion);
+ request.setCancelTarget(cancelTarget);
+
+ // invoke the token service.
+ responseMessage = this.tokenService.invoke(this.createSourceFromRequest(request));
+ baseResponse = (BaseRequestSecurityTokenResponse) parser.parse(DocumentUtil.getSourceAsStream(responseMessage));
+
+ // validate the response contents.
+ assertNotNull("Unexpected null response", baseResponse);
+ assertTrue("Unexpected response type", baseResponse instanceof RequestSecurityTokenResponseCollection);
+ collection = (RequestSecurityTokenResponseCollection) baseResponse;
+ assertEquals("Unexpected number of responses", 1, collection.getRequestSecurityTokenResponses().size());
+ RequestSecurityTokenResponse response = collection.getRequestSecurityTokenResponses().get(0);
+ assertEquals("Unexpected response context", "cancelcontext", response.getContext());
+ assertNotNull("Cancel response should contain a RequestedTokenCancelled element", response
+ .getRequestedTokenCancelled());
+
+ // try to validate the canceled assertion.
+ request = this.createRequest("validatecontext", WSTrustConstants.VALIDATE_REQUEST, null, null);
+ ValidateTargetType validateTarget = new ValidateTargetType();
+ validateTarget.add(assertion);
+ request.setValidateTarget(validateTarget);
+
+ // the response should contain a status indicating that the token is not valid.
+ responseMessage = this.tokenService.invoke(this.createSourceFromRequest(request));
+ collection = (RequestSecurityTokenResponseCollection) parser.parse(DocumentUtil
+ .getSourceAsStream(responseMessage));
+ assertEquals("Unexpected number of responses", 1, collection.getRequestSecurityTokenResponses().size());
+ response = collection.getRequestSecurityTokenResponses().get(0);
+ assertEquals("Unexpected response context", "validatecontext", response.getContext());
+ assertEquals("Unexpected token type", WSTrustConstants.STATUS_TYPE, response.getTokenType().toString());
+ StatusType status = response.getStatus();
+ assertNotNull("Unexpected null status", status);
+ assertEquals("Unexpected status code", WSTrustConstants.STATUS_CODE_INVALID, status.getCode());
+ assertEquals("Unexpected status reason", "Validation failure: assertion with id "
+ + assertion.getAttribute("AssertionID") + " has been canceled", status.getReason());
+
+ // now try to renew the canceled assertion.
+ request = this.createRequest("renewcontext", WSTrustConstants.RENEW_REQUEST, null, null);
+ RenewTargetType renewTarget = new RenewTargetType();
+ renewTarget.add(assertion);
+ request.setRenewTarget(renewTarget);
+
+ // we should receive an exception when renewing the token.
+ try
+ {
+ this.tokenService.invoke(this.createSourceFromRequest(request));
+ fail("Renewing a canceled token should result in an exception being thrown");
+ }
+ catch (WebServiceException we)
+ {
+ assertTrue("Unexpected cause type", we.getCause() instanceof WSTrustException);
+ assertEquals("Unexpected exception message", "SAMLV1.1 Assertion with id "
+ + assertion.getAttribute("AssertionID") + " has been canceled and cannot be renewed", we.getCause()
+ .getCause().getMessage());
+ }
+ }
+
+ /**
+ * <p>
* This test case first generates a SAMLV2.0 assertion and then sends a WS-Trust cancel message to the STS to cancel
* the assertion. A canceled assertion cannot be renewed or considered valid anymore.
* </p>
@@ -785,8 +1056,8 @@
assertEquals("Unexpected number of responses", 1, collection.getRequestSecurityTokenResponses().size());
RequestSecurityTokenResponse response = collection.getRequestSecurityTokenResponses().get(0);
assertEquals("Unexpected response context", "cancelcontext", response.getContext());
- assertNotNull("Cancel response should contain a RequestedTokenCancelled element",
- response.getRequestedTokenCancelled());
+ assertNotNull("Cancel response should contain a RequestedTokenCancelled element", response
+ .getRequestedTokenCancelled());
// try to validate the canceled assertion.
request = this.createRequest("validatecontext", WSTrustConstants.VALIDATE_REQUEST, null, null);
@@ -884,8 +1155,10 @@
{
assertNotNull("Unexpected null cause", we.getCause());
assertTrue("Unexpected cause type", we.getCause() instanceof WSTrustException);
- /*assertEquals("Either AppliesTo or TokenType must be present in a security token request", we.getCause()
- .getMessage());*/
+ /*
+ * assertEquals("Either AppliesTo or TokenType must be present in a security token request", we.getCause()
+ * .getMessage());
+ */
}
// a request that asks for a public key to be used as proof key will fail if the public key is not available.
@@ -962,8 +1235,10 @@
{
assertNotNull("Unexpected null cause", we.getCause());
assertTrue("Unexpected cause type", we.getCause() instanceof WSTrustException);
- /*assertEquals("No SecurityTokenProvider configured for http://www.unknowntoken.org:UnknownToken", we.getCause()
- .getMessage());*/
+ /*
+ * assertEquals("No SecurityTokenProvider configured for http://www.unknowntoken.org:UnknownToken",
+ * we.getCause() .getMessage());
+ */
}
}
@@ -1024,7 +1299,7 @@
RequestSecurityTokenResponse response = baseResponseColl.getRequestSecurityTokenResponses().get(0);
StatusType status = response.getStatus();
assertTrue(status.getCode().equals(WSTrustConstants.STATUS_CODE_INVALID));
- //fail("An exception should have been raised by the security token service");
+ // fail("An exception should have been raised by the security token service");
}
catch (WebServiceException we)
{
@@ -1132,13 +1407,98 @@
Element element = (Element) requestedToken.getAny().get(0);
assertEquals("Unexpected root element name", "SpecialToken", element.getLocalName());
assertEquals("Unexpected namespace value", "http://www.tokens.org", element.getNamespaceURI());
- assertEquals("Unexpected attribute value", "http://www.tokens.org/SpecialToken",
- element.getAttribute("TokenType"));
+ assertEquals("Unexpected attribute value", "http://www.tokens.org/SpecialToken", element
+ .getAttribute("TokenType"));
element = (Element) element.getFirstChild();
assertEquals("Unexpected child element name", "SpecialTokenValue", element.getLocalName());
assertEquals("Unexpected token value", "Principal:jduke", element.getFirstChild().getNodeValue());
}
+ private SAML11AssertionType validateSAML11AssertionResponse(BaseRequestSecurityTokenResponse baseResponse,
+ String context, String principal, String confirmationMethod) throws Exception
+ {
+
+ // =============================== WS-Trust Security Token Response Validation ===============================//
+
+ assertNotNull("Unexpected null response", baseResponse);
+ assertTrue("Unexpected response type", baseResponse instanceof RequestSecurityTokenResponseCollection);
+ RequestSecurityTokenResponseCollection collection = (RequestSecurityTokenResponseCollection) baseResponse;
+ assertEquals("Unexpected number of responses", 1, collection.getRequestSecurityTokenResponses().size());
+ RequestSecurityTokenResponse response = collection.getRequestSecurityTokenResponses().get(0);
+ assertEquals("Unexpected response context", context, response.getContext());
+ assertEquals("Unexpected token type", SAMLUtil.SAML11_TOKEN_TYPE, response.getTokenType().toString());
+ Lifetime lifetime = response.getLifetime();
+ assertNotNull("Unexpected null token lifetime", lifetime);
+
+ // validate the attached token reference.
+ RequestedReferenceType reference = response.getRequestedAttachedReference();
+ assertNotNull("Unexpected null attached reference", reference);
+ SecurityTokenReferenceType securityRef = reference.getSecurityTokenReference();
+ assertNotNull("Unexpected null security reference", securityRef);
+ String tokenTypeAttr = securityRef.getOtherAttributes().get(new QName(WSTrustConstants.WSSE11_NS, "TokenType"));
+ assertNotNull("Required attribute TokenType is missing", tokenTypeAttr);
+ assertEquals("TokenType attribute has an unexpected value", SAMLUtil.SAML11_TOKEN_TYPE, tokenTypeAttr);
+ KeyIdentifierType keyId = (KeyIdentifierType) securityRef.getAny().get(0);
+ assertEquals("Unexpected key value type", SAMLUtil.SAML11_VALUE_TYPE, keyId.getValueType());
+ assertNotNull("Unexpected null key identifier value", keyId.getValue());
+
+ // ====================================== SAMLV1.1 Assertion Validation ======================================//
+
+ RequestedSecurityTokenType requestedToken = response.getRequestedSecurityToken();
+ assertNotNull("Unexpected null requested security token", requestedToken);
+
+ // unmarshall the SAMLV1.1 assertion.
+ Element assertionElement = (Element) requestedToken.getAny().get(0);
+ SAML11AssertionType assertion = SAMLUtil.saml11FromElement(assertionElement);
+
+ // verify the contents of the unmarshalled assertion.
+ assertNotNull("Invalid null assertion ID", assertion.getID());
+ assertEquals(keyId.getValue().substring(1), assertion.getID());
+ assertEquals(lifetime.getCreated(), assertion.getIssueInstant());
+ assertEquals(1, assertion.getMajorVersion());
+ assertEquals(1, assertion.getMinorVersion());
+
+ // validate the assertion issuer.
+ assertNotNull("Unexpected null assertion issuer", assertion.getIssuer());
+ assertEquals("Unexpected assertion issuer name", "Test STS", assertion.getIssuer());
+
+ // validate the assertion authentication statement.
+ List<SAML11StatementAbstractType> statements = assertion.getStatements();
+ assertTrue("At least one statement is expected in a SAMLV1.1 assertion", statements.size() > 0);
+ SAML11AuthenticationStatementType authStatement = null;
+ for (SAML11StatementAbstractType statement : statements)
+ {
+ if (statement instanceof SAML11AuthenticationStatementType)
+ {
+ authStatement = (SAML11AuthenticationStatementType) statement;
+ break;
+ }
+ }
+ assertNotNull("SAMLV1.1 assertion is missing the authentication statement", authStatement);
+
+ // validate the assertion subject.
+ assertNotNull("Unexpected null subject", authStatement.getSubject());
+ SAML11SubjectType subject = authStatement.getSubject();
+
+ SAML11NameIdentifierType nameID = subject.getChoice().getNameID();
+ assertEquals("Unexpected NameIdentifier format", SAML11Constants.FORMAT_UNSPECIFIED, nameID.getFormat()
+ .toString());
+ assertEquals("Unexpected NameIdentifier value", principal, nameID.getValue());
+
+ SAML11SubjectConfirmationType subjType = subject.getSubjectConfirmation();
+ assertEquals("Unexpected confirmation method", confirmationMethod, subjType.getConfirmationMethod().get(0)
+ .toString());
+
+ // validate the assertion conditions.
+ assertNotNull("Unexpected null conditions", assertion.getConditions());
+ assertEquals(lifetime.getCreated(), assertion.getConditions().getNotBefore());
+ assertEquals(lifetime.getExpires(), assertion.getConditions().getNotOnOrAfter());
+
+ assertNotNull("Assertion should have been signed", assertion.getSignature());
+
+ return assertion;
+ }
+
/**
* <p>
* Validates the contents of a WS-Trust response message that contains a SAMLV2.0 assertion issued by the {@code
@@ -1255,8 +1615,8 @@
if (WSTrustConstants.KEY_TYPE_SYMMETRIC.equals(keyType))
{
Element encKeyElement = (Element) keyInfo.getContent().get(0);
- assertEquals("Unexpected key info content type", WSTrustConstants.XMLEnc.ENCRYPTED_KEY,
- encKeyElement.getLocalName());
+ assertEquals("Unexpected key info content type", WSTrustConstants.XMLEnc.ENCRYPTED_KEY, encKeyElement
+ .getLocalName());
}
// if the key is public, KeyInfo should either contain an encoded certificate or an encoded public key.
else if (WSTrustConstants.KEY_TYPE_PUBLIC.equals(keyType))
Modified: federation/trunk/picketlink-fed-core/src/test/resources/parser/wst/wst-batch-validate.xml
===================================================================
--- federation/trunk/picketlink-fed-core/src/test/resources/parser/wst/wst-batch-validate.xml 2011-07-13 19:35:11 UTC (rev 1088)
+++ federation/trunk/picketlink-fed-core/src/test/resources/parser/wst/wst-batch-validate.xml 2011-07-14 15:04:04 UTC (rev 1089)
@@ -6,11 +6,6 @@
<saml2:Assertion xmlns:saml2="urn:oasis:names:tc:SAML:2.0:assertion" ID="ID_ab0392ef-b557-4453-95a8-a7e168da8ac5"
IssueInstant="2010-09-30T19:13:37.869Z" Version="2.0">
<saml2:Issuer>Test STS</saml2:Issuer>
- <saml2:Subject>
- <saml2:NameID NameQualifier="urn:picketlink:identity-federation">jduke</saml2:NameID>
- <saml2:SubjectConfirmation Method="urn:oasis:names:tc:SAML:2.0:cm:bearer"/>
- </saml2:Subject>
- <saml2:Conditions NotBefore="2010-09-30T19:13:37.869Z" NotOnOrAfter="2010-09-30T21:13:37.869Z"/>
<ds:Signature xmlns:ds="http://www.w3.org/2000/09/xmldsig#">
<ds:SignedInfo>
<ds:CanonicalizationMethod Algorithm="http://www.w3.org/2001/10/xml-exc-c14n#WithComments"/>
@@ -42,6 +37,11 @@
</ds:KeyValue>
</ds:KeyInfo>
</ds:Signature>
+ <saml2:Subject>
+ <saml2:NameID NameQualifier="urn:picketlink:identity-federation">jduke</saml2:NameID>
+ <saml2:SubjectConfirmation Method="urn:oasis:names:tc:SAML:2.0:cm:bearer"/>
+ </saml2:Subject>
+ <saml2:Conditions NotBefore="2010-09-30T19:13:37.869Z" NotOnOrAfter="2010-09-30T21:13:37.869Z"/>
</saml2:Assertion>
</wst:ValidateTarget>
</wst:RequestSecurityToken>
@@ -52,15 +52,6 @@
<saml2:Assertion xmlns:saml2="urn:oasis:names:tc:SAML:2.0:assertion" ID="ID_cf9efbf0-9d7f-4b4a-b77f-d83ecaafd374"
IssueInstant="2010-09-30T19:13:37.911Z" Version="2.0">
<saml2:Issuer>Test STS</saml2:Issuer>
- <saml2:Subject>
- <saml2:NameID NameQualifier="urn:picketlink:identity-federation">jduke</saml2:NameID>
- <saml2:SubjectConfirmation Method="urn:oasis:names:tc:SAML:2.0:cm:bearer"/>
- </saml2:Subject>
- <saml2:Conditions NotBefore="2010-09-30T19:13:37.911Z" NotOnOrAfter="2010-09-30T21:13:37.911Z">
- <saml2:AudienceRestriction>
- <saml2:Audience>http://services.testcorp.org/provider2</saml2:Audience>
- </saml2:AudienceRestriction>
- </saml2:Conditions>
<ds:Signature xmlns:ds="http://www.w3.org/2000/09/xmldsig#">
<ds:SignedInfo>
<ds:CanonicalizationMethod Algorithm="http://www.w3.org/2001/10/xml-exc-c14n#WithComments"/>
@@ -92,6 +83,15 @@
</ds:KeyValue>
</ds:KeyInfo>
</ds:Signature>
+ <saml2:Subject>
+ <saml2:NameID NameQualifier="urn:picketlink:identity-federation">jduke</saml2:NameID>
+ <saml2:SubjectConfirmation Method="urn:oasis:names:tc:SAML:2.0:cm:bearer"/>
+ </saml2:Subject>
+ <saml2:Conditions NotBefore="2010-09-30T19:13:37.911Z" NotOnOrAfter="2010-09-30T21:13:37.911Z">
+ <saml2:AudienceRestriction>
+ <saml2:Audience>http://services.testcorp.org/provider2</saml2:Audience>
+ </saml2:AudienceRestriction>
+ </saml2:Conditions>
</saml2:Assertion>
</wst:ValidateTarget>
</wst:RequestSecurityToken>
Modified: federation/trunk/picketlink-fed-core/src/test/resources/parser/wst/wst-cancel-saml.xml
===================================================================
--- federation/trunk/picketlink-fed-core/src/test/resources/parser/wst/wst-cancel-saml.xml 2011-07-13 19:35:11 UTC (rev 1088)
+++ federation/trunk/picketlink-fed-core/src/test/resources/parser/wst/wst-cancel-saml.xml 2011-07-14 15:04:04 UTC (rev 1089)
@@ -4,11 +4,6 @@
<saml2:Assertion ID="ID_cb1eadf5-50a6-4fdf-96bc-412514f52882" IssueInstant="2010-09-30T19:13:37.603Z" Version="2.0"
xmlns:saml2="urn:oasis:names:tc:SAML:2.0:assertion">
<saml2:Issuer>Test STS</saml2:Issuer>
- <saml2:Subject>
- <saml2:NameID NameQualifier="urn:picketlink:identity-federation">jduke</saml2:NameID>
- <saml2:SubjectConfirmation Method="urn:oasis:names:tc:SAML:2.0:cm:bearer"/>
- </saml2:Subject>
- <saml2:Conditions NotBefore="2010-09-30T19:13:37.603Z" NotOnOrAfter="2010-09-30T21:13:37.603Z"/>
<ds:Signature xmlns:ds="http://www.w3.org/2000/09/xmldsig#">
<ds:SignedInfo>
<ds:CanonicalizationMethod Algorithm="http://www.w3.org/2001/10/xml-exc-c14n#WithComments"/>
@@ -40,6 +35,11 @@
</ds:KeyValue>
</ds:KeyInfo>
</ds:Signature>
+ <saml2:Subject>
+ <saml2:NameID NameQualifier="urn:picketlink:identity-federation">jduke</saml2:NameID>
+ <saml2:SubjectConfirmation Method="urn:oasis:names:tc:SAML:2.0:cm:bearer"/>
+ </saml2:Subject>
+ <saml2:Conditions NotBefore="2010-09-30T19:13:37.603Z" NotOnOrAfter="2010-09-30T21:13:37.603Z"/>
</saml2:Assertion>
</wst:CancelTarget>
</wst:RequestSecurityToken>
Modified: federation/trunk/picketlink-fed-core/src/test/resources/parser/wst/wst-renew-saml.xml
===================================================================
--- federation/trunk/picketlink-fed-core/src/test/resources/parser/wst/wst-renew-saml.xml 2011-07-13 19:35:11 UTC (rev 1088)
+++ federation/trunk/picketlink-fed-core/src/test/resources/parser/wst/wst-renew-saml.xml 2011-07-14 15:04:04 UTC (rev 1089)
@@ -5,15 +5,6 @@
<saml2:Assertion ID="ID_654b6092-c725-40ea-8044-de453b59cb28" IssueInstant="2010-09-30T19:13:37.429Z" Version="2.0"
xmlns:saml2="urn:oasis:names:tc:SAML:2.0:assertion">
<saml2:Issuer>Test STS</saml2:Issuer>
- <saml2:Subject>
- <saml2:NameID NameQualifier="urn:picketlink:identity-federation">jduke</saml2:NameID>
- <saml2:SubjectConfirmation Method="urn:oasis:names:tc:SAML:2.0:cm:bearer"/>
- </saml2:Subject>
- <saml2:Conditions NotBefore="2010-09-30T19:13:37.429Z" NotOnOrAfter="2010-09-30T21:13:37.429Z">
- <saml2:AudienceRestriction>
- <saml2:Audience>http://services.testcorp.org/provider2</saml2:Audience>
- </saml2:AudienceRestriction>
- </saml2:Conditions>
<ds:Signature xmlns:ds="http://www.w3.org/2000/09/xmldsig#">
<ds:SignedInfo>
<ds:CanonicalizationMethod Algorithm="http://www.w3.org/2001/10/xml-exc-c14n#WithComments"/>
@@ -45,6 +36,15 @@
</ds:KeyValue>
</ds:KeyInfo>
</ds:Signature>
+ <saml2:Subject>
+ <saml2:NameID NameQualifier="urn:picketlink:identity-federation">jduke</saml2:NameID>
+ <saml2:SubjectConfirmation Method="urn:oasis:names:tc:SAML:2.0:cm:bearer"/>
+ </saml2:Subject>
+ <saml2:Conditions NotBefore="2010-09-30T19:13:37.429Z" NotOnOrAfter="2010-09-30T21:13:37.429Z">
+ <saml2:AudienceRestriction>
+ <saml2:Audience>http://services.testcorp.org/provider2</saml2:Audience>
+ </saml2:AudienceRestriction>
+ </saml2:Conditions>
</saml2:Assertion>
</wst:RenewTarget>
</wst:RequestSecurityToken>
Modified: federation/trunk/picketlink-fed-core/src/test/resources/parser/wst/wst-validate-saml.xml
===================================================================
--- federation/trunk/picketlink-fed-core/src/test/resources/parser/wst/wst-validate-saml.xml 2011-07-13 19:35:11 UTC (rev 1088)
+++ federation/trunk/picketlink-fed-core/src/test/resources/parser/wst/wst-validate-saml.xml 2011-07-14 15:04:04 UTC (rev 1089)
@@ -5,11 +5,6 @@
<saml2:Assertion ID="ID_654b6092-c725-40ea-8044-de453b59cb28" IssueInstant="2010-09-30T19:13:37.186Z" Version="2.0"
xmlns:saml2="urn:oasis:names:tc:SAML:2.0:assertion">
<saml2:Issuer>Test STS</saml2:Issuer>
- <saml2:Subject>
- <saml2:NameID NameQualifier="urn:picketlink:identity-federation">jduke</saml2:NameID>
- <saml2:SubjectConfirmation Method="urn:oasis:names:tc:SAML:2.0:cm:bearer"/>
- </saml2:Subject>
- <saml2:Conditions NotBefore="2010-09-30T19:13:37.186Z" NotOnOrAfter="2010-09-30T21:13:37.186Z"/>
<ds:Signature xmlns:ds="http://www.w3.org/2000/09/xmldsig#">
<ds:SignedInfo>
<ds:CanonicalizationMethod Algorithm="http://www.w3.org/2001/10/xml-exc-c14n#WithComments"/>
@@ -41,6 +36,11 @@
</ds:KeyValue>
</ds:KeyInfo>
</ds:Signature>
+ <saml2:Subject>
+ <saml2:NameID NameQualifier="urn:picketlink:identity-federation">jduke</saml2:NameID>
+ <saml2:SubjectConfirmation Method="urn:oasis:names:tc:SAML:2.0:cm:bearer"/>
+ </saml2:Subject>
+ <saml2:Conditions NotBefore="2010-09-30T19:13:37.186Z" NotOnOrAfter="2010-09-30T21:13:37.186Z"/>
</saml2:Assertion>
</wst:ValidateTarget>
</wst:RequestSecurityToken>
Modified: federation/trunk/picketlink-fed-core/src/test/resources/sts/picketlink-sts.xml
===================================================================
--- federation/trunk/picketlink-fed-core/src/test/resources/sts/picketlink-sts.xml 2011-07-13 19:35:11 UTC (rev 1088)
+++ federation/trunk/picketlink-fed-core/src/test/resources/sts/picketlink-sts.xml 2011-07-14 15:04:04 UTC (rev 1089)
@@ -17,6 +17,10 @@
<Property Key="Property1" Value="Value1"/>
<Property Key="Property2" Value="Value2"/>
</TokenProvider>
+ <TokenProvider ProviderClass="org.picketlink.identity.federation.core.wstrust.plugins.saml.SAML11TokenProvider"
+ TokenType="http://docs.oasis-open.org/wss/oasis-wss-saml-token-profile-1.1#SAMLV1.1"
+ TokenElement="Assertion"
+ TokenElementNS="urn:oasis:names:tc:SAML:1.0:assertion"/>
<TokenProvider ProviderClass="org.picketlink.identity.federation.core.wstrust.plugins.saml.SAML20TokenProvider"
TokenType="http://docs.oasis-open.org/wss/oasis-wss-saml-token-profile-1.1#SAMLV2.0"
TokenElement="Assertion"
Modified: federation/trunk/picketlink-webapps/picketlink-sts/src/main/resources/picketlink-sts.xml
===================================================================
--- federation/trunk/picketlink-webapps/picketlink-sts/src/main/resources/picketlink-sts.xml 2011-07-13 19:35:11 UTC (rev 1088)
+++ federation/trunk/picketlink-webapps/picketlink-sts/src/main/resources/picketlink-sts.xml 2011-07-14 15:04:04 UTC (rev 1089)
@@ -8,9 +8,13 @@
<ValidatingAlias Key="http://services.testcorp.org/provider1" Value="service1"/>
</KeyProvider>
<TokenProviders>
- <TokenProvider ProviderClass="org.picketlink.identity.federation.core.wstrust.plugins.saml.SAML20TokenProvider"
- TokenType="http://docs.oasis-open.org/wss/oasis-wss-saml-token-profile-1.1#SAMLV2.0"
+ <TokenProvider ProviderClass="org.picketlink.identity.federation.core.wstrust.plugins.saml.SAML11TokenProvider"
+ TokenType="http://docs.oasis-open.org/wss/oasis-wss-saml-token-profile-1.1#SAMLV1.1"
TokenElement="Assertion"
+ TokenElementNS="urn:oasis:names:tc:SAML:1.0:assertion"/>
+ <TokenProvider ProviderClass="org.picketlink.identity.federation.core.wstrust.plugins.saml.SAML20TokenProvider"
+ TokenType="http://docs.oasis-open.org/wss/oasis-wss-saml-token-profile-1.1#SAMLV2.0"
+ TokenElement="Assertion"
TokenElementNS="urn:oasis:names:tc:SAML:2.0:assertion"/>
</TokenProviders>
<ServiceProviders>
13 years, 5 months
Picketlink SVN: r1088 - in trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws: util and 1 other directory.
by picketlink-commits@lists.jboss.org
Author: anil.saldhana(a)jboss.com
Date: 2011-07-13 15:35:11 -0400 (Wed, 13 Jul 2011)
New Revision: 1088
Added:
trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/util/JBossWSNativeStackUtil.java
trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/util/SecurityActions.java
Modified:
trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/handler/WSAuthorizationHandler.java
Log:
use native stack internals as reflection in the case the JBossWS stack does not set the port name on the message context
Modified: trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/handler/WSAuthorizationHandler.java
===================================================================
--- trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/handler/WSAuthorizationHandler.java 2011-07-13 19:34:25 UTC (rev 1087)
+++ trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/handler/WSAuthorizationHandler.java 2011-07-13 19:35:11 UTC (rev 1088)
@@ -32,7 +32,11 @@
import javax.security.auth.Subject;
import javax.servlet.ServletContext;
import javax.xml.namespace.QName;
+import javax.xml.soap.SOAPBody;
+import javax.xml.soap.SOAPException;
+import javax.xml.soap.SOAPMessage;
import javax.xml.ws.handler.MessageContext;
+import javax.xml.ws.handler.soap.SOAPMessageContext;
import org.jboss.security.AuthorizationManager;
import org.jboss.security.SecurityContext;
@@ -40,7 +44,9 @@
import org.jboss.security.callbacks.SecurityContextCallbackHandler;
import org.jboss.wsf.spi.invocation.SecurityAdaptor;
import org.picketlink.identity.federation.core.exceptions.ProcessingException;
+import org.picketlink.trust.jbossws.util.JBossWSNativeStackUtil;
import org.picketlink.trust.jbossws.util.JBossWSSERoleExtractor;
+import org.w3c.dom.Node;
/**
* An authorization handler for the POJO Web services
@@ -63,6 +69,7 @@
if(trace)
{
log.trace("Handling Inbound Message");
+ trace(msgContext);
}
ServletContext context = (ServletContext) msgContext.get(MessageContext.SERVLET_CONTEXT);
//Read the jboss-wsse.xml file
@@ -70,12 +77,24 @@
if( is == null )
throw new RuntimeException( "unable to load jboss-wsse.xml");
- QName portName = (QName) msgContext.get(MessageContext.WSDL_PORT);
+ QName portName = (QName) msgContext.get(MessageContext.WSDL_PORT);
QName opName = (QName) msgContext.get(MessageContext.WSDL_OPERATION);
+
+ if(portName == null)
+ portName = JBossWSNativeStackUtil.getPortNameViaReflection(getClass(), msgContext);
+ if(portName == null)
+ throw new RuntimeException("Unable to determine port name from the message context");
+
+ if(opName == null)
+ opName = getOperationName(msgContext);
+
+ if(opName == null)
+ throw new RuntimeException("Unable to determine operation name from the message context");
+
List<String> roles = null;
- String key = portName.getLocalPart()+"_" + opName.toString();
+ String key = portName.getLocalPart()+ "_" + opName.toString();
//First check in cache
if( cache.containsKey(key))
@@ -146,4 +165,25 @@
is = cl.getResourceAsStream("/WEB-INF/jboss-wsse.xml");
return is;
}
+
+ private QName getOperationName(MessageContext msgContext)
+ {
+ SOAPMessageContext soapMessageContext = (SOAPMessageContext) msgContext;
+ SOAPMessage soapMessage = soapMessageContext.getMessage();
+ SOAPBody soapBody;
+ try
+ {
+ soapBody = soapMessage.getSOAPBody();
+ Node child = soapBody.getFirstChild();
+ String childNamespace = child.getNamespaceURI();
+ String childName = child.getLocalName();
+ return new QName(childNamespace, childName);
+ }
+ catch (SOAPException e)
+ {
+ if(trace)
+ log.trace("Exception using backup method to get op name=",e);
+ }
+ return null;
+ }
}
\ No newline at end of file
Added: trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/util/JBossWSNativeStackUtil.java
===================================================================
--- trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/util/JBossWSNativeStackUtil.java (rev 0)
+++ trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/util/JBossWSNativeStackUtil.java 2011-07-13 19:35:11 UTC (rev 1088)
@@ -0,0 +1,70 @@
+/*
+ * JBoss, Home of Professional Open Source.
+ * Copyright 2008, Red Hat Middleware LLC, and individual contributors
+ * as indicated by the @author tags. See the copyright.txt file in the
+ * distribution for a full listing of individual contributors.
+ *
+ * This is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU Lesser General Public License as
+ * published by the Free Software Foundation; either version 2.1 of
+ * the License, or (at your option) any later version.
+ *
+ * This software is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this software; if not, write to the Free
+ * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
+ * 02110-1301 USA, or see the FSF site: http://www.fsf.org.
+ */
+package org.picketlink.trust.jbossws.util;
+
+import java.lang.reflect.Method;
+
+import javax.xml.namespace.QName;
+import javax.xml.ws.handler.MessageContext;
+
+import org.jboss.logging.Logger;
+
+
+/**
+ * Utility class that uses reflection on the
+ * JBossWS Native Stack as backup strategy
+ *
+ * @author Anil.Saldhana(a)redhat.com
+ * @since Jul 13, 2011
+ */
+public class JBossWSNativeStackUtil
+{
+ protected static Logger log = Logger.getLogger(JBossWSNativeStackUtil.class);
+ protected static boolean trace = log.isTraceEnabled();
+
+ /**
+ * It is unfortunate that the {@link MessageContext} does not contain the port name.
+ * We will use reflection on the JBoss WS Native stack
+ * @param msgContext
+ * @return
+ */
+ public static QName getPortNameViaReflection(Class<?> callingClazz, MessageContext msgContext)
+ {
+ try
+ {
+ Class<?> clazz = SecurityActions.getClassLoader(callingClazz).loadClass("org.jboss.ws.core.jaxws.handler.SOAPMessageContextJAXWS");
+ Method endpointMDMethod = clazz.getMethod("getEndpointMetaData", new Class[0]);
+ Object endpointMD = endpointMDMethod.invoke(msgContext, new Object[0]);
+
+ clazz = SecurityActions.getClassLoader(callingClazz).loadClass("org.jboss.ws.metadata.umdm.EndpointMetaData");
+ Method portNameMethod = clazz.getMethod("getPortName", new Class[0]);
+
+ return (QName) portNameMethod.invoke(endpointMD, new Object[0]);
+ }
+ catch (Exception e)
+ {
+ if(trace)
+ log.trace("Exception using backup method to get port name=",e);
+ }
+ return null;
+ }
+}
\ No newline at end of file
Added: trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/util/SecurityActions.java
===================================================================
--- trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/util/SecurityActions.java (rev 0)
+++ trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/util/SecurityActions.java 2011-07-13 19:35:11 UTC (rev 1088)
@@ -0,0 +1,167 @@
+/*
+ * JBoss, Home of Professional Open Source.
+ * Copyright 2010, Red Hat Middleware LLC, and individual contributors
+ * as indicated by the @author tags. See the copyright.txt file in the
+ * distribution for a full listing of individual contributors.
+ *
+ * This is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU Lesser General Public License as
+ * published by the Free Software Foundation; either version 2.1 of
+ * the License, or (at your option) any later version.
+ *
+ * This software is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this software; if not, write to the Free
+ * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
+ * 02110-1301 USA, or see the FSF site: http://www.fsf.org.
+ */
+package org.picketlink.trust.jbossws.util;
+
+import java.security.AccessController;
+import java.security.Principal;
+import java.security.PrivilegedAction;
+import java.security.acl.Group;
+import java.util.List;
+
+import javax.security.auth.Subject;
+
+import org.jboss.security.SecurityConstants;
+import org.jboss.security.SecurityContext;
+import org.jboss.security.SecurityContextAssociation;
+import org.jboss.security.SecurityContextFactory;
+import org.jboss.security.SimplePrincipal;
+import org.picketlink.identity.federation.bindings.jboss.subject.PicketLinkGroup;
+
+/**
+ * Privileged actions.
+ *
+ * @author <a href="mmoyses(a)redhat.com">Marcus Moyses</a>
+ * @author Anil Saldhana
+ * @version $Revision: 1 $
+ */
+class SecurityActions
+{
+ static SecurityContext createSecurityContext(final Principal p, final Object cred, final Subject subject)
+ {
+ return AccessController.doPrivileged(new PrivilegedAction<SecurityContext>()
+ {
+ public SecurityContext run()
+ {
+ SecurityContext sc = null;
+ try
+ {
+ sc = SecurityContextFactory.createSecurityContext(p, cred, subject, "SAML2_HANDLER");
+ }
+ catch (Exception e)
+ {
+ throw new RuntimeException(e);
+ }
+ return sc;
+ }
+ });
+ }
+
+ static void setSecurityContext(final SecurityContext sc)
+ {
+ AccessController.doPrivileged(new PrivilegedAction<Object>()
+ {
+ public Object run()
+ {
+ SecurityContextAssociation.setSecurityContext(sc);
+ return null;
+ }
+ });
+ }
+
+ static SecurityContext getSecurityContext()
+ {
+ return AccessController.doPrivileged(new PrivilegedAction<SecurityContext>()
+ {
+ public SecurityContext run()
+ {
+ return SecurityContextAssociation.getSecurityContext();
+ }
+ });
+ }
+ /**
+ * Get the {@link Subject} from the {@link SecurityContextAssociation}
+ * @return authenticated subject or null
+ */
+ static Subject getAuthenticatedSubject()
+ {
+ return AccessController.doPrivileged(new PrivilegedAction<Subject>()
+ {
+ public Subject run()
+ {
+ SecurityContext sc = SecurityContextAssociation.getSecurityContext();
+ if( sc != null )
+ return sc.getUtil().getSubject();
+ return null;
+ }
+ });
+ }
+
+ /**
+ * Get a system property
+ * @param key the property name
+ * @param defaultValue default value in absence of property
+ * @return
+ */
+ static String getSystemProperty( final String key, final String defaultValue)
+ {
+ return AccessController.doPrivileged(new PrivilegedAction<String>()
+ {
+ public String run()
+ {
+ return System.getProperty(key, defaultValue);
+ }
+ });
+ }
+
+ static ClassLoader getClassLoader( final Class<?> clazz)
+ {
+ return AccessController.doPrivileged(new PrivilegedAction<ClassLoader>()
+ {
+ public ClassLoader run()
+ {
+ return clazz.getClassLoader();
+ }
+ });
+ }
+
+ static ClassLoader getContextClassLoader()
+ {
+ return AccessController.doPrivileged(new PrivilegedAction<ClassLoader>()
+ {
+ public ClassLoader run()
+ {
+ return Thread.currentThread().getContextClassLoader();
+ }
+ });
+ }
+
+ /**
+ * Given a {@link List} of role names, construct a group principal of type {@link Group}
+ * @param roles
+ * @return
+ */
+ static Group group(final List<String> roles)
+ {
+ return AccessController.doPrivileged(new PrivilegedAction<Group>()
+ {
+ public Group run()
+ {
+ Group theGroup = new PicketLinkGroup(SecurityConstants.ROLES_IDENTIFIER);
+ for(String role: roles)
+ {
+ theGroup.addMember(new SimplePrincipal(role));
+ }
+ return theGroup;
+ }
+ });
+ }
+}
\ No newline at end of file
13 years, 5 months
Picketlink SVN: r1087 - trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/handler.
by picketlink-commits@lists.jboss.org
Author: anil.saldhana(a)jboss.com
Date: 2011-07-13 15:34:25 -0400 (Wed, 13 Jul 2011)
New Revision: 1087
Modified:
trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/handler/AbstractPicketLinkTrustHandler.java
trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/handler/SAML2Handler.java
trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/handler/WSAuthenticationHandler.java
Log:
add logging
Modified: trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/handler/AbstractPicketLinkTrustHandler.java
===================================================================
--- trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/handler/AbstractPicketLinkTrustHandler.java 2011-07-13 00:54:02 UTC (rev 1086)
+++ trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/handler/AbstractPicketLinkTrustHandler.java 2011-07-13 19:34:25 UTC (rev 1087)
@@ -30,6 +30,8 @@
import javax.naming.NamingException;
import javax.security.auth.Subject;
import javax.xml.namespace.QName;
+import javax.xml.ws.handler.MessageContext;
+import javax.xml.ws.handler.soap.SOAPMessageContext;
import org.jboss.logging.Logger;
import org.jboss.security.AuthenticationManager;
@@ -121,6 +123,21 @@
Util.addNamespace(element, Constants.XML_ENCRYPTION_PREFIX, Constants.XML_SIGNATURE_NS);
return element;
}
+
+ protected void trace(MessageContext msgContext)
+ {
+ if(trace)
+ {
+ if(msgContext instanceof SOAPMessageContext)
+ {
+ SOAPMessageContext soapMessageContext = (SOAPMessageContext) msgContext;
+ log.trace("WSDL_PORT="+soapMessageContext.get(SOAPMessageContext.WSDL_PORT));
+ log.trace("WSDL_OPERATION="+soapMessageContext.get(SOAPMessageContext.WSDL_OPERATION));
+ log.trace("WSDL_INTERFACE="+soapMessageContext.get(SOAPMessageContext.WSDL_INTERFACE));
+ log.trace("WSDL_SERVICE="+soapMessageContext.get(SOAPMessageContext.WSDL_SERVICE));
+ }
+ }
+ }
/**
* Given the NameID {@link Element}, return the user name
Modified: trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/handler/SAML2Handler.java
===================================================================
--- trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/handler/SAML2Handler.java 2011-07-13 00:54:02 UTC (rev 1086)
+++ trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/handler/SAML2Handler.java 2011-07-13 19:34:25 UTC (rev 1087)
@@ -114,26 +114,26 @@
}
if(trace)
- log.trace("Rolekeys to extract roles from the assertion:" + roleKeys);
+ log.trace("Inbound::Rolekeys to extract roles from the assertion:" + roleKeys);
List<String> roles = AssertionUtil.getRoles(assertionType, roleKeys);
if(roles.size() > 0 )
{
if(trace)
- log.trace("Roles in the assertion:" + roles);
+ log.trace("Inbound::Roles in the assertion:" + roles);
Group roleGroup = SecurityActions.group(roles);
theSubject.getPrincipals().add(roleGroup);
}
else
{
if(trace)
- log.trace("Did not find roles in the assertion");
+ log.trace("Inbound::Did not find roles in the assertion");
}
}
}
else
{
- log.warn("We did not find any assertion");
+ log.warn("Inbound::We did not find any assertion");
}
return true;
}
@@ -164,7 +164,7 @@
{
if(trace)
{
- log.trace("No Assertion was found on the message context or authenticated subject. Returning");
+ log.trace("Outbound::No Assertion was found on the message context or authenticated subject. Returning");
}
return true;
}
Modified: trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/handler/WSAuthenticationHandler.java
===================================================================
--- trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/handler/WSAuthenticationHandler.java 2011-07-13 00:54:02 UTC (rev 1086)
+++ trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/handler/WSAuthenticationHandler.java 2011-07-13 19:34:25 UTC (rev 1087)
@@ -46,6 +46,7 @@
if(trace)
{
log.trace("Handling Inbound Message");
+ trace(msgContext);
}
AuthenticationManager authenticationManager = getAuthenticationManager();
SecurityAdaptor securityAdaptor = secAdapterfactory.newSecurityAdapter();
13 years, 5 months
Picketlink SVN: r1086 - trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/handler.
by picketlink-commits@lists.jboss.org
Author: anil.saldhana(a)jboss.com
Date: 2011-07-12 20:54:02 -0400 (Tue, 12 Jul 2011)
New Revision: 1086
Modified:
trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/handler/SAML2Handler.java
Log:
PLFED-171: add group principal to subject if roles
Modified: trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/handler/SAML2Handler.java
===================================================================
--- trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/handler/SAML2Handler.java 2011-07-13 00:52:18 UTC (rev 1085)
+++ trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/handler/SAML2Handler.java 2011-07-13 00:54:02 UTC (rev 1086)
@@ -54,6 +54,9 @@
*/
public class SAML2Handler extends AbstractPicketLinkTrustHandler
{
+ //The system property key that can be set to determine the keys under which the roles may be in the assertion
+ public static final String ROLE_KEY_SYS_PROP = "picketlink.rolekey";
+
/**
* Retrieves the SAML assertion from the SOAP payload and lets invocation go to JAAS for validation.
*/
@@ -104,7 +107,7 @@
if(assertionType != null )
{
List<String> roleKeys = new ArrayList<String>();
- String roleKey = SecurityActions.getSystemProperty("picketlink.rolekey", "Role");
+ String roleKey = SecurityActions.getSystemProperty( ROLE_KEY_SYS_PROP, "Role");
if(StringUtil.isNotNull(roleKey))
{
roleKeys.addAll(StringUtil.tokenize(roleKey));
13 years, 5 months
Picketlink SVN: r1085 - in trust/trunk/jbossws/src: test/java/org/picketlink/test/trust/jbossws and 3 other directories.
by picketlink-commits@lists.jboss.org
Author: anil.saldhana(a)jboss.com
Date: 2011-07-12 20:52:18 -0400 (Tue, 12 Jul 2011)
New Revision: 1085
Added:
trust/trunk/jbossws/src/test/java/org/picketlink/test/trust/jbossws/handler/
trust/trunk/jbossws/src/test/java/org/picketlink/test/trust/jbossws/handler/SAML2HandlerUnitTestCase.java
trust/trunk/jbossws/src/test/resources/jbossws/xml/
trust/trunk/jbossws/src/test/resources/jbossws/xml/wsse-saml.xml
Modified:
trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/handler/SAML2Handler.java
trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/handler/SecurityActions.java
Log:
PLFED-171: add group principal to subject if roles
Modified: trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/handler/SAML2Handler.java
===================================================================
--- trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/handler/SAML2Handler.java 2011-07-12 21:11:12 UTC (rev 1084)
+++ trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/handler/SAML2Handler.java 2011-07-13 00:52:18 UTC (rev 1085)
@@ -21,6 +21,10 @@
*/
package org.picketlink.trust.jbossws.handler;
+import java.security.acl.Group;
+import java.util.ArrayList;
+import java.util.List;
+
import javax.security.auth.Subject;
import javax.xml.namespace.QName;
import javax.xml.soap.SOAPMessage;
@@ -30,7 +34,11 @@
import org.jboss.security.SecurityContext;
import org.picketlink.identity.federation.bindings.jboss.subject.PicketLinkPrincipal;
import org.picketlink.identity.federation.core.saml.v2.constants.JBossSAMLURIConstants;
+import org.picketlink.identity.federation.core.saml.v2.util.AssertionUtil;
+import org.picketlink.identity.federation.core.util.StringUtil;
import org.picketlink.identity.federation.core.wstrust.SamlCredential;
+import org.picketlink.identity.federation.core.wstrust.plugins.saml.SAMLUtil;
+import org.picketlink.identity.federation.saml.v2.assertion.AssertionType;
import org.picketlink.trust.jbossws.SAML2Constants;
import org.picketlink.trust.jbossws.Util;
import org.w3c.dom.Document;
@@ -59,12 +67,26 @@
SOAPMessageContext ctx = (SOAPMessageContext) msgContext;
SOAPMessage soapMessage = ctx.getMessage();
+ if(soapMessage == null)
+ throw new IllegalStateException("SOAP Message is null");
+
// retrieve the assertion
Document document = soapMessage.getSOAPPart();
Element soapHeader = Util.findOrCreateSoapHeader(document.getDocumentElement());
Element assertion = Util.findElement(soapHeader, new QName(assertionNS, "Assertion"));
if (assertion != null)
{
+ AssertionType assertionType = null;
+ try
+ {
+ assertionType = SAMLUtil.fromElement(assertion);
+ if(AssertionUtil.hasExpired(assertionType))
+ throw new RuntimeException("Assertion has expired");
+ }
+ catch(Exception e )
+ {
+ log.error("Exception in parsing the assertion:",e);
+ }
SamlCredential credential = new SamlCredential(assertion);
if (log.isTraceEnabled())
{
@@ -75,15 +97,41 @@
Element nameID = Util.findElement(subject, new QName(assertionNS, "NameID"));
String username = getUsername(nameID);
// set SecurityContext
- Subject s = new Subject();
- SecurityContext sc = SecurityActions.createSecurityContext(new PicketLinkPrincipal(username), credential, s);
+ Subject theSubject = new Subject();
+ SecurityContext sc = SecurityActions.createSecurityContext(new PicketLinkPrincipal(username), credential, theSubject);
SecurityActions.setSecurityContext(sc);
+
+ if(assertionType != null )
+ {
+ List<String> roleKeys = new ArrayList<String>();
+ String roleKey = SecurityActions.getSystemProperty("picketlink.rolekey", "Role");
+ if(StringUtil.isNotNull(roleKey))
+ {
+ roleKeys.addAll(StringUtil.tokenize(roleKey));
+ }
+
+ if(trace)
+ log.trace("Rolekeys to extract roles from the assertion:" + roleKeys);
+
+ List<String> roles = AssertionUtil.getRoles(assertionType, roleKeys);
+ if(roles.size() > 0 )
+ {
+ if(trace)
+ log.trace("Roles in the assertion:" + roles);
+ Group roleGroup = SecurityActions.group(roles);
+ theSubject.getPrincipals().add(roleGroup);
+ }
+ else
+ {
+ if(trace)
+ log.trace("Did not find roles in the assertion");
+ }
+ }
}
else
{
log.warn("We did not find any assertion");
- }
-
+ }
return true;
}
Modified: trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/handler/SecurityActions.java
===================================================================
--- trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/handler/SecurityActions.java 2011-07-12 21:11:12 UTC (rev 1084)
+++ trust/trunk/jbossws/src/main/java/org/picketlink/trust/jbossws/handler/SecurityActions.java 2011-07-13 00:52:18 UTC (rev 1085)
@@ -24,12 +24,17 @@
import java.security.AccessController;
import java.security.Principal;
import java.security.PrivilegedAction;
+import java.security.acl.Group;
+import java.util.List;
import javax.security.auth.Subject;
+import org.jboss.security.SecurityConstants;
import org.jboss.security.SecurityContext;
import org.jboss.security.SecurityContextAssociation;
import org.jboss.security.SecurityContextFactory;
+import org.jboss.security.SimplePrincipal;
+import org.picketlink.identity.federation.bindings.jboss.subject.PicketLinkGroup;
/**
* Privileged actions.
@@ -138,4 +143,25 @@
}
});
}
+
+ /**
+ * Given a {@link List} of role names, construct a group principal of type {@link Group}
+ * @param roles
+ * @return
+ */
+ static Group group(final List<String> roles)
+ {
+ return AccessController.doPrivileged(new PrivilegedAction<Group>()
+ {
+ public Group run()
+ {
+ Group theGroup = new PicketLinkGroup(SecurityConstants.ROLES_IDENTIFIER);
+ for(String role: roles)
+ {
+ theGroup.addMember(new SimplePrincipal(role));
+ }
+ return theGroup;
+ }
+ });
+ }
}
\ No newline at end of file
Added: trust/trunk/jbossws/src/test/java/org/picketlink/test/trust/jbossws/handler/SAML2HandlerUnitTestCase.java
===================================================================
--- trust/trunk/jbossws/src/test/java/org/picketlink/test/trust/jbossws/handler/SAML2HandlerUnitTestCase.java (rev 0)
+++ trust/trunk/jbossws/src/test/java/org/picketlink/test/trust/jbossws/handler/SAML2HandlerUnitTestCase.java 2011-07-13 00:52:18 UTC (rev 1085)
@@ -0,0 +1,193 @@
+/*
+ * JBoss, Home of Professional Open Source.
+ * Copyright 2008, Red Hat Middleware LLC, and individual contributors
+ * as indicated by the @author tags. See the copyright.txt file in the
+ * distribution for a full listing of individual contributors.
+ *
+ * This is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU Lesser General Public License as
+ * published by the Free Software Foundation; either version 2.1 of
+ * the License, or (at your option) any later version.
+ *
+ * This software is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this software; if not, write to the Free
+ * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
+ * 02110-1301 USA, or see the FSF site: http://www.fsf.org.
+ */
+package org.picketlink.test.trust.jbossws.handler;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertNotNull;
+import static org.junit.Assert.assertTrue;
+
+import java.io.IOException;
+import java.io.InputStream;
+import java.security.acl.Group;
+import java.util.Collection;
+import java.util.HashMap;
+import java.util.Map;
+import java.util.Set;
+
+import javax.security.auth.Subject;
+import javax.xml.bind.JAXBContext;
+import javax.xml.namespace.QName;
+import javax.xml.soap.SOAPException;
+import javax.xml.soap.SOAPMessage;
+import javax.xml.ws.handler.MessageContext;
+import javax.xml.ws.handler.soap.SOAPMessageContext;
+
+import org.jboss.security.SecurityContext;
+import org.jboss.security.SecurityContextAssociation;
+import org.jboss.security.SimplePrincipal;
+import org.junit.Test;
+import org.picketlink.identity.federation.core.util.SOAPUtil;
+import org.picketlink.trust.jbossws.handler.SAML2Handler;
+
+/**
+ * Unit test the {@link SAML2Handler}
+ * @author Anil.Saldhana(a)redhat.com
+ * @since Jul 12, 2011
+ */
+public class SAML2HandlerUnitTestCase
+{
+ @Test
+ public void testIn() throws Exception
+ {
+ DelegatingHandler handler = new DelegatingHandler();
+ SAML2HandlerUnitTestCaseMessageContext msgContext = new SAML2HandlerUnitTestCaseMessageContext();
+ SOAPMessage soapMessage = get();
+
+ System.setProperty("picketlink.rolekey", "Role,Roles,Membership");
+ msgContext.setMessage(soapMessage);
+ handler.handleInbound(msgContext);
+
+ SecurityContext securityContext = SecurityContextAssociation.getSecurityContext();
+ assertNotNull(securityContext);
+ assertEquals("admin", securityContext.getUtil().getUserName());
+ Subject subject = securityContext.getUtil().getSubject();
+ Set<Group> groups = subject.getPrincipals(Group.class);
+ assertEquals(1, groups.size());
+ Group grp = groups.iterator().next();
+ assertTrue(grp.isMember(new SimplePrincipal("meco")));
+ }
+
+ private SOAPMessage get() throws SOAPException, IOException
+ {
+ InputStream is = Thread.currentThread().getContextClassLoader().getResourceAsStream("jbossws/xml/wsse-saml.xml");
+ SOAPMessage soapMessage = SOAPUtil.getSOAPMessage(is);
+ return soapMessage;
+ }
+
+ private static class DelegatingHandler extends SAML2Handler
+ {
+ @Override
+ protected boolean handleInbound(MessageContext msgContext)
+ {
+ return super.handleInbound(msgContext);
+ }
+ }
+
+ private static class SAML2HandlerUnitTestCaseMessageContext implements SOAPMessageContext
+ {
+ private Map<String,Object> map = new HashMap<String, Object>();
+
+ private Map<String,Scope> scopes = new HashMap<String, MessageContext.Scope>();
+
+ private SOAPMessage msg;
+
+ public int size()
+ {
+ return 0;
+ }
+
+ public boolean isEmpty()
+ {
+ return false;
+ }
+
+ public boolean containsKey(Object key)
+ {
+ return map.containsKey(key);
+ }
+
+ public boolean containsValue(Object value)
+ {
+ return map.containsValue(value);
+ }
+
+ public Object get(Object key)
+ {
+ return map.get(key);
+ }
+
+ public Object put(String key, Object value)
+ {
+ return map.put(key, value);
+ }
+
+ public Object remove(Object key)
+ {
+ return map.remove(key);
+ }
+
+ public void putAll(Map<? extends String, ? extends Object> m)
+ {
+ map.putAll(m);
+ }
+
+ public void clear()
+ {
+ map.clear();
+ }
+
+ public Set<String> keySet()
+ {
+ return map.keySet();
+ }
+
+ public Collection<Object> values()
+ {
+ return map.values();
+ }
+
+ public Set<java.util.Map.Entry<String, Object>> entrySet()
+ {
+ return map.entrySet();
+ }
+
+ public Scope getScope(String arg0)
+ {
+ return scopes.get(arg0);
+ }
+
+ public void setScope(String arg0, Scope arg1)
+ {
+ scopes.put(arg0, arg1);
+ }
+
+ public Object[] getHeaders(QName arg0, JAXBContext arg1, boolean arg2)
+ {
+ throw new RuntimeException("NYI");
+ }
+
+ public SOAPMessage getMessage()
+ {
+ return msg;
+ }
+
+ public Set<String> getRoles()
+ {
+ throw new RuntimeException("NYI");
+ }
+
+ public void setMessage(SOAPMessage arg0)
+ {
+ msg =arg0;
+ }
+ }
+}
\ No newline at end of file
Added: trust/trunk/jbossws/src/test/resources/jbossws/xml/wsse-saml.xml
===================================================================
--- trust/trunk/jbossws/src/test/resources/jbossws/xml/wsse-saml.xml (rev 0)
+++ trust/trunk/jbossws/src/test/resources/jbossws/xml/wsse-saml.xml 2011-07-13 00:52:18 UTC (rev 1085)
@@ -0,0 +1,58 @@
+<env:Envelope xmlns:env='http://schemas.xmlsoap.org/soap/envelope/'>
+ " +
+ <env:Header>
+ <wsse:Security
+ xmlns:wsse='http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext...'>
+ <saml:Assertion xmlns:saml='urn:oasis:names:tc:SAML:2.0:assertion'
+ xmlns='urn:oasis:names:tc:SAML:2.0:assertion' ID='ID_7069926b-792e-4f90-8727-0e16ec9c3073'
+ IssueInstant='2011-07-13T00:16:13.990Z' Version='2.0'>
+ <Issuer xmlns:saml='urn:oasis:names:tc:SAML:2.0:assertion'>PicketLinkSTS</Issuer>
+ <saml:Subject>
+ <saml:NameID NameQualifier='urn:picketlink:identity-federation'
+ xmlns:saml='urn:oasis:names:tc:SAML:2.0:assertion'>admin</saml:NameID>
+ <saml:SubjectConfirmation Method='urn:oasis:names:tc:SAML:2.0:cm:bearer' />
+ </saml:Subject>
+ <saml:Conditions NotBefore='2011-07-13T00:16:13.990Z'
+ NotOnOrAfter='2030-07-13T02:16:13.990Z'>
+ <saml:AudienceRestriction>
+ <saml:Audience>http://services.testcorp.org/provider1
+ </saml:Audience>
+ </saml:AudienceRestriction>
+ </saml:Conditions>
+ <saml:AuthnStatement AuthnInstant="2011-06-06T21:30:07Z"
+ xmlns:saml="urn:oasis:names:tc:SAML:2.0:assertion">
+ <saml:AuthnContext xmlns:saml="urn:oasis:names:tc:SAML:2.0:assertion">
+ <saml:AuthnContextClassRef xmlns:saml="urn:oasis:names:tc:SAML:2.0:assertion">urn:oasis:names:tc:SAML:2.0:ac:classes:Password
+ </saml:AuthnContextClassRef>
+ </saml:AuthnContext>
+ </saml:AuthnStatement>
+ <saml:AttributeStatement xmlns:saml="urn:oasis:names:tc:SAML:2.0:assertion">
+ <saml:Attribute Name="FGADataset"
+ NameFormat="urn:oasis:names:tc:SAML:2.0:assertion" xmlns:saml="urn:oasis:names:tc:SAML:2.0:assertion">
+ <saml:AttributeValue xmlns:saml="urn:oasis:names:tc:SAML:2.0:assertion"
+ xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:type="xs:string">1234
+ </saml:AttributeValue>
+ <saml:AttributeValue xmlns:saml="urn:oasis:names:tc:SAML:2.0:assertion"
+ xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:type="xs:string">4768
+ </saml:AttributeValue>
+ </saml:Attribute>
+ <saml:Attribute Name="Roles"
+ NameFormat="urn:oasis:names:tc:SAML:2.0:profiles:attribute:DCE:groups">
+ <saml:AttributeValue xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:type="xs:string">meco</saml:AttributeValue>
+ <saml:AttributeValue xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:type="xs:string">aispoc_grp1</saml:AttributeValue>
+ <saml:AttributeValue xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:type="xs:string">grp-poc</saml:AttributeValue>
+ </saml:Attribute>
+ <saml:Attribute Name="Membership"
+ NameFormat="urn:oasis:names:tc:SAML:2.0:profiles:attribute:DCE:groups">
+ <saml:AttributeValue xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:type="xs:string">meco</saml:AttributeValue>
+ </saml:Attribute>
+ </saml:AttributeStatement>
+ </saml:Assertion>
+ </wsse:Security>
+ </env:Header>
+ <env:Body />
+</env:Envelope>
\ No newline at end of file
13 years, 5 months