Repository: cxf Updated Branches: refs/heads/master 03f0d1b79 -> 78664f430
[CXF-5311] Adding a system test with JWS HMAC signature Project: http://git-wip-us.apache.org/repos/asf/cxf/repo Commit: http://git-wip-us.apache.org/repos/asf/cxf/commit/78664f43 Tree: http://git-wip-us.apache.org/repos/asf/cxf/tree/78664f43 Diff: http://git-wip-us.apache.org/repos/asf/cxf/diff/78664f43 Branch: refs/heads/master Commit: 78664f4301d15e35a1061266a2680a3cd82d6d28 Parents: 03f0d1b Author: Sergey Beryozkin <[email protected]> Authored: Fri Jul 11 13:31:39 2014 +0100 Committer: Sergey Beryozkin <[email protected]> Committed: Fri Jul 11 13:31:39 2014 +0100 ---------------------------------------------------------------------- .../oauth2/jws/HmacJwsSignatureProvider.java | 13 ++++++-- .../jwt/jaxrs/AbstractJwsReaderProvider.java | 8 ++--- .../jwt/jaxrs/AbstractJwsWriterProvider.java | 5 ++- .../security/oauth2/utils/crypto/HmacUtils.java | 22 +++++++++++-- .../jaxrs/security/jwt/JAXRSJweJwsTest.java | 24 ++++++++++++-- .../cxf/systest/jaxrs/security/jwt/server.xml | 34 +++++++++++++++++--- 6 files changed, 87 insertions(+), 19 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/cxf/blob/78664f43/rt/rs/security/oauth-parent/oauth2-jwt/src/main/java/org/apache/cxf/rs/security/oauth2/jws/HmacJwsSignatureProvider.java ---------------------------------------------------------------------- diff --git a/rt/rs/security/oauth-parent/oauth2-jwt/src/main/java/org/apache/cxf/rs/security/oauth2/jws/HmacJwsSignatureProvider.java b/rt/rs/security/oauth-parent/oauth2-jwt/src/main/java/org/apache/cxf/rs/security/oauth2/jws/HmacJwsSignatureProvider.java index 6bb1e0d..aa387fb 100644 --- a/rt/rs/security/oauth-parent/oauth2-jwt/src/main/java/org/apache/cxf/rs/security/oauth2/jws/HmacJwsSignatureProvider.java +++ b/rt/rs/security/oauth-parent/oauth2-jwt/src/main/java/org/apache/cxf/rs/security/oauth2/jws/HmacJwsSignatureProvider.java @@ -18,6 +18,7 @@ */ package org.apache.cxf.rs.security.oauth2.jws; +import java.security.spec.AlgorithmParameterSpec; import java.util.Arrays; import java.util.HashSet; import java.util.Set; @@ -36,10 +37,15 @@ public class HmacJwsSignatureProvider extends AbstractJwsSignatureProvider imple Algorithm.HmacSHA384.getJwtName(), Algorithm.HmacSHA512.getJwtName())); private byte[] key; + private AlgorithmParameterSpec hmacSpec; public HmacJwsSignatureProvider(byte[] key) { + this(key, null); + } + public HmacJwsSignatureProvider(byte[] key, AlgorithmParameterSpec spec) { super(SUPPORTED_ALGORITHMS); this.key = key; + this.hmacSpec = spec; } public HmacJwsSignatureProvider(String encodedKey) { super(SUPPORTED_ALGORITHMS); @@ -50,6 +56,7 @@ public class HmacJwsSignatureProvider extends AbstractJwsSignatureProvider imple } } + @Override public byte[] sign(JwtHeaders headers, String unsignedText) { headers = prepareHeaders(headers); @@ -64,12 +71,14 @@ public class HmacJwsSignatureProvider extends AbstractJwsSignatureProvider imple private byte[] computeMac(JwtHeaders headers, String text) { return HmacUtils.computeHmac(key, - Algorithm.toJavaName(headers.getAlgorithm()), + Algorithm.toJavaName(headers.getAlgorithm()), + hmacSpec, text); } @Override protected JwsSignatureProviderWorker createJwsSignatureWorker(JwtHeaders headers) { - final Mac mac = HmacUtils.getMac(Algorithm.toJavaName(headers.getAlgorithm())); + final Mac mac = HmacUtils.getInitializedMac(key, Algorithm.toJavaName(headers.getAlgorithm()), + hmacSpec); return new JwsSignatureProviderWorker() { @Override http://git-wip-us.apache.org/repos/asf/cxf/blob/78664f43/rt/rs/security/oauth-parent/oauth2-jwt/src/main/java/org/apache/cxf/rs/security/oauth2/jwt/jaxrs/AbstractJwsReaderProvider.java ---------------------------------------------------------------------- diff --git a/rt/rs/security/oauth-parent/oauth2-jwt/src/main/java/org/apache/cxf/rs/security/oauth2/jwt/jaxrs/AbstractJwsReaderProvider.java b/rt/rs/security/oauth-parent/oauth2-jwt/src/main/java/org/apache/cxf/rs/security/oauth2/jwt/jaxrs/AbstractJwsReaderProvider.java index d463b40..5dbacf4 100644 --- a/rt/rs/security/oauth-parent/oauth2-jwt/src/main/java/org/apache/cxf/rs/security/oauth2/jwt/jaxrs/AbstractJwsReaderProvider.java +++ b/rt/rs/security/oauth-parent/oauth2-jwt/src/main/java/org/apache/cxf/rs/security/oauth2/jwt/jaxrs/AbstractJwsReaderProvider.java @@ -33,12 +33,12 @@ public class AbstractJwsReaderProvider { private JwsSignatureProperties sigProperties; private String defaultMediaType; - public void setSigVerifier(JwsSignatureVerifier sigVerifier) { - this.sigVerifier = sigVerifier; + public void setSignatureVerifier(JwsSignatureVerifier signatureVerifier) { + this.sigVerifier = signatureVerifier; } - public void setSigProperties(JwsSignatureProperties sigProperties) { - this.sigProperties = sigProperties; + public void setSignatureProperties(JwsSignatureProperties signatureProperties) { + this.sigProperties = signatureProperties; } public JwsSignatureProperties getSigProperties() { http://git-wip-us.apache.org/repos/asf/cxf/blob/78664f43/rt/rs/security/oauth-parent/oauth2-jwt/src/main/java/org/apache/cxf/rs/security/oauth2/jwt/jaxrs/AbstractJwsWriterProvider.java ---------------------------------------------------------------------- diff --git a/rt/rs/security/oauth-parent/oauth2-jwt/src/main/java/org/apache/cxf/rs/security/oauth2/jwt/jaxrs/AbstractJwsWriterProvider.java b/rt/rs/security/oauth-parent/oauth2-jwt/src/main/java/org/apache/cxf/rs/security/oauth2/jwt/jaxrs/AbstractJwsWriterProvider.java index 25a5599..a03312c 100644 --- a/rt/rs/security/oauth-parent/oauth2-jwt/src/main/java/org/apache/cxf/rs/security/oauth2/jwt/jaxrs/AbstractJwsWriterProvider.java +++ b/rt/rs/security/oauth-parent/oauth2-jwt/src/main/java/org/apache/cxf/rs/security/oauth2/jwt/jaxrs/AbstractJwsWriterProvider.java @@ -39,10 +39,9 @@ public class AbstractJwsWriterProvider { private JwsSignatureProvider sigProvider; - public void setSigProvider(JwsSignatureProvider sigProvider) { - this.sigProvider = sigProvider; + public void setSignatureProvider(JwsSignatureProvider signatureProvider) { + this.sigProvider = signatureProvider; } - protected JwsSignatureProvider getInitializedSigProvider() { if (sigProvider != null) { http://git-wip-us.apache.org/repos/asf/cxf/blob/78664f43/rt/rs/security/oauth-parent/oauth2/src/main/java/org/apache/cxf/rs/security/oauth2/utils/crypto/HmacUtils.java ---------------------------------------------------------------------- diff --git a/rt/rs/security/oauth-parent/oauth2/src/main/java/org/apache/cxf/rs/security/oauth2/utils/crypto/HmacUtils.java b/rt/rs/security/oauth-parent/oauth2/src/main/java/org/apache/cxf/rs/security/oauth2/utils/crypto/HmacUtils.java index 2395a6e..7b1dc78 100644 --- a/rt/rs/security/oauth-parent/oauth2/src/main/java/org/apache/cxf/rs/security/oauth2/utils/crypto/HmacUtils.java +++ b/rt/rs/security/oauth-parent/oauth2/src/main/java/org/apache/cxf/rs/security/oauth2/utils/crypto/HmacUtils.java @@ -78,8 +78,12 @@ public final class HmacUtils { } public static byte[] computeHmac(byte[] key, String macAlgoJavaName, String data) { + return computeHmac(key, macAlgoJavaName, null, data); + } + public static byte[] computeHmac(byte[] key, String macAlgoJavaName, AlgorithmParameterSpec spec, + String data) { Mac mac = getMac(macAlgoJavaName); - return computeHmac(key, mac, data); + return computeHmac(new SecretKeySpec(key, mac.getAlgorithm()), mac, spec, data); } public static byte[] computeHmac(String key, Mac hmac, String data) { @@ -100,13 +104,27 @@ public final class HmacUtils { } public static byte[] computeHmac(Key secretKey, Mac hmac, AlgorithmParameterSpec spec, String data) { + initMac(hmac, secretKey, spec); + return hmac.doFinal(data.getBytes()); + } + + public static Mac getInitializedMac(byte[] key, String algo, AlgorithmParameterSpec spec) { + Mac hmac = getMac(algo); + initMac(hmac, key, spec); + return hmac; + } + + private static void initMac(Mac hmac, byte[] key, AlgorithmParameterSpec spec) { + initMac(hmac, new SecretKeySpec(key, hmac.getAlgorithm()), spec); + + } + private static void initMac(Mac hmac, Key secretKey, AlgorithmParameterSpec spec) { try { if (spec == null) { hmac.init(secretKey); } else { hmac.init(secretKey, spec); } - return hmac.doFinal(data.getBytes()); } catch (InvalidKeyException e) { throw new OAuthServiceException(e); } catch (InvalidAlgorithmParameterException e) { http://git-wip-us.apache.org/repos/asf/cxf/blob/78664f43/systests/rs-security/src/test/java/org/apache/cxf/systest/jaxrs/security/jwt/JAXRSJweJwsTest.java ---------------------------------------------------------------------- diff --git a/systests/rs-security/src/test/java/org/apache/cxf/systest/jaxrs/security/jwt/JAXRSJweJwsTest.java b/systests/rs-security/src/test/java/org/apache/cxf/systest/jaxrs/security/jwt/JAXRSJweJwsTest.java index e9bbc3b..20848c4 100644 --- a/systests/rs-security/src/test/java/org/apache/cxf/systest/jaxrs/security/jwt/JAXRSJweJwsTest.java +++ b/systests/rs-security/src/test/java/org/apache/cxf/systest/jaxrs/security/jwt/JAXRSJweJwsTest.java @@ -30,6 +30,8 @@ import javax.crypto.Cipher; import org.apache.cxf.Bus; import org.apache.cxf.bus.spring.SpringBusFactory; import org.apache.cxf.jaxrs.client.JAXRSClientFactoryBean; +import org.apache.cxf.rs.security.oauth2.jws.HmacJwsSignatureProvider; +import org.apache.cxf.rs.security.oauth2.jws.JwsSignatureProvider; import org.apache.cxf.rs.security.oauth2.jwt.Algorithm; import org.apache.cxf.rs.security.oauth2.jwt.jaxrs.JweClientResponseFilter; import org.apache.cxf.rs.security.oauth2.jwt.jaxrs.JweWriterInterceptor; @@ -49,7 +51,8 @@ public class JAXRSJweJwsTest extends AbstractBusClientServerTestBase { "org/apache/cxf/systest/jaxrs/security/bob.rs.properties"; private static final String SERVER_JWEJWS_PROPERTIES = "org/apache/cxf/systest/jaxrs/security/alice.rs.properties"; - + private static final String ENCODED_MAC_KEY = "AyM1SysPpbyDfgZld3umj1qzKObwVMkoqQ-EstJQLr_T-1qS0gZH75" + + "aKtMN3Yj0iPS4hcgUuTwjAzZr1Z9CAow"; @BeforeClass public static void startServers() throws Exception { assertTrue("server did not launch correctly", @@ -72,8 +75,20 @@ public class JAXRSJweJwsTest extends AbstractBusClientServerTestBase { } @Test - public void testJweJwsRsa() throws Exception { - String address = "https://localhost:" + PORT + "/jwejws"; + public void testJweRsaJwsRsa() throws Exception { + String address = "https://localhost:" + PORT + "/jwejwsrsa"; + doTestJweJwsRsa(address, null); + } + @Test + public void testJweRsaJwsHMac() throws Exception { + String address = "https://localhost:" + PORT + "/jwejwshmac"; + HmacJwsSignatureProvider hmacProvider = new HmacJwsSignatureProvider(ENCODED_MAC_KEY); + hmacProvider.setDefaultJwtAlgorithm(Algorithm.HmacSHA256.getJwtName()); + doTestJweJwsRsa(address, hmacProvider); + } + + private void doTestJweJwsRsa(String address, + JwsSignatureProvider jwsSigProvider) throws Exception { JAXRSClientFactoryBean bean = new JAXRSClientFactoryBean(); SpringBusFactory bf = new SpringBusFactory(); URL busFile = JAXRSJweJwsTest.class.getResource("client.xml"); @@ -87,6 +102,9 @@ public class JAXRSJweJwsTest extends AbstractBusClientServerTestBase { providers.add(jweWriter); providers.add(new JweClientResponseFilter()); JwsWriterInterceptor jwsWriter = new JwsWriterInterceptor(); + if (jwsSigProvider != null) { + jwsWriter.setSignatureProvider(jwsSigProvider); + } jwsWriter.setUseJwsOutputStream(true); providers.add(jwsWriter); providers.add(new JwsClientResponseFilter()); http://git-wip-us.apache.org/repos/asf/cxf/blob/78664f43/systests/rs-security/src/test/java/org/apache/cxf/systest/jaxrs/security/jwt/server.xml ---------------------------------------------------------------------- diff --git a/systests/rs-security/src/test/java/org/apache/cxf/systest/jaxrs/security/jwt/server.xml b/systests/rs-security/src/test/java/org/apache/cxf/systest/jaxrs/security/jwt/server.xml index 37bcec7..f587972 100644 --- a/systests/rs-security/src/test/java/org/apache/cxf/systest/jaxrs/security/jwt/server.xml +++ b/systests/rs-security/src/test/java/org/apache/cxf/systest/jaxrs/security/jwt/server.xml @@ -48,18 +48,24 @@ under the License. <bean id="serviceBean" class="org.apache.cxf.systest.jaxrs.security.jwt.BookStore"/> <bean id="jweInFilter" class="org.apache.cxf.rs.security.oauth2.jwt.jaxrs.JweContainerRequestFilter"/> <bean id="jweOutFilter" class="org.apache.cxf.rs.security.oauth2.jwt.jaxrs.JweWriterInterceptor"/> - <bean id="jwsInFilter" class="org.apache.cxf.rs.security.oauth2.jwt.jaxrs.JwsContainerRequestFilter"/> - <bean id="jwsOutFilter" class="org.apache.cxf.rs.security.oauth2.jwt.jaxrs.JwsWriterInterceptor"/> + <bean id="hmacSigVerifier" class="org.apache.cxf.rs.security.oauth2.jws.HmacJwsSignatureProvider"> + <constructor-arg value="AyM1SysPpbyDfgZld3umj1qzKObwVMkoqQ-EstJQLr_T-1qS0gZH75aKtMN3Yj0iPS4hcgUuTwjAzZr1Z9CAow"/> + </bean> + <bean id="jwsHmacInFilter" class="org.apache.cxf.rs.security.oauth2.jwt.jaxrs.JwsContainerRequestFilter"> + <property name="signatureVerifier" ref="hmacSigVerifier"/> + </bean> + <bean id="jwsRsaInFilter" class="org.apache.cxf.rs.security.oauth2.jwt.jaxrs.JwsContainerRequestFilter"/> + <bean id="jwsRsaOutFilter" class="org.apache.cxf.rs.security.oauth2.jwt.jaxrs.JwsWriterInterceptor"/> <bean id="keyPasswordProvider" class="org.apache.cxf.systest.jaxrs.security.jwt.PrivateKeyPasswordProviderImpl"/> - <jaxrs:server address="https://localhost:${testutil.ports.jaxrs-jwt}/jwejws"> + <jaxrs:server address="https://localhost:${testutil.ports.jaxrs-jwt}/jwejwsrsa"> <jaxrs:serviceBeans> <ref bean="serviceBean"/> </jaxrs:serviceBeans> <jaxrs:providers> <ref bean="jweInFilter"/> <ref bean="jweOutFilter"/> - <ref bean="jwsInFilter"/> - <ref bean="jwsOutFilter"/> + <ref bean="jwsRsaInFilter"/> + <ref bean="jwsRsaOutFilter"/> </jaxrs:providers> <jaxrs:properties> <entry key="rs.security.encryption.in.properties" value="org/apache/cxf/systest/jaxrs/security/alice.rs.properties"/> @@ -70,4 +76,22 @@ under the License. <entry key="rs.security.decryption.key.password.provider" value-ref="keyPasswordProvider"/> </jaxrs:properties> </jaxrs:server> + <jaxrs:server address="https://localhost:${testutil.ports.jaxrs-jwt}/jwejwshmac"> + <jaxrs:serviceBeans> + <ref bean="serviceBean"/> + </jaxrs:serviceBeans> + <jaxrs:providers> + <ref bean="jweInFilter"/> + <ref bean="jweOutFilter"/> + <ref bean="jwsHmacInFilter"/> + <ref bean="jwsRsaOutFilter"/> + </jaxrs:providers> + <jaxrs:properties> + <entry key="rs.security.encryption.in.properties" value="org/apache/cxf/systest/jaxrs/security/alice.rs.properties"/> + <entry key="rs.security.encryption.out.properties" value="org/apache/cxf/systest/jaxrs/security/bob.rs.properties"/> + <entry key="rs.security.signature.out.properties" value="org/apache/cxf/systest/jaxrs/security/alice.rs.properties"/> + <entry key="rs.security.signature.key.password.provider" value-ref="keyPasswordProvider"/> + <entry key="rs.security.decryption.key.password.provider" value-ref="keyPasswordProvider"/> + </jaxrs:properties> + </jaxrs:server> </beans>
