Return-Path: X-Original-To: apmail-cxf-commits-archive@www.apache.org Delivered-To: apmail-cxf-commits-archive@www.apache.org Received: from mail.apache.org (hermes.apache.org [140.211.11.3]) by minotaur.apache.org (Postfix) with SMTP id C856817FB5 for ; Tue, 17 Nov 2015 13:59:22 +0000 (UTC) Received: (qmail 59035 invoked by uid 500); 17 Nov 2015 13:59:22 -0000 Delivered-To: apmail-cxf-commits-archive@cxf.apache.org Received: (qmail 58878 invoked by uid 500); 17 Nov 2015 13:59:22 -0000 Mailing-List: contact commits-help@cxf.apache.org; run by ezmlm Precedence: bulk List-Help: List-Unsubscribe: List-Post: List-Id: Reply-To: dev@cxf.apache.org Delivered-To: mailing list commits@cxf.apache.org Received: (qmail 58811 invoked by uid 99); 17 Nov 2015 13:59:22 -0000 Received: from git1-us-west.apache.org (HELO git1-us-west.apache.org) (140.211.11.23) by apache.org (qpsmtpd/0.29) with ESMTP; Tue, 17 Nov 2015 13:59:22 +0000 Received: by git1-us-west.apache.org (ASF Mail Server at git1-us-west.apache.org, from userid 33) id 3F5B7DFF87; Tue, 17 Nov 2015 13:59:22 +0000 (UTC) Content-Type: text/plain; charset="us-ascii" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit From: coheigea@apache.org To: commits@cxf.apache.org Date: Tue, 17 Nov 2015 13:59:22 -0000 Message-Id: <7e73be50ec874b62aaae3ee15f42e918@git.apache.org> X-Mailer: ASF-Git Admin Mailer Subject: [1/2] cxf git commit: Added support for realms with JWT validation Repository: cxf Updated Branches: refs/heads/3.1.x-fixes 5e5470e7b -> cec8828bd Added support for realms with JWT validation Project: http://git-wip-us.apache.org/repos/asf/cxf/repo Commit: http://git-wip-us.apache.org/repos/asf/cxf/commit/662b14a6 Tree: http://git-wip-us.apache.org/repos/asf/cxf/tree/662b14a6 Diff: http://git-wip-us.apache.org/repos/asf/cxf/diff/662b14a6 Branch: refs/heads/3.1.x-fixes Commit: 662b14a6e267808e71e786ff873ee27945122a20 Parents: 5e5470e Author: Colm O hEigeartaigh Authored: Tue Nov 17 12:39:46 2015 +0000 Committer: Colm O hEigeartaigh Committed: Tue Nov 17 13:51:55 2015 +0000 ---------------------------------------------------------------------- .../ws/security/trust/AbstractSTSClient.java | 4 +- .../cxf/sts/operation/TokenIssueOperation.java | 10 +- .../apache/cxf/sts/request/ReceivedToken.java | 5 - .../cxf/sts/token/realm/JWTRealmCodec.java | 36 +++ .../token/validator/jwt/JWTTokenValidator.java | 56 ++-- .../sts/operation/IssueJWTClaimsUnitTest.java | 61 ++-- .../operation/IssueJWTOnbehalfofUnitTest.java | 46 +-- .../sts/operation/IssueJWTRealmUnitTest.java | 63 +++-- .../cxf/sts/operation/IssueJWTUnitTest.java | 16 +- .../validator/JWTTokenValidatorRealmTest.java | 280 +++++++++++++++++++ .../token/validator/JWTTokenValidatorTest.java | 23 +- .../apache/cxf/systest/sts/jwt/JWTUnitTest.java | 41 ++- .../cxf/systest/sts/deployment/cxf-sts.xml | 3 + 13 files changed, 514 insertions(+), 130 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/cxf/blob/662b14a6/rt/ws/security/src/main/java/org/apache/cxf/ws/security/trust/AbstractSTSClient.java ---------------------------------------------------------------------- diff --git a/rt/ws/security/src/main/java/org/apache/cxf/ws/security/trust/AbstractSTSClient.java b/rt/ws/security/src/main/java/org/apache/cxf/ws/security/trust/AbstractSTSClient.java index f06ff80..0b6f619 100755 --- a/rt/ws/security/src/main/java/org/apache/cxf/ws/security/trust/AbstractSTSClient.java +++ b/rt/ws/security/src/main/java/org/apache/cxf/ws/security/trust/AbstractSTSClient.java @@ -1117,7 +1117,9 @@ public abstract class AbstractSTSClient implements Configurable, InterceptorProv writer.writeStartElement("wst", "ValidateTarget", namespace); Element el = tok.getToken(); - StaxUtils.copy(el, writer); + if (el != null) { + StaxUtils.copy(el, writer); + } writer.writeEndElement(); writer.writeEndElement(); http://git-wip-us.apache.org/repos/asf/cxf/blob/662b14a6/services/sts/sts-core/src/main/java/org/apache/cxf/sts/operation/TokenIssueOperation.java ---------------------------------------------------------------------- diff --git a/services/sts/sts-core/src/main/java/org/apache/cxf/sts/operation/TokenIssueOperation.java b/services/sts/sts-core/src/main/java/org/apache/cxf/sts/operation/TokenIssueOperation.java index 383535e..7a9b57a 100644 --- a/services/sts/sts-core/src/main/java/org/apache/cxf/sts/operation/TokenIssueOperation.java +++ b/services/sts/sts-core/src/main/java/org/apache/cxf/sts/operation/TokenIssueOperation.java @@ -39,7 +39,6 @@ import org.apache.cxf.helpers.CastUtils; import org.apache.cxf.helpers.DOMUtils; import org.apache.cxf.rt.security.claims.ClaimCollection; import org.apache.cxf.sts.QNameConstants; -import org.apache.cxf.sts.STSConstants; import org.apache.cxf.sts.event.STSIssueFailureEvent; import org.apache.cxf.sts.event.STSIssueSuccessEvent; import org.apache.cxf.sts.request.KeyRequirements; @@ -294,14 +293,13 @@ public class TokenIssueOperation extends AbstractOperation implements IssueOpera } else { if (tokenResponse.getToken() instanceof String) { Document doc = DOMUtils.newDocument(); - Element requestedTokenEl = doc.createElementNS(STSConstants.WST_NS_05_12, - "RequestedSecurityToken"); - requestedTokenEl.setTextContent((String)tokenResponse.getToken()); - response.getAny().add(requestedTokenEl); + Element tokenWrapper = doc.createElementNS(null, "TokenWrapper"); + tokenWrapper.setTextContent((String)tokenResponse.getToken()); + requestedTokenType.setAny(tokenWrapper); } else { requestedTokenType.setAny(tokenResponse.getToken()); - response.getAny().add(requestedToken); } + response.getAny().add(requestedToken); } if (returnReferences) { http://git-wip-us.apache.org/repos/asf/cxf/blob/662b14a6/services/sts/sts-core/src/main/java/org/apache/cxf/sts/request/ReceivedToken.java ---------------------------------------------------------------------- diff --git a/services/sts/sts-core/src/main/java/org/apache/cxf/sts/request/ReceivedToken.java b/services/sts/sts-core/src/main/java/org/apache/cxf/sts/request/ReceivedToken.java index 252ec60..d220670 100644 --- a/services/sts/sts-core/src/main/java/org/apache/cxf/sts/request/ReceivedToken.java +++ b/services/sts/sts-core/src/main/java/org/apache/cxf/sts/request/ReceivedToken.java @@ -74,11 +74,6 @@ public class ReceivedToken { } this.token = receivedToken; isDOMElement = true; - } else if (receivedToken instanceof String) { - if (LOG.isLoggable(Level.FINE)) { - LOG.fine("Found ValidateTarget String"); - } - this.token = receivedToken; } else { LOG.fine("Found ValidateTarget object of unknown type"); throw new STSException( http://git-wip-us.apache.org/repos/asf/cxf/blob/662b14a6/services/sts/sts-core/src/main/java/org/apache/cxf/sts/token/realm/JWTRealmCodec.java ---------------------------------------------------------------------- diff --git a/services/sts/sts-core/src/main/java/org/apache/cxf/sts/token/realm/JWTRealmCodec.java b/services/sts/sts-core/src/main/java/org/apache/cxf/sts/token/realm/JWTRealmCodec.java new file mode 100644 index 0000000..540e1c8 --- /dev/null +++ b/services/sts/sts-core/src/main/java/org/apache/cxf/sts/token/realm/JWTRealmCodec.java @@ -0,0 +1,36 @@ +/** + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +package org.apache.cxf.sts.token.realm; + +import org.apache.cxf.rs.security.jose.jwt.JwtToken; + +/** + * This interface defines a pluggable way to return a realm associated with a JWT Token. + */ +public interface JWTRealmCodec { + + /** + * Get the realm associated with the JwtToken parameter + * @param token a JwtToken Object + * @return the realm associated with the JwtToken parameter + */ + String getRealmFromToken(JwtToken token); + +} http://git-wip-us.apache.org/repos/asf/cxf/blob/662b14a6/services/sts/sts-core/src/main/java/org/apache/cxf/sts/token/validator/jwt/JWTTokenValidator.java ---------------------------------------------------------------------- diff --git a/services/sts/sts-core/src/main/java/org/apache/cxf/sts/token/validator/jwt/JWTTokenValidator.java b/services/sts/sts-core/src/main/java/org/apache/cxf/sts/token/validator/jwt/JWTTokenValidator.java index 110a611..4fb9dec 100644 --- a/services/sts/sts-core/src/main/java/org/apache/cxf/sts/token/validator/jwt/JWTTokenValidator.java +++ b/services/sts/sts-core/src/main/java/org/apache/cxf/sts/token/validator/jwt/JWTTokenValidator.java @@ -25,6 +25,10 @@ import java.util.Set; import java.util.logging.Level; import java.util.logging.Logger; +import javax.xml.soap.Node; + +import org.w3c.dom.Element; + import org.apache.cxf.common.logging.LogUtils; import org.apache.cxf.common.security.SimplePrincipal; import org.apache.cxf.rs.security.jose.common.JoseConstants; @@ -37,6 +41,7 @@ import org.apache.cxf.rs.security.jose.jwt.JwtUtils; import org.apache.cxf.sts.STSPropertiesMBean; import org.apache.cxf.sts.request.ReceivedToken; import org.apache.cxf.sts.request.ReceivedToken.STATE; +import org.apache.cxf.sts.token.realm.JWTRealmCodec; import org.apache.cxf.sts.token.validator.TokenValidator; import org.apache.cxf.sts.token.validator.TokenValidatorParameters; import org.apache.cxf.sts.token.validator.TokenValidatorResponse; @@ -53,6 +58,7 @@ public class JWTTokenValidator implements TokenValidator { private int clockOffset; private int ttl; private JWTRoleParser roleParser; + private JWTRealmCodec realmCodec; /** * Return true if this TokenValidator implementation is capable of validating the @@ -68,14 +74,17 @@ public class JWTTokenValidator implements TokenValidator { */ public boolean canHandleToken(ReceivedToken validateTarget, String realm) { Object token = validateTarget.getToken(); - if (token instanceof String) { - try { - JwsJwtCompactConsumer jwtConsumer = new JwsJwtCompactConsumer((String)token); - if (jwtConsumer.getJwtToken() != null) { - return true; + if (token instanceof Element) { + Element tokenEl = (Element)token; + if (tokenEl.getFirstChild().getNodeType() == Node.TEXT_NODE) { + try { + JwsJwtCompactConsumer jwtConsumer = new JwsJwtCompactConsumer(tokenEl.getTextContent()); + if (jwtConsumer.getJwtToken() != null) { + return true; + } + } catch (RuntimeException ex) { + return false; } - } catch (RuntimeException ex) { - return false; } } return false; @@ -93,8 +102,8 @@ public class JWTTokenValidator implements TokenValidator { validateTarget.setState(STATE.INVALID); response.setToken(validateTarget); - String token = (String)validateTarget.getToken(); - if (token == null) { + String token = ((Element)validateTarget.getToken()).getTextContent(); + if (token == null || "".equals(token)) { return response; } @@ -137,24 +146,11 @@ public class JWTTokenValidator implements TokenValidator { } - /* - // Get the realm of the SAML token - String tokenRealm = null; - if (samlRealmCodec != null) { - tokenRealm = samlRealmCodec.getRealmFromToken(assertion); - // verify the realm against the cached token - if (secToken != null) { - Map props = secToken.getProperties(); - if (props != null) { - String cachedRealm = (String)props.get(STSConstants.TOKEN_REALM); - if (cachedRealm != null && !tokenRealm.equals(cachedRealm)) { - return response; - } - } - } + // Get the realm of the JWT Token + if (realmCodec != null) { + String tokenRealm = realmCodec.getRealmFromToken(jwt); + response.setTokenRealm(tokenRealm); } - response.setTokenRealm(tokenRealm); - */ if (isVerifiedWithAPublicKey(jwt)) { Principal principal = new SimplePrincipal(jwt.getClaims().getSubject()); @@ -215,4 +211,12 @@ public class JWTTokenValidator implements TokenValidator { public void setRoleParser(JWTRoleParser roleParser) { this.roleParser = roleParser; } + + public JWTRealmCodec getRealmCodec() { + return realmCodec; + } + + public void setRealmCodec(JWTRealmCodec realmCodec) { + this.realmCodec = realmCodec; + } } http://git-wip-us.apache.org/repos/asf/cxf/blob/662b14a6/services/sts/sts-core/src/test/java/org/apache/cxf/sts/operation/IssueJWTClaimsUnitTest.java ---------------------------------------------------------------------- diff --git a/services/sts/sts-core/src/test/java/org/apache/cxf/sts/operation/IssueJWTClaimsUnitTest.java b/services/sts/sts-core/src/test/java/org/apache/cxf/sts/operation/IssueJWTClaimsUnitTest.java index ab20e96..82d921b 100644 --- a/services/sts/sts-core/src/test/java/org/apache/cxf/sts/operation/IssueJWTClaimsUnitTest.java +++ b/services/sts/sts-core/src/test/java/org/apache/cxf/sts/operation/IssueJWTClaimsUnitTest.java @@ -77,6 +77,7 @@ import org.apache.cxf.ws.security.sts.provider.model.OnBehalfOfType; import org.apache.cxf.ws.security.sts.provider.model.RequestSecurityTokenResponseCollectionType; import org.apache.cxf.ws.security.sts.provider.model.RequestSecurityTokenResponseType; import org.apache.cxf.ws.security.sts.provider.model.RequestSecurityTokenType; +import org.apache.cxf.ws.security.sts.provider.model.RequestedSecurityTokenType; import org.apache.wss4j.common.crypto.Crypto; import org.apache.wss4j.common.crypto.CryptoFactory; import org.apache.wss4j.common.ext.WSSecurityException; @@ -136,20 +137,21 @@ public class IssueJWTClaimsUnitTest extends org.junit.Assert { webServiceContext); // Test the generated token. - String jwtToken = null; + Element token = null; for (Object tokenObject : securityTokenResponse.get(0).getAny()) { - if (tokenObject instanceof Element - && REQUESTED_SECURITY_TOKEN.getLocalPart().equals(((Element)tokenObject).getLocalName()) - && REQUESTED_SECURITY_TOKEN.getNamespaceURI().equals(((Element)tokenObject).getNamespaceURI())) { - jwtToken = ((Element)tokenObject).getTextContent(); + if (tokenObject instanceof JAXBElement + && REQUESTED_SECURITY_TOKEN.equals(((JAXBElement)tokenObject).getName())) { + RequestedSecurityTokenType rstType = + (RequestedSecurityTokenType)((JAXBElement)tokenObject).getValue(); + token = (Element)rstType.getAny(); break; } } - assertNotNull(jwtToken); + assertNotNull(token); // Validate the token - JwsJwtCompactConsumer jwtConsumer = new JwsJwtCompactConsumer(jwtToken); + JwsJwtCompactConsumer jwtConsumer = new JwsJwtCompactConsumer(token.getTextContent()); JwtToken jwt = jwtConsumer.getJwtToken(); Assert.assertEquals("alice", jwt.getClaim(JwtConstants.CLAIM_SUBJECT)); assertEquals(jwt.getClaim(ClaimTypes.LASTNAME.toString()), "doe"); @@ -262,20 +264,21 @@ public class IssueJWTClaimsUnitTest extends org.junit.Assert { webServiceContext); // Test the generated token. - String jwtToken = null; + Element token = null; for (Object tokenObject : securityTokenResponse.get(0).getAny()) { - if (tokenObject instanceof Element - && REQUESTED_SECURITY_TOKEN.getLocalPart().equals(((Element)tokenObject).getLocalName()) - && REQUESTED_SECURITY_TOKEN.getNamespaceURI().equals(((Element)tokenObject).getNamespaceURI())) { - jwtToken = ((Element)tokenObject).getTextContent(); + if (tokenObject instanceof JAXBElement + && REQUESTED_SECURITY_TOKEN.equals(((JAXBElement)tokenObject).getName())) { + RequestedSecurityTokenType rstType = + (RequestedSecurityTokenType)((JAXBElement)tokenObject).getValue(); + token = (Element)rstType.getAny(); break; } } - assertNotNull(jwtToken); + assertNotNull(token); // Validate the token - JwsJwtCompactConsumer jwtConsumer = new JwsJwtCompactConsumer(jwtToken); + JwsJwtCompactConsumer jwtConsumer = new JwsJwtCompactConsumer(token.getTextContent()); JwtToken jwt = jwtConsumer.getJwtToken(); Assert.assertEquals("alice", jwt.getClaim(JwtConstants.CLAIM_SUBJECT)); assertEquals(jwt.getClaim(ClaimTypes.LASTNAME.toString()), "doe"); @@ -387,20 +390,21 @@ public class IssueJWTClaimsUnitTest extends org.junit.Assert { request, webServiceContext); // Test the generated token. - String jwtToken = null; + Element token = null; for (Object tokenObject : securityTokenResponseList.get(0).getAny()) { - if (tokenObject instanceof Element - && REQUESTED_SECURITY_TOKEN.getLocalPart().equals(((Element)tokenObject).getLocalName()) - && REQUESTED_SECURITY_TOKEN.getNamespaceURI().equals(((Element)tokenObject).getNamespaceURI())) { - jwtToken = ((Element)tokenObject).getTextContent(); + if (tokenObject instanceof JAXBElement + && REQUESTED_SECURITY_TOKEN.equals(((JAXBElement)tokenObject).getName())) { + RequestedSecurityTokenType rstType = + (RequestedSecurityTokenType)((JAXBElement)tokenObject).getValue(); + token = (Element)rstType.getAny(); break; } } - assertNotNull(jwtToken); + assertNotNull(token); // Validate the token - JwsJwtCompactConsumer jwtConsumer = new JwsJwtCompactConsumer(jwtToken); + JwsJwtCompactConsumer jwtConsumer = new JwsJwtCompactConsumer(token.getTextContent()); JwtToken jwt = jwtConsumer.getJwtToken(); // subject unchanged Assert.assertEquals("alice", jwt.getClaim(JwtConstants.CLAIM_SUBJECT)); @@ -539,20 +543,21 @@ public class IssueJWTClaimsUnitTest extends org.junit.Assert { request, webServiceContext); // Test the generated token. - String jwtToken = null; + Element token = null; for (Object tokenObject : securityTokenResponseList.get(0).getAny()) { - if (tokenObject instanceof Element - && REQUESTED_SECURITY_TOKEN.getLocalPart().equals(((Element)tokenObject).getLocalName()) - && REQUESTED_SECURITY_TOKEN.getNamespaceURI().equals(((Element)tokenObject).getNamespaceURI())) { - jwtToken = ((Element)tokenObject).getTextContent(); + if (tokenObject instanceof JAXBElement + && REQUESTED_SECURITY_TOKEN.equals(((JAXBElement)tokenObject).getName())) { + RequestedSecurityTokenType rstType = + (RequestedSecurityTokenType)((JAXBElement)tokenObject).getValue(); + token = (Element)rstType.getAny(); break; } } - assertNotNull(jwtToken); + assertNotNull(token); // Validate the token - JwsJwtCompactConsumer jwtConsumer = new JwsJwtCompactConsumer(jwtToken); + JwsJwtCompactConsumer jwtConsumer = new JwsJwtCompactConsumer(token.getTextContent()); JwtToken jwt = jwtConsumer.getJwtToken(); // subject changed (to uppercase) Assert.assertEquals("ALICE", jwt.getClaim(JwtConstants.CLAIM_SUBJECT)); http://git-wip-us.apache.org/repos/asf/cxf/blob/662b14a6/services/sts/sts-core/src/test/java/org/apache/cxf/sts/operation/IssueJWTOnbehalfofUnitTest.java ---------------------------------------------------------------------- diff --git a/services/sts/sts-core/src/test/java/org/apache/cxf/sts/operation/IssueJWTOnbehalfofUnitTest.java b/services/sts/sts-core/src/test/java/org/apache/cxf/sts/operation/IssueJWTOnbehalfofUnitTest.java index dc2352f..5d1bfa6 100644 --- a/services/sts/sts-core/src/test/java/org/apache/cxf/sts/operation/IssueJWTOnbehalfofUnitTest.java +++ b/services/sts/sts-core/src/test/java/org/apache/cxf/sts/operation/IssueJWTOnbehalfofUnitTest.java @@ -68,6 +68,7 @@ import org.apache.cxf.ws.security.sts.provider.model.OnBehalfOfType; import org.apache.cxf.ws.security.sts.provider.model.RequestSecurityTokenResponseCollectionType; import org.apache.cxf.ws.security.sts.provider.model.RequestSecurityTokenResponseType; import org.apache.cxf.ws.security.sts.provider.model.RequestSecurityTokenType; +import org.apache.cxf.ws.security.sts.provider.model.RequestedSecurityTokenType; import org.apache.cxf.ws.security.sts.provider.model.secext.AttributedString; import org.apache.cxf.ws.security.sts.provider.model.secext.PasswordString; import org.apache.cxf.ws.security.sts.provider.model.secext.UsernameTokenType; @@ -159,20 +160,21 @@ public class IssueJWTOnbehalfofUnitTest extends org.junit.Assert { assertTrue(!securityTokenResponse.isEmpty()); // Test the generated token. - String jwtToken = null; + Element token = null; for (Object tokenObject : securityTokenResponse.get(0).getAny()) { - if (tokenObject instanceof Element - && REQUESTED_SECURITY_TOKEN.getLocalPart().equals(((Element)tokenObject).getLocalName()) - && REQUESTED_SECURITY_TOKEN.getNamespaceURI().equals(((Element)tokenObject).getNamespaceURI())) { - jwtToken = ((Element)tokenObject).getTextContent(); + if (tokenObject instanceof JAXBElement + && REQUESTED_SECURITY_TOKEN.equals(((JAXBElement)tokenObject).getName())) { + RequestedSecurityTokenType rstType = + (RequestedSecurityTokenType)((JAXBElement)tokenObject).getValue(); + token = (Element)rstType.getAny(); break; } } - assertNotNull(jwtToken); + assertNotNull(token); // Validate the token - JwsJwtCompactConsumer jwtConsumer = new JwsJwtCompactConsumer(jwtToken); + JwsJwtCompactConsumer jwtConsumer = new JwsJwtCompactConsumer(token.getTextContent()); JwtToken jwt = jwtConsumer.getJwtToken(); Assert.assertEquals("alice", jwt.getClaim(JwtConstants.CLAIM_SUBJECT)); } @@ -256,20 +258,21 @@ public class IssueJWTOnbehalfofUnitTest extends org.junit.Assert { assertTrue(!securityTokenResponse.isEmpty()); // Test the generated token. - String jwtToken = null; + Element token = null; for (Object tokenObject : securityTokenResponse.get(0).getAny()) { - if (tokenObject instanceof Element - && REQUESTED_SECURITY_TOKEN.getLocalPart().equals(((Element)tokenObject).getLocalName()) - && REQUESTED_SECURITY_TOKEN.getNamespaceURI().equals(((Element)tokenObject).getNamespaceURI())) { - jwtToken = ((Element)tokenObject).getTextContent(); + if (tokenObject instanceof JAXBElement + && REQUESTED_SECURITY_TOKEN.equals(((JAXBElement)tokenObject).getName())) { + RequestedSecurityTokenType rstType = + (RequestedSecurityTokenType)((JAXBElement)tokenObject).getValue(); + token = (Element)rstType.getAny(); break; } } - assertNotNull(jwtToken); + assertNotNull(token); // Validate the token - JwsJwtCompactConsumer jwtConsumer = new JwsJwtCompactConsumer(jwtToken); + JwsJwtCompactConsumer jwtConsumer = new JwsJwtCompactConsumer(token.getTextContent()); JwtToken jwt = jwtConsumer.getJwtToken(); Assert.assertEquals("alice", jwt.getClaim(JwtConstants.CLAIM_SUBJECT)); } @@ -357,20 +360,21 @@ public class IssueJWTOnbehalfofUnitTest extends org.junit.Assert { assertTrue(!securityTokenResponse.isEmpty()); // Test the generated token. - String jwtToken = null; + Element token = null; for (Object tokenObject : securityTokenResponse.get(0).getAny()) { - if (tokenObject instanceof Element - && REQUESTED_SECURITY_TOKEN.getLocalPart().equals(((Element)tokenObject).getLocalName()) - && REQUESTED_SECURITY_TOKEN.getNamespaceURI().equals(((Element)tokenObject).getNamespaceURI())) { - jwtToken = ((Element)tokenObject).getTextContent(); + if (tokenObject instanceof JAXBElement + && REQUESTED_SECURITY_TOKEN.equals(((JAXBElement)tokenObject).getName())) { + RequestedSecurityTokenType rstType = + (RequestedSecurityTokenType)((JAXBElement)tokenObject).getValue(); + token = (Element)rstType.getAny(); break; } } - assertNotNull(jwtToken); + assertNotNull(token); // Validate the token - JwsJwtCompactConsumer jwtConsumer = new JwsJwtCompactConsumer(jwtToken); + JwsJwtCompactConsumer jwtConsumer = new JwsJwtCompactConsumer(token.getTextContent()); JwtToken jwt = jwtConsumer.getJwtToken(); Assert.assertEquals("ALICE", jwt.getClaim(JwtConstants.CLAIM_SUBJECT)); } http://git-wip-us.apache.org/repos/asf/cxf/blob/662b14a6/services/sts/sts-core/src/test/java/org/apache/cxf/sts/operation/IssueJWTRealmUnitTest.java ---------------------------------------------------------------------- diff --git a/services/sts/sts-core/src/test/java/org/apache/cxf/sts/operation/IssueJWTRealmUnitTest.java b/services/sts/sts-core/src/test/java/org/apache/cxf/sts/operation/IssueJWTRealmUnitTest.java index 3a8b496..4608396 100644 --- a/services/sts/sts-core/src/test/java/org/apache/cxf/sts/operation/IssueJWTRealmUnitTest.java +++ b/services/sts/sts-core/src/test/java/org/apache/cxf/sts/operation/IssueJWTRealmUnitTest.java @@ -54,6 +54,7 @@ import org.apache.cxf.ws.security.sts.provider.STSException; import org.apache.cxf.ws.security.sts.provider.model.RequestSecurityTokenResponseCollectionType; import org.apache.cxf.ws.security.sts.provider.model.RequestSecurityTokenResponseType; import org.apache.cxf.ws.security.sts.provider.model.RequestSecurityTokenType; +import org.apache.cxf.ws.security.sts.provider.model.RequestedSecurityTokenType; import org.apache.wss4j.common.crypto.Crypto; import org.apache.wss4j.common.crypto.CryptoFactory; import org.apache.wss4j.common.principal.CustomTokenPrincipal; @@ -130,18 +131,19 @@ public class IssueJWTRealmUnitTest extends org.junit.Assert { assertTrue(!securityTokenResponse.isEmpty()); // Test the generated token. - String jwtToken = null; + Element token = null; for (Object tokenObject : securityTokenResponse.get(0).getAny()) { - if (tokenObject instanceof Element - && REQUESTED_SECURITY_TOKEN.getLocalPart().equals(((Element)tokenObject).getLocalName()) - && REQUESTED_SECURITY_TOKEN.getNamespaceURI().equals(((Element)tokenObject).getNamespaceURI())) { - jwtToken = ((Element)tokenObject).getTextContent(); + if (tokenObject instanceof JAXBElement + && REQUESTED_SECURITY_TOKEN.equals(((JAXBElement)tokenObject).getName())) { + RequestedSecurityTokenType rstType = + (RequestedSecurityTokenType)((JAXBElement)tokenObject).getValue(); + token = (Element)rstType.getAny(); break; } } - assertNotNull(jwtToken); - JwsJwtCompactConsumer jwtConsumer = new JwsJwtCompactConsumer(jwtToken); + assertNotNull(token); + JwsJwtCompactConsumer jwtConsumer = new JwsJwtCompactConsumer(token.getTextContent()); JwtToken jwt = jwtConsumer.getJwtToken(); Assert.assertEquals("A-Issuer", jwt.getClaim(JwtConstants.CLAIM_ISSUER)); } @@ -204,18 +206,19 @@ public class IssueJWTRealmUnitTest extends org.junit.Assert { assertTrue(!securityTokenResponse.isEmpty()); // Test the generated token. - String jwtToken = null; + Element token = null; for (Object tokenObject : securityTokenResponse.get(0).getAny()) { - if (tokenObject instanceof Element - && REQUESTED_SECURITY_TOKEN.getLocalPart().equals(((Element)tokenObject).getLocalName()) - && REQUESTED_SECURITY_TOKEN.getNamespaceURI().equals(((Element)tokenObject).getNamespaceURI())) { - jwtToken = ((Element)tokenObject).getTextContent(); + if (tokenObject instanceof JAXBElement + && REQUESTED_SECURITY_TOKEN.equals(((JAXBElement)tokenObject).getName())) { + RequestedSecurityTokenType rstType = + (RequestedSecurityTokenType)((JAXBElement)tokenObject).getValue(); + token = (Element)rstType.getAny(); break; } } - assertNotNull(jwtToken); - JwsJwtCompactConsumer jwtConsumer = new JwsJwtCompactConsumer(jwtToken); + assertNotNull(token); + JwsJwtCompactConsumer jwtConsumer = new JwsJwtCompactConsumer(token.getTextContent()); JwtToken jwt = jwtConsumer.getJwtToken(); Assert.assertEquals("B-Issuer", jwt.getClaim(JwtConstants.CLAIM_ISSUER)); } @@ -278,18 +281,19 @@ public class IssueJWTRealmUnitTest extends org.junit.Assert { assertTrue(!securityTokenResponse.isEmpty()); // Test the generated token. - String jwtToken = null; + Element token = null; for (Object tokenObject : securityTokenResponse.get(0).getAny()) { - if (tokenObject instanceof Element - && REQUESTED_SECURITY_TOKEN.getLocalPart().equals(((Element)tokenObject).getLocalName()) - && REQUESTED_SECURITY_TOKEN.getNamespaceURI().equals(((Element)tokenObject).getNamespaceURI())) { - jwtToken = ((Element)tokenObject).getTextContent(); + if (tokenObject instanceof JAXBElement + && REQUESTED_SECURITY_TOKEN.equals(((JAXBElement)tokenObject).getName())) { + RequestedSecurityTokenType rstType = + (RequestedSecurityTokenType)((JAXBElement)tokenObject).getValue(); + token = (Element)rstType.getAny(); break; } } - assertNotNull(jwtToken); - JwsJwtCompactConsumer jwtConsumer = new JwsJwtCompactConsumer(jwtToken); + assertNotNull(token); + JwsJwtCompactConsumer jwtConsumer = new JwsJwtCompactConsumer(token.getTextContent()); JwtToken jwt = jwtConsumer.getJwtToken(); Assert.assertEquals("STS", jwt.getClaim(JwtConstants.CLAIM_ISSUER)); } @@ -371,19 +375,20 @@ public class IssueJWTRealmUnitTest extends org.junit.Assert { response.getRequestSecurityTokenResponse(); assertTrue(!securityTokenResponse.isEmpty()); - // Test the generated token. - String jwtToken = null; + // Test the generated token. + Element token = null; for (Object tokenObject : securityTokenResponse.get(0).getAny()) { - if (tokenObject instanceof Element - && REQUESTED_SECURITY_TOKEN.getLocalPart().equals(((Element)tokenObject).getLocalName()) - && REQUESTED_SECURITY_TOKEN.getNamespaceURI().equals(((Element)tokenObject).getNamespaceURI())) { - jwtToken = ((Element)tokenObject).getTextContent(); + if (tokenObject instanceof JAXBElement + && REQUESTED_SECURITY_TOKEN.equals(((JAXBElement)tokenObject).getName())) { + RequestedSecurityTokenType rstType = + (RequestedSecurityTokenType)((JAXBElement)tokenObject).getValue(); + token = (Element)rstType.getAny(); break; } } - assertNotNull(jwtToken); - JwsJwtCompactConsumer jwtConsumer = new JwsJwtCompactConsumer(jwtToken); + assertNotNull(token); + JwsJwtCompactConsumer jwtConsumer = new JwsJwtCompactConsumer(token.getTextContent()); JwtToken jwt = jwtConsumer.getJwtToken(); Assert.assertEquals("B-Issuer", jwt.getClaim(JwtConstants.CLAIM_ISSUER)); } http://git-wip-us.apache.org/repos/asf/cxf/blob/662b14a6/services/sts/sts-core/src/test/java/org/apache/cxf/sts/operation/IssueJWTUnitTest.java ---------------------------------------------------------------------- diff --git a/services/sts/sts-core/src/test/java/org/apache/cxf/sts/operation/IssueJWTUnitTest.java b/services/sts/sts-core/src/test/java/org/apache/cxf/sts/operation/IssueJWTUnitTest.java index 58d6b25..5cd7a3c 100644 --- a/services/sts/sts-core/src/test/java/org/apache/cxf/sts/operation/IssueJWTUnitTest.java +++ b/services/sts/sts-core/src/test/java/org/apache/cxf/sts/operation/IssueJWTUnitTest.java @@ -51,6 +51,7 @@ import org.apache.cxf.sts.token.provider.jwt.JWTTokenProvider; import org.apache.cxf.ws.security.sts.provider.model.RequestSecurityTokenResponseCollectionType; import org.apache.cxf.ws.security.sts.provider.model.RequestSecurityTokenResponseType; import org.apache.cxf.ws.security.sts.provider.model.RequestSecurityTokenType; +import org.apache.cxf.ws.security.sts.provider.model.RequestedSecurityTokenType; import org.apache.cxf.ws.security.tokenstore.TokenStore; import org.apache.wss4j.common.crypto.Crypto; import org.apache.wss4j.common.crypto.CryptoFactory; @@ -127,20 +128,21 @@ public class IssueJWTUnitTest extends org.junit.Assert { assertTrue(!securityTokenResponse.isEmpty()); // Test the generated token. - String jwtToken = null; + Element token = null; for (Object tokenObject : securityTokenResponse.get(0).getAny()) { - if (tokenObject instanceof Element - && REQUESTED_SECURITY_TOKEN.getLocalPart().equals(((Element)tokenObject).getLocalName()) - && REQUESTED_SECURITY_TOKEN.getNamespaceURI().equals(((Element)tokenObject).getNamespaceURI())) { - jwtToken = ((Element)tokenObject).getTextContent(); + if (tokenObject instanceof JAXBElement + && REQUESTED_SECURITY_TOKEN.equals(((JAXBElement)tokenObject).getName())) { + RequestedSecurityTokenType rstType = + (RequestedSecurityTokenType)((JAXBElement)tokenObject).getValue(); + token = (Element)rstType.getAny(); break; } } - assertNotNull(jwtToken); + assertNotNull(token); // Validate the token - JwsJwtCompactConsumer jwtConsumer = new JwsJwtCompactConsumer(jwtToken); + JwsJwtCompactConsumer jwtConsumer = new JwsJwtCompactConsumer(token.getTextContent()); JwtToken jwt = jwtConsumer.getJwtToken(); Assert.assertEquals("alice", jwt.getClaim(JwtConstants.CLAIM_SUBJECT)); } http://git-wip-us.apache.org/repos/asf/cxf/blob/662b14a6/services/sts/sts-core/src/test/java/org/apache/cxf/sts/token/validator/JWTTokenValidatorRealmTest.java ---------------------------------------------------------------------- diff --git a/services/sts/sts-core/src/test/java/org/apache/cxf/sts/token/validator/JWTTokenValidatorRealmTest.java b/services/sts/sts-core/src/test/java/org/apache/cxf/sts/token/validator/JWTTokenValidatorRealmTest.java new file mode 100644 index 0000000..a73c3e1 --- /dev/null +++ b/services/sts/sts-core/src/test/java/org/apache/cxf/sts/token/validator/JWTTokenValidatorRealmTest.java @@ -0,0 +1,280 @@ +/** + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ +package org.apache.cxf.sts.token.validator; + +import java.security.Principal; +import java.util.HashMap; +import java.util.Map; +import java.util.Properties; + +import org.w3c.dom.Document; +import org.w3c.dom.Element; + +import org.apache.cxf.helpers.DOMUtils; +import org.apache.cxf.jaxws.context.WebServiceContextImpl; +import org.apache.cxf.jaxws.context.WrappedMessageContext; +import org.apache.cxf.message.MessageImpl; +import org.apache.cxf.rs.security.jose.jwt.JwtConstants; +import org.apache.cxf.rs.security.jose.jwt.JwtToken; +import org.apache.cxf.sts.STSConstants; +import org.apache.cxf.sts.StaticSTSProperties; +import org.apache.cxf.sts.cache.DefaultInMemoryTokenStore; +import org.apache.cxf.sts.common.PasswordCallbackHandler; +import org.apache.cxf.sts.request.KeyRequirements; +import org.apache.cxf.sts.request.ReceivedToken; +import org.apache.cxf.sts.request.ReceivedToken.STATE; +import org.apache.cxf.sts.request.TokenRequirements; +import org.apache.cxf.sts.service.EncryptionProperties; +import org.apache.cxf.sts.token.provider.TokenProvider; +import org.apache.cxf.sts.token.provider.TokenProviderParameters; +import org.apache.cxf.sts.token.provider.TokenProviderResponse; +import org.apache.cxf.sts.token.provider.jwt.JWTTokenProvider; +import org.apache.cxf.sts.token.realm.JWTRealmCodec; +import org.apache.cxf.sts.token.realm.RealmProperties; +import org.apache.cxf.sts.token.validator.jwt.JWTTokenValidator; +import org.apache.cxf.ws.security.tokenstore.TokenStore; +import org.apache.wss4j.common.crypto.Crypto; +import org.apache.wss4j.common.crypto.CryptoFactory; +import org.apache.wss4j.common.ext.WSSecurityException; +import org.apache.wss4j.common.principal.CustomTokenPrincipal; + +/** + * Some unit tests for validating JWTTokens in different realms + */ +public class JWTTokenValidatorRealmTest extends org.junit.Assert { + private static TokenStore tokenStore = new DefaultInMemoryTokenStore(); + + @org.junit.Test + public void testRealmA() throws Exception { + // Create + TokenProvider jwtTokenProvider = new JWTTokenProvider(); + ((JWTTokenProvider)jwtTokenProvider).setSignToken(true); + ((JWTTokenProvider)jwtTokenProvider).setRealmMap(getRealms()); + + TokenProviderParameters providerParameters = createProviderParameters(); + providerParameters.setRealm("A"); + + assertTrue(jwtTokenProvider.canHandleToken(JWTTokenProvider.JWT_TOKEN_TYPE)); + TokenProviderResponse providerResponse = jwtTokenProvider.createToken(providerParameters); + assertTrue(providerResponse != null); + assertTrue(providerResponse.getToken() != null && providerResponse.getTokenId() != null); + + String token = (String)providerResponse.getToken(); + assertNotNull(token); + assertTrue(token.split("\\.").length == 3); + + // Validate the token - no realm is returned + TokenValidator jwtTokenValidator = new JWTTokenValidator(); + TokenValidatorParameters validatorParameters = createValidatorParameters(); + TokenRequirements tokenRequirements = validatorParameters.getTokenRequirements(); + + // Create a ValidateTarget consisting of a JWT Token + ReceivedToken validateTarget = new ReceivedToken(createTokenWrapper(token)); + tokenRequirements.setValidateTarget(validateTarget); + validatorParameters.setToken(validateTarget); + + assertTrue(jwtTokenValidator.canHandleToken(validateTarget)); + + TokenValidatorResponse validatorResponse = + jwtTokenValidator.validateToken(validatorParameters); + assertTrue(validatorResponse != null); + assertTrue(validatorResponse.getToken() != null); + assertTrue(validatorResponse.getToken().getState() == STATE.VALID); + assertNull(validatorResponse.getTokenRealm()); + + // Now set the JWTRealmCodec implementation on the Validator + ((JWTTokenValidator)jwtTokenValidator).setRealmCodec(new IssuerJWTRealmCodec()); + + validatorResponse = jwtTokenValidator.validateToken(validatorParameters); + assertTrue(validatorResponse != null); + assertTrue(validatorResponse.getToken() != null); + assertTrue(validatorResponse.getToken().getState() == STATE.VALID); + assertTrue(validatorResponse.getTokenRealm().equals("A")); + + Principal principal = validatorResponse.getPrincipal(); + assertTrue(principal != null && principal.getName() != null); + } + + @org.junit.Test + public void testRealmB() throws Exception { + // Create + TokenProvider jwtTokenProvider = new JWTTokenProvider(); + ((JWTTokenProvider)jwtTokenProvider).setSignToken(true); + ((JWTTokenProvider)jwtTokenProvider).setRealmMap(getRealms()); + + TokenProviderParameters providerParameters = createProviderParameters(); + providerParameters.setRealm("B"); + + assertTrue(jwtTokenProvider.canHandleToken(JWTTokenProvider.JWT_TOKEN_TYPE)); + TokenProviderResponse providerResponse = jwtTokenProvider.createToken(providerParameters); + assertTrue(providerResponse != null); + assertTrue(providerResponse.getToken() != null && providerResponse.getTokenId() != null); + + String token = (String)providerResponse.getToken(); + assertNotNull(token); + assertTrue(token.split("\\.").length == 3); + + // Validate the token - no realm is returned + TokenValidator jwtTokenValidator = new JWTTokenValidator(); + TokenValidatorParameters validatorParameters = createValidatorParameters(); + TokenRequirements tokenRequirements = validatorParameters.getTokenRequirements(); + + // Create a ValidateTarget consisting of a JWT Token + ReceivedToken validateTarget = new ReceivedToken(createTokenWrapper(token)); + tokenRequirements.setValidateTarget(validateTarget); + validatorParameters.setToken(validateTarget); + + assertTrue(jwtTokenValidator.canHandleToken(validateTarget)); + + TokenValidatorResponse validatorResponse = + jwtTokenValidator.validateToken(validatorParameters); + assertTrue(validatorResponse != null); + assertTrue(validatorResponse.getToken() != null); + assertTrue(validatorResponse.getToken().getState() == STATE.VALID); + assertNull(validatorResponse.getTokenRealm()); + + // Now set the JWTRealmCodec implementation on the Validator + ((JWTTokenValidator)jwtTokenValidator).setRealmCodec(new IssuerJWTRealmCodec()); + + validatorResponse = jwtTokenValidator.validateToken(validatorParameters); + assertTrue(validatorResponse != null); + assertTrue(validatorResponse.getToken() != null); + assertTrue(validatorResponse.getToken().getState() == STATE.VALID); + assertTrue(validatorResponse.getTokenRealm().equals("B")); + + Principal principal = validatorResponse.getPrincipal(); + assertTrue(principal != null && principal.getName() != null); + } + + private Map getRealms() { + // Create Realms + Map realms = new HashMap(); + RealmProperties realm = new RealmProperties(); + realm.setIssuer("A-Issuer"); + realms.put("A", realm); + realm = new RealmProperties(); + realm.setIssuer("B-Issuer"); + realms.put("B", realm); + return realms; + } + + private TokenProviderParameters createProviderParameters() throws WSSecurityException { + TokenProviderParameters parameters = new TokenProviderParameters(); + + TokenRequirements tokenRequirements = new TokenRequirements(); + tokenRequirements.setTokenType(JWTTokenProvider.JWT_TOKEN_TYPE); + parameters.setTokenRequirements(tokenRequirements); + + KeyRequirements keyRequirements = new KeyRequirements(); + parameters.setKeyRequirements(keyRequirements); + + parameters.setTokenStore(tokenStore); + + parameters.setPrincipal(new CustomTokenPrincipal("alice")); + // Mock up message context + MessageImpl msg = new MessageImpl(); + WrappedMessageContext msgCtx = new WrappedMessageContext(msg); + WebServiceContextImpl webServiceContext = new WebServiceContextImpl(msgCtx); + parameters.setWebServiceContext(webServiceContext); + + parameters.setAppliesToAddress("http://dummy-service.com/dummy"); + + // Add STSProperties object + StaticSTSProperties stsProperties = new StaticSTSProperties(); + Crypto crypto = CryptoFactory.getInstance(getEncryptionProperties()); + stsProperties.setSignatureCrypto(crypto); + stsProperties.setSignatureUsername("mystskey"); + stsProperties.setCallbackHandler(new PasswordCallbackHandler()); + stsProperties.setIssuer("STS"); + parameters.setStsProperties(stsProperties); + + parameters.setEncryptionProperties(new EncryptionProperties()); + stsProperties.setEncryptionCrypto(crypto); + stsProperties.setEncryptionUsername("myservicekey"); + stsProperties.setCallbackHandler(new PasswordCallbackHandler()); + + return parameters; + } + + private TokenValidatorParameters createValidatorParameters() throws WSSecurityException { + TokenValidatorParameters parameters = new TokenValidatorParameters(); + + TokenRequirements tokenRequirements = new TokenRequirements(); + tokenRequirements.setTokenType(STSConstants.STATUS); + parameters.setTokenRequirements(tokenRequirements); + + KeyRequirements keyRequirements = new KeyRequirements(); + parameters.setKeyRequirements(keyRequirements); + + parameters.setPrincipal(new CustomTokenPrincipal("alice")); + // Mock up message context + MessageImpl msg = new MessageImpl(); + WrappedMessageContext msgCtx = new WrappedMessageContext(msg); + WebServiceContextImpl webServiceContext = new WebServiceContextImpl(msgCtx); + parameters.setWebServiceContext(webServiceContext); + + // Add STSProperties object + StaticSTSProperties stsProperties = new StaticSTSProperties(); + Crypto crypto = CryptoFactory.getInstance(getEncryptionProperties()); + stsProperties.setEncryptionCrypto(crypto); + stsProperties.setSignatureCrypto(crypto); + stsProperties.setEncryptionUsername("myservicekey"); + stsProperties.setSignatureUsername("mystskey"); + stsProperties.setCallbackHandler(new PasswordCallbackHandler()); + stsProperties.setIssuer("STS"); + parameters.setStsProperties(stsProperties); + parameters.setTokenStore(tokenStore); + + return parameters; + } + + private Properties getEncryptionProperties() { + Properties properties = new Properties(); + properties.put( + "org.apache.wss4j.crypto.provider", "org.apache.wss4j.common.crypto.Merlin" + ); + properties.put("org.apache.wss4j.crypto.merlin.keystore.password", "stsspass"); + properties.put("org.apache.wss4j.crypto.merlin.keystore.file", "stsstore.jks"); + + return properties; + } + + private Element createTokenWrapper(String token) { + Document doc = DOMUtils.newDocument(); + Element tokenWrapper = doc.createElementNS(null, "TokenWrapper"); + tokenWrapper.setTextContent(token); + return tokenWrapper; + } + + /** + * This class returns a realm associated with a JWTToken depending on the issuer. + */ + private class IssuerJWTRealmCodec implements JWTRealmCodec { + + public String getRealmFromToken(JwtToken token) { + if ("A-Issuer".equals(token.getClaim(JwtConstants.CLAIM_ISSUER))) { + return "A"; + } else if ("B-Issuer".equals(token.getClaim(JwtConstants.CLAIM_ISSUER))) { + return "B"; + } + return null; + } + + } +} http://git-wip-us.apache.org/repos/asf/cxf/blob/662b14a6/services/sts/sts-core/src/test/java/org/apache/cxf/sts/token/validator/JWTTokenValidatorTest.java ---------------------------------------------------------------------- diff --git a/services/sts/sts-core/src/test/java/org/apache/cxf/sts/token/validator/JWTTokenValidatorTest.java b/services/sts/sts-core/src/test/java/org/apache/cxf/sts/token/validator/JWTTokenValidatorTest.java index 6882751..13a60b8 100644 --- a/services/sts/sts-core/src/test/java/org/apache/cxf/sts/token/validator/JWTTokenValidatorTest.java +++ b/services/sts/sts-core/src/test/java/org/apache/cxf/sts/token/validator/JWTTokenValidatorTest.java @@ -27,6 +27,10 @@ import javax.security.auth.callback.Callback; import javax.security.auth.callback.CallbackHandler; import javax.security.auth.callback.UnsupportedCallbackException; +import org.w3c.dom.Document; +import org.w3c.dom.Element; + +import org.apache.cxf.helpers.DOMUtils; import org.apache.cxf.jaxws.context.WebServiceContextImpl; import org.apache.cxf.jaxws.context.WrappedMessageContext; import org.apache.cxf.message.MessageImpl; @@ -85,7 +89,7 @@ public class JWTTokenValidatorTest extends org.junit.Assert { TokenRequirements tokenRequirements = validatorParameters.getTokenRequirements(); // Create a ValidateTarget consisting of a JWT Token - ReceivedToken validateTarget = new ReceivedToken(token); + ReceivedToken validateTarget = new ReceivedToken(createTokenWrapper(token)); tokenRequirements.setValidateTarget(validateTarget); validatorParameters.setToken(validateTarget); @@ -129,7 +133,7 @@ public class JWTTokenValidatorTest extends org.junit.Assert { TokenRequirements tokenRequirements = validatorParameters.getTokenRequirements(); // Create a ValidateTarget consisting of a JWT Token - ReceivedToken validateTarget = new ReceivedToken(token); + ReceivedToken validateTarget = new ReceivedToken(createTokenWrapper(token)); tokenRequirements.setValidateTarget(validateTarget); validatorParameters.setToken(validateTarget); @@ -170,7 +174,7 @@ public class JWTTokenValidatorTest extends org.junit.Assert { TokenRequirements tokenRequirements = validatorParameters.getTokenRequirements(); // Create a ValidateTarget consisting of a JWT Token - ReceivedToken validateTarget = new ReceivedToken(token); + ReceivedToken validateTarget = new ReceivedToken(createTokenWrapper(token)); tokenRequirements.setValidateTarget(validateTarget); validatorParameters.setToken(validateTarget); @@ -212,7 +216,7 @@ public class JWTTokenValidatorTest extends org.junit.Assert { TokenRequirements tokenRequirements = validatorParameters.getTokenRequirements(); // Create a ValidateTarget consisting of a JWT Token - ReceivedToken validateTarget = new ReceivedToken(token); + ReceivedToken validateTarget = new ReceivedToken(createTokenWrapper(token)); tokenRequirements.setValidateTarget(validateTarget); validatorParameters.setToken(validateTarget); @@ -256,7 +260,7 @@ public class JWTTokenValidatorTest extends org.junit.Assert { TokenRequirements tokenRequirements = validatorParameters.getTokenRequirements(); // Create a ValidateTarget consisting of a JWT Token - ReceivedToken validateTarget = new ReceivedToken(token); + ReceivedToken validateTarget = new ReceivedToken(createTokenWrapper(token)); tokenRequirements.setValidateTarget(validateTarget); validatorParameters.setToken(validateTarget); @@ -299,7 +303,7 @@ public class JWTTokenValidatorTest extends org.junit.Assert { TokenRequirements tokenRequirements = validatorParameters.getTokenRequirements(); // Create a ValidateTarget consisting of a JWT Token - ReceivedToken validateTarget = new ReceivedToken(token); + ReceivedToken validateTarget = new ReceivedToken(createTokenWrapper(token)); tokenRequirements.setValidateTarget(validateTarget); validatorParameters.setToken(validateTarget); @@ -426,6 +430,13 @@ public class JWTTokenValidatorTest extends org.junit.Assert { } } + private Element createTokenWrapper(String token) { + Document doc = DOMUtils.newDocument(); + Element tokenWrapper = doc.createElementNS(null, "TokenWrapper"); + tokenWrapper.setTextContent(token); + return tokenWrapper; + } + private static class RoleJWTClaimsProvider extends DefaultJWTClaimsProvider { private String role; http://git-wip-us.apache.org/repos/asf/cxf/blob/662b14a6/services/sts/systests/advanced/src/test/java/org/apache/cxf/systest/sts/jwt/JWTUnitTest.java ---------------------------------------------------------------------- diff --git a/services/sts/systests/advanced/src/test/java/org/apache/cxf/systest/sts/jwt/JWTUnitTest.java b/services/sts/systests/advanced/src/test/java/org/apache/cxf/systest/sts/jwt/JWTUnitTest.java index 837db43..2f094e5 100644 --- a/services/sts/systests/advanced/src/test/java/org/apache/cxf/systest/sts/jwt/JWTUnitTest.java +++ b/services/sts/systests/advanced/src/test/java/org/apache/cxf/systest/sts/jwt/JWTUnitTest.java @@ -67,10 +67,16 @@ public class JWTUnitTest extends AbstractBusClientServerTestBase { SpringBusFactory.setDefaultBus(bus); SpringBusFactory.setThreadDefaultBus(bus); + // Issue the token SecurityToken token = requestSecurityToken(JWT_TOKEN_TYPE, bus, DEFAULT_ADDRESS, null, null); assertNotNull(token); - assertNotNull(token.getData()); + assertNotNull(token.getToken()); + + // Validate the token + token = validateSecurityToken(token, bus, null, null); + assertNotNull(token); + assertNotNull(token.getToken()); } private SecurityToken requestSecurityToken( @@ -107,4 +113,37 @@ public class JWTUnitTest extends AbstractBusClientServerTestBase { return stsClient.requestSecurityToken(endpointAddress); } + + private SecurityToken validateSecurityToken( + SecurityToken token, + Bus bus, + Map msgProperties, + String wsdlPort + ) throws Exception { + STSClient stsClient = new STSClient(bus); + String port = STSPORT; + + stsClient.setWsdlLocation("https://localhost:" + port + "/SecurityTokenService/Transport?wsdl"); + stsClient.setServiceName("{http://docs.oasis-open.org/ws-sx/ws-trust/200512/}SecurityTokenService"); + if (wsdlPort != null) { + stsClient.setEndpointName("{http://docs.oasis-open.org/ws-sx/ws-trust/200512/}" + wsdlPort); + } else { + stsClient.setEndpointName("{http://docs.oasis-open.org/ws-sx/ws-trust/200512/}Transport_Port"); + } + + Map properties = msgProperties; + if (properties == null) { + properties = new HashMap(); + properties.put(SecurityConstants.USERNAME, "alice"); + properties.put( + SecurityConstants.CALLBACK_HANDLER, + "org.apache.cxf.systest.sts.common.CommonCallbackHandler" + ); + } + + stsClient.setProperties(properties); + stsClient.setSendKeyType(false); + + return stsClient.validateSecurityToken(token).get(0); + } } http://git-wip-us.apache.org/repos/asf/cxf/blob/662b14a6/services/sts/systests/advanced/src/test/resources/org/apache/cxf/systest/sts/deployment/cxf-sts.xml ---------------------------------------------------------------------- diff --git a/services/sts/systests/advanced/src/test/resources/org/apache/cxf/systest/sts/deployment/cxf-sts.xml b/services/sts/systests/advanced/src/test/resources/org/apache/cxf/systest/sts/deployment/cxf-sts.xml index 989873f..f33a137 100644 --- a/services/sts/systests/advanced/src/test/resources/org/apache/cxf/systest/sts/deployment/cxf-sts.xml +++ b/services/sts/systests/advanced/src/test/resources/org/apache/cxf/systest/sts/deployment/cxf-sts.xml @@ -57,6 +57,7 @@ + @@ -104,6 +105,8 @@ + +