use of com.nimbusds.openid.connect.sdk.OIDCClaimsRequest in project di-authentication-api by alphagov.
the class IPVAuthorisationHandlerTest method withAuthenticationRequest.
private AuthenticationRequest withAuthenticationRequest(String clientId) {
Scope scope = new Scope();
scope.add(OIDCScopeValue.OPENID);
var oidcClaimsRequest = new OIDCClaimsRequest().withUserInfoClaimsRequest(claimsSetRequest);
return new AuthenticationRequest.Builder(new ResponseType(ResponseType.Value.CODE), scope, new ClientID(clientId), REDIRECT_URI).state(new State()).nonce(new Nonce()).claims(oidcClaimsRequest).build();
}
use of com.nimbusds.openid.connect.sdk.OIDCClaimsRequest in project di-authentication-api by alphagov.
the class TokenHandler method handleRequest.
@Override
public APIGatewayProxyResponseEvent handleRequest(APIGatewayProxyRequestEvent input, Context context) {
return isWarming(input).orElseGet(() -> {
LOG.info("Token request received");
Optional<ErrorObject> invalidRequestParamError = tokenService.validateTokenRequestParams(input.getBody());
if (invalidRequestParamError.isPresent()) {
LOG.warn("Invalid Token Request. ErrorCode: {}. ErrorDescription: {}", invalidRequestParamError.get().getCode(), invalidRequestParamError.get().getDescription());
return generateApiGatewayProxyResponse(400, invalidRequestParamError.get().toJSONObject().toJSONString());
}
Map<String, String> requestBody = parseRequestBody(input.getBody());
String clientID = requestBody.get("client_id");
ClientRegistry client;
try {
client = clientService.getClient(clientID).orElseThrow();
} catch (NoSuchElementException e) {
LOG.warn("Client not found in Client Registry with Client ID {}", clientID);
return generateApiGatewayProxyResponse(400, OAuth2Error.INVALID_CLIENT.toJSONObject().toJSONString());
}
String baseUrl = configurationService.getBaseURL().orElseThrow(() -> {
LOG.error("Application was not configured with baseURL");
// exceptions
return new RuntimeException("Application was not configured with baseURL");
});
String tokenUrl = buildURI(baseUrl, TOKEN_PATH).toString();
Optional<ErrorObject> invalidPrivateKeyJwtError = tokenService.validatePrivateKeyJWT(input.getBody(), client.getPublicKey(), tokenUrl, clientID);
if (invalidPrivateKeyJwtError.isPresent()) {
LOG.warn("Private Key JWT is not valid for Client ID: {}", clientID);
return generateApiGatewayProxyResponse(400, invalidPrivateKeyJwtError.get().toJSONObject().toJSONString());
}
if (requestBody.get("grant_type").equals(GrantType.REFRESH_TOKEN.getValue())) {
LOG.info("Processing refresh token request");
return processRefreshTokenRequest(requestBody, client.getScopes(), new RefreshToken(requestBody.get("refresh_token")));
}
AuthCodeExchangeData authCodeExchangeData;
try {
authCodeExchangeData = authorisationCodeService.getExchangeDataForCode(requestBody.get("code")).orElseThrow();
} catch (NoSuchElementException e) {
LOG.warn("Could not retrieve client session ID from code", e);
return generateApiGatewayProxyResponse(400, OAuth2Error.INVALID_GRANT.toJSONObject().toJSONString());
}
ClientSession clientSession = clientSessionService.getClientSession(authCodeExchangeData.getClientSessionId());
AuthenticationRequest authRequest;
try {
authRequest = AuthenticationRequest.parse(clientSession.getAuthRequestParams());
} catch (ParseException e) {
LOG.warn("Could not parse authentication request from client session", e);
throw new RuntimeException(format("Unable to parse Auth Request\n Auth Request Params: %s \n Exception: %s", clientSession.getAuthRequestParams(), e));
}
if (!authRequest.getRedirectionURI().toString().equals(requestBody.get("redirect_uri"))) {
LOG.warn("Redirect URI for auth request ({}) does not match redirect URI for request body ({})", authRequest.getRedirectionURI(), requestBody.get("redirect_uri"));
return generateApiGatewayProxyResponse(400, OAuth2Error.INVALID_GRANT.toJSONObject().toJSONString());
}
UserProfile userProfile = dynamoService.getUserProfileByEmail(authCodeExchangeData.getEmail());
Subject publicSubject = ClientSubjectHelper.getSubject(userProfile, client, dynamoService);
Map<String, Object> additionalTokenClaims = new HashMap<>();
if (authRequest.getNonce() != null) {
additionalTokenClaims.put("nonce", authRequest.getNonce());
}
String vot = clientSession.getEffectiveVectorOfTrust().retrieveVectorOfTrustForToken();
OIDCClaimsRequest claimsRequest = null;
if (Objects.nonNull(clientSession.getEffectiveVectorOfTrust().getLevelOfConfidence()) && Objects.nonNull(authRequest.getOIDCClaims())) {
claimsRequest = authRequest.getOIDCClaims();
}
var tokenResponse = tokenService.generateTokenResponse(clientID, new Subject(userProfile.getSubjectID()), authRequest.getScope(), additionalTokenClaims, publicSubject, vot, userProfile.getClientConsent(), client.isConsentRequired(), claimsRequest);
clientSessionService.saveClientSession(authCodeExchangeData.getClientSessionId(), clientSession.setIdTokenHint(tokenResponse.getOIDCTokens().getIDToken().serialize()));
LOG.info("Successfully generated tokens");
return generateApiGatewayProxyResponse(200, tokenResponse.toJSONObject().toJSONString());
});
}
use of com.nimbusds.openid.connect.sdk.OIDCClaimsRequest in project di-authentication-api by alphagov.
the class AuthorizationServiceTest method shouldReturnErrorWhenValidatingAuthRequestWhichContainsInvalidClaims.
@Test
void shouldReturnErrorWhenValidatingAuthRequestWhichContainsInvalidClaims() {
ResponseType responseType = new ResponseType(ResponseType.Value.CODE);
Scope scope = new Scope();
scope.add(OIDCScopeValue.OPENID);
when(dynamoClientService.getClient(CLIENT_ID.toString())).thenReturn(Optional.of(generateClientRegistry(REDIRECT_URI.toString(), CLIENT_ID.toString())));
var claimsSetRequest = new ClaimsSetRequest().add("nickname").add("birthdate");
var oidcClaimsRequest = new OIDCClaimsRequest().withUserInfoClaimsRequest(claimsSetRequest);
AuthenticationRequest authRequest = generateAuthRequest(REDIRECT_URI.toString(), responseType, scope, jsonArrayOf("Cl.Cm", "Cl"), Optional.of(oidcClaimsRequest));
Optional<ErrorObject> errorObject = authorizationService.validateAuthRequest(authRequest);
assertThat(errorObject, equalTo(Optional.of(new ErrorObject(OAuth2Error.INVALID_REQUEST_CODE, "Request contains invalid claims"))));
}
use of com.nimbusds.openid.connect.sdk.OIDCClaimsRequest in project di-authentication-api by alphagov.
the class AuthorizationServiceTest method shouldSuccessfullyValidateAuthRequestWhenValidClaimsArePresent.
@Test
void shouldSuccessfullyValidateAuthRequestWhenValidClaimsArePresent() {
ResponseType responseType = new ResponseType(ResponseType.Value.CODE);
Scope scope = new Scope();
scope.add(OIDCScopeValue.OPENID);
when(dynamoClientService.getClient(CLIENT_ID.toString())).thenReturn(Optional.of(generateClientRegistry(REDIRECT_URI.toString(), CLIENT_ID.toString())));
var claimsSetRequest = new ClaimsSetRequest().add("name").add("birthdate");
var oidcClaimsRequest = new OIDCClaimsRequest().withUserInfoClaimsRequest(claimsSetRequest);
AuthenticationRequest authRequest = generateAuthRequest(REDIRECT_URI.toString(), responseType, scope, jsonArrayOf("Cl.Cm", "Cl"), Optional.of(oidcClaimsRequest));
Optional<ErrorObject> errorObject = authorizationService.validateAuthRequest(authRequest);
assertThat(errorObject, equalTo(Optional.empty()));
}
use of com.nimbusds.openid.connect.sdk.OIDCClaimsRequest in project di-authentication-api by alphagov.
the class TokenServiceTest method shouldOnlyIncludeIdentityClaimsInAccessTokenWhenRequested.
@Test
void shouldOnlyIncludeIdentityClaimsInAccessTokenWhenRequested() throws ParseException, JOSEException, Json.JsonException, com.nimbusds.oauth2.sdk.ParseException {
var claimsSetRequest = new ClaimsSetRequest().add("nickname").add("birthdate");
var oidcClaimsRequest = new OIDCClaimsRequest().withUserInfoClaimsRequest(claimsSetRequest);
when(configurationService.getTokenSigningKeyAlias()).thenReturn(KEY_ID);
createSignedIdToken();
createSignedAccessToken();
Map<String, Object> additionalTokenClaims = new HashMap<>();
additionalTokenClaims.put("nonce", nonce);
Set<String> claimsForListOfScopes = ValidScopes.getClaimsForListOfScopes(SCOPES_OFFLINE_ACCESS.toStringList());
OIDCTokenResponse tokenResponse = tokenService.generateTokenResponse(CLIENT_ID, INTERNAL_SUBJECT, SCOPES_OFFLINE_ACCESS, additionalTokenClaims, PUBLIC_SUBJECT, VOT, Collections.singletonList(new ClientConsent(CLIENT_ID, claimsForListOfScopes, LocalDateTime.now(ZoneId.of("UTC")).toString())), false, oidcClaimsRequest, false);
assertSuccessfullTokenResponse(tokenResponse);
assertNotNull(tokenResponse.getOIDCTokens().getRefreshToken());
assertNull(SignedJWT.parse(tokenResponse.getOIDCTokens().getRefreshToken().getValue()).getJWTClaimsSet().getClaim("claims"));
JSONArray jsonarray = JSONArrayUtils.parse(SignedJWT.parse(tokenResponse.getOIDCTokens().getAccessToken().getValue()).getJWTClaimsSet().getClaim("claims").toString());
assertTrue(jsonarray.contains("nickname"));
assertTrue(jsonarray.contains("birthdate"));
RefreshTokenStore refreshTokenStore = new RefreshTokenStore(tokenResponse.getOIDCTokens().getRefreshToken().getValue(), INTERNAL_SUBJECT.getValue());
ArgumentCaptor<String> redisKey = ArgumentCaptor.forClass(String.class);
verify(redisConnectionService).saveWithExpiry(redisKey.capture(), eq(objectMapper.writeValueAsString(refreshTokenStore)), eq(300L));
var refreshToken = SignedJWT.parse(tokenResponse.getOIDCTokens().getRefreshToken().getValue());
var jti = refreshToken.getJWTClaimsSet().getJWTID();
assertThat(redisKey.getValue(), startsWith(REFRESH_TOKEN_PREFIX));
assertThat(redisKey.getValue().split(":")[1], equalTo(jti));
}
Aggregations