diff --git a/authz/client/src/main/java/org/keycloak/authorization/client/resource/PermissionResource.java b/authz/client/src/main/java/org/keycloak/authorization/client/resource/PermissionResource.java index aca7f56451..300f09fd84 100644 --- a/authz/client/src/main/java/org/keycloak/authorization/client/resource/PermissionResource.java +++ b/authz/client/src/main/java/org/keycloak/authorization/client/resource/PermissionResource.java @@ -237,13 +237,43 @@ public class PermissionResource { if (ticket.getId() == null) { throw new IllegalArgumentException("Permission ticket must have an id"); } - Callable callable = new Callable() { + Callable callable = new Callable() { @Override - public Object call() throws Exception { - http.put(serverConfiguration.getPermissionEndpoint()+"/ticket") + public Void call() throws Exception { + http.put(serverConfiguration.getPermissionEndpoint()+"/ticket") .json(JsonSerialization.writeValueAsBytes(ticket)) .authorizationBearer(pat.call()) - .response().json(List.class).execute(); + .response() + .execute(); + return null; + } + }; + try { + callable.call(); + } catch (Exception cause) { + Throwables.retryAndWrapExceptionIfNecessary(callable, pat, "Error updating permission ticket", cause); + } + } + + /** + * Deletes a permission ticket. + * + * @param ticket the permission ticket + */ + public void delete(final PermissionTicketRepresentation ticket) { + if (ticket == null) { + throw new IllegalArgumentException("Permission ticket must not be null or empty"); + } + if (ticket.getId() == null) { + throw new IllegalArgumentException("Permission ticket must have an id"); + } + Callable callable = new Callable() { + @Override + public Void call() throws Exception { + http.delete(serverConfiguration.getPermissionEndpoint() + "/ticket/" + ticket.getId()) + .authorizationBearer(pat.call()) + .response() + .execute(); return null; } }; diff --git a/testsuite/integration-arquillian/tests/base/src/test/java/org/keycloak/testsuite/authz/UserManagedAccessTest.java b/testsuite/integration-arquillian/tests/base/src/test/java/org/keycloak/testsuite/authz/UserManagedAccessTest.java index 4eb3717d30..8454c5ea0f 100644 --- a/testsuite/integration-arquillian/tests/base/src/test/java/org/keycloak/testsuite/authz/UserManagedAccessTest.java +++ b/testsuite/integration-arquillian/tests/base/src/test/java/org/keycloak/testsuite/authz/UserManagedAccessTest.java @@ -255,6 +255,22 @@ public class UserManagedAccessTest extends AbstractResourceServerTest { assertNotNull(permissions); assertPermissions(permissions, resource.getName(), "ScopeA", "ScopeB"); assertTrue(permissions.isEmpty()); + + + for (PermissionTicketRepresentation ticket : tickets) { + getAuthzClient().protection().permission().delete(ticket); + } + + tickets = getAuthzClient().protection().permission().find(resource.getId(), null, null, null, null, null, null, null); + + assertEquals(0, tickets.size()); + try { + + response = authorize("kolo", "password", resource.getId(), new String[] {"ScopeA", "ScopeB"}); + fail("User should not have access to resource from another user"); + } catch (AuthorizationDeniedException ade) { + + } } @Test @@ -513,6 +529,14 @@ public class UserManagedAccessTest extends AbstractResourceServerTest { for (PermissionTicketRepresentation ticket : permissionTickets) { assertTrue(ticket.isGranted()); } + + for (PermissionTicketRepresentation ticket : permissionTickets) { + permissionResource.delete(ticket); + } + + permissionTickets = permissionResource.findByResource(resource.getId()); + + assertEquals(0, permissionTickets.size()); } @Test @@ -588,10 +612,12 @@ public class UserManagedAccessTest extends AbstractResourceServerTest { for (PermissionTicketRepresentation representation : new ArrayList<>(permissionTickets)) { if (representation.isGranted()) { - permissionTickets.remove(representation); + permissionResource.delete(representation); } } + permissionTickets = permissionResource.findByResource(resource.getId()); + assertEquals(1, permissionTickets.size()); }