use of com.nimbusds.jose.JWSHeader in project tomee by apache.
the class TokenUtils method generateTokenString.
/**
* Utility method to generate a JWT string from a JSON resource file that is signed by the privateKey.pem
* test resource key, possibly with invalid fields.
*
* @param jsonResName - name of test resources file
* @param invalidClaims - the set of claims that should be added with invalid values to test failure modes
* @param timeClaims - used to return the exp, iat, auth_time claims
* @return the JWT string
* @throws Exception on parse failure
*/
public static String generateTokenString(String jsonResName, Set<InvalidClaims> invalidClaims, Map<String, Long> timeClaims) throws Exception {
if (invalidClaims == null) {
invalidClaims = Collections.emptySet();
}
InputStream contentIS = TokenUtils.class.getResourceAsStream(jsonResName);
byte[] tmp = new byte[4096];
int length = contentIS.read(tmp);
byte[] content = new byte[length];
System.arraycopy(tmp, 0, content, 0, length);
JSONParser parser = new JSONParser(DEFAULT_PERMISSIVE_MODE);
JSONObject jwtContent = (JSONObject) parser.parse(content);
// Change the issuer to INVALID_ISSUER for failure testing if requested
if (invalidClaims.contains(InvalidClaims.ISSUER)) {
jwtContent.put(Claims.iss.name(), "INVALID_ISSUER");
}
long currentTimeInSecs = currentTimeInSecs();
long exp = currentTimeInSecs + 300;
// Check for an input exp to override the default of now + 300 seconds
if (timeClaims != null && timeClaims.containsKey(Claims.exp.name())) {
exp = timeClaims.get(Claims.exp.name());
}
jwtContent.put(Claims.iat.name(), currentTimeInSecs);
jwtContent.put(Claims.auth_time.name(), currentTimeInSecs);
// If the exp claim is not updated, it will be an old value that should be seen as expired
if (!invalidClaims.contains(InvalidClaims.EXP)) {
jwtContent.put(Claims.exp.name(), exp);
}
if (timeClaims != null) {
timeClaims.put(Claims.iat.name(), currentTimeInSecs);
timeClaims.put(Claims.auth_time.name(), currentTimeInSecs);
timeClaims.put(Claims.exp.name(), exp);
}
PrivateKey pk;
if (invalidClaims.contains(InvalidClaims.SIGNER)) {
// Generate a new random private key to sign with to test invalid signatures
KeyPair keyPair = generateKeyPair(2048);
pk = keyPair.getPrivate();
} else {
// Use the test private key associated with the test public key for a valid signature
pk = readPrivateKey("/privateKey.pem");
}
// Create RSA-signer with the private key
JWSSigner signer = new RSASSASigner(pk);
JWTClaimsSet claimsSet = JWTClaimsSet.parse(jwtContent);
JWSAlgorithm alg = JWSAlgorithm.RS256;
if (invalidClaims.contains(InvalidClaims.ALG)) {
alg = JWSAlgorithm.HS256;
SecureRandom random = new SecureRandom();
BigInteger secret = BigInteger.probablePrime(256, random);
signer = new MACSigner(secret.toByteArray());
}
JWSHeader jwtHeader = new JWSHeader.Builder(alg).keyID("/privateKey.pem").type(JOSEObjectType.JWT).build();
SignedJWT signedJWT = new SignedJWT(jwtHeader, claimsSet);
signedJWT.sign(signer);
return signedJWT.serialize();
}
use of com.nimbusds.jose.JWSHeader in project tomee by apache.
the class BookstoreTest method token.
private String token(boolean managerUser) {
JSONObject claims = new JSONObject();
claims.put(Claims.iss.name(), "https://server.example.com");
claims.put(Claims.upn.name(), managerUser ? "alice@example.com" : "bob@exmaple.com");
long currentTimeInSecs = System.currentTimeMillis() / 1000;
claims.put(Claims.iat.name(), currentTimeInSecs);
claims.put(Claims.auth_time.name(), currentTimeInSecs);
claims.put(Claims.exp.name(), currentTimeInSecs + 300);
claims.put(Claims.jti.name(), "a-123");
claims.put(Claims.sub.name(), "24400320");
claims.put(Claims.preferred_username.name(), managerUser ? "alice" : "bob");
claims.put(Claims.aud.name(), "s6BhdRkqt3");
List<String> groups = new ArrayList<>();
if (managerUser) {
groups.add("manager");
groups.add("reader");
} else {
groups.add("reader");
}
claims.put(Claims.groups.name(), groups);
try {
PrivateKey pk = readPrivateKey("/privateKey.pem");
JWSHeader header = new JWSHeader.Builder(JWSAlgorithm.RS256).keyID("/privateKey.pem").type(JOSEObjectType.JWT).build();
JWTClaimsSet claimsSet = JWTClaimsSet.parse(claims);
SignedJWT jwt = new SignedJWT(header, claimsSet);
jwt.sign(new RSASSASigner(pk));
return jwt.serialize();
} catch (Exception e) {
throw new RuntimeException("Could not sign JWT");
}
}
use of com.nimbusds.jose.JWSHeader in project tomee by apache.
the class Tokens method asToken.
public String asToken(final String claims) throws Exception {
try {
final JWSHeader header = new JWSHeader.Builder(new JWSAlgorithm("RS" + hashSize, Requirement.OPTIONAL)).type(JOSEObjectType.JWT).build();
final JWTClaimsSet claimsSet = JWTClaimsSet.parse(claims);
final SignedJWT jwt = new SignedJWT(header, claimsSet);
jwt.sign(new RSASSASigner(privateKey));
return jwt.serialize();
} catch (Exception e) {
throw new RuntimeException("Could not sign JWT");
}
}
use of com.nimbusds.jose.JWSHeader in project carbon-apimgt by wso2.
the class JWTValidatorImplTest method setup.
@Before
public void setup() {
jwsHeader = new JWSHeader(this.jwsAlgorithm);
jwsHeader = new JWSHeader.Builder(jwsHeader).keyID(KeyId).build();
signedJWTInfo = new SignedJWTInfo();
signedJWT = Mockito.mock(SignedJWT.class);
signedJWTInfo.setSignedJWT(signedJWT);
Calendar now = Calendar.getInstance();
now.add(Calendar.HOUR, 1);
JSONObject transportCertHash = new JSONObject();
transportCertHash.put("x5t#S256", CERT_HASH);
JWTClaimsSet jwtClaimsSet = new JWTClaimsSet.Builder().expirationTime(now.getTime()).claim(APIConstants.CNF, transportCertHash).build();
signedJWTInfo.setJwtClaimsSet(jwtClaimsSet);
System.setProperty("javax.net.ssl.trustStore", CertificateManagerImplTest.class.getClassLoader().getResource("security/client-truststore.jks").getPath());
System.setProperty("javax.net.ssl.trustStorePassword", PASSWORD);
}
use of com.nimbusds.jose.JWSHeader in project carbon-apimgt by wso2.
the class InternalAPIKeyAuthenticator method authenticate.
@Override
public AuthenticationResponse authenticate(MessageContext synCtx) {
API retrievedApi = GatewayUtils.getAPI(synCtx);
if (retrievedApi != null) {
if (log.isDebugEnabled()) {
log.info("Internal Key Authentication initialized");
}
try {
// Extract internal from the request while removing it from the msg context.
String internalKey = extractInternalKey(synCtx);
if (StringUtils.isEmpty(internalKey)) {
return new AuthenticationResponse(false, false, true, APISecurityConstants.API_AUTH_INVALID_CREDENTIALS, APISecurityConstants.API_AUTH_INVALID_CREDENTIALS_MESSAGE);
}
OpenAPI openAPI = (OpenAPI) synCtx.getProperty(APIMgtGatewayConstants.OPEN_API_OBJECT);
if (openAPI == null && !APIConstants.GRAPHQL_API.equals(synCtx.getProperty(APIConstants.API_TYPE))) {
log.error("Swagger is missing in the gateway. " + "Therefore, Internal Key authentication cannot be performed.");
return new AuthenticationResponse(false, true, false, APISecurityConstants.API_AUTH_MISSING_OPEN_API_DEF, APISecurityConstants.API_AUTH_MISSING_OPEN_API_DEF_ERROR_MESSAGE);
}
JWTTokenPayloadInfo payloadInfo = null;
String[] splitToken = internalKey.split("\\.");
JWTClaimsSet payload;
SignedJWT signedJWT;
String tokenIdentifier;
JWSHeader jwsHeader;
String alias;
if (splitToken.length != 3) {
log.error("Internal Key does not have the format {header}.{payload}.{signature} ");
throw new APISecurityException(APISecurityConstants.API_AUTH_INVALID_CREDENTIALS, APISecurityConstants.API_AUTH_INVALID_CREDENTIALS_MESSAGE);
}
signedJWT = SignedJWT.parse(internalKey);
payload = signedJWT.getJWTClaimsSet();
tokenIdentifier = payload.getJWTID();
jwsHeader = signedJWT.getHeader();
if (jwsHeader != null && StringUtils.isNotEmpty(jwsHeader.getKeyID())) {
alias = jwsHeader.getKeyID();
} else {
alias = APIUtil.getInternalApiKeyAlias();
}
// Check if the decoded header contains type as 'InternalKey'.
if (!GatewayUtils.isInternalKey(payload)) {
if (log.isDebugEnabled()) {
log.debug("Invalid Internal Key token type. Internal Key: " + GatewayUtils.getMaskedToken(splitToken[0]));
}
log.error("Invalid Internal Key token type.");
throw new APISecurityException(APISecurityConstants.API_AUTH_INVALID_CREDENTIALS, APISecurityConstants.API_AUTH_INVALID_CREDENTIALS_MESSAGE);
}
String apiContext = (String) synCtx.getProperty(RESTConstants.REST_API_CONTEXT);
String apiVersion = (String) synCtx.getProperty(RESTConstants.SYNAPSE_REST_API_VERSION);
String httpMethod = (String) ((Axis2MessageContext) synCtx).getAxis2MessageContext().getProperty(Constants.Configuration.HTTP_METHOD);
String matchingResource = (String) synCtx.getProperty(APIConstants.API_ELECTED_RESOURCE);
String resourceCacheKey = APIUtil.getResourceInfoDTOCacheKey(apiContext, apiVersion, matchingResource, httpMethod);
VerbInfoDTO verbInfoDTO = new VerbInfoDTO();
verbInfoDTO.setHttpVerb(httpMethod);
// Not doing resource level authentication
verbInfoDTO.setAuthType(APIConstants.AUTH_NO_AUTHENTICATION);
verbInfoDTO.setRequestKey(resourceCacheKey);
verbInfoDTO.setThrottling(OpenAPIUtils.getResourceThrottlingTier(openAPI, synCtx));
List<VerbInfoDTO> verbInfoList = new ArrayList<>();
verbInfoList.add(verbInfoDTO);
synCtx.setProperty(APIConstants.VERB_INFO_DTO, verbInfoList);
String cacheKey = GatewayUtils.getAccessTokenCacheKey(tokenIdentifier, apiContext, apiVersion, matchingResource, httpMethod);
String tenantDomain = GatewayUtils.getTenantDomain();
boolean isVerified = false;
String cacheToken = (String) getGatewayInternalKeyCache().get(tokenIdentifier);
if (cacheToken != null) {
if (log.isDebugEnabled()) {
log.debug("Internal Key retrieved from the Internal Key cache.");
}
if (getGatewayInternalKeyDataCache().get(cacheKey) != null) {
// Token is found in the key cache
payloadInfo = (JWTTokenPayloadInfo) getGatewayInternalKeyDataCache().get(cacheKey);
String accessToken = payloadInfo.getAccessToken();
isVerified = accessToken.equals(internalKey);
}
} else if (getInvalidGatewayInternalKeyCache().get(tokenIdentifier) != null) {
if (log.isDebugEnabled()) {
log.debug("Internal Key retrieved from the invalid Internal Key cache. Internal Key: " + GatewayUtils.getMaskedToken(splitToken[0]));
}
log.error("Invalid Internal Key." + GatewayUtils.getMaskedToken(splitToken[0]));
throw new APISecurityException(APISecurityConstants.API_AUTH_INVALID_CREDENTIALS, APISecurityConstants.API_AUTH_INVALID_CREDENTIALS_MESSAGE);
}
// Not found in cache or caching disabled
if (!isVerified) {
if (log.isDebugEnabled()) {
log.debug("Internal Key not found in the cache.");
}
isVerified = GatewayUtils.verifyTokenSignature(signedJWT, alias) && !GatewayUtils.isJwtTokenExpired(payload);
// Add token to tenant token cache
if (isVerified) {
getGatewayInternalKeyCache().put(tokenIdentifier, tenantDomain);
} else {
getInvalidGatewayInternalKeyCache().put(tokenIdentifier, tenantDomain);
}
if (!MultitenantConstants.SUPER_TENANT_DOMAIN_NAME.equals(tenantDomain)) {
try {
// Start super tenant flow
PrivilegedCarbonContext.startTenantFlow();
PrivilegedCarbonContext.getThreadLocalCarbonContext().setTenantDomain(MultitenantConstants.SUPER_TENANT_DOMAIN_NAME, true);
// Add token to super tenant token cache
if (isVerified) {
getGatewayInternalKeyCache().put(tokenIdentifier, tenantDomain);
}
} finally {
PrivilegedCarbonContext.endTenantFlow();
}
}
}
// If Internal Key signature is verified
if (isVerified) {
if (log.isDebugEnabled()) {
log.debug("Internal Key signature is verified.");
}
if (payloadInfo != null) {
// Internal Key is found in the key cache
payload = payloadInfo.getPayload();
if (GatewayUtils.isJwtTokenExpired(payload)) {
getGatewayInternalKeyCache().remove(tokenIdentifier);
getInvalidGatewayInternalKeyCache().put(tokenIdentifier, tenantDomain);
log.error("Internal Key is expired");
throw new APISecurityException(APISecurityConstants.API_AUTH_INVALID_CREDENTIALS, APISecurityConstants.API_AUTH_INVALID_CREDENTIALS_MESSAGE);
}
} else {
// Retrieve payload from InternalKey
if (log.isDebugEnabled()) {
log.debug("InternalKey payload not found in the cache.");
}
JWTTokenPayloadInfo jwtTokenPayloadInfo = new JWTTokenPayloadInfo();
jwtTokenPayloadInfo.setPayload(payload);
jwtTokenPayloadInfo.setAccessToken(internalKey);
getGatewayInternalKeyDataCache().put(cacheKey, jwtTokenPayloadInfo);
}
JSONObject api = GatewayUtils.validateAPISubscription(apiContext, apiVersion, payload, splitToken, false);
if (log.isDebugEnabled()) {
log.debug("Internal Key authentication successful.");
}
AuthenticationContext authenticationContext = GatewayUtils.generateAuthenticationContext(tokenIdentifier, payload, api, retrievedApi.getApiTier());
APISecurityUtils.setAuthenticationContext(synCtx, authenticationContext);
if (log.isDebugEnabled()) {
log.debug("User is authorized to access the resource using Internal Key.");
}
return new AuthenticationResponse(true, true, false, 0, null);
}
if (log.isDebugEnabled()) {
log.debug("Internal Key signature verification failure. Internal Key: " + GatewayUtils.getMaskedToken(splitToken[0]));
}
log.error("Invalid Internal Key. Signature verification failed.");
throw new APISecurityException(APISecurityConstants.API_AUTH_INVALID_CREDENTIALS, APISecurityConstants.API_AUTH_INVALID_CREDENTIALS_MESSAGE);
} catch (APISecurityException e) {
return new AuthenticationResponse(false, true, false, e.getErrorCode(), e.getMessage());
} catch (ParseException e) {
log.error("Error while parsing Internal Key", e);
return new AuthenticationResponse(false, true, false, APISecurityConstants.API_AUTH_GENERAL_ERROR, APISecurityConstants.API_AUTH_GENERAL_ERROR_MESSAGE);
}
}
return new AuthenticationResponse(false, true, false, APISecurityConstants.API_AUTH_GENERAL_ERROR, APISecurityConstants.API_AUTH_GENERAL_ERROR_MESSAGE);
}
Aggregations