diff --git a/testsuite/integration-arquillian/tests/base/src/main/java/org/keycloak/testsuite/adapter/page/PhotozClientAuthzTestApp.java b/testsuite/integration-arquillian/tests/base/src/main/java/org/keycloak/testsuite/adapter/page/PhotozClientAuthzTestApp.java
index 618f66bf35..d5bcf46cf9 100644
--- a/testsuite/integration-arquillian/tests/base/src/main/java/org/keycloak/testsuite/adapter/page/PhotozClientAuthzTestApp.java
+++ b/testsuite/integration-arquillian/tests/base/src/main/java/org/keycloak/testsuite/adapter/page/PhotozClientAuthzTestApp.java
@@ -188,7 +188,6 @@ public class PhotozClientAuthzTestApp extends AbstractPageWithInjectedUrl {
public void accountPage() {
testExecutor.openAccountPage(null);
- waitForPageToLoad();
}
public void accountMyResources() {
@@ -196,7 +195,6 @@ public class PhotozClientAuthzTestApp extends AbstractPageWithInjectedUrl {
WebElement myResources = driver.findElement(By.xpath("//a[text() = 'My Resources']"));
waitUntilElement(myResources).is().clickable();
myResources.click();
- waitForPageToLoad();
}
public void accountMyResource(String name) {
@@ -204,7 +202,6 @@ public class PhotozClientAuthzTestApp extends AbstractPageWithInjectedUrl {
WebElement myResource = driver.findElement(By.id("detail-" + name));
waitUntilElement(myResource).is().clickable();
myResource.click();
- waitForPageToLoad();
}
public void accountGrantResource(String name, String requester) {
@@ -212,7 +209,6 @@ public class PhotozClientAuthzTestApp extends AbstractPageWithInjectedUrl {
WebElement grantResource = driver.findElement(By.id("grant-" + name + "-" + requester));
waitUntilElement(grantResource).is().clickable();
grantResource.click();
- waitForPageToLoad();
}
public void accountGrantRemoveScope(String name, String requester, String scope) {
@@ -220,7 +216,6 @@ public class PhotozClientAuthzTestApp extends AbstractPageWithInjectedUrl {
WebElement grantRemoveScope = driver.findElement(By.id("grant-remove-scope-" + name + "-" + requester + "-" + scope));
waitUntilElement(grantRemoveScope).is().clickable();
grantRemoveScope.click();
- waitForPageToLoad();
}
public void accountRevokeResource(String name, String requester) {
@@ -228,7 +223,6 @@ public class PhotozClientAuthzTestApp extends AbstractPageWithInjectedUrl {
WebElement revokeResource = driver.findElement(By.id("revoke-" + name + "-" + requester));
waitUntilElement(revokeResource).is().clickable();
revokeResource.click();
- waitForPageToLoad();
}
public void accountShareResource(String name, String user) {
@@ -241,7 +235,6 @@ public class PhotozClientAuthzTestApp extends AbstractPageWithInjectedUrl {
WebElement shareButton = driver.findElement(By.id("share-button"));
waitUntilElement(shareButton).is().clickable();
shareButton.click();
- waitForPageToLoad();
}
public void accountShareRemoveScope(String name, String user, String scope) {
@@ -255,13 +248,10 @@ public class PhotozClientAuthzTestApp extends AbstractPageWithInjectedUrl {
WebElement shareRemoveScope = driver.findElement(By.id("share-remove-scope-" + name + "-" + scope));
waitUntilElement(shareRemoveScope).is().clickable();
shareRemoveScope.click();
- waitForPageToLoad();
-
+
WebElement shareButton = driver.findElement(By.id("share-button"));
waitUntilElement(shareButton).is().clickable();
shareButton.click();
-
- waitForPageToLoad();
}
public void accountDenyResource(String name) {
diff --git a/testsuite/integration-arquillian/tests/base/src/test/java/org/keycloak/testsuite/adapter/example/authorization/AbstractBasePhotozExampleAdapterTest.java b/testsuite/integration-arquillian/tests/base/src/test/java/org/keycloak/testsuite/adapter/example/authorization/AbstractBasePhotozExampleAdapterTest.java
new file mode 100644
index 0000000000..fe798590a9
--- /dev/null
+++ b/testsuite/integration-arquillian/tests/base/src/test/java/org/keycloak/testsuite/adapter/example/authorization/AbstractBasePhotozExampleAdapterTest.java
@@ -0,0 +1,287 @@
+/*
+ * Copyright 2019 Red Hat, Inc. and/or its affiliates
+ * and other contributors as indicated by the @author tags.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.keycloak.testsuite.adapter.example.authorization;
+
+import static org.assertj.core.api.Assertions.assertThat;
+import static org.junit.Assert.assertFalse;
+import static org.junit.Assert.assertTrue;
+import static org.keycloak.testsuite.util.URLAssert.assertCurrentUrlStartsWith;
+import static org.keycloak.testsuite.util.WaitUtils.waitForPageToLoad;
+import static org.keycloak.testsuite.utils.io.IOUtil.loadJson;
+import static org.keycloak.testsuite.utils.io.IOUtil.loadRealm;
+
+import javax.ws.rs.core.Response;
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.FileNotFoundException;
+import java.io.IOException;
+import java.util.Arrays;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.concurrent.TimeoutException;
+import java.util.stream.Collectors;
+
+import org.apache.http.client.methods.HttpGet;
+import org.apache.http.impl.client.CloseableHttpClient;
+import org.apache.http.impl.client.HttpClientBuilder;
+import org.apache.http.impl.client.LaxRedirectStrategy;
+import org.jboss.arquillian.container.test.api.Deployer;
+import org.jboss.arquillian.graphene.page.Page;
+import org.jboss.arquillian.test.api.ArquillianResource;
+import org.junit.After;
+import org.junit.Assert;
+import org.junit.Before;
+import org.junit.Test;
+import org.keycloak.admin.client.resource.AuthorizationResource;
+import org.keycloak.admin.client.resource.ClientResource;
+import org.keycloak.admin.client.resource.ClientScopesResource;
+import org.keycloak.admin.client.resource.ClientsResource;
+import org.keycloak.admin.client.resource.PoliciesResource;
+import org.keycloak.admin.client.resource.RealmResource;
+import org.keycloak.admin.client.resource.ResourcesResource;
+import org.keycloak.admin.client.resource.RoleResource;
+import org.keycloak.admin.client.resource.UserResource;
+import org.keycloak.admin.client.resource.UsersResource;
+import org.keycloak.protocol.ProtocolMapperUtils;
+import org.keycloak.protocol.oidc.mappers.UserClientRoleMappingMapper;
+import org.keycloak.representations.idm.ClientRepresentation;
+import org.keycloak.representations.idm.ClientScopeRepresentation;
+import org.keycloak.representations.idm.ProtocolMapperRepresentation;
+import org.keycloak.representations.idm.RealmRepresentation;
+import org.keycloak.representations.idm.RoleRepresentation;
+import org.keycloak.representations.idm.UserRepresentation;
+import org.keycloak.representations.idm.authorization.PolicyRepresentation;
+import org.keycloak.representations.idm.authorization.ResourceRepresentation;
+import org.keycloak.representations.idm.authorization.ResourceServerRepresentation;
+import org.keycloak.testsuite.adapter.page.PhotozClientAuthzTestApp;
+import org.keycloak.testsuite.admin.ApiUtil;
+import org.keycloak.testsuite.arquillian.AppServerTestEnricher;
+import org.keycloak.testsuite.arquillian.annotation.UncaughtServerErrorExpected;
+import org.keycloak.testsuite.auth.page.login.OAuthGrant;
+import org.keycloak.testsuite.util.DroneUtils;
+import org.keycloak.testsuite.util.JavascriptBrowser;
+import org.keycloak.testsuite.util.javascript.JavascriptTestExecutorWithAuthorization;
+import org.keycloak.util.JsonSerialization;
+import org.openqa.selenium.JavascriptExecutor;
+import org.openqa.selenium.WebDriver;
+import org.openqa.selenium.WebElement;
+import org.openqa.selenium.support.FindBy;
+import org.wildfly.extras.creaper.core.online.CliException;
+import org.wildfly.extras.creaper.core.online.OnlineManagementClient;
+import org.wildfly.extras.creaper.core.online.operations.admin.Administration;
+
+/**
+ * @author Pedro Igor
+ */
+public abstract class AbstractBasePhotozExampleAdapterTest extends AbstractPhotozJavascriptExecutorTest {
+
+ protected static final String RESOURCE_SERVER_ID = "photoz-restful-api";
+ protected static final String ALICE_ALBUM_NAME = "Alice-Family-Album";
+ private static final int TOKEN_LIFESPAN_LEEWAY = 3; // seconds
+
+ @ArquillianResource
+ private Deployer deployer;
+
+ @Page
+ @JavascriptBrowser protected PhotozClientAuthzTestApp clientPage;
+
+ @Page
+ @JavascriptBrowser
+ private OAuthGrant oAuthGrantPage;
+
+ protected JavascriptTestExecutorWithAuthorization testExecutor;
+
+ @FindBy(id = "output")
+ @JavascriptBrowser
+ protected WebElement outputArea;
+
+ @FindBy(id = "events")
+ @JavascriptBrowser
+ protected WebElement eventsArea;
+
+ @Override
+ public void setDefaultPageUriParameters() {
+ super.setDefaultPageUriParameters();
+ testRealmPage.setAuthRealm(REALM_NAME);
+ oAuthGrantPage.setAuthRealm(REALM_NAME);
+ }
+
+ @Before
+ public void beforePhotozExampleAdapterTest() throws Exception {
+ DroneUtils.addWebDriver(jsDriver);
+ this.deployer.deploy(RESOURCE_SERVER_ID);
+
+ clientPage.navigateTo();
+// waitForPageToLoad();
+ assertCurrentUrlStartsWith(clientPage.toString());
+
+ testExecutor = JavascriptTestExecutorWithAuthorization.create(jsDriver, jsDriverTestRealmLoginPage);
+ clientPage.setTestExecutorPlayground(testExecutor, appServerContextRootPage + "/" + RESOURCE_SERVER_ID);
+ jsDriver.manage().deleteAllCookies();
+
+ try (CloseableHttpClient httpClient = HttpClientBuilder.create().setRedirectStrategy(new LaxRedirectStrategy()).build()) {
+ HttpGet request = new HttpGet(clientPage.toString() + "/unsecured/clean");
+ httpClient.execute(request).close();
+ }
+ }
+
+ // workaround for KEYCLOAK-8660 from https://stackoverflow.com/questions/50917932/what-versions-of-jackson-are-allowed-in-jboss-6-4-20-patch
+ @Before
+ public void fixBrokenDeserializationOnEAP6() throws IOException, CliException, TimeoutException, InterruptedException {
+ if (AppServerTestEnricher.isEAP6AppServer()) {
+ OnlineManagementClient client = AppServerTestEnricher.getManagementClient();
+ Administration administration = new Administration(client);
+
+ client.execute("/system-property=jackson.deserialization.whitelist.packages:add(value=org.keycloak.example.photoz)");
+ administration.reloadIfRequired();
+ }
+ }
+
+ @After
+ public void afterPhotozExampleAdapterTest() {
+ this.deployer.undeploy(RESOURCE_SERVER_ID);
+ DroneUtils.removeWebDriver();
+ }
+
+ @Override
+ public void addAdapterTestRealms(List testRealms) {
+ RealmRepresentation realm = loadRealm(new File(TEST_APPS_HOME_DIR + "/photoz/photoz-realm.json"));
+
+ realm.setAccessTokenLifespan(30 + TOKEN_LIFESPAN_LEEWAY); // seconds
+
+ testRealms.add(realm);
+ }
+
+ @Override
+ public void beforeAbstractKeycloakTest() throws Exception {
+ super.beforeAbstractKeycloakTest();
+ importResourceServerSettings();
+ }
+
+ protected List getResourcesOfUser(String username) throws FileNotFoundException {
+ return getAuthorizationResource().resources().resources().stream().filter(resource -> resource.getOwner().getName().equals(username)).collect(Collectors.toList());
+ }
+
+ protected void printUpdatedPolicies() throws FileNotFoundException {
+ log.debug("Check updated policies");
+ for (PolicyRepresentation policy : getAuthorizationResource().policies().policies()) {
+ log.debugf("Policy: %s", policy.getName());
+ for (String key : policy.getConfig().keySet()) {
+ log.debugf("-- key: %s, value: %s", key, policy.getConfig().get(key));
+ }
+ }
+ log.debug("------------------------------");
+ }
+
+ protected void assertOnTestAppUrl(WebDriver jsDriver, Object output, WebElement events) {
+ waitForPageToLoad();
+ assertCurrentUrlStartsWith(clientPage.toString(), jsDriver);
+ }
+
+ protected void assertWasDenied(Map response) {
+ assertThat(response.get("status")).isEqualTo(401L);
+ }
+
+ protected void assertWasNotDenied(Map response) {
+ assertThat(response.get("status")).isEqualTo(200L);
+ }
+
+ private void importResourceServerSettings() throws FileNotFoundException {
+ ResourceServerRepresentation authSettings = loadJson(new FileInputStream(new File(TEST_APPS_HOME_DIR + "/photoz/photoz-restful-api-authz-service.json")), ResourceServerRepresentation.class);
+
+ authSettings.getPolicies().stream()
+ .filter(x -> "Only Owner Policy".equals(x.getName()))
+ .forEach(x -> x.getConfig().put("mavenArtifactVersion", System.getProperty("project.version")));
+
+ getAuthorizationResource().importSettings(authSettings);
+ }
+
+ protected AuthorizationResource getAuthorizationResource() throws FileNotFoundException {
+ return getClientResource(RESOURCE_SERVER_ID).authorization();
+ }
+
+ protected ClientResource getClientResource(String clientId) {
+ ClientsResource clients = this.realmsResouce().realm(REALM_NAME).clients();
+ ClientRepresentation resourceServer = clients.findByClientId(clientId).get(0);
+ return clients.get(resourceServer.getId());
+ }
+
+ protected void loginToClientPage(UserRepresentation user, String... scopes) throws InterruptedException {
+ log.debugf("--logging in as {0} with password: {1}; scopes: {2}", user.getUsername(), user.getCredentials().get(0).getValue(), Arrays.toString(scopes));
+
+ if (testExecutor.isLoggedIn()) {
+ testExecutor.logout(this::assertOnTestAppUrl);
+ jsDriver.manage().deleteAllCookies();
+
+ jsDriver.navigate().to(testRealmLoginPage.toString());
+ jsDriver.manage().deleteAllCookies();
+ }
+
+ clientPage.navigateTo();
+ testExecutor.init(defaultArguments(), this::assertInitNotAuth)
+ .login(this::assertOnLoginPage)
+ .loginFormWithScopesWithPossibleConsentPage(user, this::assertOnTestAppUrl, oAuthGrantPage, scopes)
+ .init(defaultArguments(), this::assertSuccessfullyLoggedIn);
+ }
+
+ public boolean isLoaded(WebDriver w) {
+ JavascriptExecutor jsExecutor = (JavascriptExecutor) w;
+
+ Map o = (Map) jsExecutor.executeScript("return window.authorization.config");
+
+ return o != null && o.containsKey("token_endpoint");
+ }
+
+ protected void setManageAlbumScopeRequired() {
+ ClientScopeRepresentation clientScope = new ClientScopeRepresentation();
+
+ clientScope.setName("manage-albums");
+ clientScope.setProtocol("openid-connect");
+
+ ProtocolMapperRepresentation mapper = new ProtocolMapperRepresentation();
+
+ mapper.setName("manage-albums");
+ mapper.setProtocol("openid-connect");
+ mapper.setProtocolMapper(UserClientRoleMappingMapper.PROVIDER_ID);
+
+ Map config = new HashMap<>();
+ config.put("access.token.claim", "true");
+ config.put("id.token.claim", "true");
+ config.put("userinfo.token.claim", "true");
+ config.put(ProtocolMapperUtils.USER_MODEL_CLIENT_ROLE_MAPPING_CLIENT_ID, "photoz-restful-api");
+
+ mapper.setConfig(config);
+
+ clientScope.setProtocolMappers(Arrays.asList(mapper));
+
+ RealmResource realmResource = realmsResouce().realm(REALM_NAME);
+ ClientScopesResource clientScopes = realmResource.clientScopes();
+ Response resp = clientScopes.create(clientScope);
+ Assert.assertEquals(201, resp.getStatus());
+ resp.close();
+ String clientScopeId = ApiUtil.getCreatedId(resp);
+ ClientResource resourceServer = getClientResource(RESOURCE_SERVER_ID);
+ clientScopes.get(clientScopeId).getScopeMappings().clientLevel(resourceServer.toRepresentation().getId()).add(Arrays.asList(resourceServer.roles().get("manage-albums").toRepresentation()));
+ ClientResource html5ClientApp = getClientResource("photoz-html5-client");
+ html5ClientApp.addOptionalClientScope(clientScopeId);
+ html5ClientApp.getScopeMappings().realmLevel().add(Arrays.asList(realmResource.roles().get("user").toRepresentation(), realmResource.roles().get("admin").toRepresentation()));
+ ClientRepresentation clientRep = html5ClientApp.toRepresentation();
+ clientRep.setFullScopeAllowed(false);
+ html5ClientApp.update(clientRep);
+ }
+}
diff --git a/testsuite/integration-arquillian/tests/base/src/test/java/org/keycloak/testsuite/adapter/example/authorization/AbstractPhotozAccountResourcesAdapterTest.java b/testsuite/integration-arquillian/tests/base/src/test/java/org/keycloak/testsuite/adapter/example/authorization/AbstractPhotozAccountResourcesAdapterTest.java
new file mode 100644
index 0000000000..02065403f6
--- /dev/null
+++ b/testsuite/integration-arquillian/tests/base/src/test/java/org/keycloak/testsuite/adapter/example/authorization/AbstractPhotozAccountResourcesAdapterTest.java
@@ -0,0 +1,120 @@
+/*
+ * Copyright 2019 Red Hat, Inc. and/or its affiliates
+ * and other contributors as indicated by the @author tags.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.keycloak.testsuite.adapter.example.authorization;
+
+import org.junit.Test;
+
+/**
+ * @author Pedro Igor
+ */
+public abstract class AbstractPhotozAccountResourcesAdapterTest extends AbstractBasePhotozExampleAdapterTest {
+
+ @Test
+ public void testOwnerSharingResource() throws Exception {
+ loginToClientPage(aliceUser);
+ clientPage.createAlbum(ALICE_ALBUM_NAME, true);
+ clientPage.accountShareResource(ALICE_ALBUM_NAME, "jdoe");
+
+ // get back to clientPage and init javascript adapter in order to log out correctly
+ clientPage.navigateTo();
+ testExecutor.init(defaultArguments(), this::assertInitNotAuth)
+ .login()
+ .init(defaultArguments(), this::assertSuccessfullyLoggedIn);
+
+ loginToClientPage(jdoeUser);
+ clientPage.viewAlbum(ALICE_ALBUM_NAME, this::assertWasNotDenied);
+ clientPage.deleteAlbum(ALICE_ALBUM_NAME, this::assertWasNotDenied);
+
+ loginToClientPage(aliceUser);
+ clientPage.createAlbum(ALICE_ALBUM_NAME, true);
+ clientPage.accountShareRemoveScope(ALICE_ALBUM_NAME, "jdoe", "album:delete");
+
+ // get back to clientPage and init javascript adapter in order to log out correctly
+ clientPage.navigateTo();
+ testExecutor.init(defaultArguments(), this::assertInitNotAuth)
+ .login(this::assertOnTestAppUrl)
+ .init(defaultArguments(), this::assertSuccessfullyLoggedIn);
+
+ loginToClientPage(jdoeUser);
+ clientPage.viewAlbum(ALICE_ALBUM_NAME, this::assertWasNotDenied);
+ clientPage.deleteAlbum(ALICE_ALBUM_NAME, this::assertWasDenied);
+
+ loginToClientPage(aliceUser);
+ clientPage.accountRevokeResource(ALICE_ALBUM_NAME, "jdoe");
+
+ // get back to clientPage and init javascript adapter in order to log out correctly
+ clientPage.navigateTo();
+ testExecutor.init(defaultArguments(), this::assertInitNotAuth)
+ .login()
+ .init(defaultArguments(), this::assertSuccessfullyLoggedIn);
+
+ loginToClientPage(jdoeUser);
+ clientPage.viewAlbum(ALICE_ALBUM_NAME, this::assertWasDenied);
+ }
+
+ @Test
+ public void testRequestResourceToOwner() throws Exception {
+ loginToClientPage(aliceUser);
+ clientPage.createAlbum(ALICE_ALBUM_NAME, true);
+
+ loginToClientPage(jdoeUser);
+ clientPage.viewAlbum(ALICE_ALBUM_NAME, this::assertWasDenied);
+ clientPage.deleteAlbum(ALICE_ALBUM_NAME, this::assertWasDenied);
+
+ loginToClientPage(aliceUser);
+ clientPage.accountGrantResource(ALICE_ALBUM_NAME, "jdoe");
+
+ // get back to clientPage and init javascript adapter in order to log out correctly
+ clientPage.navigateTo();
+
+ testExecutor.init(defaultArguments(), this::assertInitNotAuth)
+ .login()
+ .init(defaultArguments(), this::assertSuccessfullyLoggedIn);
+
+ loginToClientPage(jdoeUser);
+ clientPage.viewAlbum(ALICE_ALBUM_NAME, this::assertWasNotDenied);
+ clientPage.deleteAlbum(ALICE_ALBUM_NAME, this::assertWasNotDenied);
+
+ loginToClientPage(aliceUser);
+ clientPage.createAlbum(ALICE_ALBUM_NAME, true);
+
+ loginToClientPage(jdoeUser);
+ clientPage.viewAlbum(ALICE_ALBUM_NAME, this::assertWasDenied);
+ clientPage.deleteAlbum(ALICE_ALBUM_NAME, this::assertWasDenied);
+
+ loginToClientPage(aliceUser);
+ clientPage.accountGrantRemoveScope(ALICE_ALBUM_NAME, "jdoe", "album:delete");
+
+ // get back to clientPage and init javascript adapter in order to navigate to accountPage again
+ clientPage.navigateTo();
+ testExecutor.init(defaultArguments(), this::assertInitNotAuth)
+ .login(this::assertOnTestAppUrl)
+ .init(defaultArguments(), this::assertSuccessfullyLoggedIn);
+ clientPage.accountGrantResource(ALICE_ALBUM_NAME, "jdoe");
+
+ // get back to clientPage and init javascript adapter in order to log out correctly
+ clientPage.navigateTo();
+ testExecutor.init(defaultArguments(), this::assertInitNotAuth)
+ .login()
+ .init(defaultArguments(), this::assertSuccessfullyLoggedIn);
+
+
+ loginToClientPage(jdoeUser);
+ clientPage.viewAlbum(ALICE_ALBUM_NAME, this::assertWasNotDenied);
+ clientPage.deleteAlbum(ALICE_ALBUM_NAME, this::assertWasDenied);
+ }
+}
diff --git a/testsuite/integration-arquillian/tests/base/src/test/java/org/keycloak/testsuite/adapter/example/authorization/AbstractPhotozExampleAdapterTest.java b/testsuite/integration-arquillian/tests/base/src/test/java/org/keycloak/testsuite/adapter/example/authorization/AbstractPhotozExampleAdapterTest.java
index 530fc057e8..05e91df02d 100644
--- a/testsuite/integration-arquillian/tests/base/src/test/java/org/keycloak/testsuite/adapter/example/authorization/AbstractPhotozExampleAdapterTest.java
+++ b/testsuite/integration-arquillian/tests/base/src/test/java/org/keycloak/testsuite/adapter/example/authorization/AbstractPhotozExampleAdapterTest.java
@@ -16,193 +16,39 @@
*/
package org.keycloak.testsuite.adapter.example.authorization;
-import org.apache.http.client.methods.HttpGet;
-import org.apache.http.impl.client.CloseableHttpClient;
-import org.apache.http.impl.client.HttpClientBuilder;
-import org.apache.http.impl.client.LaxRedirectStrategy;
-import org.jboss.arquillian.container.test.api.Deployer;
-import org.jboss.arquillian.graphene.page.Page;
-import org.jboss.arquillian.test.api.ArquillianResource;
-import org.junit.After;
-import org.junit.Assert;
-import org.junit.Before;
-import org.junit.Test;
-import org.keycloak.admin.client.resource.AuthorizationResource;
-import org.keycloak.admin.client.resource.ClientResource;
-import org.keycloak.admin.client.resource.ClientScopesResource;
-import org.keycloak.admin.client.resource.ClientsResource;
-import org.keycloak.admin.client.resource.RealmResource;
-import org.keycloak.admin.client.resource.ResourcesResource;
-import org.keycloak.admin.client.resource.RoleResource;
-import org.keycloak.admin.client.resource.UserResource;
-import org.keycloak.admin.client.resource.UsersResource;
-import org.keycloak.protocol.ProtocolMapperUtils;
-import org.keycloak.protocol.oidc.mappers.UserClientRoleMappingMapper;
-import org.keycloak.representations.idm.ClientRepresentation;
-import org.keycloak.representations.idm.ClientScopeRepresentation;
-import org.keycloak.representations.idm.ProtocolMapperRepresentation;
-import org.keycloak.representations.idm.RealmRepresentation;
-import org.keycloak.representations.idm.RoleRepresentation;
-import org.keycloak.representations.idm.UserRepresentation;
-import org.keycloak.representations.idm.authorization.PolicyRepresentation;
-import org.keycloak.representations.idm.authorization.ResourceRepresentation;
-import org.keycloak.representations.idm.authorization.ResourceServerRepresentation;
-import org.keycloak.testsuite.adapter.page.PhotozClientAuthzTestApp;
-import org.keycloak.testsuite.admin.ApiUtil;
-import org.keycloak.testsuite.arquillian.AppServerTestEnricher;
-import org.keycloak.testsuite.arquillian.annotation.UncaughtServerErrorExpected;
-import org.keycloak.testsuite.auth.page.login.OAuthGrant;
-import org.keycloak.testsuite.util.DroneUtils;
-import org.keycloak.testsuite.util.JavascriptBrowser;
-import org.keycloak.testsuite.util.javascript.JavascriptTestExecutorWithAuthorization;
-import org.keycloak.util.JsonSerialization;
-import org.openqa.selenium.JavascriptExecutor;
-import org.openqa.selenium.WebDriver;
-import org.openqa.selenium.WebElement;
-import org.openqa.selenium.support.FindBy;
-import org.openqa.selenium.support.ui.WebDriverWait;
-import org.wildfly.extras.creaper.core.online.CliException;
-import org.wildfly.extras.creaper.core.online.OnlineManagementClient;
-import org.wildfly.extras.creaper.core.online.operations.admin.Administration;
+import static org.assertj.core.api.Assertions.assertThat;
+import static org.junit.Assert.assertFalse;
+import static org.junit.Assert.assertTrue;
-import java.io.File;
-import java.io.FileInputStream;
-import java.io.FileNotFoundException;
import java.io.IOException;
import java.util.Arrays;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
-import java.util.concurrent.TimeoutException;
import java.util.stream.Collectors;
-import static org.assertj.core.api.Assertions.assertThat;
-import static org.junit.Assert.assertFalse;
-import static org.junit.Assert.assertTrue;
-import static org.keycloak.testsuite.util.URLAssert.assertCurrentUrlStartsWith;
-import static org.keycloak.testsuite.utils.io.IOUtil.loadJson;
-import static org.keycloak.testsuite.utils.io.IOUtil.loadRealm;
-import static org.keycloak.testsuite.util.WaitUtils.waitForPageToLoad;
-
-import javax.ws.rs.core.Response;
+import org.junit.Test;
+import org.keycloak.admin.client.resource.AuthorizationResource;
+import org.keycloak.admin.client.resource.ClientResource;
+import org.keycloak.admin.client.resource.PoliciesResource;
+import org.keycloak.admin.client.resource.RealmResource;
+import org.keycloak.admin.client.resource.ResourcesResource;
+import org.keycloak.admin.client.resource.RoleResource;
+import org.keycloak.admin.client.resource.UserResource;
+import org.keycloak.admin.client.resource.UsersResource;
+import org.keycloak.representations.idm.ClientRepresentation;
+import org.keycloak.representations.idm.RoleRepresentation;
+import org.keycloak.representations.idm.UserRepresentation;
+import org.keycloak.representations.idm.authorization.PolicyRepresentation;
+import org.keycloak.representations.idm.authorization.ResourceRepresentation;
+import org.keycloak.testsuite.arquillian.annotation.UncaughtServerErrorExpected;
+import org.keycloak.util.JsonSerialization;
/**
* @author Pedro Igor
*/
-public abstract class AbstractPhotozExampleAdapterTest extends AbstractPhotozJavascriptExecutorTest {
+public abstract class AbstractPhotozExampleAdapterTest extends AbstractBasePhotozExampleAdapterTest {
- protected static final String RESOURCE_SERVER_ID = "photoz-restful-api";
- protected static final String ALICE_ALBUM_NAME = "Alice-Family-Album";
- private static final int TOKEN_LIFESPAN_LEEWAY = 3; // seconds
-
- @ArquillianResource
- private Deployer deployer;
-
- @Page
- @JavascriptBrowser
- private PhotozClientAuthzTestApp clientPage;
-
- @Page
- @JavascriptBrowser
- private OAuthGrant oAuthGrantPage;
-
- private JavascriptTestExecutorWithAuthorization testExecutor;
-
- @FindBy(id = "output")
- @JavascriptBrowser
- protected WebElement outputArea;
-
- @FindBy(id = "events")
- @JavascriptBrowser
- protected WebElement eventsArea;
-
- @Override
- public void setDefaultPageUriParameters() {
- super.setDefaultPageUriParameters();
- testRealmPage.setAuthRealm(REALM_NAME);
- oAuthGrantPage.setAuthRealm(REALM_NAME);
- }
-
- @Before
- public void beforePhotozExampleAdapterTest() throws Exception {
- DroneUtils.addWebDriver(jsDriver);
- this.deployer.deploy(RESOURCE_SERVER_ID);
-
- clientPage.navigateTo();
- waitForPageToLoad();
- assertCurrentUrlStartsWith(clientPage.toString());
-
- testExecutor = JavascriptTestExecutorWithAuthorization.create(jsDriver, jsDriverTestRealmLoginPage);
- clientPage.setTestExecutorPlayground(testExecutor, appServerContextRootPage + "/" + RESOURCE_SERVER_ID);
- jsDriver.manage().deleteAllCookies();
-
- try (CloseableHttpClient httpClient = HttpClientBuilder.create().setRedirectStrategy(new LaxRedirectStrategy()).build()) {
- HttpGet request = new HttpGet(clientPage.toString() + "/unsecured/clean");
- httpClient.execute(request).close();
- }
- }
-
- // workaround for KEYCLOAK-8660 from https://stackoverflow.com/questions/50917932/what-versions-of-jackson-are-allowed-in-jboss-6-4-20-patch
- @Before
- public void fixBrokenDeserializationOnEAP6() throws IOException, CliException, TimeoutException, InterruptedException {
- if (AppServerTestEnricher.isEAP6AppServer()) {
- OnlineManagementClient client = AppServerTestEnricher.getManagementClient();
- Administration administration = new Administration(client);
-
- client.execute("/system-property=jackson.deserialization.whitelist.packages:add(value=org.keycloak.example.photoz)");
- administration.reloadIfRequired();
- }
- }
-
- @After
- public void afterPhotozExampleAdapterTest() {
- this.deployer.undeploy(RESOURCE_SERVER_ID);
- DroneUtils.removeWebDriver();
- }
-
- @Override
- public void addAdapterTestRealms(List testRealms) {
- RealmRepresentation realm = loadRealm(new File(TEST_APPS_HOME_DIR + "/photoz/photoz-realm.json"));
-
- realm.setAccessTokenLifespan(30 + TOKEN_LIFESPAN_LEEWAY); // seconds
-
- testRealms.add(realm);
- }
-
- @Override
- public void beforeAbstractKeycloakTest() throws Exception {
- super.beforeAbstractKeycloakTest();
- importResourceServerSettings();
- }
-
- private List getResourcesOfUser(String username) throws FileNotFoundException {
- return getAuthorizationResource().resources().resources().stream().filter(resource -> resource.getOwner().getName().equals(username)).collect(Collectors.toList());
- }
-
- private void printUpdatedPolicies() throws FileNotFoundException {
- log.debug("Check updated policies");
- for (PolicyRepresentation policy : getAuthorizationResource().policies().policies()) {
- log.debugf("Policy: %s", policy.getName());
- for (String key : policy.getConfig().keySet()) {
- log.debugf("-- key: %s, value: %s", key, policy.getConfig().get(key));
- }
- }
- log.debug("------------------------------");
- }
-
- private void assertOnTestAppUrl(WebDriver jsDriver, Object output, WebElement events) {
- waitForPageToLoad();
- assertCurrentUrlStartsWith(clientPage.toString(), jsDriver);
- }
-
- private void assertWasDenied(Map response) {
- assertThat(response.get("status")).isEqualTo(401L);
- }
-
- private void assertWasNotDenied(Map response) {
- assertThat(response.get("status")).isEqualTo(200L);
- }
-
@Test
public void testUserCanCreateAndDeleteAlbum() throws Exception {
loginToClientPage(aliceUser);
@@ -309,10 +155,12 @@ public abstract class AbstractPhotozExampleAdapterTest extends AbstractPhotozJav
clientPage.viewAlbum(ALICE_ALBUM_NAME, this::assertWasNotDenied);
- for (PolicyRepresentation policy : getAuthorizationResource().policies().policies()) {
+ PoliciesResource policiesResource = getAuthorizationResource().policies();
+ List policies = policiesResource.policies();
+ for (PolicyRepresentation policy : policies) {
if ("Album Resource Permission".equals(policy.getName())) {
policy.getConfig().put("applyPolicies", "[\"Any User Policy\"]");
- getAuthorizationResource().policies().policy(policy.getId()).update(policy);
+ policiesResource.policy(policy.getId()).update(policy);
}
if ("Any User Policy".equals(policy.getName())) {
ClientResource resourceServerClient = getClientResource(RESOURCE_SERVER_ID);
@@ -324,7 +172,7 @@ public abstract class AbstractPhotozExampleAdapterTest extends AbstractPhotozJav
policy.getConfig().put("roles", JsonSerialization.writeValueAsString(roles));
- getAuthorizationResource().policies().policy(policy.getId()).update(policy);
+ policiesResource.policy(policy.getId()).update(policy);
}
}
printUpdatedPolicies();
@@ -334,23 +182,19 @@ public abstract class AbstractPhotozExampleAdapterTest extends AbstractPhotozJav
clientPage.navigateToAdminAlbum(this::assertWasNotDenied);
clientPage.viewAlbum(ALICE_ALBUM_NAME, this::assertWasDenied);
- clientPage.navigateToAdminAlbum(this::assertWasNotDenied);
clientPage.deleteAlbum(ALICE_ALBUM_NAME, this::assertWasDenied);
- for (PolicyRepresentation policy : getAuthorizationResource().policies().policies()) {
+ for (PolicyRepresentation policy : policies) {
if ("Album Resource Permission".equals(policy.getName())) {
policy.getConfig().put("applyPolicies", "[\"Any User Policy\", \"Administration Policy\"]");
- getAuthorizationResource().policies().policy(policy.getId()).update(policy);
+ policiesResource.policy(policy.getId()).update(policy);
}
}
printUpdatedPolicies();
loginToClientPage(adminUser); // Clear cache
- clientPage.navigateToAdminAlbum(this::assertWasNotDenied);
clientPage.viewAlbum(ALICE_ALBUM_NAME, this::assertWasNotDenied);
-
- clientPage.navigateToAdminAlbum(this::assertWasNotDenied);
clientPage.deleteAlbum(ALICE_ALBUM_NAME, this::assertWasNotDenied);
assertThat(getResourcesOfUser("alice")).isEmpty();
}
@@ -366,11 +210,13 @@ public abstract class AbstractPhotozExampleAdapterTest extends AbstractPhotozJav
clientPage.deleteAlbum(ALICE_ALBUM_NAME, this::assertWasNotDenied);
assertThat(getResourcesOfUser("alice")).isEmpty();
-
- for (PolicyRepresentation policy : getAuthorizationResource().policies().policies()) {
+
+ PoliciesResource policiesResource = getAuthorizationResource().policies();
+ List policies = policiesResource.policies();
+ for (PolicyRepresentation policy : policies) {
if ("Delete Album Permission".equals(policy.getName())) {
policy.getConfig().put("applyPolicies", "[\"Only Owner Policy\"]");
- getAuthorizationResource().policies().policy(policy.getId()).update(policy);
+ policiesResource.policy(policy.getId()).update(policy);
}
}
printUpdatedPolicies();
@@ -379,24 +225,21 @@ public abstract class AbstractPhotozExampleAdapterTest extends AbstractPhotozJav
clientPage.createAlbum(ALICE_ALBUM_NAME);
loginToClientPage(adminUser);
- clientPage.navigateToAdminAlbum(this::assertWasNotDenied);
clientPage.viewAlbum(ALICE_ALBUM_NAME, this::assertWasNotDenied);
assertThat(getResourcesOfUser("alice")).isNotEmpty();
- clientPage.navigateToAdminAlbum(this::assertWasNotDenied);
clientPage.deleteAlbum(ALICE_ALBUM_NAME, this::assertWasDenied);
- for (PolicyRepresentation policy : getAuthorizationResource().policies().policies()) {
+ for (PolicyRepresentation policy : policies) {
if ("Delete Album Permission".equals(policy.getName())) {
policy.getConfig().put("applyPolicies", "[\"Only Owner and Administrators Policy\"]");
- getAuthorizationResource().policies().policy(policy.getId()).update(policy);
+ policiesResource.policy(policy.getId()).update(policy);
}
}
printUpdatedPolicies();
loginToClientPage(adminUser); // Clear cache
- clientPage.navigateToAdminAlbum(this::assertWasNotDenied);
clientPage.deleteAlbum(ALICE_ALBUM_NAME, this::assertWasNotDenied);
assertThat(getResourcesOfUser("alice")).isEmpty();
}
@@ -501,7 +344,8 @@ public abstract class AbstractPhotozExampleAdapterTest extends AbstractPhotozJav
loginToClientPage(aliceUser);
clientPage.createAlbum(resourceName);
- getAuthorizationResource().resources().resources().forEach(resource -> {
+ AuthorizationResource authorizationResource = getAuthorizationResource();
+ authorizationResource.resources().resources().forEach(resource -> {
if (resource.getName().equals(resourceName)) {
try {
PolicyRepresentation resourceInstancePermission = new PolicyRepresentation();
@@ -515,7 +359,7 @@ public abstract class AbstractPhotozExampleAdapterTest extends AbstractPhotozJav
config.put("applyPolicies", JsonSerialization.writeValueAsString(Arrays.asList("Only Owner Policy")));
resourceInstancePermission.setConfig(config);
- getAuthorizationResource().policies().create(resourceInstancePermission);
+ authorizationResource.policies().create(resourceInstancePermission);
} catch (IOException e) {
throw new RuntimeException("Error creating policy.", e);
}
@@ -577,7 +421,6 @@ public abstract class AbstractPhotozExampleAdapterTest extends AbstractPhotozJav
loginToClientPage(adminUser);
- clientPage.navigateToAdminAlbum(this::assertWasNotDenied);
clientPage.viewAlbum(RESOURCE_NAME, this::assertWasDenied);
clientPage.deleteAlbum(RESOURCE_NAME, this::assertWasDenied);
@@ -590,7 +433,6 @@ public abstract class AbstractPhotozExampleAdapterTest extends AbstractPhotozJav
loginToClientPage(adminUser);
- clientPage.navigateToAdminAlbum(this::assertWasNotDenied);
clientPage.viewAlbum(RESOURCE_NAME, this::assertWasNotDenied);
clientPage.deleteAlbum(RESOURCE_NAME, this::assertWasDenied);
@@ -606,10 +448,10 @@ public abstract class AbstractPhotozExampleAdapterTest extends AbstractPhotozJav
public void testEntitlementRequest() throws Exception {
loginToClientPage(adminUser);
- clientPage.requestEntitlements((driver1, output, events) -> assertThat((String)output).contains("admin:manage"));
+ clientPage.requestEntitlements((driver1, output, events) -> assertThat((String) output).contains("admin:manage"));
loginToClientPage(adminUser);
- clientPage.requestEntitlement((driver1, output, events) -> assertThat((String)output)
+ clientPage.requestEntitlement((driver1, output, events) -> assertThat((String) output)
.doesNotContain("admin:manage")
.contains("album:view")
.contains("album:delete")
@@ -625,187 +467,4 @@ public abstract class AbstractPhotozExampleAdapterTest extends AbstractPhotozJav
assertThat(response.get("status")).isIn(404L, 0L); // PhantomJS returns 0 and chrome 404
});
}
-
-
- @Test
- public void testRequestResourceToOwner() throws Exception {
- loginToClientPage(aliceUser);
- clientPage.createAlbum(ALICE_ALBUM_NAME, true);
-
- loginToClientPage(jdoeUser);
- clientPage.viewAlbum(ALICE_ALBUM_NAME, this::assertWasDenied);
- clientPage.deleteAlbum(ALICE_ALBUM_NAME, this::assertWasDenied);
-
- loginToClientPage(aliceUser);
- clientPage.accountGrantResource(ALICE_ALBUM_NAME, "jdoe");
-
- // get back to clientPage and init javascript adapter in order to log out correctly
- clientPage.navigateTo();
-
- testExecutor.init(defaultArguments(), this::assertInitNotAuth)
- .login()
- .init(defaultArguments(), this::assertSuccessfullyLoggedIn);
-
- loginToClientPage(jdoeUser);
- clientPage.viewAlbum(ALICE_ALBUM_NAME, this::assertWasNotDenied);
- clientPage.deleteAlbum(ALICE_ALBUM_NAME, this::assertWasNotDenied);
-
- loginToClientPage(aliceUser);
- clientPage.createAlbum(ALICE_ALBUM_NAME, true);
-
- loginToClientPage(jdoeUser);
- clientPage.viewAlbum(ALICE_ALBUM_NAME, this::assertWasDenied);
- clientPage.deleteAlbum(ALICE_ALBUM_NAME, this::assertWasDenied);
-
- loginToClientPage(aliceUser);
- clientPage.accountGrantRemoveScope(ALICE_ALBUM_NAME, "jdoe", "album:delete");
-
- // get back to clientPage and init javascript adapter in order to navigate to accountPage again
- clientPage.navigateTo();
- testExecutor.init(defaultArguments(), this::assertInitNotAuth)
- .login(this::assertOnTestAppUrl)
- .init(defaultArguments(), this::assertSuccessfullyLoggedIn);
- clientPage.accountGrantResource(ALICE_ALBUM_NAME, "jdoe");
-
- // get back to clientPage and init javascript adapter in order to log out correctly
- clientPage.navigateTo();
- testExecutor.init(defaultArguments(), this::assertInitNotAuth)
- .login()
- .init(defaultArguments(), this::assertSuccessfullyLoggedIn);
-
-
- loginToClientPage(jdoeUser);
- clientPage.viewAlbum(ALICE_ALBUM_NAME, this::assertWasNotDenied);
- clientPage.deleteAlbum(ALICE_ALBUM_NAME, this::assertWasDenied);
- }
-
- @Test
- public void testOwnerSharingResource() throws Exception {
- loginToClientPage(aliceUser);
- clientPage.createAlbum(ALICE_ALBUM_NAME, true);
- clientPage.accountShareResource(ALICE_ALBUM_NAME, "jdoe");
-
- // get back to clientPage and init javascript adapter in order to log out correctly
- clientPage.navigateTo();
- testExecutor.init(defaultArguments(), this::assertInitNotAuth)
- .login()
- .init(defaultArguments(), this::assertSuccessfullyLoggedIn);
-
- loginToClientPage(jdoeUser);
- clientPage.viewAlbum(ALICE_ALBUM_NAME, this::assertWasNotDenied);
- clientPage.deleteAlbum(ALICE_ALBUM_NAME, this::assertWasNotDenied);
-
- loginToClientPage(aliceUser);
- clientPage.createAlbum(ALICE_ALBUM_NAME, true);
- clientPage.accountShareRemoveScope(ALICE_ALBUM_NAME, "jdoe", "album:delete");
-
- // get back to clientPage and init javascript adapter in order to log out correctly
- clientPage.navigateTo();
- testExecutor.init(defaultArguments(), this::assertInitNotAuth)
- .login(this::assertOnTestAppUrl)
- .init(defaultArguments(), this::assertSuccessfullyLoggedIn);
-
- loginToClientPage(jdoeUser);
- clientPage.viewAlbum(ALICE_ALBUM_NAME, this::assertWasNotDenied);
- clientPage.deleteAlbum(ALICE_ALBUM_NAME, this::assertWasDenied);
-
- loginToClientPage(aliceUser);
- clientPage.accountRevokeResource(ALICE_ALBUM_NAME, "jdoe");
-
- // get back to clientPage and init javascript adapter in order to log out correctly
- clientPage.navigateTo();
- testExecutor.init(defaultArguments(), this::assertInitNotAuth)
- .login()
- .init(defaultArguments(), this::assertSuccessfullyLoggedIn);
-
- loginToClientPage(jdoeUser);
- clientPage.viewAlbum(ALICE_ALBUM_NAME, this::assertWasDenied);
- }
-
- private void importResourceServerSettings() throws FileNotFoundException {
- ResourceServerRepresentation authSettings = loadJson(new FileInputStream(new File(TEST_APPS_HOME_DIR + "/photoz/photoz-restful-api-authz-service.json")), ResourceServerRepresentation.class);
-
- authSettings.getPolicies().stream()
- .filter(x -> "Only Owner Policy".equals(x.getName()))
- .forEach(x -> x.getConfig().put("mavenArtifactVersion", System.getProperty("project.version")));
-
- getAuthorizationResource().importSettings(authSettings);
- }
-
- private AuthorizationResource getAuthorizationResource() throws FileNotFoundException {
- return getClientResource(RESOURCE_SERVER_ID).authorization();
- }
-
- private ClientResource getClientResource(String clientId) {
- ClientsResource clients = this.realmsResouce().realm(REALM_NAME).clients();
- ClientRepresentation resourceServer = clients.findByClientId(clientId).get(0);
- return clients.get(resourceServer.getId());
- }
-
- private void loginToClientPage(UserRepresentation user, String... scopes) throws InterruptedException {
- log.debugf("--logging in as {0} with password: {1}; scopes: {2}", user.getUsername(), user.getCredentials().get(0).getValue(), Arrays.toString(scopes));
-
- if (testExecutor.isLoggedIn()) {
- testExecutor.logout(this::assertOnTestAppUrl);
- jsDriver.manage().deleteAllCookies();
-
- jsDriver.navigate().to(testRealmLoginPage.toString());
- waitForPageToLoad();
- jsDriver.manage().deleteAllCookies();
- }
-
- clientPage.navigateTo();
- testExecutor.init(defaultArguments(), this::assertInitNotAuth)
- .login(this::assertOnLoginPage)
- .loginFormWithScopesWithPossibleConsentPage(user, this::assertOnTestAppUrl, oAuthGrantPage, scopes)
- .init(defaultArguments(), this::assertSuccessfullyLoggedIn);
-
- new WebDriverWait(jsDriver, 10).until(this::isLoaded);
- }
-
- public boolean isLoaded(WebDriver w) {
- JavascriptExecutor jsExecutor = (JavascriptExecutor) w;
-
- Map o = (Map) jsExecutor.executeScript("return window.authorization.config");
-
- return o != null && o.containsKey("token_endpoint");
- }
-
- private void setManageAlbumScopeRequired() {
- ClientScopeRepresentation clientScope = new ClientScopeRepresentation();
-
- clientScope.setName("manage-albums");
- clientScope.setProtocol("openid-connect");
-
- ProtocolMapperRepresentation mapper = new ProtocolMapperRepresentation();
-
- mapper.setName("manage-albums");
- mapper.setProtocol("openid-connect");
- mapper.setProtocolMapper(UserClientRoleMappingMapper.PROVIDER_ID);
-
- Map config = new HashMap<>();
- config.put("access.token.claim", "true");
- config.put("id.token.claim", "true");
- config.put("userinfo.token.claim", "true");
- config.put(ProtocolMapperUtils.USER_MODEL_CLIENT_ROLE_MAPPING_CLIENT_ID, "photoz-restful-api");
-
- mapper.setConfig(config);
-
- clientScope.setProtocolMappers(Arrays.asList(mapper));
-
- RealmResource realmResource = realmsResouce().realm(REALM_NAME);
- ClientScopesResource clientScopes = realmResource.clientScopes();
- Response resp = clientScopes.create(clientScope);
- Assert.assertEquals(201, resp.getStatus());
- resp.close();
- String clientScopeId = ApiUtil.getCreatedId(resp);
- ClientResource resourceServer = getClientResource(RESOURCE_SERVER_ID);
- clientScopes.get(clientScopeId).getScopeMappings().clientLevel(resourceServer.toRepresentation().getId()).add(Arrays.asList(resourceServer.roles().get("manage-albums").toRepresentation()));
- ClientResource html5ClientApp = getClientResource("photoz-html5-client");
- html5ClientApp.addOptionalClientScope(clientScopeId);
- html5ClientApp.getScopeMappings().realmLevel().add(Arrays.asList(realmResource.roles().get("user").toRepresentation(), realmResource.roles().get("admin").toRepresentation()));
- ClientRepresentation clientRep = html5ClientApp.toRepresentation();
- clientRep.setFullScopeAllowed(false);
- html5ClientApp.update(clientRep);
- }
}
diff --git a/testsuite/integration-arquillian/tests/base/src/test/java/org/keycloak/testsuite/adapter/example/authorization/PhotozAccountResourcesAdapterTest.java b/testsuite/integration-arquillian/tests/base/src/test/java/org/keycloak/testsuite/adapter/example/authorization/PhotozAccountResourcesAdapterTest.java
new file mode 100644
index 0000000000..d2336ab0b5
--- /dev/null
+++ b/testsuite/integration-arquillian/tests/base/src/test/java/org/keycloak/testsuite/adapter/example/authorization/PhotozAccountResourcesAdapterTest.java
@@ -0,0 +1,49 @@
+/*
+ * Copyright 2019 Red Hat, Inc. and/or its affiliates
+ * and other contributors as indicated by the @author tags.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.keycloak.testsuite.adapter.example.authorization;
+
+import java.io.File;
+import java.io.IOException;
+
+import org.jboss.arquillian.container.test.api.Deployment;
+import org.jboss.shrinkwrap.api.spec.WebArchive;
+import org.keycloak.testsuite.adapter.page.PhotozClientAuthzTestApp;
+import org.keycloak.testsuite.arquillian.annotation.AppServerContainer;
+import org.keycloak.testsuite.utils.arquillian.ContainerConstants;
+
+/**
+ * @author Pedro Igor
+ */
+@AppServerContainer(ContainerConstants.APP_SERVER_WILDFLY)
+@AppServerContainer(ContainerConstants.APP_SERVER_WILDFLY_DEPRECATED)
+@AppServerContainer(ContainerConstants.APP_SERVER_EAP)
+@AppServerContainer(ContainerConstants.APP_SERVER_EAP6)
+@AppServerContainer(ContainerConstants.APP_SERVER_EAP71)
+@AppServerContainer(ContainerConstants.APP_SERVER_UNDERTOW)
+public class PhotozAccountResourcesAdapterTest extends AbstractPhotozAccountResourcesAdapterTest {
+
+ @Deployment(name = PhotozClientAuthzTestApp.DEPLOYMENT_NAME)
+ public static WebArchive deploymentClient() throws IOException {
+ return exampleDeployment(PhotozClientAuthzTestApp.DEPLOYMENT_NAME);
+ }
+
+ @Deployment(name = RESOURCE_SERVER_ID, managed = false, testable = false)
+ public static WebArchive deploymentResourceServer() throws IOException {
+ return exampleDeployment(RESOURCE_SERVER_ID,
+ webArchive -> webArchive.addAsWebInfResource(new File(TEST_APPS_HOME_DIR + "/photoz/keycloak-lazy-load-path-authz-service.json"), "keycloak.json"));
+ }
+}