You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@syncope.apache.org by il...@apache.org on 2017/07/06 08:35:53 UTC
[1/2] syncope git commit: [SYNCOPE-1149] Simplify
Repository: syncope
Updated Branches:
refs/heads/2_0_X 894885ba3 -> 22acb57e1
refs/heads/master 2035f6b4d -> d4cd44842
[SYNCOPE-1149] Simplify
Project: http://git-wip-us.apache.org/repos/asf/syncope/repo
Commit: http://git-wip-us.apache.org/repos/asf/syncope/commit/22acb57e
Tree: http://git-wip-us.apache.org/repos/asf/syncope/tree/22acb57e
Diff: http://git-wip-us.apache.org/repos/asf/syncope/diff/22acb57e
Branch: refs/heads/2_0_X
Commit: 22acb57e1543eb86c998f3b39e3209042922f390
Parents: 894885b
Author: Francesco Chicchiriccò <il...@apache.org>
Authored: Thu Jul 6 10:32:39 2017 +0200
Committer: Francesco Chicchiriccò <il...@apache.org>
Committed: Thu Jul 6 10:32:39 2017 +0200
----------------------------------------------------------------------
.../core/spring/security/AuthDataAccessor.java | 28 +----
.../core/spring/security/JWTAccessToken.java | 103 -------------------
.../core/spring/security/JWTSSOProvider.java | 8 +-
.../spring/security/SyncopeJWTSSOProvider.java | 30 +++++-
.../core/reference/CustomJWTSSOProvider.java | 28 +----
.../org/apache/syncope/fit/core/JWTITCase.java | 4 +-
6 files changed, 44 insertions(+), 157 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/syncope/blob/22acb57e/core/spring/src/main/java/org/apache/syncope/core/spring/security/AuthDataAccessor.java
----------------------------------------------------------------------
diff --git a/core/spring/src/main/java/org/apache/syncope/core/spring/security/AuthDataAccessor.java b/core/spring/src/main/java/org/apache/syncope/core/spring/security/AuthDataAccessor.java
index 61b9aa7..4668750 100644
--- a/core/spring/src/main/java/org/apache/syncope/core/spring/security/AuthDataAccessor.java
+++ b/core/spring/src/main/java/org/apache/syncope/core/spring/security/AuthDataAccessor.java
@@ -18,7 +18,6 @@
*/
package org.apache.syncope.core.spring.security;
-import com.fasterxml.jackson.core.type.TypeReference;
import java.util.Collections;
import java.util.Date;
import java.util.HashMap;
@@ -37,7 +36,6 @@ import org.apache.commons.lang3.tuple.Pair;
import org.apache.syncope.common.lib.SyncopeConstants;
import org.apache.syncope.common.lib.types.AnyTypeKind;
import org.apache.syncope.common.lib.types.AuditElements;
-import org.apache.syncope.common.lib.types.CipherAlgorithm;
import org.apache.syncope.common.lib.types.StandardEntitlement;
import org.apache.syncope.core.persistence.api.ImplementationLookup;
import org.apache.syncope.core.persistence.api.dao.AccessTokenDAO;
@@ -63,7 +61,6 @@ import org.apache.syncope.core.provisioning.api.AuditManager;
import org.apache.syncope.core.provisioning.api.ConnectorFactory;
import org.apache.syncope.core.provisioning.api.EntitlementsHolder;
import org.apache.syncope.core.provisioning.api.MappingManager;
-import org.apache.syncope.core.provisioning.api.serialization.POJOHelper;
import org.apache.syncope.core.provisioning.api.utils.EntityUtils;
import org.apache.syncope.core.spring.ApplicationContextProvider;
import org.identityconnectors.framework.common.objects.Uid;
@@ -404,24 +401,20 @@ public class AuthDataAccessor {
authorities = getAdminAuthorities();
} else {
JWTSSOProvider jwtSSOProvider = getJWTSSOProvider(authentication.getClaims().getIssuer());
- Pair<User, AccessToken> resolved = jwtSSOProvider.resolve(authentication.getClaims());
+ Pair<User, Set<SyncopeGrantedAuthority>> resolved = jwtSSOProvider.resolve(authentication.getClaims());
if (resolved == null || resolved.getLeft() == null) {
throw new AuthenticationCredentialsNotFoundException(
"Could not find User " + authentication.getClaims().getSubject()
+ " for JWT " + authentication.getClaims().getTokenId());
}
- if (resolved == null || resolved.getRight() == null) {
- throw new AuthenticationCredentialsNotFoundException(
- "Could not find an Access Token for JWT " + authentication.getClaims().getTokenId());
- }
User user = resolved.getLeft();
username = user.getUsername();
- AccessToken accessToken = resolved.getRight();
- LOG.debug("JWT {} issued by {} resolved to User {} and Access Token {}",
+ authorities = SetUtils.emptyIfNull(resolved.getRight());
+ LOG.debug("JWT {} issued by {} resolved to User {} with authorities {}",
authentication.getClaims().getTokenId(),
authentication.getClaims().getIssuer(),
- username, accessToken.getKey());
+ username, authorities);
if (BooleanUtils.isTrue(user.isSuspended())) {
throw new DisabledException("User " + username + " is suspended");
@@ -433,20 +426,9 @@ public class AuthDataAccessor {
}
if (BooleanUtils.isTrue(user.isMustChangePassword())) {
+ LOG.debug("User {} must change password, resetting authorities", username);
authorities = Collections.singleton(
new SyncopeGrantedAuthority(StandardEntitlement.MUST_CHANGE_PASSWORD));
- } else {
- LOG.debug("Authorities found in JWT, fetching...");
-
- try {
- authorities = POJOHelper.deserialize(
- ENCRYPTOR.decode(new String(accessToken.getAuthorities()), CipherAlgorithm.AES),
- new TypeReference<Set<SyncopeGrantedAuthority>>() {
- });
- } catch (Throwable t) {
- LOG.error("Could not read stored authorities", t);
- authorities = Collections.emptySet();
- }
}
}
http://git-wip-us.apache.org/repos/asf/syncope/blob/22acb57e/core/spring/src/main/java/org/apache/syncope/core/spring/security/JWTAccessToken.java
----------------------------------------------------------------------
diff --git a/core/spring/src/main/java/org/apache/syncope/core/spring/security/JWTAccessToken.java b/core/spring/src/main/java/org/apache/syncope/core/spring/security/JWTAccessToken.java
deleted file mode 100644
index 2ddf002..0000000
--- a/core/spring/src/main/java/org/apache/syncope/core/spring/security/JWTAccessToken.java
+++ /dev/null
@@ -1,103 +0,0 @@
-/*
- * 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.syncope.core.spring.security;
-
-import java.util.Collections;
-import java.util.Date;
-import java.util.UUID;
-import org.apache.commons.lang3.ArrayUtils;
-import org.apache.cxf.rs.security.jose.jwt.JwtClaims;
-import org.apache.syncope.common.lib.types.CipherAlgorithm;
-import org.apache.syncope.core.persistence.api.entity.AccessToken;
-import org.apache.syncope.core.provisioning.api.serialization.POJOHelper;
-
-/**
- * Convenience {@link AccessToken} implementation wrapping the received JWT, for usage with custom
- * {@link JWTSSOProvider#resolve} implementations.
- */
-public class JWTAccessToken implements AccessToken {
-
- private static final long serialVersionUID = -3824671946137458487L;
-
- private static final Encryptor ENCRYPTOR = Encryptor.getInstance();
-
- private final String key = UUID.randomUUID().toString();
-
- private final JwtClaims claims;
-
- private byte[] authorities;
-
- public JWTAccessToken(final JwtClaims claims) throws Exception {
- this.claims = claims;
- this.authorities = ENCRYPTOR.encode(
- POJOHelper.serialize(Collections.emptySet()), CipherAlgorithm.AES).
- getBytes();
- }
-
- @Override
- public String getKey() {
- return key;
- }
-
- @Override
- public String getBody() {
- return null;
- }
-
- @Override
- public Date getExpiryTime() {
- return new Date(claims.getExpiryTime());
- }
-
- @Override
- public String getOwner() {
- return claims.getSubject();
- }
-
- @Override
- public byte[] getAuthorities() {
- return authorities;
- }
-
- @Override
- public void setKey(final String key) {
- // nothing to do
- }
-
- @Override
- public void setBody(final String body) {
- // nothing to do
- }
-
- @Override
- public void setExpiryTime(final Date expiryTime) {
- // nothing to do
- }
-
- @Override
- public void setOwner(final String owner) {
- // nothing to do
- }
-
- @Override
- public void setAuthorities(final byte[] authorities) {
- this.authorities = ArrayUtils.clone(authorities);
- }
-
-}
http://git-wip-us.apache.org/repos/asf/syncope/blob/22acb57e/core/spring/src/main/java/org/apache/syncope/core/spring/security/JWTSSOProvider.java
----------------------------------------------------------------------
diff --git a/core/spring/src/main/java/org/apache/syncope/core/spring/security/JWTSSOProvider.java b/core/spring/src/main/java/org/apache/syncope/core/spring/security/JWTSSOProvider.java
index cb9ce0d..a78c2ff 100644
--- a/core/spring/src/main/java/org/apache/syncope/core/spring/security/JWTSSOProvider.java
+++ b/core/spring/src/main/java/org/apache/syncope/core/spring/security/JWTSSOProvider.java
@@ -18,10 +18,10 @@
*/
package org.apache.syncope.core.spring.security;
+import java.util.Set;
import org.apache.commons.lang3.tuple.Pair;
import org.apache.cxf.rs.security.jose.jws.JwsSignatureVerifier;
import org.apache.cxf.rs.security.jose.jwt.JwtClaims;
-import org.apache.syncope.core.persistence.api.entity.AccessToken;
import org.apache.syncope.core.persistence.api.entity.user.User;
/**
@@ -38,11 +38,11 @@ public interface JWTSSOProvider extends JwsSignatureVerifier {
String getIssuer();
/**
- * Attempts to resolve the given JWT claims into internal {@link User} and {@link AccessToken}.
+ * Attempts to resolve the given JWT claims into internal {@link User} and authorities.
* <strong>IMPORTANT</strong>: this is not invoked for the {@code}admin{@code} super-user.
*
* @param jwtClaims JWT claims
- * @return internal User and Access Token matching the provided JWT claims, if found; otherwise null
+ * @return internal User, with authorities, matching the provided JWT claims, if found; otherwise null
*/
- Pair<User, AccessToken> resolve(JwtClaims jwtClaims);
+ Pair<User, Set<SyncopeGrantedAuthority>> resolve(JwtClaims jwtClaims);
}
http://git-wip-us.apache.org/repos/asf/syncope/blob/22acb57e/core/spring/src/main/java/org/apache/syncope/core/spring/security/SyncopeJWTSSOProvider.java
----------------------------------------------------------------------
diff --git a/core/spring/src/main/java/org/apache/syncope/core/spring/security/SyncopeJWTSSOProvider.java b/core/spring/src/main/java/org/apache/syncope/core/spring/security/SyncopeJWTSSOProvider.java
index 8d561a6..f5d7852 100644
--- a/core/spring/src/main/java/org/apache/syncope/core/spring/security/SyncopeJWTSSOProvider.java
+++ b/core/spring/src/main/java/org/apache/syncope/core/spring/security/SyncopeJWTSSOProvider.java
@@ -18,6 +18,9 @@
*/
package org.apache.syncope.core.spring.security;
+import com.fasterxml.jackson.core.type.TypeReference;
+import java.util.Collections;
+import java.util.Set;
import javax.annotation.Resource;
import org.apache.commons.lang3.tuple.Pair;
import org.apache.cxf.rs.security.jose.jwa.SignatureAlgorithm;
@@ -25,10 +28,14 @@ import org.apache.cxf.rs.security.jose.jws.JwsHeaders;
import org.apache.cxf.rs.security.jose.jws.JwsSignatureVerifier;
import org.apache.cxf.rs.security.jose.jws.JwsVerificationSignature;
import org.apache.cxf.rs.security.jose.jwt.JwtClaims;
+import org.apache.syncope.common.lib.types.CipherAlgorithm;
import org.apache.syncope.core.persistence.api.dao.AccessTokenDAO;
import org.apache.syncope.core.persistence.api.dao.UserDAO;
import org.apache.syncope.core.persistence.api.entity.AccessToken;
import org.apache.syncope.core.persistence.api.entity.user.User;
+import org.apache.syncope.core.provisioning.api.serialization.POJOHelper;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.transaction.annotation.Transactional;
@@ -37,6 +44,10 @@ import org.springframework.transaction.annotation.Transactional;
*/
public class SyncopeJWTSSOProvider implements JWTSSOProvider {
+ private static final Logger LOG = LoggerFactory.getLogger(SyncopeJWTSSOProvider.class);
+
+ private static final Encryptor ENCRYPTOR = Encryptor.getInstance();
+
@Resource(name = "jwtIssuer")
private String jwtIssuer;
@@ -71,8 +82,23 @@ public class SyncopeJWTSSOProvider implements JWTSSOProvider {
@Transactional(readOnly = true)
@Override
- public Pair<User, AccessToken> resolve(final JwtClaims jwtClaims) {
- return Pair.of(userDAO.findByUsername(jwtClaims.getSubject()), accessTokenDAO.find(jwtClaims.getTokenId()));
+ public Pair<User, Set<SyncopeGrantedAuthority>> resolve(final JwtClaims jwtClaims) {
+ User user = userDAO.findByUsername(jwtClaims.getSubject());
+ Set<SyncopeGrantedAuthority> authorities = null;
+ if (user != null) {
+ AccessToken accessToken = accessTokenDAO.find(jwtClaims.getTokenId());
+ try {
+ authorities = POJOHelper.deserialize(
+ ENCRYPTOR.decode(new String(accessToken.getAuthorities()), CipherAlgorithm.AES),
+ new TypeReference<Set<SyncopeGrantedAuthority>>() {
+ });
+ } catch (Throwable t) {
+ LOG.error("Could not read stored authorities", t);
+ authorities = Collections.emptySet();
+ }
+ }
+
+ return Pair.of(user, authorities);
}
}
http://git-wip-us.apache.org/repos/asf/syncope/blob/22acb57e/fit/core-reference/src/main/java/org/apache/syncope/fit/core/reference/CustomJWTSSOProvider.java
----------------------------------------------------------------------
diff --git a/fit/core-reference/src/main/java/org/apache/syncope/fit/core/reference/CustomJWTSSOProvider.java b/fit/core-reference/src/main/java/org/apache/syncope/fit/core/reference/CustomJWTSSOProvider.java
index 61ab632..199ba24 100644
--- a/fit/core-reference/src/main/java/org/apache/syncope/fit/core/reference/CustomJWTSSOProvider.java
+++ b/fit/core-reference/src/main/java/org/apache/syncope/fit/core/reference/CustomJWTSSOProvider.java
@@ -19,6 +19,7 @@
package org.apache.syncope.fit.core.reference;
import java.util.List;
+import java.util.Set;
import org.apache.commons.lang3.tuple.Pair;
import org.apache.cxf.rs.security.jose.jwa.SignatureAlgorithm;
import org.apache.cxf.rs.security.jose.jws.HmacJwsSignatureVerifier;
@@ -27,19 +28,13 @@ import org.apache.cxf.rs.security.jose.jws.JwsSignatureVerifier;
import org.apache.cxf.rs.security.jose.jws.JwsVerificationSignature;
import org.apache.cxf.rs.security.jose.jwt.JwtClaims;
import org.apache.syncope.common.lib.types.AnyTypeKind;
-import org.apache.syncope.common.lib.types.CipherAlgorithm;
import org.apache.syncope.core.persistence.api.dao.AnySearchDAO;
import org.apache.syncope.core.persistence.api.dao.search.AttributeCond;
import org.apache.syncope.core.persistence.api.dao.search.SearchCond;
-import org.apache.syncope.core.persistence.api.entity.AccessToken;
import org.apache.syncope.core.persistence.api.entity.user.User;
-import org.apache.syncope.core.provisioning.api.serialization.POJOHelper;
import org.apache.syncope.core.spring.security.AuthDataAccessor;
-import org.apache.syncope.core.spring.security.Encryptor;
-import org.apache.syncope.core.spring.security.JWTAccessToken;
import org.apache.syncope.core.spring.security.JWTSSOProvider;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
+import org.apache.syncope.core.spring.security.SyncopeGrantedAuthority;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.transaction.annotation.Transactional;
@@ -48,10 +43,6 @@ import org.springframework.transaction.annotation.Transactional;
*/
public class CustomJWTSSOProvider implements JWTSSOProvider {
- private static final Logger LOG = LoggerFactory.getLogger(CustomJWTSSOProvider.class);
-
- private static final Encryptor ENCRYPTOR = Encryptor.getInstance();
-
public static final String ISSUER = "custom-issuer";
public static final String CUSTOM_KEY = "12345678910987654321";
@@ -90,7 +81,7 @@ public class CustomJWTSSOProvider implements JWTSSOProvider {
@Transactional(readOnly = true)
@Override
- public Pair<User, AccessToken> resolve(final JwtClaims jwtClaims) {
+ public Pair<User, Set<SyncopeGrantedAuthority>> resolve(final JwtClaims jwtClaims) {
AttributeCond userIdCond = new AttributeCond();
userIdCond.setSchema("userId");
userIdCond.setType(AttributeCond.Type.EQ);
@@ -99,18 +90,9 @@ public class CustomJWTSSOProvider implements JWTSSOProvider {
List<User> matching = searchDAO.search(SearchCond.getLeafCond(userIdCond), AnyTypeKind.USER);
if (matching.size() == 1) {
User user = matching.get(0);
+ Set<SyncopeGrantedAuthority> authorities = authDataAccessor.getAuthorities(user.getUsername());
- AccessToken accessToken = null;
- try {
- accessToken = new JWTAccessToken(jwtClaims);
- accessToken.setAuthorities(ENCRYPTOR.encode(
- POJOHelper.serialize(authDataAccessor.getAuthorities(user.getUsername())), CipherAlgorithm.AES).
- getBytes());
- } catch (Exception e) {
- LOG.error("Could not fetch or store authorities", e);
- }
-
- return Pair.of(user, accessToken);
+ return Pair.of(user, authorities);
}
return null;
http://git-wip-us.apache.org/repos/asf/syncope/blob/22acb57e/fit/core-reference/src/test/java/org/apache/syncope/fit/core/JWTITCase.java
----------------------------------------------------------------------
diff --git a/fit/core-reference/src/test/java/org/apache/syncope/fit/core/JWTITCase.java b/fit/core-reference/src/test/java/org/apache/syncope/fit/core/JWTITCase.java
index 4d9e050..5beb9b6 100644
--- a/fit/core-reference/src/test/java/org/apache/syncope/fit/core/JWTITCase.java
+++ b/fit/core-reference/src/test/java/org/apache/syncope/fit/core/JWTITCase.java
@@ -512,8 +512,8 @@ public class JWTITCase extends AbstractITCase {
JwtToken jwtToken = new JwtToken(jwsHeaders, jwtClaims);
JwsJwtCompactProducer producer = new JwsJwtCompactProducer(jwtToken);
- JwsSignatureProvider jwsSignatureProvider =
- new HmacJwsSignatureProvider((CustomJWTSSOProvider.CUSTOM_KEY + "_").getBytes(), SignatureAlgorithm.HS512);
+ JwsSignatureProvider jwsSignatureProvider = new HmacJwsSignatureProvider(
+ (CustomJWTSSOProvider.CUSTOM_KEY + "_").getBytes(), SignatureAlgorithm.HS512);
String signed = producer.signWith(jwsSignatureProvider);
SyncopeClient jwtClient = clientFactory.create(signed);
[2/2] syncope git commit: [SYNCOPE-1149] Simplify
Posted by il...@apache.org.
[SYNCOPE-1149] Simplify
Project: http://git-wip-us.apache.org/repos/asf/syncope/repo
Commit: http://git-wip-us.apache.org/repos/asf/syncope/commit/d4cd4484
Tree: http://git-wip-us.apache.org/repos/asf/syncope/tree/d4cd4484
Diff: http://git-wip-us.apache.org/repos/asf/syncope/diff/d4cd4484
Branch: refs/heads/master
Commit: d4cd448427ea2a147296159fd70712ead0a42a69
Parents: 2035f6b
Author: Francesco Chicchiriccò <il...@apache.org>
Authored: Thu Jul 6 10:32:39 2017 +0200
Committer: Francesco Chicchiriccò <il...@apache.org>
Committed: Thu Jul 6 10:32:52 2017 +0200
----------------------------------------------------------------------
.../core/spring/security/AuthDataAccessor.java | 28 +----
.../core/spring/security/JWTAccessToken.java | 103 -------------------
.../core/spring/security/JWTSSOProvider.java | 8 +-
.../spring/security/SyncopeJWTSSOProvider.java | 30 +++++-
.../core/reference/CustomJWTSSOProvider.java | 28 +----
.../org/apache/syncope/fit/core/JWTITCase.java | 4 +-
6 files changed, 44 insertions(+), 157 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/syncope/blob/d4cd4484/core/spring/src/main/java/org/apache/syncope/core/spring/security/AuthDataAccessor.java
----------------------------------------------------------------------
diff --git a/core/spring/src/main/java/org/apache/syncope/core/spring/security/AuthDataAccessor.java b/core/spring/src/main/java/org/apache/syncope/core/spring/security/AuthDataAccessor.java
index 61b9aa7..4668750 100644
--- a/core/spring/src/main/java/org/apache/syncope/core/spring/security/AuthDataAccessor.java
+++ b/core/spring/src/main/java/org/apache/syncope/core/spring/security/AuthDataAccessor.java
@@ -18,7 +18,6 @@
*/
package org.apache.syncope.core.spring.security;
-import com.fasterxml.jackson.core.type.TypeReference;
import java.util.Collections;
import java.util.Date;
import java.util.HashMap;
@@ -37,7 +36,6 @@ import org.apache.commons.lang3.tuple.Pair;
import org.apache.syncope.common.lib.SyncopeConstants;
import org.apache.syncope.common.lib.types.AnyTypeKind;
import org.apache.syncope.common.lib.types.AuditElements;
-import org.apache.syncope.common.lib.types.CipherAlgorithm;
import org.apache.syncope.common.lib.types.StandardEntitlement;
import org.apache.syncope.core.persistence.api.ImplementationLookup;
import org.apache.syncope.core.persistence.api.dao.AccessTokenDAO;
@@ -63,7 +61,6 @@ import org.apache.syncope.core.provisioning.api.AuditManager;
import org.apache.syncope.core.provisioning.api.ConnectorFactory;
import org.apache.syncope.core.provisioning.api.EntitlementsHolder;
import org.apache.syncope.core.provisioning.api.MappingManager;
-import org.apache.syncope.core.provisioning.api.serialization.POJOHelper;
import org.apache.syncope.core.provisioning.api.utils.EntityUtils;
import org.apache.syncope.core.spring.ApplicationContextProvider;
import org.identityconnectors.framework.common.objects.Uid;
@@ -404,24 +401,20 @@ public class AuthDataAccessor {
authorities = getAdminAuthorities();
} else {
JWTSSOProvider jwtSSOProvider = getJWTSSOProvider(authentication.getClaims().getIssuer());
- Pair<User, AccessToken> resolved = jwtSSOProvider.resolve(authentication.getClaims());
+ Pair<User, Set<SyncopeGrantedAuthority>> resolved = jwtSSOProvider.resolve(authentication.getClaims());
if (resolved == null || resolved.getLeft() == null) {
throw new AuthenticationCredentialsNotFoundException(
"Could not find User " + authentication.getClaims().getSubject()
+ " for JWT " + authentication.getClaims().getTokenId());
}
- if (resolved == null || resolved.getRight() == null) {
- throw new AuthenticationCredentialsNotFoundException(
- "Could not find an Access Token for JWT " + authentication.getClaims().getTokenId());
- }
User user = resolved.getLeft();
username = user.getUsername();
- AccessToken accessToken = resolved.getRight();
- LOG.debug("JWT {} issued by {} resolved to User {} and Access Token {}",
+ authorities = SetUtils.emptyIfNull(resolved.getRight());
+ LOG.debug("JWT {} issued by {} resolved to User {} with authorities {}",
authentication.getClaims().getTokenId(),
authentication.getClaims().getIssuer(),
- username, accessToken.getKey());
+ username, authorities);
if (BooleanUtils.isTrue(user.isSuspended())) {
throw new DisabledException("User " + username + " is suspended");
@@ -433,20 +426,9 @@ public class AuthDataAccessor {
}
if (BooleanUtils.isTrue(user.isMustChangePassword())) {
+ LOG.debug("User {} must change password, resetting authorities", username);
authorities = Collections.singleton(
new SyncopeGrantedAuthority(StandardEntitlement.MUST_CHANGE_PASSWORD));
- } else {
- LOG.debug("Authorities found in JWT, fetching...");
-
- try {
- authorities = POJOHelper.deserialize(
- ENCRYPTOR.decode(new String(accessToken.getAuthorities()), CipherAlgorithm.AES),
- new TypeReference<Set<SyncopeGrantedAuthority>>() {
- });
- } catch (Throwable t) {
- LOG.error("Could not read stored authorities", t);
- authorities = Collections.emptySet();
- }
}
}
http://git-wip-us.apache.org/repos/asf/syncope/blob/d4cd4484/core/spring/src/main/java/org/apache/syncope/core/spring/security/JWTAccessToken.java
----------------------------------------------------------------------
diff --git a/core/spring/src/main/java/org/apache/syncope/core/spring/security/JWTAccessToken.java b/core/spring/src/main/java/org/apache/syncope/core/spring/security/JWTAccessToken.java
deleted file mode 100644
index 2ddf002..0000000
--- a/core/spring/src/main/java/org/apache/syncope/core/spring/security/JWTAccessToken.java
+++ /dev/null
@@ -1,103 +0,0 @@
-/*
- * 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.syncope.core.spring.security;
-
-import java.util.Collections;
-import java.util.Date;
-import java.util.UUID;
-import org.apache.commons.lang3.ArrayUtils;
-import org.apache.cxf.rs.security.jose.jwt.JwtClaims;
-import org.apache.syncope.common.lib.types.CipherAlgorithm;
-import org.apache.syncope.core.persistence.api.entity.AccessToken;
-import org.apache.syncope.core.provisioning.api.serialization.POJOHelper;
-
-/**
- * Convenience {@link AccessToken} implementation wrapping the received JWT, for usage with custom
- * {@link JWTSSOProvider#resolve} implementations.
- */
-public class JWTAccessToken implements AccessToken {
-
- private static final long serialVersionUID = -3824671946137458487L;
-
- private static final Encryptor ENCRYPTOR = Encryptor.getInstance();
-
- private final String key = UUID.randomUUID().toString();
-
- private final JwtClaims claims;
-
- private byte[] authorities;
-
- public JWTAccessToken(final JwtClaims claims) throws Exception {
- this.claims = claims;
- this.authorities = ENCRYPTOR.encode(
- POJOHelper.serialize(Collections.emptySet()), CipherAlgorithm.AES).
- getBytes();
- }
-
- @Override
- public String getKey() {
- return key;
- }
-
- @Override
- public String getBody() {
- return null;
- }
-
- @Override
- public Date getExpiryTime() {
- return new Date(claims.getExpiryTime());
- }
-
- @Override
- public String getOwner() {
- return claims.getSubject();
- }
-
- @Override
- public byte[] getAuthorities() {
- return authorities;
- }
-
- @Override
- public void setKey(final String key) {
- // nothing to do
- }
-
- @Override
- public void setBody(final String body) {
- // nothing to do
- }
-
- @Override
- public void setExpiryTime(final Date expiryTime) {
- // nothing to do
- }
-
- @Override
- public void setOwner(final String owner) {
- // nothing to do
- }
-
- @Override
- public void setAuthorities(final byte[] authorities) {
- this.authorities = ArrayUtils.clone(authorities);
- }
-
-}
http://git-wip-us.apache.org/repos/asf/syncope/blob/d4cd4484/core/spring/src/main/java/org/apache/syncope/core/spring/security/JWTSSOProvider.java
----------------------------------------------------------------------
diff --git a/core/spring/src/main/java/org/apache/syncope/core/spring/security/JWTSSOProvider.java b/core/spring/src/main/java/org/apache/syncope/core/spring/security/JWTSSOProvider.java
index cb9ce0d..a78c2ff 100644
--- a/core/spring/src/main/java/org/apache/syncope/core/spring/security/JWTSSOProvider.java
+++ b/core/spring/src/main/java/org/apache/syncope/core/spring/security/JWTSSOProvider.java
@@ -18,10 +18,10 @@
*/
package org.apache.syncope.core.spring.security;
+import java.util.Set;
import org.apache.commons.lang3.tuple.Pair;
import org.apache.cxf.rs.security.jose.jws.JwsSignatureVerifier;
import org.apache.cxf.rs.security.jose.jwt.JwtClaims;
-import org.apache.syncope.core.persistence.api.entity.AccessToken;
import org.apache.syncope.core.persistence.api.entity.user.User;
/**
@@ -38,11 +38,11 @@ public interface JWTSSOProvider extends JwsSignatureVerifier {
String getIssuer();
/**
- * Attempts to resolve the given JWT claims into internal {@link User} and {@link AccessToken}.
+ * Attempts to resolve the given JWT claims into internal {@link User} and authorities.
* <strong>IMPORTANT</strong>: this is not invoked for the {@code}admin{@code} super-user.
*
* @param jwtClaims JWT claims
- * @return internal User and Access Token matching the provided JWT claims, if found; otherwise null
+ * @return internal User, with authorities, matching the provided JWT claims, if found; otherwise null
*/
- Pair<User, AccessToken> resolve(JwtClaims jwtClaims);
+ Pair<User, Set<SyncopeGrantedAuthority>> resolve(JwtClaims jwtClaims);
}
http://git-wip-us.apache.org/repos/asf/syncope/blob/d4cd4484/core/spring/src/main/java/org/apache/syncope/core/spring/security/SyncopeJWTSSOProvider.java
----------------------------------------------------------------------
diff --git a/core/spring/src/main/java/org/apache/syncope/core/spring/security/SyncopeJWTSSOProvider.java b/core/spring/src/main/java/org/apache/syncope/core/spring/security/SyncopeJWTSSOProvider.java
index 8d561a6..f5d7852 100644
--- a/core/spring/src/main/java/org/apache/syncope/core/spring/security/SyncopeJWTSSOProvider.java
+++ b/core/spring/src/main/java/org/apache/syncope/core/spring/security/SyncopeJWTSSOProvider.java
@@ -18,6 +18,9 @@
*/
package org.apache.syncope.core.spring.security;
+import com.fasterxml.jackson.core.type.TypeReference;
+import java.util.Collections;
+import java.util.Set;
import javax.annotation.Resource;
import org.apache.commons.lang3.tuple.Pair;
import org.apache.cxf.rs.security.jose.jwa.SignatureAlgorithm;
@@ -25,10 +28,14 @@ import org.apache.cxf.rs.security.jose.jws.JwsHeaders;
import org.apache.cxf.rs.security.jose.jws.JwsSignatureVerifier;
import org.apache.cxf.rs.security.jose.jws.JwsVerificationSignature;
import org.apache.cxf.rs.security.jose.jwt.JwtClaims;
+import org.apache.syncope.common.lib.types.CipherAlgorithm;
import org.apache.syncope.core.persistence.api.dao.AccessTokenDAO;
import org.apache.syncope.core.persistence.api.dao.UserDAO;
import org.apache.syncope.core.persistence.api.entity.AccessToken;
import org.apache.syncope.core.persistence.api.entity.user.User;
+import org.apache.syncope.core.provisioning.api.serialization.POJOHelper;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.transaction.annotation.Transactional;
@@ -37,6 +44,10 @@ import org.springframework.transaction.annotation.Transactional;
*/
public class SyncopeJWTSSOProvider implements JWTSSOProvider {
+ private static final Logger LOG = LoggerFactory.getLogger(SyncopeJWTSSOProvider.class);
+
+ private static final Encryptor ENCRYPTOR = Encryptor.getInstance();
+
@Resource(name = "jwtIssuer")
private String jwtIssuer;
@@ -71,8 +82,23 @@ public class SyncopeJWTSSOProvider implements JWTSSOProvider {
@Transactional(readOnly = true)
@Override
- public Pair<User, AccessToken> resolve(final JwtClaims jwtClaims) {
- return Pair.of(userDAO.findByUsername(jwtClaims.getSubject()), accessTokenDAO.find(jwtClaims.getTokenId()));
+ public Pair<User, Set<SyncopeGrantedAuthority>> resolve(final JwtClaims jwtClaims) {
+ User user = userDAO.findByUsername(jwtClaims.getSubject());
+ Set<SyncopeGrantedAuthority> authorities = null;
+ if (user != null) {
+ AccessToken accessToken = accessTokenDAO.find(jwtClaims.getTokenId());
+ try {
+ authorities = POJOHelper.deserialize(
+ ENCRYPTOR.decode(new String(accessToken.getAuthorities()), CipherAlgorithm.AES),
+ new TypeReference<Set<SyncopeGrantedAuthority>>() {
+ });
+ } catch (Throwable t) {
+ LOG.error("Could not read stored authorities", t);
+ authorities = Collections.emptySet();
+ }
+ }
+
+ return Pair.of(user, authorities);
}
}
http://git-wip-us.apache.org/repos/asf/syncope/blob/d4cd4484/fit/core-reference/src/main/java/org/apache/syncope/fit/core/reference/CustomJWTSSOProvider.java
----------------------------------------------------------------------
diff --git a/fit/core-reference/src/main/java/org/apache/syncope/fit/core/reference/CustomJWTSSOProvider.java b/fit/core-reference/src/main/java/org/apache/syncope/fit/core/reference/CustomJWTSSOProvider.java
index 61ab632..199ba24 100644
--- a/fit/core-reference/src/main/java/org/apache/syncope/fit/core/reference/CustomJWTSSOProvider.java
+++ b/fit/core-reference/src/main/java/org/apache/syncope/fit/core/reference/CustomJWTSSOProvider.java
@@ -19,6 +19,7 @@
package org.apache.syncope.fit.core.reference;
import java.util.List;
+import java.util.Set;
import org.apache.commons.lang3.tuple.Pair;
import org.apache.cxf.rs.security.jose.jwa.SignatureAlgorithm;
import org.apache.cxf.rs.security.jose.jws.HmacJwsSignatureVerifier;
@@ -27,19 +28,13 @@ import org.apache.cxf.rs.security.jose.jws.JwsSignatureVerifier;
import org.apache.cxf.rs.security.jose.jws.JwsVerificationSignature;
import org.apache.cxf.rs.security.jose.jwt.JwtClaims;
import org.apache.syncope.common.lib.types.AnyTypeKind;
-import org.apache.syncope.common.lib.types.CipherAlgorithm;
import org.apache.syncope.core.persistence.api.dao.AnySearchDAO;
import org.apache.syncope.core.persistence.api.dao.search.AttributeCond;
import org.apache.syncope.core.persistence.api.dao.search.SearchCond;
-import org.apache.syncope.core.persistence.api.entity.AccessToken;
import org.apache.syncope.core.persistence.api.entity.user.User;
-import org.apache.syncope.core.provisioning.api.serialization.POJOHelper;
import org.apache.syncope.core.spring.security.AuthDataAccessor;
-import org.apache.syncope.core.spring.security.Encryptor;
-import org.apache.syncope.core.spring.security.JWTAccessToken;
import org.apache.syncope.core.spring.security.JWTSSOProvider;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
+import org.apache.syncope.core.spring.security.SyncopeGrantedAuthority;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.transaction.annotation.Transactional;
@@ -48,10 +43,6 @@ import org.springframework.transaction.annotation.Transactional;
*/
public class CustomJWTSSOProvider implements JWTSSOProvider {
- private static final Logger LOG = LoggerFactory.getLogger(CustomJWTSSOProvider.class);
-
- private static final Encryptor ENCRYPTOR = Encryptor.getInstance();
-
public static final String ISSUER = "custom-issuer";
public static final String CUSTOM_KEY = "12345678910987654321";
@@ -90,7 +81,7 @@ public class CustomJWTSSOProvider implements JWTSSOProvider {
@Transactional(readOnly = true)
@Override
- public Pair<User, AccessToken> resolve(final JwtClaims jwtClaims) {
+ public Pair<User, Set<SyncopeGrantedAuthority>> resolve(final JwtClaims jwtClaims) {
AttributeCond userIdCond = new AttributeCond();
userIdCond.setSchema("userId");
userIdCond.setType(AttributeCond.Type.EQ);
@@ -99,18 +90,9 @@ public class CustomJWTSSOProvider implements JWTSSOProvider {
List<User> matching = searchDAO.search(SearchCond.getLeafCond(userIdCond), AnyTypeKind.USER);
if (matching.size() == 1) {
User user = matching.get(0);
+ Set<SyncopeGrantedAuthority> authorities = authDataAccessor.getAuthorities(user.getUsername());
- AccessToken accessToken = null;
- try {
- accessToken = new JWTAccessToken(jwtClaims);
- accessToken.setAuthorities(ENCRYPTOR.encode(
- POJOHelper.serialize(authDataAccessor.getAuthorities(user.getUsername())), CipherAlgorithm.AES).
- getBytes());
- } catch (Exception e) {
- LOG.error("Could not fetch or store authorities", e);
- }
-
- return Pair.of(user, accessToken);
+ return Pair.of(user, authorities);
}
return null;
http://git-wip-us.apache.org/repos/asf/syncope/blob/d4cd4484/fit/core-reference/src/test/java/org/apache/syncope/fit/core/JWTITCase.java
----------------------------------------------------------------------
diff --git a/fit/core-reference/src/test/java/org/apache/syncope/fit/core/JWTITCase.java b/fit/core-reference/src/test/java/org/apache/syncope/fit/core/JWTITCase.java
index 4d9e050..5beb9b6 100644
--- a/fit/core-reference/src/test/java/org/apache/syncope/fit/core/JWTITCase.java
+++ b/fit/core-reference/src/test/java/org/apache/syncope/fit/core/JWTITCase.java
@@ -512,8 +512,8 @@ public class JWTITCase extends AbstractITCase {
JwtToken jwtToken = new JwtToken(jwsHeaders, jwtClaims);
JwsJwtCompactProducer producer = new JwsJwtCompactProducer(jwtToken);
- JwsSignatureProvider jwsSignatureProvider =
- new HmacJwsSignatureProvider((CustomJWTSSOProvider.CUSTOM_KEY + "_").getBytes(), SignatureAlgorithm.HS512);
+ JwsSignatureProvider jwsSignatureProvider = new HmacJwsSignatureProvider(
+ (CustomJWTSSOProvider.CUSTOM_KEY + "_").getBytes(), SignatureAlgorithm.HS512);
String signed = producer.signWith(jwsSignatureProvider);
SyncopeClient jwtClient = clientFactory.create(signed);