cxf-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From cohei...@apache.org
Subject svn commit: r1177564 - in /cxf/trunk/services/sts/sts-core/src: main/java/org/apache/cxf/sts/cache/ main/java/org/apache/cxf/sts/token/provider/ main/java/org/apache/cxf/sts/token/validator/ test/java/org/apache/cxf/sts/token/validator/
Date Fri, 30 Sep 2011 09:28:25 GMT
Author: coheigea
Date: Fri Sep 30 09:28:25 2011
New Revision: 1177564

URL: http://svn.apache.org/viewvc?rev=1177564&view=rev
Log:
[CXF-3835] - SAML and Username tokens should be cached in the STS service
 - Patch applied, thanks

Modified:
    cxf/trunk/services/sts/sts-core/src/main/java/org/apache/cxf/sts/cache/DefaultInMemoryTokenStore.java
    cxf/trunk/services/sts/sts-core/src/main/java/org/apache/cxf/sts/cache/HazelCastTokenStore.java
    cxf/trunk/services/sts/sts-core/src/main/java/org/apache/cxf/sts/token/provider/SAMLTokenProvider.java
    cxf/trunk/services/sts/sts-core/src/main/java/org/apache/cxf/sts/token/validator/SAMLTokenValidator.java
    cxf/trunk/services/sts/sts-core/src/main/java/org/apache/cxf/sts/token/validator/UsernameTokenValidator.java
    cxf/trunk/services/sts/sts-core/src/test/java/org/apache/cxf/sts/token/validator/SAMLTokenValidatorTest.java

Modified: cxf/trunk/services/sts/sts-core/src/main/java/org/apache/cxf/sts/cache/DefaultInMemoryTokenStore.java
URL: http://svn.apache.org/viewvc/cxf/trunk/services/sts/sts-core/src/main/java/org/apache/cxf/sts/cache/DefaultInMemoryTokenStore.java?rev=1177564&r1=1177563&r2=1177564&view=diff
==============================================================================
--- cxf/trunk/services/sts/sts-core/src/main/java/org/apache/cxf/sts/cache/DefaultInMemoryTokenStore.java
(original)
+++ cxf/trunk/services/sts/sts-core/src/main/java/org/apache/cxf/sts/cache/DefaultInMemoryTokenStore.java
Fri Sep 30 09:28:25 2011
@@ -20,6 +20,7 @@
 package org.apache.cxf.sts.cache;
 
 import java.util.Collection;
+import java.util.Iterator;
 
 import net.sf.ehcache.Cache;
 import net.sf.ehcache.CacheManager;
@@ -102,7 +103,14 @@ public class DefaultInMemoryTokenStore i
     }
 
     public SecurityToken getTokenByAssociatedHash(int hashCode) {
-        // TODO Auto-generated method stub
+        @SuppressWarnings("unchecked")
+        Iterator<String> ids = cache.getKeys().iterator();
+        while (ids.hasNext()) {
+            SecurityToken securityToken = getToken(ids.next());
+            if (hashCode == securityToken.getAssociatedHash()) {
+                return securityToken;
+            }
+        }
         return null;
     }
 

Modified: cxf/trunk/services/sts/sts-core/src/main/java/org/apache/cxf/sts/cache/HazelCastTokenStore.java
URL: http://svn.apache.org/viewvc/cxf/trunk/services/sts/sts-core/src/main/java/org/apache/cxf/sts/cache/HazelCastTokenStore.java?rev=1177564&r1=1177563&r2=1177564&view=diff
==============================================================================
--- cxf/trunk/services/sts/sts-core/src/main/java/org/apache/cxf/sts/cache/HazelCastTokenStore.java
(original)
+++ cxf/trunk/services/sts/sts-core/src/main/java/org/apache/cxf/sts/cache/HazelCastTokenStore.java
Fri Sep 30 09:28:25 2011
@@ -20,6 +20,7 @@
 package org.apache.cxf.sts.cache;
 
 import java.util.Collection;
+import java.util.Iterator;
 import java.util.concurrent.TimeUnit;
 
 import com.hazelcast.core.Hazelcast;
@@ -90,7 +91,13 @@ public class HazelCastTokenStore impleme
     }
 
     public SecurityToken getTokenByAssociatedHash(int hashCode) {
-        // TODO Auto-generated method stub
+        Iterator<Object> ids = cacheMap.keySet().iterator();
+        while (ids.hasNext()) {
+            SecurityToken securityToken = getToken((String)ids.next());
+            if (hashCode == securityToken.getAssociatedHash()) {
+                return securityToken;
+            }
+        }
         return null;
     }
 

Modified: cxf/trunk/services/sts/sts-core/src/main/java/org/apache/cxf/sts/token/provider/SAMLTokenProvider.java
URL: http://svn.apache.org/viewvc/cxf/trunk/services/sts/sts-core/src/main/java/org/apache/cxf/sts/token/provider/SAMLTokenProvider.java?rev=1177564&r1=1177563&r2=1177564&view=diff
==============================================================================
--- cxf/trunk/services/sts/sts-core/src/main/java/org/apache/cxf/sts/token/provider/SAMLTokenProvider.java
(original)
+++ cxf/trunk/services/sts/sts-core/src/main/java/org/apache/cxf/sts/token/provider/SAMLTokenProvider.java
Fri Sep 30 09:28:25 2011
@@ -20,6 +20,7 @@
 package org.apache.cxf.sts.token.provider;
 
 import java.util.ArrayList;
+import java.util.Arrays;
 import java.util.HashMap;
 import java.util.List;
 import java.util.Map;
@@ -37,6 +38,7 @@ import org.apache.cxf.sts.request.KeyReq
 import org.apache.cxf.sts.request.TokenRequirements;
 import org.apache.cxf.sts.token.realm.SAMLRealm;
 import org.apache.cxf.ws.security.sts.provider.STSException;
+import org.apache.cxf.ws.security.tokenstore.SecurityToken;
 
 import org.apache.ws.security.WSConstants;
 import org.apache.ws.security.WSPasswordCallback;
@@ -114,6 +116,20 @@ public class SAMLTokenProvider implement
             AssertionWrapper assertion = createSamlToken(tokenParameters, secret, doc);
             Element token = assertion.toDOM(doc);
             
+            // set the token in cache
+            if (tokenParameters.getTokenStore() != null) {
+                SecurityToken securityToken = new SecurityToken(assertion.getId());
+                securityToken.setToken(token);
+                int hash = 0;
+                byte[] signatureValue = assertion.getSignatureValue();
+                if (signatureValue != null && signatureValue.length > 0) {
+                    hash = Arrays.hashCode(signatureValue);
+                    securityToken.setAssociatedHash(hash);
+                }
+                Integer timeToLive = (int)(conditionsProvider.getLifetime() * 1000);
+                tokenParameters.getTokenStore().add(securityToken, timeToLive);
+            }
+            
             TokenProviderResponse response = new TokenProviderResponse();
             response.setToken(token);
             String tokenType = tokenRequirements.getTokenType();

Modified: cxf/trunk/services/sts/sts-core/src/main/java/org/apache/cxf/sts/token/validator/SAMLTokenValidator.java
URL: http://svn.apache.org/viewvc/cxf/trunk/services/sts/sts-core/src/main/java/org/apache/cxf/sts/token/validator/SAMLTokenValidator.java?rev=1177564&r1=1177563&r2=1177564&view=diff
==============================================================================
--- cxf/trunk/services/sts/sts-core/src/main/java/org/apache/cxf/sts/token/validator/SAMLTokenValidator.java
(original)
+++ cxf/trunk/services/sts/sts-core/src/main/java/org/apache/cxf/sts/token/validator/SAMLTokenValidator.java
Fri Sep 30 09:28:25 2011
@@ -18,6 +18,7 @@
  */
 package org.apache.cxf.sts.token.validator;
 
+import java.util.Arrays;
 import java.util.HashMap;
 import java.util.Map;
 import java.util.logging.Level;
@@ -32,6 +33,7 @@ import org.apache.cxf.sts.STSPropertiesM
 import org.apache.cxf.sts.request.ReceivedToken;
 import org.apache.cxf.sts.request.TokenRequirements;
 import org.apache.cxf.sts.token.realm.SAMLRealm;
+import org.apache.cxf.ws.security.tokenstore.SecurityToken;
 
 import org.apache.ws.security.SAMLTokenPrincipal;
 import org.apache.ws.security.WSConstants;
@@ -105,13 +107,7 @@ public class SAMLTokenValidator implemen
         STSPropertiesMBean stsProperties = tokenParameters.getStsProperties();
         Crypto sigCrypto = stsProperties.getSignatureCrypto();
         CallbackHandler callbackHandler = stsProperties.getCallbackHandler();
-
-        RequestData requestData = new RequestData();
-        requestData.setSigCrypto(sigCrypto);
-        WSSConfig wssConfig = WSSConfig.getNewInstance();
-        requestData.setWssConfig(wssConfig);
-        requestData.setCallbackHandler(callbackHandler);
-
+        
         TokenValidatorResponse response = new TokenValidatorResponse();
         response.setValid(false);
         
@@ -122,41 +118,65 @@ public class SAMLTokenValidator implemen
         try {
             Element validateTargetElement = (Element)validateTarget.getToken();
             AssertionWrapper assertion = new AssertionWrapper(validateTargetElement);
-            if (!assertion.isSigned()) {
-                LOG.log(Level.WARNING, "The received assertion is not signed, and therefore
not trusted");
-                return response;
-            }
-            // Verify the signature
-            assertion.verifySignature(
-                requestData, new WSDocInfo(validateTargetElement.getOwnerDocument())
-            );
-
-            // Now verify trust on the signature
-            Credential trustCredential = new Credential();
-            SAMLKeyInfo samlKeyInfo = assertion.getSignatureKeyInfo();
-            trustCredential.setPublicKey(samlKeyInfo.getPublicKey());
-            trustCredential.setCertificates(samlKeyInfo.getCerts());
-
-            validator.validate(trustCredential, requestData);
-
-            // Finally check that the issuer is trusted
-            String trustedIssuer = null;
-            String assertionIssuer = assertion.getIssuerString();
-            for (String realm : realmMap.keySet()) {
-                SAMLRealm samlRealm = realmMap.get(realm);
-                if (samlRealm.getIssuer().equals(assertionIssuer)) {
-                    trustedIssuer = realm;
-                    break;
+            
+            SecurityToken secToken = null;
+            if (tokenParameters.getTokenStore() != null) {
+                int hash = 0;
+                byte[] signatureValue = assertion.getSignatureValue();
+                if (signatureValue != null && signatureValue.length > 0) {
+                    hash = Arrays.hashCode(signatureValue);
+                    secToken = tokenParameters.getTokenStore().getTokenByAssociatedHash(hash);
                 }
             }
-            if (trustedIssuer == null && assertionIssuer.equals(stsProperties.getIssuer()))
{
-                trustedIssuer = stsProperties.getIssuer();
-            }
-            if (trustedIssuer != null) {
+            if (secToken == null) {
+                if (!assertion.isSigned()) {
+                    LOG.log(Level.WARNING, "The received assertion is not signed, and therefore
not trusted");
+                    return response;
+                }
+                
+                RequestData requestData = new RequestData();
+                requestData.setSigCrypto(sigCrypto);
+                WSSConfig wssConfig = WSSConfig.getNewInstance();
+                requestData.setWssConfig(wssConfig);
+                requestData.setCallbackHandler(callbackHandler);
+                
+                // Verify the signature
+                assertion.verifySignature(
+                    requestData, new WSDocInfo(validateTargetElement.getOwnerDocument())
+                );
+
+                // Now verify trust on the signature
+                Credential trustCredential = new Credential();
+                SAMLKeyInfo samlKeyInfo = assertion.getSignatureKeyInfo();
+                trustCredential.setPublicKey(samlKeyInfo.getPublicKey());
+                trustCredential.setCertificates(samlKeyInfo.getCerts());
+    
+                validator.validate(trustCredential, requestData);
+
+                // Finally check that the issuer is trusted
+                String trustedIssuer = null;
+                String assertionIssuer = assertion.getIssuerString();
+                for (String realm : realmMap.keySet()) {
+                    SAMLRealm samlRealm = realmMap.get(realm);
+                    if (samlRealm.getIssuer().equals(assertionIssuer)) {
+                        trustedIssuer = realm;
+                        break;
+                    }
+                }
+                if (trustedIssuer == null && assertionIssuer.equals(stsProperties.getIssuer()))
{
+                    trustedIssuer = stsProperties.getIssuer();
+                }
+                if (trustedIssuer != null) {
+                    response.setValid(true);
+                    SAMLTokenPrincipal samlPrincipal = new SAMLTokenPrincipal(assertion);
+                    response.setPrincipal(samlPrincipal);
+                    response.setTokenRealm(trustedIssuer);
+                }
+            } else {
                 response.setValid(true);
                 SAMLTokenPrincipal samlPrincipal = new SAMLTokenPrincipal(assertion);
                 response.setPrincipal(samlPrincipal);
-                response.setTokenRealm(trustedIssuer);
+                response.setTokenRealm(assertion.getIssuerString());
             }
         } catch (WSSecurityException ex) {
             LOG.log(Level.WARNING, "", ex);

Modified: cxf/trunk/services/sts/sts-core/src/main/java/org/apache/cxf/sts/token/validator/UsernameTokenValidator.java
URL: http://svn.apache.org/viewvc/cxf/trunk/services/sts/sts-core/src/main/java/org/apache/cxf/sts/token/validator/UsernameTokenValidator.java?rev=1177564&r1=1177563&r2=1177564&view=diff
==============================================================================
--- cxf/trunk/services/sts/sts-core/src/main/java/org/apache/cxf/sts/token/validator/UsernameTokenValidator.java
(original)
+++ cxf/trunk/services/sts/sts-core/src/main/java/org/apache/cxf/sts/token/validator/UsernameTokenValidator.java
Fri Sep 30 09:28:25 2011
@@ -39,6 +39,7 @@ import org.apache.cxf.sts.request.Receiv
 import org.apache.cxf.sts.request.TokenRequirements;
 
 import org.apache.cxf.ws.security.sts.provider.model.secext.UsernameTokenType;
+import org.apache.cxf.ws.security.tokenstore.SecurityToken;
 
 import org.apache.ws.security.WSConstants;
 import org.apache.ws.security.WSSConfig;
@@ -114,23 +115,33 @@ public class UsernameTokenValidator impl
         // Turn the JAXB UsernameTokenType into a DOM Element for validation
         //
         UsernameTokenType usernameTokenType = (UsernameTokenType)validateTarget.getToken();
-        Element rootElement = null;
-        try {
-            JAXBContext jaxbContext = 
-                JAXBContext.newInstance("org.apache.cxf.ws.security.sts.provider.model");
-            Marshaller marshaller = jaxbContext.createMarshaller();
-            Document doc = DOMUtils.createDocument();
-            rootElement = doc.createElement("root-element");
-            JAXBElement<UsernameTokenType> tokenType = 
-                new JAXBElement<UsernameTokenType>(
-                    QNameConstants.USERNAME_TOKEN, UsernameTokenType.class, usernameTokenType
-                );
-            marshaller.marshal(tokenType, rootElement);
-        } catch (JAXBException ex) {
-            LOG.log(Level.WARNING, "", ex);
-            return response;
+        SecurityToken secToken = null;
+        if (tokenParameters.getTokenStore() != null) {
+            secToken = tokenParameters.getTokenStore().getToken(usernameTokenType.getId());
         }
         
+        Element rootElement = null;
+        Element usernameTokenElement = null;
+        if (secToken == null) {
+            try {
+                JAXBContext jaxbContext = 
+                    JAXBContext.newInstance("org.apache.cxf.ws.security.sts.provider.model");
+                Marshaller marshaller = jaxbContext.createMarshaller();
+                Document doc = DOMUtils.createDocument();
+                rootElement = doc.createElement("root-element");
+                JAXBElement<UsernameTokenType> tokenType = 
+                    new JAXBElement<UsernameTokenType>(
+                        QNameConstants.USERNAME_TOKEN, UsernameTokenType.class, usernameTokenType
+                    );
+                marshaller.marshal(tokenType, rootElement);
+            } catch (JAXBException ex) {
+                LOG.log(Level.WARNING, "", ex);
+                return response;
+            }
+            usernameTokenElement = (Element)rootElement.getFirstChild();
+        } else {
+            usernameTokenElement = secToken.getToken();
+        }
         //
         // Validate the token
         //
@@ -138,17 +149,17 @@ public class UsernameTokenValidator impl
             boolean allowNamespaceQualifiedPasswordTypes = 
                 wssConfig.getAllowNamespaceQualifiedPasswordTypes();
             boolean bspCompliant = wssConfig.isWsiBSPCompliant();
-            Element usernameTokenElement = (Element)rootElement.getFirstChild();
-            
             UsernameToken ut = 
                 new UsernameToken(usernameTokenElement, allowNamespaceQualifiedPasswordTypes,
bspCompliant);
             if (ut.getPassword() == null) {
                 return response;
             }
-            Credential credential = new Credential();
-            credential.setUsernametoken(ut);
-            validator.validate(credential, requestData);
             
+            if (secToken == null || (secToken.getAssociatedHash() != ut.hashCode())) {
+                Credential credential = new Credential();
+                credential.setUsernametoken(ut);
+                validator.validate(credential, requestData);
+            }
             Principal principal = 
                 createPrincipal(
                     ut.getName(), ut.getPassword(), ut.getPasswordType(), ut.getNonce(),
ut.getCreated()

Modified: cxf/trunk/services/sts/sts-core/src/test/java/org/apache/cxf/sts/token/validator/SAMLTokenValidatorTest.java
URL: http://svn.apache.org/viewvc/cxf/trunk/services/sts/sts-core/src/test/java/org/apache/cxf/sts/token/validator/SAMLTokenValidatorTest.java?rev=1177564&r1=1177563&r2=1177564&view=diff
==============================================================================
--- cxf/trunk/services/sts/sts-core/src/test/java/org/apache/cxf/sts/token/validator/SAMLTokenValidatorTest.java
(original)
+++ cxf/trunk/services/sts/sts-core/src/test/java/org/apache/cxf/sts/token/validator/SAMLTokenValidatorTest.java
Fri Sep 30 09:28:25 2011
@@ -34,6 +34,8 @@ import org.apache.cxf.jaxws.context.Wrap
 import org.apache.cxf.message.MessageImpl;
 import org.apache.cxf.sts.STSConstants;
 import org.apache.cxf.sts.StaticSTSProperties;
+import org.apache.cxf.sts.cache.DefaultInMemoryTokenStore;
+import org.apache.cxf.sts.cache.STSTokenStore;
 import org.apache.cxf.sts.common.PasswordCallbackHandler;
 import org.apache.cxf.sts.request.KeyRequirements;
 import org.apache.cxf.sts.request.ReceivedToken;
@@ -49,6 +51,7 @@ import org.apache.ws.security.WSPassword
 import org.apache.ws.security.WSSecurityException;
 import org.apache.ws.security.components.crypto.Crypto;
 import org.apache.ws.security.components.crypto.CryptoFactory;
+import org.junit.BeforeClass;
 
 
 /**
@@ -56,6 +59,13 @@ import org.apache.ws.security.components
  */
 public class SAMLTokenValidatorTest extends org.junit.Assert {
     
+    private static STSTokenStore tokenStore;
+    
+    @BeforeClass
+    public static void init() {
+        tokenStore = new DefaultInMemoryTokenStore();
+    }
+    
     /**
      * Test a valid SAML 1.1 Assertion
      */
@@ -140,6 +150,9 @@ public class SAMLTokenValidatorTest exte
         
         assertTrue(samlTokenValidator.canHandleToken(validateTarget));
         
+        // Set tokenstore to null so that issued token is not found in the cache
+        validatorParameters.setTokenStore(null);
+        
         // Change the issuer and so validation should fail
         validatorParameters.getStsProperties().setIssuer("NewSTS");
         
@@ -170,7 +183,10 @@ public class SAMLTokenValidatorTest exte
         tokenRequirements.setValidateTarget(validateTarget);
         
         assertTrue(samlTokenValidator.canHandleToken(validateTarget));
-        
+ 
+        // Set tokenstore to null so that issued token is not found in the cache
+        validatorParameters.setTokenStore(null);
+
         // Change the issuer and so validation should fail
         validatorParameters.getStsProperties().setIssuer("NewSTS");
         
@@ -202,6 +218,9 @@ public class SAMLTokenValidatorTest exte
         
         assertTrue(samlTokenValidator.canHandleToken(validateTarget));
         
+        // Set tokenstore to null so that issued token is not found in the cache
+        validatorParameters.setTokenStore(null);
+
         TokenValidatorResponse validatorResponse = 
             samlTokenValidator.validateToken(validatorParameters);
         assertTrue(validatorResponse != null);
@@ -230,6 +249,9 @@ public class SAMLTokenValidatorTest exte
         
         assertTrue(samlTokenValidator.canHandleToken(validateTarget));
         
+        // Set tokenstore to null so that issued token is not found in the cache
+        validatorParameters.setTokenStore(null);
+
         TokenValidatorResponse validatorResponse = 
             samlTokenValidator.validateToken(validatorParameters);
         assertTrue(validatorResponse != null);
@@ -263,6 +285,7 @@ public class SAMLTokenValidatorTest exte
         stsProperties.setCallbackHandler(new PasswordCallbackHandler());
         stsProperties.setIssuer("STS");
         parameters.setStsProperties(stsProperties);
+        parameters.setTokenStore(tokenStore);
         
         return parameters;
     }
@@ -314,7 +337,8 @@ public class SAMLTokenValidatorTest exte
         parameters.setStsProperties(stsProperties);
 
         parameters.setEncryptionProperties(new EncryptionProperties());
-
+        parameters.setTokenStore(tokenStore);
+        
         return parameters;
     }
     



Mime
View raw message