From 6eed1c01fbe0fbb178bd4030253b153180058102 Mon Sep 17 00:00:00 2001 From: Jean-Baptiste Lievremont Date: Mon, 27 Apr 2015 14:58:55 +0200 Subject: [PATCH] SONAR-6428 Replace server-side URL generation with display conditions --- .../server/platform/ServerComponents.java | 2 - .../ui/ws/ComponentConfigurationPages.java | 162 ------------------ .../ui/ws/ComponentNavigationAction.java | 71 ++++++-- .../sonar/server/ui/ws/example-component.json | 32 ++-- .../ws/ComponentConfigurationPagesTest.java | 159 ----------------- .../ui/ws/ComponentNavigationActionTest.java | 102 ++++++----- .../on_module.json | 29 ++++ .../quality_profile_admin.json | 18 +- .../with_admin_rights.json | 36 ++-- .../with_all_properties.json | 29 ++++ 10 files changed, 231 insertions(+), 409 deletions(-) delete mode 100644 server/sonar-server/src/main/java/org/sonar/server/ui/ws/ComponentConfigurationPages.java delete mode 100644 server/sonar-server/src/test/java/org/sonar/server/ui/ws/ComponentConfigurationPagesTest.java create mode 100644 server/sonar-server/src/test/resources/org/sonar/server/ui/ws/ComponentNavigationActionTest/on_module.json create mode 100644 server/sonar-server/src/test/resources/org/sonar/server/ui/ws/ComponentNavigationActionTest/with_all_properties.json diff --git a/server/sonar-server/src/main/java/org/sonar/server/platform/ServerComponents.java b/server/sonar-server/src/main/java/org/sonar/server/platform/ServerComponents.java index e455d67390a..60a9cab58aa 100644 --- a/server/sonar-server/src/main/java/org/sonar/server/platform/ServerComponents.java +++ b/server/sonar-server/src/main/java/org/sonar/server/platform/ServerComponents.java @@ -354,7 +354,6 @@ import org.sonar.server.text.RubyTextService; import org.sonar.server.ui.JRubyI18n; import org.sonar.server.ui.PageDecorations; import org.sonar.server.ui.Views; -import org.sonar.server.ui.ws.ComponentConfigurationPages; import org.sonar.server.ui.ws.ComponentNavigationAction; import org.sonar.server.ui.ws.GlobalNavigationAction; import org.sonar.server.ui.ws.NavigationWs; @@ -925,7 +924,6 @@ class ServerComponents { // UI pico.addSingleton(GlobalNavigationAction.class); pico.addSingleton(SettingsNavigationAction.class); - pico.addSingleton(ComponentConfigurationPages.class); pico.addSingleton(ComponentNavigationAction.class); pico.addSingleton(NavigationWs.class); diff --git a/server/sonar-server/src/main/java/org/sonar/server/ui/ws/ComponentConfigurationPages.java b/server/sonar-server/src/main/java/org/sonar/server/ui/ws/ComponentConfigurationPages.java deleted file mode 100644 index b8b8fbebc42..00000000000 --- a/server/sonar-server/src/main/java/org/sonar/server/ui/ws/ComponentConfigurationPages.java +++ /dev/null @@ -1,162 +0,0 @@ -/* - * SonarQube, open source software quality management tool. - * Copyright (C) 2008-2014 SonarSource - * mailto:contact AT sonarsource DOT com - * - * SonarQube is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation; either - * version 3 of the License, or (at your option) any later version. - * - * SonarQube is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with this program; if not, write to the Free Software Foundation, - * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. - */ -package org.sonar.server.ui.ws; - -import com.google.common.base.Charsets; -import com.google.common.base.Predicate; -import com.google.common.collect.Collections2; -import com.google.common.collect.Lists; -import org.sonar.api.ServerComponent; -import org.sonar.api.i18n.I18n; -import org.sonar.api.resources.Qualifiers; -import org.sonar.api.resources.ResourceType; -import org.sonar.api.resources.ResourceTypes; -import org.sonar.api.web.UserRole; -import org.sonar.core.component.ComponentDto; -import org.sonar.server.user.UserSession; - -import java.io.UnsupportedEncodingException; -import java.net.URLEncoder; -import java.util.Collection; -import java.util.List; -import java.util.Locale; - -public class ComponentConfigurationPages implements ServerComponent { - - static final String PROPERTY_COMPARABLE = "comparable"; - static final String PROPERTY_CONFIGURABLE = "configurable"; - static final String PROPERTY_HAS_ROLE_POLICY = "hasRolePolicy"; - static final String PROPERTY_MODIFIABLE_HISTORY = "modifiable_history"; - static final String PROPERTY_UPDATABLE_KEY = "updatable_key"; - static final String PROPERTY_DELETABLE = "deletable"; - - private final I18n i18n; - private final ResourceTypes resourceTypes; - - public ComponentConfigurationPages(I18n i18n, ResourceTypes resourceTypes) { - this.i18n = i18n; - this.resourceTypes = resourceTypes; - } - - Collection getConfigPages(ComponentDto component, UserSession userSession) { - boolean isAdmin = userSession.hasProjectPermissionByUuid(UserRole.ADMIN, component.projectUuid()); - boolean isProject = Qualifiers.PROJECT.equals(component.qualifier()); - Locale locale = userSession.locale(); - String componentKey = encodeComponentKey(component); - - List configPages = Lists.newArrayList(); - - configPages.add(new ConfigPage( - isAdmin && componentTypeHasProperty(component, PROPERTY_CONFIGURABLE), - String.format("/project/settings?id=%s", componentKey), - i18n.message(locale, "project_settings.page", null))); - - configPages.add(new ConfigPage( - isProject, - String.format("/project/profile?id=%s", componentKey), - i18n.message(locale, "project_quality_profiles.page", null))); - - configPages.add(new ConfigPage( - isProject, - String.format("/project/qualitygate?id=%s", componentKey), - i18n.message(locale, "project_quality_gate.page", null))); - - configPages.add(new ConfigPage( - isAdmin, - String.format("/manual_measures/index?id=%s", componentKey), - i18n.message(locale, "manual_measures.page", null))); - - configPages.add(new ConfigPage( - isAdmin && isProject, - String.format("/action_plans/index?id=%s", componentKey), - i18n.message(locale, "action_plans.page", null))); - - configPages.add(new ConfigPage( - isAdmin && isProject, - String.format("/project/links?id=%s", componentKey), - i18n.message(locale, "project_links.page", null))); - - configPages.add(new ConfigPage( - componentTypeHasProperty(component, PROPERTY_HAS_ROLE_POLICY), - String.format("/project_roles/index?id=%s", componentKey), - i18n.message(locale, "permissions.page", null))); - - configPages.add(new ConfigPage( - componentTypeHasProperty(component, PROPERTY_MODIFIABLE_HISTORY), - String.format("/project/history?id=%s", componentKey), - i18n.message(locale, "project_history.page", null))); - - configPages.add(new ConfigPage( - componentTypeHasProperty(component, PROPERTY_UPDATABLE_KEY), - String.format("/project/key?id=%s", componentKey), - i18n.message(locale, "update_key.page", null))); - - configPages.add(new ConfigPage( - componentTypeHasProperty(component, PROPERTY_DELETABLE), - String.format("/project/deletion?id=%s", componentKey), - i18n.message(locale, "deletion.page", null))); - - return Collections2.filter(configPages, new Predicate() { - @Override - public boolean apply(ConfigPage input) { - return input.visible; - } - }); - } - - static String encodeComponentKey(ComponentDto component) { - String componentKey = component.getKey(); - try { - componentKey = URLEncoder.encode(componentKey, Charsets.UTF_8.name()); - } catch (UnsupportedEncodingException unknownEncoding) { - throw new IllegalStateException(unknownEncoding); - } - return componentKey; - } - - boolean componentTypeHasProperty(ComponentDto component, String resourceTypeProperty) { - ResourceType resourceType = resourceTypes.get(component.qualifier()); - if (resourceType != null) { - return resourceType.getBooleanProperty(resourceTypeProperty); - } - return false; - } - - static class ConfigPage { - private final boolean visible; - private final String url; - private final String name; - - ConfigPage(boolean visible, String url, String name) { - this.visible = visible; - this.url = url; - this.name = name; - } - - String url() { - return url; - } - - String name() { - return name; - } - } - -} diff --git a/server/sonar-server/src/main/java/org/sonar/server/ui/ws/ComponentNavigationAction.java b/server/sonar-server/src/main/java/org/sonar/server/ui/ws/ComponentNavigationAction.java index 7192ae1d5c1..59bb790d9d6 100644 --- a/server/sonar-server/src/main/java/org/sonar/server/ui/ws/ComponentNavigationAction.java +++ b/server/sonar-server/src/main/java/org/sonar/server/ui/ws/ComponentNavigationAction.java @@ -19,8 +19,12 @@ */ package org.sonar.server.ui.ws; +import com.google.common.base.Charsets; import com.google.common.collect.Lists; import org.sonar.api.i18n.I18n; +import org.sonar.api.resources.Qualifiers; +import org.sonar.api.resources.ResourceType; +import org.sonar.api.resources.ResourceTypes; import org.sonar.api.server.ws.Request; import org.sonar.api.server.ws.Response; import org.sonar.api.server.ws.WebService.NewAction; @@ -41,11 +45,12 @@ import org.sonar.core.properties.PropertyQuery; import org.sonar.server.db.DbClient; import org.sonar.server.ui.ViewProxy; import org.sonar.server.ui.Views; -import org.sonar.server.ui.ws.ComponentConfigurationPages.ConfigPage; import org.sonar.server.user.UserSession; import javax.annotation.Nullable; +import java.io.UnsupportedEncodingException; +import java.net.URLEncoder; import java.util.Date; import java.util.List; import java.util.Locale; @@ -54,19 +59,25 @@ public class ComponentNavigationAction implements NavigationAction { private static final String PARAM_COMPONENT_KEY = "componentKey"; + private static final String PROPERTY_COMPARABLE = "comparable"; + private static final String PROPERTY_CONFIGURABLE = "configurable"; + private static final String PROPERTY_HAS_ROLE_POLICY = "hasRolePolicy"; + private static final String PROPERTY_MODIFIABLE_HISTORY = "modifiable_history"; + private static final String PROPERTY_UPDATABLE_KEY = "updatable_key"; + private static final String PROPERTY_DELETABLE = "deletable"; + private final DbClient dbClient; private final ActiveDashboardDao activeDashboardDao; private final Views views; private final I18n i18n; - private final ComponentConfigurationPages projectConfiguration; + private final ResourceTypes resourceTypes; - public ComponentNavigationAction(DbClient dbClient, ActiveDashboardDao activeDashboardDao, Views views, I18n i18n, - ComponentConfigurationPages projectConfiguration) { + public ComponentNavigationAction(DbClient dbClient, ActiveDashboardDao activeDashboardDao, Views views, I18n i18n, ResourceTypes resourceTypes) { this.dbClient = dbClient; this.activeDashboardDao = activeDashboardDao; this.views = views; this.i18n = i18n; - this.projectConfiguration = projectConfiguration; + this.resourceTypes = resourceTypes; } @Override @@ -120,7 +131,7 @@ public class ComponentNavigationAction implements NavigationAction { json.prop("key", component.key()) .prop("uuid", component.uuid()) .prop("name", component.name()) - .prop("isComparable", projectConfiguration.componentTypeHasProperty(component, ComponentConfigurationPages.PROPERTY_COMPARABLE)) + .prop("isComparable", componentTypeHasProperty(component, PROPERTY_COMPARABLE)) .prop("canBeFavorite", userSession.isLoggedIn()) .prop("isFavorite", isFavourite(session, component, userSession)); @@ -156,7 +167,7 @@ public class ComponentNavigationAction implements NavigationAction { private String getPageUrl(ViewProxy page, ComponentDto component) { String result = null; - String componentKey = ComponentConfigurationPages.encodeComponentKey(component); + String componentKey = encodeComponentKey(component); if (page.isController()) { result = String.format("%s?id=%s", page.getId(), componentKey); } else { @@ -165,6 +176,16 @@ public class ComponentNavigationAction implements NavigationAction { return result; } + private static String encodeComponentKey(ComponentDto component) { + String componentKey = component.getKey(); + try { + componentKey = URLEncoder.encode(componentKey, Charsets.UTF_8.name()); + } catch (UnsupportedEncodingException unknownEncoding) { + throw new IllegalStateException(unknownEncoding); + } + return componentKey; + } + private void writeDashboards(JsonWriter json, ComponentDto component, List dashboards, Locale locale) { json.name("dashboards").beginArray(); for (DashboardDto dashboard : dashboards) { @@ -180,21 +201,41 @@ public class ComponentNavigationAction implements NavigationAction { boolean isAdmin = userSession.hasProjectPermissionByUuid(UserRole.ADMIN, component.projectUuid()); Locale locale = userSession.locale(); - json.name("configuration").beginArray(); - for (ConfigPage page : projectConfiguration.getConfigPages(component, userSession)) { - json.beginObject() - .prop("url", page.url()) - .prop("name", page.name()) - .endObject(); - } + json.name("configuration").beginObject(); + writeConfigPageAccess(json, isAdmin, component, userSession); if (isAdmin) { + json.name("extensions").beginArray(); List> configPages = views.getPages(NavigationSection.RESOURCE_CONFIGURATION, component.scope(), component.qualifier(), component.language(), null); for (ViewProxy page : configPages) { writePage(json, getPageUrl(page, component), i18n.message(locale, page.getId() + ".page", page.getTitle())); } + json.endArray(); } - json.endArray(); + json.endObject(); + } + + private void writeConfigPageAccess(JsonWriter json, boolean isAdmin, ComponentDto component, UserSession userSession) { + boolean isProject = Qualifiers.PROJECT.equals(component.qualifier()); + + json.prop("showSettings", isAdmin && componentTypeHasProperty(component, PROPERTY_CONFIGURABLE)) + .prop("showQualityProfiles", isProject) + .prop("showQualityGates", isProject) + .prop("showManualMeasures", isAdmin) + .prop("showActionPlans", isAdmin && isProject) + .prop("showLinks", isAdmin && isProject) + .prop("showPermissions", isAdmin && componentTypeHasProperty(component, PROPERTY_HAS_ROLE_POLICY)) + .prop("showHistory", isAdmin && componentTypeHasProperty(component, PROPERTY_MODIFIABLE_HISTORY)) + .prop("showUpdateKey", isAdmin && componentTypeHasProperty(component, PROPERTY_UPDATABLE_KEY)) + .prop("showDeletion", isAdmin && componentTypeHasProperty(component, PROPERTY_DELETABLE)); + } + + private boolean componentTypeHasProperty(ComponentDto component, String resourceTypeProperty) { + ResourceType resourceType = resourceTypes.get(component.qualifier()); + if (resourceType != null) { + return resourceType.getBooleanProperty(resourceTypeProperty); + } + return false; } private void writePage(JsonWriter json, String url, String name) { diff --git a/server/sonar-server/src/main/resources/org/sonar/server/ui/ws/example-component.json b/server/sonar-server/src/main/resources/org/sonar/server/ui/ws/example-component.json index b03cef5d95d..93a4fe89021 100644 --- a/server/sonar-server/src/main/resources/org/sonar/server/ui/ws/example-component.json +++ b/server/sonar-server/src/main/resources/org/sonar/server/ui/ws/example-component.json @@ -19,16 +19,28 @@ "url": "/plugins/resource/2865?page=my-resource-plugin" } ], - "configuration": [ - { - "name": "General Settings", - "url": "/project/settings/2865" - }, - { - "name": "Action Plans", - "url": "/action_plans/index/2865" - } - ], + "configuration": { + "showSettings": true, + "showQualityProfiles": true, + "showQualityGates": true, + "showManualMeasures": true, + "showActionPlans": true, + "showLinks": true, + "showPermissions": true, + "showHistory": true, + "showUpdateKey": true, + "showDeletion": true, + "extensions": [ + { + "name": "General Settings", + "url": "/project/settings/2865" + }, + { + "name": "Action Plans", + "url": "/action_plans/index/2865" + } + ] + }, "breadcrumbs": [ { "name": "SonarQube", diff --git a/server/sonar-server/src/test/java/org/sonar/server/ui/ws/ComponentConfigurationPagesTest.java b/server/sonar-server/src/test/java/org/sonar/server/ui/ws/ComponentConfigurationPagesTest.java deleted file mode 100644 index 391ee96239c..00000000000 --- a/server/sonar-server/src/test/java/org/sonar/server/ui/ws/ComponentConfigurationPagesTest.java +++ /dev/null @@ -1,159 +0,0 @@ -/* - * SonarQube, open source software quality management tool. - * Copyright (C) 2008-2014 SonarSource - * mailto:contact AT sonarsource DOT com - * - * SonarQube is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation; either - * version 3 of the License, or (at your option) any later version. - * - * SonarQube is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with this program; if not, write to the Free Software Foundation, - * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. - */ -package org.sonar.server.ui.ws; - -import org.junit.Before; -import org.junit.Test; -import org.junit.runner.RunWith; -import org.mockito.Matchers; -import org.mockito.Mock; -import org.mockito.invocation.InvocationOnMock; -import org.mockito.runners.MockitoJUnitRunner; -import org.mockito.stubbing.Answer; -import org.sonar.api.i18n.I18n; -import org.sonar.api.resources.ResourceType; -import org.sonar.api.resources.ResourceTypes; -import org.sonar.api.web.UserRole; -import org.sonar.core.component.ComponentDto; -import org.sonar.server.component.ComponentTesting; -import org.sonar.server.ui.ws.ComponentConfigurationPages.ConfigPage; -import org.sonar.server.user.MockUserSession; -import org.sonar.server.user.UserSession; - -import java.util.Collection; -import java.util.Locale; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.mockito.Mockito.when; - -@RunWith(MockitoJUnitRunner.class) -public class ComponentConfigurationPagesTest { - - @Mock - private I18n i18n; - - @Mock - private ResourceTypes resourceTypes; - - @Before - public void before() { - when(i18n.message(Matchers.any(Locale.class), Matchers.anyString(), Matchers.anyString())).thenAnswer(new Answer() { - @Override - public String answer(InvocationOnMock invocation) throws Throwable { - return invocation.getArgumentAt(1, String.class); - } - }); - } - - @Test - public void pages_for_project() throws Exception { - String uuid = "abcd"; - ComponentDto component = ComponentTesting.newProjectDto(uuid).setKey("org.codehaus.sonar:sonar"); - UserSession userSession = MockUserSession.set().setLogin("obiwan").addProjectUuidPermissions(UserRole.ADMIN, uuid); - - Collection pages = new ComponentConfigurationPages(i18n, resourceTypes).getConfigPages(component, userSession); - assertThat(pages).extracting("name").containsExactly( - "project_quality_profiles.page", - "project_quality_gate.page", - "manual_measures.page", - "action_plans.page", - "project_links.page" - ); - assertThat(pages).extracting("url").containsExactly( - "/project/profile?id=org.codehaus.sonar%3Asonar", - "/project/qualitygate?id=org.codehaus.sonar%3Asonar", - "/manual_measures/index?id=org.codehaus.sonar%3Asonar", - "/action_plans/index?id=org.codehaus.sonar%3Asonar", - "/project/links?id=org.codehaus.sonar%3Asonar" - ); - } - - @Test - public void pages_for_project_with_resource_type_property() throws Exception { - String uuid = "abcd"; - ComponentDto component = ComponentTesting.newProjectDto(uuid); - UserSession userSession = MockUserSession.set().setLogin("obiwan").addProjectUuidPermissions(UserRole.ADMIN, uuid); - when(resourceTypes.get(component.qualifier())).thenReturn( - ResourceType.builder(component.qualifier()).setProperty("configurable", true).build()); - - Collection pages = new ComponentConfigurationPages(i18n, resourceTypes).getConfigPages(component, userSession); - assertThat(pages).extracting("name").containsExactly( - "project_settings.page", - "project_quality_profiles.page", - "project_quality_gate.page", - "manual_measures.page", - "action_plans.page", - "project_links.page" - ); - } - - @Test - public void pages_for_module() throws Exception { - String uuid = "abcd"; - ComponentDto project = ComponentTesting.newProjectDto(uuid); - ComponentDto module = ComponentTesting.newModuleDto(project); - UserSession userSession = MockUserSession.set().setLogin("obiwan").addProjectUuidPermissions(UserRole.ADMIN, uuid); - - Collection pages = new ComponentConfigurationPages(i18n, resourceTypes).getConfigPages(module, userSession); - assertThat(pages).extracting("name").containsExactly("manual_measures.page"); - } - - @Test - public void pages_for_non_admin() throws Exception { - String uuid = "abcd"; - ComponentDto project = ComponentTesting.newProjectDto(uuid); - UserSession userSession = MockUserSession.set().setLogin("obiwan").addProjectUuidPermissions(UserRole.USER, uuid); - - Collection pages = new ComponentConfigurationPages(i18n, resourceTypes).getConfigPages(project, userSession); - assertThat(pages).extracting("name").containsExactly( - "project_quality_profiles.page", - "project_quality_gate.page" - ); - } - - @Test - public void pages_for_project_with_all_resource_type_properties() throws Exception { - String uuid = "abcd"; - ComponentDto component = ComponentTesting.newProjectDto(uuid); - UserSession userSession = MockUserSession.set().setLogin("obiwan").addProjectUuidPermissions(UserRole.ADMIN, uuid); - when(resourceTypes.get(component.qualifier())).thenReturn( - ResourceType.builder(component.qualifier()) - .setProperty("configurable", true) - .setProperty("hasRolePolicy", true) - .setProperty("modifiable_history", true) - .setProperty("updatable_key", true) - .setProperty("deletable", true) - .build()); - - Collection pages = new ComponentConfigurationPages(i18n, resourceTypes).getConfigPages(component, userSession); - assertThat(pages).extracting("name").containsExactly( - "project_settings.page", - "project_quality_profiles.page", - "project_quality_gate.page", - "manual_measures.page", - "action_plans.page", - "project_links.page", - "permissions.page", - "project_history.page", - "update_key.page", - "deletion.page" - ); - } -} diff --git a/server/sonar-server/src/test/java/org/sonar/server/ui/ws/ComponentNavigationActionTest.java b/server/sonar-server/src/test/java/org/sonar/server/ui/ws/ComponentNavigationActionTest.java index bac40488281..778d1ef154a 100644 --- a/server/sonar-server/src/test/java/org/sonar/server/ui/ws/ComponentNavigationActionTest.java +++ b/server/sonar-server/src/test/java/org/sonar/server/ui/ws/ComponentNavigationActionTest.java @@ -19,8 +19,6 @@ */ package org.sonar.server.ui.ws; -import com.google.common.collect.Maps; -import org.apache.commons.lang.BooleanUtils; import org.junit.After; import org.junit.Before; import org.junit.ClassRule; @@ -29,6 +27,8 @@ import org.mockito.invocation.InvocationOnMock; import org.mockito.stubbing.Answer; import org.sonar.api.i18n.I18n; import org.sonar.api.resources.Qualifiers; +import org.sonar.api.resources.ResourceType; +import org.sonar.api.resources.ResourceTypes; import org.sonar.api.resources.Scopes; import org.sonar.api.utils.DateUtils; import org.sonar.api.utils.System2; @@ -58,15 +58,11 @@ import org.sonar.server.exceptions.NotFoundException; import org.sonar.server.measure.persistence.MeasureDao; import org.sonar.server.ui.Views; import org.sonar.server.user.MockUserSession; -import org.sonar.server.user.UserSession; import org.sonar.server.user.db.UserDao; import org.sonar.server.ws.WsTester; -import java.util.Arrays; import java.util.Date; -import java.util.List; import java.util.Locale; -import java.util.Map; import static org.mockito.Matchers.any; import static org.mockito.Mockito.mock; @@ -91,7 +87,7 @@ public class ComponentNavigationActionTest { private I18n i18n; - private ProjectConfigurationPagesStub projectConfigurationPages; + private ResourceTypes resourceTypes; @Before public void before() throws Exception { @@ -115,7 +111,7 @@ public class ComponentNavigationActionTest { } }); - projectConfigurationPages = new ProjectConfigurationPagesStub(); + resourceTypes = mock(ResourceTypes.class); session = dbClient.openSession(false); } @@ -158,7 +154,7 @@ public class ComponentNavigationActionTest { MockUserSession.set().addProjectUuidPermissions(UserRole.USER, "abcd"); wsTester = new WsTester(new NavigationWs(new ComponentNavigationAction(dbClient, activeDashboardDao, - new Views(), i18n, projectConfigurationPages))); + new Views(), i18n, resourceTypes))); wsTester.newGetRequest("api/navigation", "component").setParam("componentKey", "polop").execute().assertJson(getClass(), "no_snapshot.json"); } @@ -174,7 +170,7 @@ public class ComponentNavigationActionTest { MockUserSession.set().setLogin("obiwan").setUserId(userId).addProjectUuidPermissions(UserRole.USER, "abcd"); wsTester = new WsTester(new NavigationWs(new ComponentNavigationAction(dbClient, activeDashboardDao, - new Views(), i18n, projectConfigurationPages))); + new Views(), i18n, resourceTypes))); wsTester.newGetRequest("api/navigation", "component").setParam("componentKey", "polop").execute().assertJson(getClass(), "no_snapshot_user_favourite.json"); } @@ -193,7 +189,7 @@ public class ComponentNavigationActionTest { MockUserSession.set().setLogin("obiwan").setUserId(userId).addProjectUuidPermissions(UserRole.USER, "abcd"); wsTester = new WsTester(new NavigationWs(new ComponentNavigationAction(dbClient, activeDashboardDao, - new Views(), i18n, projectConfigurationPages))); + new Views(), i18n, resourceTypes))); wsTester.newGetRequest("api/navigation", "component").setParam("componentKey", "polop").execute().assertJson(getClass(), "with_snapshot_and_connected_user.json"); } @@ -210,7 +206,7 @@ public class ComponentNavigationActionTest { MockUserSession.set().addProjectUuidPermissions(UserRole.USER, "abcd"); wsTester = new WsTester(new NavigationWs(new ComponentNavigationAction(dbClient, activeDashboardDao, - new Views(), i18n, projectConfigurationPages))); + new Views(), i18n, resourceTypes))); wsTester.newGetRequest("api/navigation", "component").setParam("componentKey", "polop").execute().assertJson(getClass(), "with_dashboards.json"); } @@ -261,7 +257,7 @@ public class ComponentNavigationActionTest { Page page2 = new SecondPage(); wsTester = new WsTester(new NavigationWs(new ComponentNavigationAction(dbClient, activeDashboardDao, - new Views(new Page[] {page1, page2}), i18n, projectConfigurationPages))); + new Views(new Page[] {page1, page2}), i18n, resourceTypes))); wsTester.newGetRequest("api/navigation", "component").setParam("componentKey", "polop").execute().assertJson(getClass(), "with_extensions.json"); } @@ -313,11 +309,60 @@ public class ComponentNavigationActionTest { Page page2 = new SecondPage(); wsTester = new WsTester(new NavigationWs(new ComponentNavigationAction(dbClient, activeDashboardDao, - new Views(new Page[] {page1, page2}), i18n, projectConfigurationPages))); + new Views(new Page[] {page1, page2}), i18n, resourceTypes))); wsTester.newGetRequest("api/navigation", "component").setParam("componentKey", "polop").execute().assertJson(getClass(), "with_admin_rights.json"); } + @Test + public void with_component_which_has_all_properties() throws Exception { + int userId = 42; + ComponentDto project = ComponentTesting.newProjectDto("abcd") + .setKey("polop").setName("Polop"); + dbClient.componentDao().insert(session, project); + session.commit(); + + MockUserSession.set().setLogin("obiwan").setUserId(userId) + .addProjectUuidPermissions(UserRole.USER, "abcd") + .addProjectUuidPermissions(UserRole.ADMIN, "abcd"); + + ResourceType projectResourceType = ResourceType.builder(project.qualifier()) + .setProperty("comparable", true) + .setProperty("configurable", true) + .setProperty("hasRolePolicy", true) + .setProperty("modifiable_history", true) + .setProperty("updatable_key", true) + .setProperty("deletable", true) + .build(); + when(resourceTypes.get(project.qualifier())) + .thenReturn(projectResourceType); + + wsTester = new WsTester(new NavigationWs(new ComponentNavigationAction(dbClient, activeDashboardDao, + new Views(), i18n, resourceTypes))); + + wsTester.newGetRequest("api/navigation", "component").setParam("componentKey", "polop").execute().assertJson(getClass(), "with_all_properties.json"); + } + + @Test + public void on_module() throws Exception { + int userId = 42; + ComponentDto project = ComponentTesting.newProjectDto("abcd") + .setKey("polop").setName("Polop"); + ComponentDto module = ComponentTesting.newModuleDto("bcde", project) + .setKey("palap").setName("Palap"); + dbClient.componentDao().insert(session, project, module); + session.commit(); + + MockUserSession.set().setLogin("obiwan").setUserId(userId) + .addProjectUuidPermissions(UserRole.USER, "abcd") + .addProjectUuidPermissions(UserRole.ADMIN, "abcd"); + + wsTester = new WsTester(new NavigationWs(new ComponentNavigationAction(dbClient, activeDashboardDao, + new Views(), i18n, resourceTypes))); + + wsTester.newGetRequest("api/navigation", "component").setParam("componentKey", "palap").execute().assertJson(getClass(), "on_module.json"); + } + @Test public void with_quality_profile_admin_rights() throws Exception { final String language = "xoo"; @@ -345,7 +390,7 @@ public class ComponentNavigationActionTest { Page page = new FirstPage(); wsTester = new WsTester(new NavigationWs(new ComponentNavigationAction(dbClient, activeDashboardDao, - new Views(new Page[] {page}), i18n, projectConfigurationPages))); + new Views(new Page[] {page}), i18n, resourceTypes))); wsTester.newGetRequest("api/navigation", "component").setParam("componentKey", "polop").execute().assertJson(getClass(), "quality_profile_admin.json"); } @@ -395,33 +440,8 @@ public class ComponentNavigationActionTest { MockUserSession.set().addProjectUuidPermissions(UserRole.USER, "abcd"); wsTester = new WsTester(new NavigationWs(new ComponentNavigationAction(dbClient, activeDashboardDao, - new Views(), i18n, projectConfigurationPages))); + new Views(), i18n, resourceTypes))); wsTester.newGetRequest("api/navigation", "component").setParam("componentKey", "palap:src/main/xoo/Source.xoo").execute().assertJson(getClass(), "breadcrumbs.json"); } - - class ProjectConfigurationPagesStub extends ComponentConfigurationPages { - - private Map resourceTypeHasProperty; - - public ProjectConfigurationPagesStub() { - super(i18n, null); - resourceTypeHasProperty = Maps.newHashMap(); - } - - void setComponentTypeProperty(String resourceTypeProperty, boolean value) { - resourceTypeHasProperty.put(resourceTypeProperty, value); - } - - @Override - boolean componentTypeHasProperty(ComponentDto component, String resourceTypeProperty) { - return BooleanUtils.isTrue(resourceTypeHasProperty.get(resourceTypeProperty)); - } - - @Override - List getConfigPages(ComponentDto component, UserSession userSession) { - return Arrays.asList( - new ConfigPage(true, "/visible/page", "Visible Config Page")); - } - } } diff --git a/server/sonar-server/src/test/resources/org/sonar/server/ui/ws/ComponentNavigationActionTest/on_module.json b/server/sonar-server/src/test/resources/org/sonar/server/ui/ws/ComponentNavigationActionTest/on_module.json new file mode 100644 index 00000000000..edf146d10b6 --- /dev/null +++ b/server/sonar-server/src/test/resources/org/sonar/server/ui/ws/ComponentNavigationActionTest/on_module.json @@ -0,0 +1,29 @@ +{ + "key": "palap", + "uuid": "bcde", + "name": "Palap", + "isComparable": false, + "canBeFavorite": true, + "isFavorite": false, + "dashboards": [], + "configuration": { + "showSettings": false, + "showQualityProfiles": false, + "showQualityGates": false, + "showManualMeasures": true, + "showActionPlans": false, + "showLinks": false, + "showPermissions": false, + "showHistory": false, + "showUpdateKey": false, + "showDeletion": false, + "extensions": [] + }, + "breadcrumbs": [ + { + "key": "palap", + "name": "Palap", + "qualifier": "BRC" + } + ] +} diff --git a/server/sonar-server/src/test/resources/org/sonar/server/ui/ws/ComponentNavigationActionTest/quality_profile_admin.json b/server/sonar-server/src/test/resources/org/sonar/server/ui/ws/ComponentNavigationActionTest/quality_profile_admin.json index c377a7b5fa3..987d7c1d2cb 100644 --- a/server/sonar-server/src/test/resources/org/sonar/server/ui/ws/ComponentNavigationActionTest/quality_profile_admin.json +++ b/server/sonar-server/src/test/resources/org/sonar/server/ui/ws/ComponentNavigationActionTest/quality_profile_admin.json @@ -6,12 +6,18 @@ "canBeFavorite": true, "isFavorite": false, "dashboards": [], - "configuration": [ - { - "name": "Visible Config Page", - "url": "/visible/page" - } - ], + "configuration": { + "showSettings": false, + "showQualityProfiles": true, + "showQualityGates": true, + "showManualMeasures": false, + "showActionPlans": false, + "showLinks": false, + "showPermissions": false, + "showHistory": false, + "showUpdateKey": false, + "showDeletion": false + }, "breadcrumbs": [ { "key": "polop", diff --git a/server/sonar-server/src/test/resources/org/sonar/server/ui/ws/ComponentNavigationActionTest/with_admin_rights.json b/server/sonar-server/src/test/resources/org/sonar/server/ui/ws/ComponentNavigationActionTest/with_admin_rights.json index 09726b6186b..21a739685e9 100644 --- a/server/sonar-server/src/test/resources/org/sonar/server/ui/ws/ComponentNavigationActionTest/with_admin_rights.json +++ b/server/sonar-server/src/test/resources/org/sonar/server/ui/ws/ComponentNavigationActionTest/with_admin_rights.json @@ -6,20 +6,28 @@ "canBeFavorite": true, "isFavorite": false, "dashboards": [], - "configuration": [ - { - "name": "Visible Config Page", - "url": "/visible/page" - }, - { - "name": "First Page", - "url": "/plugins/resource/polop?page=first_page" - }, - { - "name": "Second Page", - "url": "/second/page?id=polop" - } - ], + "configuration": { + "showSettings": false, + "showQualityProfiles": true, + "showQualityGates": true, + "showManualMeasures": true, + "showActionPlans": true, + "showLinks": true, + "showPermissions": false, + "showHistory": false, + "showUpdateKey": false, + "showDeletion": false, + "extensions": [ + { + "name": "First Page", + "url": "/plugins/resource/polop?page=first_page" + }, + { + "name": "Second Page", + "url": "/second/page?id=polop" + } + ] + }, "breadcrumbs": [ { "key": "polop", diff --git a/server/sonar-server/src/test/resources/org/sonar/server/ui/ws/ComponentNavigationActionTest/with_all_properties.json b/server/sonar-server/src/test/resources/org/sonar/server/ui/ws/ComponentNavigationActionTest/with_all_properties.json new file mode 100644 index 00000000000..1acea8658f2 --- /dev/null +++ b/server/sonar-server/src/test/resources/org/sonar/server/ui/ws/ComponentNavigationActionTest/with_all_properties.json @@ -0,0 +1,29 @@ +{ + "key": "polop", + "uuid": "abcd", + "name": "Polop", + "isComparable": true, + "canBeFavorite": true, + "isFavorite": false, + "dashboards": [], + "configuration": { + "showSettings": true, + "showQualityProfiles": true, + "showQualityGates": true, + "showManualMeasures": true, + "showActionPlans": true, + "showLinks": true, + "showPermissions": true, + "showHistory": true, + "showUpdateKey": true, + "showDeletion": true, + "extensions": [] + }, + "breadcrumbs": [ + { + "key": "polop", + "name": "Polop", + "qualifier": "TRK" + } + ] +} -- 2.39.5