OIDC Authentication
The following example shows an implementation of a client that performs OIDC authentication against
the IBM Jazz platform.
/**
* Constructor.
*/
public JazzRestClientBuilder(URI jazzUri, String user, String pw) throws IOException {
...
}
/**
* Override the createHttpClient() method to return an authenticated client.
*/
@Override /* RestClientBuilder */
protected CloseableHttpClient createHttpClient() throws Exception {
CloseableHttpClient client = super.createHttpClient();
oidcAuthenticate(client);
return client;
}
private void oidcAuthenticate(HttpClient client) throws IOException {
HttpGet request = new HttpGet(jazzUri);
request.setConfig(RequestConfig.custom().setRedirectsEnabled(false).build());
// Charset must explicitly be set to UTF-8 to handle user/pw with non-ascii characters.
request.addHeader("Content-Type", "application/x-www-form-urlencoded; charset=utf-8");
HttpResponse response = client.execute(request);
try {
int code = response.getStatusLine().getStatusCode();
// Already authenticated
if (code == SC_OK)
return;
if (code != SC_UNAUTHORIZED)
throw new RestCallException("Unexpected response during OIDC authentication: "
+ response.getStatusLine());
// x-jsa-authorization-redirect
String redirectUri = getHeader(response, "X-JSA-AUTHORIZATION-REDIRECT");
if (redirectUri == null)
throw new RestCallException("Expected a redirect URI during OIDC authentication: "
+ response.getStatusLine());
// Handle Bearer Challenge
HttpGet method = new HttpGet(redirectUri + "&prompt=none");
addDefaultOidcHeaders(method);
response = client.execute(method);
code = response.getStatusLine().getStatusCode();
if (code != SC_OK)
throw new RestCallException("Unexpected response during OIDC authentication phase 2: "
+ response.getStatusLine());
String loginRequired = getHeader(response, "X-JSA-LOGIN-REQUIRED");
if (! "true".equals(loginRequired))
throw new RestCallException("X-JSA-LOGIN-REQUIRED header not found on response during OIDC authentication phase 2: "
+ response.getStatusLine());
method = new HttpGet(redirectUri + "&prompt=none");
addDefaultOidcHeaders(method);
response = client.execute(method);
code = response.getStatusLine().getStatusCode();
if (code != SC_OK)
throw new RestCallException("Unexpected response during OIDC authentication phase 3: "
+ response.getStatusLine());
// Handle JAS Challenge
method = new HttpGet(redirectUri);
addDefaultOidcHeaders(method);
response = client.execute(method);
code = response.getStatusLine().getStatusCode();
if (code != SC_OK)
throw new RestCallException("Unexpected response during OIDC authentication phase 4: "
+ response.getStatusLine());
cookie = getHeader(response, "Set-Cookie");
Header[] defaultHeaders = new Header[] {
BasicStringHeader.of("User-Agent", "Jazz Native Client"),
BasicStringHeader.of("X-com-ibm-team-configuration-versions",
"com.ibm.team.rtc=6.0.0,com.ibm.team.jazz.foundation=6.0"),
BasicStringHeader.of("Accept", "text/json"),
BasicStringHeader.of("Authorization", "Basic "
+ StringUtils.base64EncodeToString(user + ":" + pw)),
BasicStringHeader.of("Cookie", cookie)
};
setDefaultHeaders(AList.of(defaultHeaders));
} finally {
EntityUtils.consume(response.getEntity());
}
}
private void addDefaultOidcHeaders(HttpRequestBase method) {
method.addHeader("User-Agent", "Jazz Native Client");
method.addHeader("X-com-ibm-team-configuration-versions",
"com.ibm.team.rtc=6.0.0,com.ibm.team.jazz.foundation=6.0");
method.addHeader("Accept", "text/json");
if (cookie != null) {
method.addHeader("Authorization", "Basic "
+ StringUtils.base64EncodeToString(user + ":" + pw));
method.addHeader("Cookie", cookie);
}
}