Skip to content

Commit

Permalink
Merge pull request #182 from sadilchamishka/Federated-idp-logout-impr…
Browse files Browse the repository at this point in the history
…ovements

Improve federated idp initiated logout for multiple IDP sessions
  • Loading branch information
sadilchamishka authored Apr 25, 2024
2 parents 834a8d7 + 577313a commit 8d3835d
Show file tree
Hide file tree
Showing 3 changed files with 51 additions and 14 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -70,6 +70,7 @@
import static org.wso2.carbon.identity.application.authenticator.oidc.OIDCAuthenticatorConstants.BackchannelLogout.DEFAULT_IAT_VALIDITY_PERIOD;
import static org.wso2.carbon.identity.application.authenticator.oidc.OIDCAuthenticatorConstants.OIDC_BACKCHANNEL_LOGOUT_ENDPOINT_URL_PATTERN;
import static org.wso2.carbon.identity.application.authenticator.oidc.util.OIDCErrorConstants.ErrorMessages;
import static org.wso2.carbon.identity.application.common.util.IdentityApplicationConstants.RESIDENT_IDP_RESERVED_NAME;

/**
* Processes the OIDC federated idp initiated logout requests.
Expand Down Expand Up @@ -175,22 +176,26 @@ protected LogoutResponse.LogoutResponseBuilder logoutUsingSid(String sid)
if (log.isDebugEnabled()) {
log.debug(String.format("Trying federated IdP initiated logout using sid: %s.", sid));
}
FederatedUserSession federatedUserSession = getFederatedUserSessionFromSid(sid);
List<FederatedUserSession> federatedUserSessionList = getFederatedUserSessionsFromSid(sid);
String sessionId = null;
if (federatedUserSession != null) {
sessionId = federatedUserSession.getSessionId();
}
if (StringUtils.isBlank(sessionId)) {
return new LogoutResponse.LogoutResponseBuilder(HttpServletResponse.SC_OK, StringUtils.EMPTY);
}
for (FederatedUserSession federatedUserSession: federatedUserSessionList) {
if (federatedUserSession != null) {
sessionId = federatedUserSession.getSessionId();
}
if (StringUtils.isBlank(sessionId)) {
return new LogoutResponse.LogoutResponseBuilder(HttpServletResponse.SC_OK, StringUtils.EMPTY);
}

ServerSessionManagementService serverSessionManagementService =
OpenIDConnectAuthenticatorDataHolder.getInstance().getServerSessionManagementService();
serverSessionManagementService.removeSession(sessionId);
if (log.isDebugEnabled()) {
log.debug("Session terminated for session Id: " + sessionId);
ServerSessionManagementService serverSessionManagementService =
OpenIDConnectAuthenticatorDataHolder.getInstance().getServerSessionManagementService();
serverSessionManagementService.removeSession(sessionId);
removeFederatedIDPSessionMapping(sessionId);
if (log.isDebugEnabled()) {
log.debug("Session terminated for session Id: " + sessionId);
}
}


return new LogoutResponse.LogoutResponseBuilder(HttpServletResponse.SC_OK,
OIDCAuthenticatorConstants.BackchannelLogout.LOGOUT_SUCCESS);
}
Expand Down Expand Up @@ -220,6 +225,24 @@ protected FederatedUserSession getFederatedUserSessionFromSid(String sid) throws
}
}

protected List<FederatedUserSession> getFederatedUserSessionsFromSid(String sid) throws LogoutServerException {

try {
UserSessionDAO userSessionDAO = new UserSessionDAOImpl();
List<FederatedUserSession> federatedUserSession = userSessionDAO.getFederatedAuthSessionsDetails(sid);
if (federatedUserSession == null) {
if (log.isDebugEnabled()) {
log.debug(String.format("No session information found for the sid: %s. ", sid) + "Probably the " +
"session was cleared by another mechanism.");
}
return null;
}
return federatedUserSession;
} catch (SessionManagementServerException e) {
throw handleLogoutServerException(ErrorMessages.RETRIEVING_SESSION_ID_MAPPING_FAILED, e, sid);
}
}

/**
* Terminate all the sessions of the user related sub claim.
*
Expand Down Expand Up @@ -346,6 +369,10 @@ protected void validateIssuerClaim(JWTClaimsSet claimsSet) throws LogoutClientEx
*/
protected void validateAudience(List<String> aud, IdentityProvider idp) throws LogoutClientException {

// Validate audience is skipped for the resident IDP.
if (RESIDENT_IDP_RESERVED_NAME.equals(idp.getIdentityProviderName())) {
return;
}
String clientId = null;
// Get the client id from the authenticator config.
for (Property property : idp.getDefaultAuthenticatorConfig().getProperties()) {
Expand Down Expand Up @@ -691,4 +718,13 @@ private IdentityProvider getResidentIDPForIssuer(String tenantDomain, String jwt
}
return jwtIssuer.equals(issuer) ? residentIdentityProvider : null;
}

private void removeFederatedIDPSessionMapping(String sessionID) throws LogoutServerException {

try {
UserSessionStore.getInstance().removeFederatedAuthSessionInfo(sessionID);
} catch (UserSessionException e) {
throw new LogoutServerException("Exception occurred while removing federated IDP session mapping.");
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -72,6 +72,7 @@
import javax.sql.DataSource;
import javax.xml.stream.XMLInputFactory;

import static org.mockito.ArgumentMatchers.anyBoolean;
import static org.mockito.ArgumentMatchers.anyString;
import static org.mockito.Mockito.mock;
import static org.powermock.api.mockito.PowerMockito.mockStatic;
Expand Down Expand Up @@ -485,7 +486,7 @@ public void testOidcFederatedLogout() throws Exception {
DataSource dataSource = mock(DataSource.class);
mockStatic(IdentityDatabaseUtil.class);
when(IdentityDatabaseUtil.getDataSource()).thenReturn(dataSource);
when(IdentityDatabaseUtil.getDBConnection(false)).thenReturn(getConnection(DB_NAME));
when(IdentityDatabaseUtil.getDBConnection(anyBoolean())).thenReturn(getConnection(DB_NAME));
when(dataSource.getConnection()).thenReturn(getConnection(DB_NAME));

// Mock the server session management service.
Expand Down
2 changes: 1 addition & 1 deletion pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -304,7 +304,7 @@
<identity.application.auth.oidc.package.export.version>${project.version}
</identity.application.auth.oidc.package.export.version>

<carbon.identity.framework.version>7.0.93</carbon.identity.framework.version>
<carbon.identity.framework.version>7.1.39</carbon.identity.framework.version>
<oltu.version>1.0.0.wso2v3</oltu.version>
<json-smart.version>2.4.7</json-smart.version>
<json.wso2.version>3.0.0.wso2v4</json.wso2.version>
Expand Down

0 comments on commit 8d3835d

Please sign in to comment.