You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@usergrid.apache.org by mr...@apache.org on 2016/08/01 16:53:57 UTC
[22/50] [abbrv] usergrid git commit: Cleanup. Add tests.
Cleanup. Add tests.
Project: http://git-wip-us.apache.org/repos/asf/usergrid/repo
Commit: http://git-wip-us.apache.org/repos/asf/usergrid/commit/6d88bcfd
Tree: http://git-wip-us.apache.org/repos/asf/usergrid/tree/6d88bcfd
Diff: http://git-wip-us.apache.org/repos/asf/usergrid/diff/6d88bcfd
Branch: refs/heads/master
Commit: 6d88bcfdccc458b382b16483b5d3048df699262c
Parents: 5fcad44
Author: Ayesha Dastagiri <ay...@gmail.com>
Authored: Tue Jul 26 11:49:42 2016 -0700
Committer: Ayesha Dastagiri <ay...@gmail.com>
Committed: Tue Jul 26 11:49:42 2016 -0700
----------------------------------------------------------------------
stack/rest/pom.xml | 8 +
.../rest/management/ManagementResource.java | 13 +-
.../rest/management/ExternalSSOEnabledIT.java | 175 +++++++++++++++++++
.../rest/management/ManagementResourceIT.java | 24 ++-
.../security/sso/ApigeeSSO2Provider.java | 28 +--
.../tokens/cassandra/TokenServiceImpl.java | 3 +
6 files changed, 233 insertions(+), 18 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/usergrid/blob/6d88bcfd/stack/rest/pom.xml
----------------------------------------------------------------------
diff --git a/stack/rest/pom.xml b/stack/rest/pom.xml
index 89d14b4..580814c 100644
--- a/stack/rest/pom.xml
+++ b/stack/rest/pom.xml
@@ -306,6 +306,14 @@
<version>${jackson-2-version}</version>
</dependency>
+ <!-- for mocking the Apigee SSO Service -->
+ <dependency>
+ <groupId>org.mockito</groupId>
+ <artifactId>mockito-core</artifactId>
+ <version>${mockito.version}</version>
+ <scope>test</scope>
+ </dependency>
+
<!-- databinding; ObjectMapper, JsonNode and related classes are here -->
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
http://git-wip-us.apache.org/repos/asf/usergrid/blob/6d88bcfd/stack/rest/src/main/java/org/apache/usergrid/rest/management/ManagementResource.java
----------------------------------------------------------------------
diff --git a/stack/rest/src/main/java/org/apache/usergrid/rest/management/ManagementResource.java b/stack/rest/src/main/java/org/apache/usergrid/rest/management/ManagementResource.java
index 7217c49..c5d7c77 100644
--- a/stack/rest/src/main/java/org/apache/usergrid/rest/management/ManagementResource.java
+++ b/stack/rest/src/main/java/org/apache/usergrid/rest/management/ManagementResource.java
@@ -385,9 +385,14 @@ public class ManagementResource extends AbstractContextResource {
//moved the check for sso enabled form MangementServiceImpl since was unable to get the current user there to check if its super user.
if( tokens.isExternalSSOProviderEnabled()
- && !userServiceAdmin(user.getUsername()) ){
- throw new RuntimeException("SSO Integration is enabled, Admin users must login via provider: "+
- properties.getProperty(TokenServiceImpl.USERGRID_EXTERNAL_PROVIDER));
+ && !userServiceAdmin(username) ){
+ OAuthResponse response =
+ OAuthResponse.errorResponse( SC_BAD_REQUEST ).setError( OAuthError.TokenResponse.INVALID_GRANT )
+ .setErrorDescription( "SSO Integration is enabled, Admin users must login via provider: "+
+ properties.getProperty(TokenServiceImpl.USERGRID_EXTERNAL_PROVIDER) ).buildJSONMessage();
+ return Response.status( response.getResponseStatus() ).type( jsonMediaType( callback ) )
+ .entity( wrapWithCallback( response.getBody(), callback ) ).build();
+
}
String token = management.getAccessTokenForAdminUser( user.getUuid(), ttl );
@@ -616,7 +621,7 @@ public class ManagementResource extends AbstractContextResource {
if ( tokens.isExternalSSOProviderEnabled() ) {
// when external tokens enabled then only superuser can obtain an access token
- if ( userServiceAdmin(username)) {
+ if ( !userServiceAdmin(username)) {
// this guy is not the superuser
throw new IllegalArgumentException( "Admin Users must login via " +
properties.getProperty( USERGRID_EXTERNAL_PROVIDER_URL ) );
http://git-wip-us.apache.org/repos/asf/usergrid/blob/6d88bcfd/stack/rest/src/test/java/org/apache/usergrid/rest/management/ExternalSSOEnabledIT.java
----------------------------------------------------------------------
diff --git a/stack/rest/src/test/java/org/apache/usergrid/rest/management/ExternalSSOEnabledIT.java b/stack/rest/src/test/java/org/apache/usergrid/rest/management/ExternalSSOEnabledIT.java
new file mode 100644
index 0000000..75fa0b5
--- /dev/null
+++ b/stack/rest/src/test/java/org/apache/usergrid/rest/management/ExternalSSOEnabledIT.java
@@ -0,0 +1,175 @@
+/*
+ * 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.usergrid.rest.management;
+
+import io.jsonwebtoken.Jwts;
+import io.jsonwebtoken.SignatureAlgorithm;
+import io.jsonwebtoken.impl.crypto.RsaProvider;
+import org.apache.commons.collections4.map.HashedMap;
+import org.apache.usergrid.cassandra.SpringResource;
+import org.apache.usergrid.persistence.index.utils.UUIDUtils;
+import org.apache.usergrid.rest.test.resource.AbstractRestIT;
+import org.apache.usergrid.rest.test.resource.RestClient;
+import org.apache.usergrid.rest.test.resource.model.ApiResponse;
+import org.apache.usergrid.rest.test.resource.model.Entity;
+import org.apache.usergrid.security.sso.ApigeeSSO2Provider;
+import org.codehaus.jackson.JsonNode;
+import org.junit.Before;
+import org.junit.Ignore;
+import org.junit.Test;
+
+import java.security.*;
+import java.util.HashMap;
+import java.util.Map;
+
+import static org.junit.Assert.*;
+
+/**
+ * Created by ayeshadastagiri on 7/20/16.
+ */
+@Ignore("Need to figure out a way to set the public key for Mock server.")
+public class ExternalSSOEnabledIT extends AbstractRestIT {
+
+ Key key;
+ PublicKey publicKey;
+ PrivateKey privateKey;
+ String compactJws;
+ String username = "SSOadminuser" + UUIDUtils.newTimeUUID();
+ ApigeeSSO2Provider apigeeSSO2ProviderTest;
+ //SSO2 implementation
+ public static final String USERGRID_EXTERNAL_SSO_ENABLED = "usergrid.external.sso.enabled";
+ public static final String USERGRID_EXTERNAL_PROVIDER = "usergrid.external.sso.provider";
+
+ public ExternalSSOEnabledIT() throws Exception {
+
+ }
+
+ @Before
+ public void setup() throws NoSuchAlgorithmException {
+ generateKey();
+ }
+
+ private void generateKey() {
+ KeyPair kp = RsaProvider.generateKeyPair(1024);
+ publicKey = kp.getPublic();
+ privateKey = kp.getPrivate();
+ }
+
+ private String genrateToken(){
+ Map<String, Object> claims = new HashedMap<String, Object>();
+ claims.put("jti","c7df0339-3847-450b-a925-628ef237953a");
+ claims.put("sub","b6d62259-217b-4e96-8f49-e00c366e4fed");
+ claims.put("scope","size = 5");
+ claims.put("client_id", "edgecli");
+ claims.put("azp","edgecli");
+ claims.put("grant_type" ,"password");
+ claims.put("user_id","b6d62259-217b-4e96-8f49-e00c366e4fed");
+ claims.put( "origin","usergrid");
+ claims.put("user_name","AyeshaSSOUser");
+ claims.put("email", "adastagiri+ssotesting@apigee.com");
+ claims.put( "rev_sig","dfe5d0d3");
+ claims.put("iat","1466550862");
+ claims.put("exp", System.currentTimeMillis() + 1000);
+ claims.put("iss", "https://login.apigee.com/oauth/token");
+ claims.put( "zid","uaa");
+ claims.put( "aud"," size = 6");
+ claims.put("grant_type","password");
+
+ String jwt = Jwts.builder().setClaims(claims).signWith(SignatureAlgorithm.RS256, privateKey).compact();
+ return jwt;
+
+ }
+
+ @Test
+ public void SuperUserTestsFor() throws NoSuchAlgorithmException {
+
+ // create a admin user.
+ RestClient restClient = clientSetup.getRestClient();
+
+ //Create adminUser values
+ Entity adminUserPayload = new Entity();
+ adminUserPayload.put("username", "TestUser");
+ adminUserPayload.put("name", username);
+ adminUserPayload.put("email", "adastagiri+ssotesting@apigee.com");
+ adminUserPayload.put("password", username);
+
+ //create adminUser
+ ApiResponse adminUserEntityResponse = management().orgs().org(clientSetup.getOrganizationName()).users().post(ApiResponse.class, adminUserPayload);
+
+ Entity adminUserResponse = new Entity(adminUserEntityResponse);
+ //verify that the response contains the correct data
+ assertNotNull(adminUserResponse);
+ assertEquals("TestUser", adminUserResponse.get("username"));
+
+ Map<String, String> props = new HashMap<String, String>();
+
+ props.put( USERGRID_EXTERNAL_SSO_ENABLED, "true" );
+ props.put( USERGRID_EXTERNAL_PROVIDER, "apigee" );
+ pathResource( "testproperties" ).post( props );
+
+ // /management/me --> superuser and query params --> Generate a super usesr token.
+ Map<String, Object> loginInfo = new HashMap<String, Object>() {{
+ put( "username", "superuser" );
+ put( "password", "superpassword" );
+ put( "grant_type", "password" );
+ }};
+ ApiResponse postResponse2 = pathResource( "management/token" ).post( false,ApiResponse.class,loginInfo );
+ assertTrue(postResponse2.getAccessToken() != null );
+
+
+ // /orgs create an org with superuser credentials.
+ // /management/me --> superuser and query params --> Generate a super usesr token.
+ Map<String, Object> orgDetails = new HashMap<String, Object>() {{
+ put( "email", "adastagiri+ssotesting@apigee.com" );
+ put( "name", "testuser" );
+ put( "organization", username );
+ }};
+
+ context().getToken().put("access_token",postResponse2.getAccessToken());
+ postResponse2 = pathResource( "management/orgs" ).post( true,ApiResponse.class,orgDetails);
+ assertTrue(postResponse2.getData() != null);
+
+ postResponse2 = pathResource("management/orgs").get(ApiResponse.class,true);
+ assertTrue(postResponse2 != null);
+
+
+ compactJws = genrateToken();
+
+ SpringResource.getInstance().getAppContext().getBean(ApigeeSSO2Provider.class).setPublicKey( publicKey );
+ context().getToken().put("access_token",compactJws);
+ // /management/me --> admin user and jwt token. Return the user information and "token" should have jwt token.
+ JsonNode responseToken = management().me().get(JsonNode.class,true);
+ assertTrue(responseToken.get("access_token") != null);
+
+
+ // /management/me --> admin and query params --> Generate a super usesr token.
+ Map<String, Object> loginInfo1 = new HashMap<String, Object>() {{
+ put( "username", "TestUser" );
+ put( "password", username );
+ put( "grant_type", "password" );
+ }};
+
+ // /managment/token -> adminusername and password --> should fail.
+ ApiResponse postResponse1 = pathResource("management/token").post(false, ApiResponse.class,loginInfo1);
+// fail( "SSO Integration is enabled, Admin users must login via provider: "+ USERGRID_EXTERNAL_PROVIDER_URL);
+
+
+
+
+ }
+}
http://git-wip-us.apache.org/repos/asf/usergrid/blob/6d88bcfd/stack/rest/src/test/java/org/apache/usergrid/rest/management/ManagementResourceIT.java
----------------------------------------------------------------------
diff --git a/stack/rest/src/test/java/org/apache/usergrid/rest/management/ManagementResourceIT.java b/stack/rest/src/test/java/org/apache/usergrid/rest/management/ManagementResourceIT.java
index 1fe4f01..21c62ba 100644
--- a/stack/rest/src/test/java/org/apache/usergrid/rest/management/ManagementResourceIT.java
+++ b/stack/rest/src/test/java/org/apache/usergrid/rest/management/ManagementResourceIT.java
@@ -38,6 +38,7 @@ import java.io.IOException;
import java.util.*;
import static org.apache.usergrid.security.tokens.cassandra.TokenServiceImpl.USERGRID_EXTERNAL_PROVIDER_URL;
+import static org.apache.usergrid.security.tokens.cassandra.TokenServiceImpl.USERGRID_EXTERNAL_SSO_ENABLED;
import static org.apache.usergrid.utils.MapUtils.hashMap;
import static org.junit.Assert.*;
@@ -671,6 +672,7 @@ public class ManagementResourceIT extends AbstractRestIT {
String suToken = clientSetup.getSuperuserToken().getAccessToken();
Map<String, String> props = new HashMap<String, String>();
+ props.put(USERGRID_EXTERNAL_SSO_ENABLED, "true");
props.put( USERGRID_EXTERNAL_PROVIDER_URL, getBaseURI().toURL().toExternalForm() );
pathResource( "testproperties" ).post( props );
@@ -685,7 +687,7 @@ public class ManagementResourceIT extends AbstractRestIT {
put( "grant_type", "password" );
}};
ApiResponse postResponse = pathResource( "management/token" ).post( false, ApiResponse.class, loginInfo );
- fail( "Login as Admin User must fail when validate external tokens is enabled" );
+ fail( "SSO Integration is enabled, Admin users must login via provider: "+ USERGRID_EXTERNAL_PROVIDER_URL);
} catch (ClientErrorException actual) {
assertEquals( 400, actual.getResponse().getStatus() );
@@ -709,11 +711,31 @@ public class ManagementResourceIT extends AbstractRestIT {
String accessToken = postResponse2.getAccessToken();
assertNotNull( accessToken );
+ //Superuser : GET -> get tokenInfo with access_token
+ ApiResponse getResponse3 = pathResource("management/me").get(ApiResponse.class,new QueryParameters()
+ .addParam("grant_type", "password").addParam("password", "superpassword")
+ .addParam("username", "superuser"),false);
+
+ assertNotNull(getResponse3.getAccessToken());
+
+ //Superuser : POST -> Add org using super user credentials.
+ Map<String, Object> orgAdminUserInfo = new HashMap<String, Object>() {{
+ put( "username", username+"test" );
+ put("password","RandomPassword");
+ put("email",username+"@gmail.com");
+ put( "organization", username+"RandomOrgName" );
+ }};
+ ApiResponse postResponse4 = pathResource("management/orgs")
+ .post(false,orgAdminUserInfo,new QueryParameters().addParam("access_token",getResponse3.getAccessToken()));
+ assertNotNull(postResponse4.getData());
+
+
} finally {
// turn off validate external tokens by un-setting the usergrid.central.url
props.put( USERGRID_EXTERNAL_PROVIDER_URL, "" );
+ props.put(USERGRID_EXTERNAL_SSO_ENABLED, "");
pathResource( "testproperties" ).post( props );
}
}
http://git-wip-us.apache.org/repos/asf/usergrid/blob/6d88bcfd/stack/services/src/main/java/org/apache/usergrid/security/sso/ApigeeSSO2Provider.java
----------------------------------------------------------------------
diff --git a/stack/services/src/main/java/org/apache/usergrid/security/sso/ApigeeSSO2Provider.java b/stack/services/src/main/java/org/apache/usergrid/security/sso/ApigeeSSO2Provider.java
index 61a1601..d48495d 100644
--- a/stack/services/src/main/java/org/apache/usergrid/security/sso/ApigeeSSO2Provider.java
+++ b/stack/services/src/main/java/org/apache/usergrid/security/sso/ApigeeSSO2Provider.java
@@ -57,7 +57,7 @@ public class ApigeeSSO2Provider implements ExternalSSOProvider {
protected Properties properties;
protected ManagementService management;
protected Client client;
- protected String publicKey;
+ protected PublicKey publicKey;
public static final String USERGRID_EXTERNAL_PUBLICKEY_URL = "usergrid.external.sso.url";
@@ -67,12 +67,17 @@ public class ApigeeSSO2Provider implements ExternalSSOProvider {
client = ClientBuilder.newClient(clientConfig);
}
- public String getPublicKey(String keyUrl) {
+ public PublicKey getPublicKey(String keyUrl) {
if(keyUrl != null && !keyUrl.isEmpty()) {
try {
Map<String, Object> publicKey = client.target(keyUrl).request().get(Map.class);
- return publicKey.get(RESPONSE_PUBLICKEY_VALUE).toString().split("----\n")[1].split("\n---")[0];
+ String ssoPublicKey = publicKey.get(RESPONSE_PUBLICKEY_VALUE).toString().split("----\n")[1].split("\n---")[0];
+ byte[] publicBytes = decodeBase64(ssoPublicKey);
+ X509EncodedKeySpec keySpec = new X509EncodedKeySpec(publicBytes);
+ KeyFactory keyFactory = KeyFactory.getInstance("RSA");
+ PublicKey pubKey = keyFactory.generatePublic(keySpec);
+ return pubKey;
}
catch(Exception e){
throw new IllegalArgumentException("error getting public key");
@@ -140,7 +145,7 @@ public class ApigeeSSO2Provider implements ExternalSSOProvider {
return properties.getProperty(USERGRID_EXTERNAL_PUBLICKEY_URL);
}
- public Jws<Claims> getClaimsForKeyUrl(String token, String ssoPublicKey) throws NoSuchAlgorithmException, InvalidKeySpecException, BadTokenException {
+ public Jws<Claims> getClaimsForKeyUrl(String token, PublicKey ssoPublicKey) throws NoSuchAlgorithmException, InvalidKeySpecException, BadTokenException {
Jws<Claims> claims = null;
if(ssoPublicKey == null){
@@ -148,14 +153,8 @@ public class ApigeeSSO2Provider implements ExternalSSOProvider {
"token in order to verify signature.");
}
-
- byte[] publicBytes = decodeBase64(ssoPublicKey);
- X509EncodedKeySpec keySpec = new X509EncodedKeySpec(publicBytes);
- KeyFactory keyFactory = KeyFactory.getInstance("RSA");
- PublicKey pubKey = keyFactory.generatePublic(keySpec);
-
try {
- claims = Jwts.parser().setSigningKey(pubKey).parseClaimsJws(token);
+ claims = Jwts.parser().setSigningKey(ssoPublicKey).parseClaimsJws(token);
} catch (SignatureException se) {
if(logger.isDebugEnabled()) {
logger.debug("Signature was invalid for Apigee JWT: {} and key: {}", token, ssoPublicKey);
@@ -196,10 +195,13 @@ public class ApigeeSSO2Provider implements ExternalSSOProvider {
throw new ExpiredTokenException(String.format("Token expired %d millisecons ago.", expirationDelta ));
}
-
}
+ public void setPublicKey( PublicKey publicKeyArg){
+ this.publicKey = publicKeyArg;
+ }
+
@Autowired
public void setManagement(ManagementService management) {
this.management = management;
@@ -208,6 +210,6 @@ public class ApigeeSSO2Provider implements ExternalSSOProvider {
@Autowired
public void setProperties(Properties properties) {
this.properties = properties;
- this.publicKey = getPublicKey(getExternalSSOUrl());
+ this.publicKey = getPublicKey(getExternalSSOUrl());
}
}
http://git-wip-us.apache.org/repos/asf/usergrid/blob/6d88bcfd/stack/services/src/main/java/org/apache/usergrid/security/tokens/cassandra/TokenServiceImpl.java
----------------------------------------------------------------------
diff --git a/stack/services/src/main/java/org/apache/usergrid/security/tokens/cassandra/TokenServiceImpl.java b/stack/services/src/main/java/org/apache/usergrid/security/tokens/cassandra/TokenServiceImpl.java
index 62d454a..46ea7fe 100644
--- a/stack/services/src/main/java/org/apache/usergrid/security/tokens/cassandra/TokenServiceImpl.java
+++ b/stack/services/src/main/java/org/apache/usergrid/security/tokens/cassandra/TokenServiceImpl.java
@@ -328,6 +328,9 @@ public class TokenServiceImpl implements TokenService {
try{
uuid = getUUIDForToken( token );
}
+ catch (ExpiredTokenException expiredTokenException){
+ throw new ExpiredTokenException(expiredTokenException.getMessage());
+ }
catch(Exception e){
// If the token doesn't parse as a Usergrid token, see if an external provider other than Usergrid is