[KEYCLOAK-7435] Added code to delete a specific session and tests for session deletion

This commit is contained in:
Douglas Palmer 2018-07-20 09:24:03 +01:00 committed by Stian Thorgersen
parent 25b390b2ae
commit b748e269ec
3 changed files with 57 additions and 9 deletions

View file

@ -48,6 +48,7 @@ import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.zip.GZIPInputStream;
import org.apache.http.client.methods.HttpDelete;
/**
* @author <a href="mailto:sthorger@redhat.com">Stian Thorgersen</a>
@ -72,6 +73,14 @@ public class SimpleHttp {
this.method = method;
}
public static SimpleHttp doDelete(String url, KeycloakSession session) {
return doDelete(url, session.getProvider(HttpClientProvider.class).getHttpClient());
}
public static SimpleHttp doDelete(String url, HttpClient client) {
return new SimpleHttp(url, "DELETE", client);
}
public static SimpleHttp doGet(String url, KeycloakSession session) {
return doGet(url, session.getProvider(HttpClientProvider.class).getHttpClient());
}
@ -157,12 +166,17 @@ public class SimpleHttp {
private Response makeRequest() throws IOException {
boolean get = method.equals("GET");
boolean post = method.equals("POST");
boolean delete = method.equals("DELETE");
HttpRequestBase httpRequest = new HttpPost(url);
if (get) {
httpRequest = new HttpGet(appendParameterToUrl(url));
}
if (delete) {
httpRequest = new HttpDelete(appendParameterToUrl(url));
}
if (post) {
if (params != null) {
((HttpPost) httpRequest).setEntity(getFormEntityFromParameter());

View file

@ -39,14 +39,7 @@ import org.keycloak.services.messages.Messages;
import org.keycloak.services.resources.Cors;
import org.keycloak.storage.ReadOnlyException;
import javax.ws.rs.Consumes;
import javax.ws.rs.DELETE;
import javax.ws.rs.GET;
import javax.ws.rs.OPTIONS;
import javax.ws.rs.POST;
import javax.ws.rs.Path;
import javax.ws.rs.Produces;
import javax.ws.rs.QueryParam;
import javax.ws.rs.*;
import javax.ws.rs.core.Context;
import javax.ws.rs.core.HttpHeaders;
import javax.ws.rs.core.MediaType;
@ -261,12 +254,30 @@ public class AccountRestService {
return Cors.add(request, Response.ok()).auth().allowedOrigins(auth.getToken()).build();
}
/**
* Remove a specific session
*
* @param id a specific session to remove
* @return
*/
@Path("/session")
@DELETE
@Produces(MediaType.APPLICATION_JSON)
@NoCache
public Response sessionLogout(@QueryParam("id") String id) {
UserSessionModel userSession = session.sessions().getUserSession(realm, id);
if (userSession != null && userSession.getUser().equals(user)) {
AuthenticationManager.backchannelLogout(session, userSession, true);
}
return Cors.add(request, Response.ok()).auth().allowedOrigins(auth.getToken()).build();
}
@Path("/credentials")
public AccountCredentialResource credentials() {
return new AccountCredentialResource(session, event, user);
}
// TODO Federated identities
// TODO Federated identities
// TODO Applications
// TODO Logs

View file

@ -250,6 +250,29 @@ public class AccountRestServiceTest extends AbstractTestRealmKeycloakTest {
assertEquals(expectedStatus, status);
}
public void testDeleteSessions() throws IOException {
TokenUtil viewToken = new TokenUtil("view-account-access", "password");
oauth.doLogin("view-account-access", "password");
List<SessionRepresentation> sessions = SimpleHttp.doGet(getAccountUrl("sessions"), client).auth(viewToken.getToken()).asJson(new TypeReference<List<SessionRepresentation>>() {});
assertEquals(2, sessions.size());
int status = SimpleHttp.doDelete(getAccountUrl("sessions?current=false"), client).acceptJson().auth(viewToken.getToken()).asStatus();
assertEquals(200, status);
sessions = SimpleHttp.doGet(getAccountUrl("sessions"), client).auth(viewToken.getToken()).asJson(new TypeReference<List<SessionRepresentation>>() {});
assertEquals(1, sessions.size());
}
@Test
public void testDeleteSession() throws IOException {
TokenUtil viewToken = new TokenUtil("view-account-access", "password");
String sessionId = oauth.doLogin("view-account-access", "password").getSessionState();
List<SessionRepresentation> sessions = SimpleHttp.doGet(getAccountUrl("sessions"), client).auth(viewToken.getToken()).asJson(new TypeReference<List<SessionRepresentation>>() {});
assertEquals(2, sessions.size());
int status = SimpleHttp.doDelete(getAccountUrl("session?id=" + sessionId), client).acceptJson().auth(viewToken.getToken()).asStatus();
assertEquals(200, status);
sessions = SimpleHttp.doGet(getAccountUrl("sessions"), client).auth(viewToken.getToken()).asJson(new TypeReference<List<SessionRepresentation>>() {});
assertEquals(1, sessions.size());
}
private String getAccountUrl(String resource) {
return suiteContext.getAuthServerInfo().getContextRoot().toString() + "/auth/realms/test/account" + (resource != null ? "/" + resource : "");
}