This is an automated email from the ASF dual-hosted git repository.

coheigea pushed a commit to branch 3.2.x-fixes
in repository https://gitbox.apache.org/repos/asf/cxf.git


The following commit(s) were added to refs/heads/3.2.x-fixes by this push:
     new 0e0a899  CXF-7788 - Support POST method for OAuth authorization service
0e0a899 is described below

commit 0e0a899435260cf4400a9a4d954cea481615107a
Author: Colm O hEigeartaigh <cohei...@apache.org>
AuthorDate: Thu Jul 12 11:02:10 2018 +0100

    CXF-7788 - Support POST method for OAuth authorization service
    
    (cherry picked from commit ebfb3a364c496f76c8b27aacc9bdd7b8aa804602)
---
 .../oauth2/services/AuthorizationService.java      |  13 +++
 .../services/RedirectionBasedGrantService.java     |  17 +++-
 .../security/oauth2/common/OAuth2TestUtils.java    |  10 +-
 .../oauth2/grants/AuthorizationGrantTest.java      |  42 ++++++++
 .../systest/jaxrs/security/oidc/OIDCFlowTest.java  | 113 +++++++++++++++++++++
 5 files changed, 190 insertions(+), 5 deletions(-)

diff --git 
a/rt/rs/security/oauth-parent/oauth2/src/main/java/org/apache/cxf/rs/security/oauth2/services/AuthorizationService.java
 
b/rt/rs/security/oauth-parent/oauth2/src/main/java/org/apache/cxf/rs/security/oauth2/services/AuthorizationService.java
index 2674194..263bc36 100644
--- 
a/rt/rs/security/oauth-parent/oauth2/src/main/java/org/apache/cxf/rs/security/oauth2/services/AuthorizationService.java
+++ 
b/rt/rs/security/oauth-parent/oauth2/src/main/java/org/apache/cxf/rs/security/oauth2/services/AuthorizationService.java
@@ -50,6 +50,7 @@ public class AuthorizationService {
             service.setMessageContext(context);
         }
     }
+
     @GET
     @Produces({"application/xhtml+xml", "text/html", "application/xml", 
"application/json" })
     public Response authorize(@QueryParam(OAuthConstants.RESPONSE_TYPE) String 
responseType) {
@@ -60,6 +61,18 @@ public class AuthorizationService {
         return reportInvalidResponseType();
     }
 
+    @POST
+    @Consumes("application/x-www-form-urlencoded")
+    @Produces({"application/xhtml+xml", "text/html", "application/xml", 
"application/json" })
+    public Response authorizePost(MultivaluedMap<String, String> params) {
+        String responseType = params.getFirst(OAuthConstants.RESPONSE_TYPE);
+        RedirectionBasedGrantService service = getService(responseType);
+        if (service != null) {
+            return service.authorize();
+        }
+        return reportInvalidResponseType();
+    }
+
     @GET
     @Path("/decision")
     public Response 
authorizeDecision(@QueryParam(OAuthConstants.RESPONSE_TYPE) String 
responseType) {
diff --git 
a/rt/rs/security/oauth-parent/oauth2/src/main/java/org/apache/cxf/rs/security/oauth2/services/RedirectionBasedGrantService.java
 
b/rt/rs/security/oauth-parent/oauth2/src/main/java/org/apache/cxf/rs/security/oauth2/services/RedirectionBasedGrantService.java
index b016df3..90c3285 100644
--- 
a/rt/rs/security/oauth-parent/oauth2/src/main/java/org/apache/cxf/rs/security/oauth2/services/RedirectionBasedGrantService.java
+++ 
b/rt/rs/security/oauth-parent/oauth2/src/main/java/org/apache/cxf/rs/security/oauth2/services/RedirectionBasedGrantService.java
@@ -99,6 +99,19 @@ public abstract class RedirectionBasedGrantService extends 
AbstractOAuthService
     }
 
     /**
+     * Handles the initial authorization request by preparing
+     * the authorization challenge data and returning it to the user.
+     * Typically the data are expected to be presented in the HTML form
+     * @return the authorization data
+     */
+    @POST
+    @Consumes("application/x-www-form-urlencoded")
+    @Produces({"application/xhtml+xml", "text/html", "application/xml", 
"application/json" })
+    public Response authorizePost(MultivaluedMap<String, String> params) {
+        return startAuthorization(params);
+    }
+
+    /**
      * Processes the end user decision
      * @return The grant value, authorization code or the token
      */
@@ -389,7 +402,7 @@ public abstract class RedirectionBasedGrantService extends 
AbstractOAuthService
             return createErrorResponse(params, redirectUri, 
OAuthConstants.INVALID_SCOPE);
         }
         getMessageContext().put(AUTHORIZATION_REQUEST_PARAMETERS, params);
-        
+
         String preAuthorizedTokenKey = 
params.getFirst(PREAUTHORIZED_TOKEN_KEY);
         if (preAuthorizedTokenKey != null && 
isRevokePreauthorizedTokenOnApproval()) {
             getDataProvider().revokeToken(client, preAuthorizedTokenKey, 
OAuthConstants.ACCESS_TOKEN);
@@ -410,7 +423,7 @@ public abstract class RedirectionBasedGrantService extends 
AbstractOAuthService
     public void setRevokePreauthorizedTokenOnApproval(boolean revoke) {
         this.revokePreauthorizedTokenOnApproval = revoke;
     }
-    
+
     public void 
setSessionAuthenticityTokenProvider(SessionAuthenticityTokenProvider 
sessionAuthenticityTokenProvider) {
         this.sessionAuthenticityTokenProvider = 
sessionAuthenticityTokenProvider;
     }
diff --git 
a/systests/rs-security/src/test/java/org/apache/cxf/systest/jaxrs/security/oauth2/common/OAuth2TestUtils.java
 
b/systests/rs-security/src/test/java/org/apache/cxf/systest/jaxrs/security/oauth2/common/OAuth2TestUtils.java
index a19a75f..1db41b7 100644
--- 
a/systests/rs-security/src/test/java/org/apache/cxf/systest/jaxrs/security/oauth2/common/OAuth2TestUtils.java
+++ 
b/systests/rs-security/src/test/java/org/apache/cxf/systest/jaxrs/security/oauth2/common/OAuth2TestUtils.java
@@ -105,6 +105,10 @@ public final class OAuth2TestUtils {
         Response response = client.get();
 
         OAuthAuthorizationData authzData = 
response.readEntity(OAuthAuthorizationData.class);
+        return getLocation(client, authzData, parameters.getState());
+    }
+
+    public static String getLocation(WebClient client, OAuthAuthorizationData 
authzData, String state) {
 
         // Now call "decision" to get the authorization code grant
         client.path("decision");
@@ -126,10 +130,10 @@ public final class OAuth2TestUtils {
         form.param("response_type", authzData.getResponseType());
         form.param("oauthDecision", "allow");
 
-        response = client.post(form);
+        Response response = client.post(form);
         String location = response.getHeaderString("Location");
-        if (parameters.getState() != null) {
-            Assert.assertTrue(location.contains("state=" + 
parameters.getState()));
+        if (state != null) {
+            Assert.assertTrue(location.contains("state=" + state));
         }
 
         return location;
diff --git 
a/systests/rs-security/src/test/java/org/apache/cxf/systest/jaxrs/security/oauth2/grants/AuthorizationGrantTest.java
 
b/systests/rs-security/src/test/java/org/apache/cxf/systest/jaxrs/security/oauth2/grants/AuthorizationGrantTest.java
index ae22085..2fdf4a7 100644
--- 
a/systests/rs-security/src/test/java/org/apache/cxf/systest/jaxrs/security/oauth2/grants/AuthorizationGrantTest.java
+++ 
b/systests/rs-security/src/test/java/org/apache/cxf/systest/jaxrs/security/oauth2/grants/AuthorizationGrantTest.java
@@ -74,6 +74,48 @@ public class AuthorizationGrantTest extends 
AbstractBusClientServerTestBase {
         assertNotNull(accessToken.getTokenKey());
     }
 
+    // The authorization server MUST support the use of the HTTP "GET"
+    // method [RFC2616] for the authorization endpoint and MAY support the
+    // use of the "POST" method as well.
+    @org.junit.Test
+    public void testAuthorizationCodeGrantPOST() throws Exception {
+        URL busFile = AuthorizationGrantTest.class.getResource("client.xml");
+
+        String address = "https://localhost:"; + PORT + "/services/";
+        WebClient client = WebClient.create(address, 
OAuth2TestUtils.setupProviders(),
+                                            "alice", "security", 
busFile.toString());
+        // Save the Cookie for the second request...
+        WebClient.getConfig(client).getRequestContext().put(
+            org.apache.cxf.message.Message.MAINTAIN_SESSION, Boolean.TRUE);
+
+        // Make initial authorization request
+        client.type("application/x-www-form-urlencoded");
+
+        client.path("authorize/");
+
+        Form form = new Form();
+        form.param("client_id", "consumer-id");
+        form.param("redirect_uri", "http://www.blah.apache.org";);
+        form.param("response_type", "code");
+        Response response = client.post(form);
+
+        OAuthAuthorizationData authzData = 
response.readEntity(OAuthAuthorizationData.class);
+        String location = OAuth2TestUtils.getLocation(client, authzData, null);
+        String code =  OAuth2TestUtils.getSubstring(location, "code");
+        assertNotNull(code);
+
+        // Now get the access token
+        client = WebClient.create(address, OAuth2TestUtils.setupProviders(),
+                                  "consumer-id", "this-is-a-secret", 
busFile.toString());
+        // Save the Cookie for the second request...
+        WebClient.getConfig(client).getRequestContext().put(
+            org.apache.cxf.message.Message.MAINTAIN_SESSION, Boolean.TRUE);
+
+        ClientAccessToken accessToken =
+            OAuth2TestUtils.getAccessTokenWithAuthorizationCode(client, code);
+        assertNotNull(accessToken.getTokenKey());
+    }
+
     @org.junit.Test
     public void testAuthorizationCodeGrantRefresh() throws Exception {
         URL busFile = AuthorizationGrantTest.class.getResource("client.xml");
diff --git 
a/systests/rs-security/src/test/java/org/apache/cxf/systest/jaxrs/security/oidc/OIDCFlowTest.java
 
b/systests/rs-security/src/test/java/org/apache/cxf/systest/jaxrs/security/oidc/OIDCFlowTest.java
index 1e15986..010d483 100644
--- 
a/systests/rs-security/src/test/java/org/apache/cxf/systest/jaxrs/security/oidc/OIDCFlowTest.java
+++ 
b/systests/rs-security/src/test/java/org/apache/cxf/systest/jaxrs/security/oidc/OIDCFlowTest.java
@@ -104,6 +104,54 @@ public class OIDCFlowTest extends 
AbstractBusClientServerTestBase {
         validateIdToken(idToken, null);
     }
 
+    // Authorization Servers MUST support the use of the HTTP GET and POST 
methods defined in RFC 2616
+    // [RFC2616] at the Authorization Endpoint.
+    @org.junit.Test
+    public void testAuthorizationCodeFlowPOST() throws Exception {
+        URL busFile = OIDCFlowTest.class.getResource("client.xml");
+
+        String address = "https://localhost:"; + PORT + "/services/";
+        WebClient client = WebClient.create(address, 
OAuth2TestUtils.setupProviders(),
+                                            "alice", "security", 
busFile.toString());
+
+        // Save the Cookie for the second request...
+        WebClient.getConfig(client).getRequestContext().put(
+            org.apache.cxf.message.Message.MAINTAIN_SESSION, Boolean.TRUE);
+
+        // Make initial authorization request
+        client.type("application/x-www-form-urlencoded");
+
+        client.path("authorize/");
+
+        Form form = new Form();
+        form.param("client_id", "consumer-id");
+        form.param("scope", "openid");
+        form.param("redirect_uri", "http://www.blah.apache.org";);
+        form.param("response_type", "code");
+        Response response = client.post(form);
+
+        OAuthAuthorizationData authzData = 
response.readEntity(OAuthAuthorizationData.class);
+        String location = OAuth2TestUtils.getLocation(client, authzData, null);
+        String code =  OAuth2TestUtils.getSubstring(location, "code");
+        assertNotNull(code);
+
+        // Now get the access token
+        client = WebClient.create(address, OAuth2TestUtils.setupProviders(),
+                                  "consumer-id", "this-is-a-secret", 
busFile.toString());
+        // Save the Cookie for the second request...
+        WebClient.getConfig(client).getRequestContext().put(
+            org.apache.cxf.message.Message.MAINTAIN_SESSION, Boolean.TRUE);
+
+        ClientAccessToken accessToken =
+            OAuth2TestUtils.getAccessTokenWithAuthorizationCode(client, code);
+        assertNotNull(accessToken.getTokenKey());
+        assertTrue(accessToken.getApprovedScope().contains("openid"));
+
+        String idToken = accessToken.getParameters().get("id_token");
+        assertNotNull(idToken);
+        validateIdToken(idToken, null);
+    }
+
     // Just a normal OAuth invocation, check it all works ok
     @org.junit.Test
     public void testAuthorizationCodeOAuth() throws Exception {
@@ -373,6 +421,71 @@ public class OIDCFlowTest extends 
AbstractBusClientServerTestBase {
         OidcUtils.validateAccessTokenHash(accessToken, jwt, true);
     }
 
+    // Authorization Servers MUST support the use of the HTTP GET and POST 
methods defined in RFC 2616
+    // [RFC2616] at the Authorization Endpoint.
+    @org.junit.Test
+    public void testImplicitFlowPOST() throws Exception {
+        URL busFile = OIDCFlowTest.class.getResource("client.xml");
+
+        String address = "https://localhost:"; + PORT + "/services/";
+        WebClient client = WebClient.create(address, 
OAuth2TestUtils.setupProviders(),
+                                            "alice", "security", 
busFile.toString());
+        // Save the Cookie for the second request...
+        WebClient.getConfig(client).getRequestContext().put(
+            org.apache.cxf.message.Message.MAINTAIN_SESSION, Boolean.TRUE);
+
+        // Get Access Token
+        client.type("application/x-www-form-urlencoded");
+
+        client.path("authorize-implicit/");
+
+        Form form = new Form();
+        form.param("client_id", "consumer-id");
+        form.param("scope", "openid");
+        form.param("redirect_uri", "http://www.blah.apache.org";);
+        form.param("response_type", "id_token token");
+        form.param("nonce", "123456789");
+        Response response = client.post(form);
+
+        OAuthAuthorizationData authzData = 
response.readEntity(OAuthAuthorizationData.class);
+
+        // Now call "decision" to get the access token
+        client.path("decision");
+        client.type("application/x-www-form-urlencoded");
+
+        form = new Form();
+        form.param("session_authenticity_token", 
authzData.getAuthenticityToken());
+        form.param("client_id", authzData.getClientId());
+        form.param("redirect_uri", authzData.getRedirectUri());
+        form.param("scope", authzData.getProposedScope());
+        if (authzData.getResponseType() != null) {
+            form.param("response_type", authzData.getResponseType());
+        }
+        if (authzData.getNonce() != null) {
+            form.param("nonce", authzData.getNonce());
+        }
+        form.param("oauthDecision", "allow");
+
+        response = client.post(form);
+
+        String location = response.getHeaderString("Location");
+
+        // Check Access Token
+        String accessToken = OAuth2TestUtils.getSubstring(location, 
"access_token");
+        assertNotNull(accessToken);
+
+        // Check IdToken
+        String idToken = OAuth2TestUtils.getSubstring(location, "id_token");
+        assertNotNull(idToken);
+        validateIdToken(idToken, null);
+
+        JwsJwtCompactConsumer jwtConsumer = new JwsJwtCompactConsumer(idToken);
+        JwtToken jwt = jwtConsumer.getJwtToken();
+        
Assert.assertNotNull(jwt.getClaims().getClaim(IdToken.ACCESS_TOKEN_HASH_CLAIM));
+        Assert.assertNotNull(jwt.getClaims().getClaim(IdToken.NONCE_CLAIM));
+        OidcUtils.validateAccessTokenHash(accessToken, jwt, true);
+    }
+
     @org.junit.Test
     public void testImplicitFlowNoAccessToken() throws Exception {
         URL busFile = OIDCFlowTest.class.getResource("client.xml");

Reply via email to