SONAR-8354 Remove dashboards startup registration

This commit is contained in:
Julien Lancelot 2016-11-07 15:27:02 +01:00
parent 1bf30ee99c
commit cb4cb7791b
7 changed files with 0 additions and 849 deletions

View File

@ -32,12 +32,10 @@ import org.sonar.server.startup.ClearRulesOverloadedDebt;
import org.sonar.server.startup.DeleteOldAnalysisReportsFromFs;
import org.sonar.server.startup.DisplayLogOnDeprecatedProjects;
import org.sonar.server.startup.GeneratePluginIndex;
import org.sonar.server.startup.RegisterDashboards;
import org.sonar.server.startup.RegisterMetrics;
import org.sonar.server.startup.RegisterNewMeasureFilters;
import org.sonar.server.startup.RegisterPermissionTemplates;
import org.sonar.server.startup.RenameDeprecatedPropertyKeys;
import org.sonar.server.startup.RenameIssueWidgets;
import org.sonar.server.user.DoPrivileged;
import org.sonar.server.user.ThreadLocalUserSession;
@ -60,11 +58,9 @@ public class PlatformLevelStartup extends PlatformLevel {
RegisterRules.class,
RegisterQualityProfiles.class,
RegisterNewMeasureFilters.class,
RegisterDashboards.class,
RegisterPermissionTemplates.class,
RenameDeprecatedPropertyKeys.class,
RegisterIssueFilters.class,
RenameIssueWidgets.class,
DisplayLogOnDeprecatedProjects.class,
ClearRulesOverloadedDebt.class,
DeleteOldAnalysisReportsFromFs.class);

View File

@ -1,183 +0,0 @@
/*
* SonarQube
* Copyright (C) 2009-2016 SonarSource SA
* mailto:contact AT sonarsource DOT com
*
* This program 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.
*
* This program 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.startup;
import com.google.common.collect.Lists;
import com.google.common.collect.Ordering;
import java.io.Serializable;
import java.util.Date;
import java.util.List;
import java.util.Map.Entry;
import org.picocontainer.Startable;
import org.sonar.api.utils.log.Logger;
import org.sonar.api.utils.log.Loggers;
import org.sonar.api.utils.log.Profiler;
import org.sonar.api.web.Dashboard;
import org.sonar.api.web.DashboardTemplate;
import org.sonar.db.dashboard.ActiveDashboardDao;
import org.sonar.db.dashboard.ActiveDashboardDto;
import org.sonar.db.dashboard.DashboardDao;
import org.sonar.db.dashboard.DashboardDto;
import org.sonar.db.dashboard.WidgetDto;
import org.sonar.db.dashboard.WidgetPropertyDto;
import org.sonar.db.loadedtemplate.LoadedTemplateDao;
import org.sonar.db.loadedtemplate.LoadedTemplateDto;
import org.sonar.server.issue.filter.RegisterIssueFilters;
/**
* @since 2.13
*/
public class RegisterDashboards implements Startable {
private static final Logger LOG = Loggers.get(RegisterDashboards.class);
static final String DEFAULT_DASHBOARD_NAME = "Dashboard";
private final List<DashboardTemplate> dashboardTemplates;
private final DashboardDao dashboardDao;
private final ActiveDashboardDao activeDashboardDao;
private final LoadedTemplateDao loadedTemplateDao;
public RegisterDashboards(DashboardTemplate[] dashboardTemplatesArray, DashboardDao dashboardDao,
ActiveDashboardDao activeDashboardDao, LoadedTemplateDao loadedTemplateDao, RegisterIssueFilters startupDependency) {
this.dashboardTemplates = Lists.newArrayList(dashboardTemplatesArray);
this.dashboardDao = dashboardDao;
this.activeDashboardDao = activeDashboardDao;
this.loadedTemplateDao = loadedTemplateDao;
// RegisterIssueFilters must be run before this task, to be able to reference issue filters in widget properties
}
/**
* Used when no plugin is defining some DashboardTemplate
*/
public RegisterDashboards(DashboardDao dashboardDao, ActiveDashboardDao activeDashboardDao, LoadedTemplateDao loadedTemplateDao, RegisterIssueFilters registerIssueFilters) {
this(new DashboardTemplate[] {}, dashboardDao, activeDashboardDao, loadedTemplateDao, registerIssueFilters);
}
@Override
public void start() {
Profiler profiler = Profiler.create(Loggers.get(getClass())).startInfo("Register dashboards");
List<DashboardDto> registeredDashboards = Lists.newArrayList();
dashboardTemplates.stream()
.filter(template -> shouldRegister(template.getName()))
.forEach(template -> {
Dashboard dashboard = template.createDashboard();
if (dashboard.isGlobal()) {
DashboardDto dto = register(template.getName(), dashboard);
if ((dto != null) && dashboard.isActivated() && dashboard.isGlobal()) {
registeredDashboards.add(dto);
}
}
});
activate(registeredDashboards);
profiler.stopDebug();
}
@Override
public void stop() {
// nothing to do
}
protected void activate(List<DashboardDto> loadedDashboards) {
int nextOrderIndex = activeDashboardDao.selectMaxOrderIndexForNullUser() + 1;
for (DashboardDto dashboardDto : new DashboardOrdering().sortedCopy(loadedDashboards)) {
activate(dashboardDto, nextOrderIndex);
nextOrderIndex++;
}
}
private void activate(DashboardDto dashboardDto, int index) {
LOG.info("Register dashboard: " + dashboardDto.getName());
ActiveDashboardDto activeDashboardDto = new ActiveDashboardDto()
.setDashboardId(dashboardDto.getId())
.setOrderIndex(index);
activeDashboardDao.insert(activeDashboardDto);
}
protected DashboardDto register(String name, Dashboard dashboard) {
DashboardDto dto = null;
if (dashboardDao.selectGlobalDashboard(name) == null) {
dto = createDtoFromExtension(name, dashboard);
dashboardDao.insert(dto);
}
// and save the fact that is has now already been loaded
loadedTemplateDao.insert(new LoadedTemplateDto(name, LoadedTemplateDto.DASHBOARD_TYPE));
return dto;
}
protected DashboardDto createDtoFromExtension(String name, Dashboard dashboard) {
Date now = new Date();
DashboardDto dashboardDto = new DashboardDto()
.setName(name)
.setDescription(dashboard.getDescription())
.setColumnLayout(dashboard.getLayout().getCode())
.setShared(true);
dashboardDto.setCreatedAt(now).setUpdatedAt(now);
for (int columnIndex = 1; columnIndex <= dashboard.getLayout().getColumns(); columnIndex++) {
List<Dashboard.Widget> widgets = dashboard.getWidgetsOfColumn(columnIndex);
for (int rowIndex = 1; rowIndex <= widgets.size(); rowIndex++) {
Dashboard.Widget widget = widgets.get(rowIndex - 1);
WidgetDto widgetDto = new WidgetDto()
.setWidgetKey(widget.getId())
.setColumnIndex(columnIndex)
.setRowIndex(rowIndex)
.setConfigured(true);
widgetDto.setCreatedAt(now).setUpdatedAt(now);
dashboardDto.addWidget(widgetDto);
for (Entry<String, String> property : widget.getProperties().entrySet()) {
WidgetPropertyDto propDto = new WidgetPropertyDto()
.setPropertyKey(property.getKey())
.setTextValue(property.getValue());
widgetDto.addWidgetProperty(propDto);
}
}
}
return dashboardDto;
}
protected boolean shouldRegister(String dashboardName) {
return loadedTemplateDao.countByTypeAndKey(LoadedTemplateDto.DASHBOARD_TYPE, dashboardName) == 0;
}
private static class DashboardOrdering extends Ordering<DashboardDto> implements Serializable {
private static final long serialVersionUID = 0;
@Override
public int compare(DashboardDto left, DashboardDto right) {
String leftName = (left == null) ? null : left.getName();
String rightName = (right == null) ? null : right.getName();
// the default dashboard must be the first one to be activated
if (DEFAULT_DASHBOARD_NAME.equals(leftName)) {
return -1;
}
if (DEFAULT_DASHBOARD_NAME.equals(rightName)) {
return 1;
}
return Ordering.natural().nullsLast().compare(leftName, rightName);
}
}
}

View File

@ -1,164 +0,0 @@
/*
* SonarQube
* Copyright (C) 2009-2016 SonarSource SA
* mailto:contact AT sonarsource DOT com
*
* This program 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.
*
* This program 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.startup;
import com.google.common.collect.ImmutableMap;
import com.google.common.collect.Lists;
import java.util.Date;
import java.util.List;
import java.util.Map;
import org.picocontainer.Startable;
import org.sonar.api.utils.System2;
import org.sonar.api.utils.log.Logger;
import org.sonar.api.utils.log.Loggers;
import org.sonar.db.DbClient;
import org.sonar.db.DbSession;
import org.sonar.db.MyBatis;
import org.sonar.db.dashboard.DashboardDto;
import org.sonar.db.dashboard.WidgetDto;
import org.sonar.db.dashboard.WidgetPropertyDto;
import org.sonar.db.issue.IssueFilterDto;
import org.sonar.db.loadedtemplate.LoadedTemplateDto;
import org.sonar.server.issue.filter.RegisterIssueFilters;
public class RenameIssueWidgets implements Startable {
private static final Logger LOGGER = Loggers.get(RenameIssueWidgets.class);
private static final String TASK_KEY = "RenameIssueWidgets";
private static final String WIDGET_FALSE_POSITIVES = "false_positive_reviews";
private static final String WIDGET_MY_UNRESOLVED = "my_reviews";
private static final String WIDGET_UNRESOLVED_BY_DEVELOPER = "reviews_per_developer";
private static final String WIDGET_UNRESOLVED_BY_STATUS = "unresolved_issues_statuses";
private static final String WIDGET_ISSUE_FILTER = "issue_filter";
private static final String WIDGET_PROJECT_ISSUE_FILTER = "project_issue_filter";
private static final String FILTER_PROPERTY = "filter";
private static final String DISTRIBUTION_AXIS_PROPERTY = "distributionAxis";
private final DbClient dbClient;
private final System2 system;
public RenameIssueWidgets(DbClient dbClient, System2 system, RegisterIssueFilters startupDependency) {
this.dbClient = dbClient;
this.system = system;
// RegisterIssueFilters must be run before this task, to be able to reference issue filters in widget properties
}
@Override
public void start() {
DbSession session = dbClient.openSession(false);
try {
if (dbClient.loadedTemplateDao().countByTypeAndKey(LoadedTemplateDto.ONE_SHOT_TASK_TYPE, TASK_KEY, session) != 0) {
// Already done
return;
}
Map<String, IssueFilterDto> filterByWidgetKey = loadRequiredIssueFilters();
Map<String, String> distributionAxisByWidgetKey = ImmutableMap.of(
WIDGET_FALSE_POSITIVES, "resolutions",
WIDGET_MY_UNRESOLVED, "severities",
WIDGET_UNRESOLVED_BY_DEVELOPER, "assignees",
WIDGET_UNRESOLVED_BY_STATUS, "statuses"
);
LOGGER.info("Replacing issue related widgets with issue filter widgets");
List<Long> updatedWidgetIds = Lists.newArrayList();
List<WidgetPropertyDto> newWidgetProperties = Lists.newArrayList();
for (WidgetDto widget : dbClient.widgetDao().findAll(session)) {
String widgetKey = widget.getWidgetKey();
if (filterByWidgetKey.keySet().contains(widgetKey)) {
updatedWidgetIds.add(widget.getId());
newWidgetProperties.add(createFilterProperty(filterByWidgetKey.get(widgetKey), widget));
newWidgetProperties.add(createDistributionAxisProperty(distributionAxisByWidgetKey.get(widgetKey), widget));
updateWidget(session, widget);
}
}
dbClient.widgetPropertyDao().deleteByWidgetIds(session, updatedWidgetIds);
dbClient.widgetPropertyDao().insert(session, newWidgetProperties);
dbClient.loadedTemplateDao().insert(new LoadedTemplateDto()
.setType(LoadedTemplateDto.ONE_SHOT_TASK_TYPE)
.setKey(TASK_KEY), session);
session.commit();
} finally {
MyBatis.closeQuietly(session);
}
}
protected Map<String, IssueFilterDto> loadRequiredIssueFilters() {
IssueFilterDto unresolvedIssues = dbClient.issueFilterDao().selectProvidedFilterByName("Unresolved Issues");
IssueFilterDto hiddenDebt = dbClient.issueFilterDao().selectProvidedFilterByName("False Positive and Won't Fix Issues");
IssueFilterDto myUnresolvedIssues = dbClient.issueFilterDao().selectProvidedFilterByName("My Unresolved Issues");
return ImmutableMap.of(
WIDGET_FALSE_POSITIVES, hiddenDebt,
WIDGET_MY_UNRESOLVED, myUnresolvedIssues,
WIDGET_UNRESOLVED_BY_DEVELOPER, unresolvedIssues,
WIDGET_UNRESOLVED_BY_STATUS, unresolvedIssues
);
}
private WidgetPropertyDto createFilterProperty(IssueFilterDto issueFilter, WidgetDto widget) {
return createWidgetProperty(FILTER_PROPERTY, issueFilter.getId().toString(), widget);
}
private WidgetPropertyDto createDistributionAxisProperty(String distributionAxis, WidgetDto widget) {
return createWidgetProperty(DISTRIBUTION_AXIS_PROPERTY, distributionAxis, widget);
}
private WidgetPropertyDto createWidgetProperty(String key, String value, WidgetDto widget) {
return new WidgetPropertyDto()
.setWidgetId(widget.getId())
.setPropertyKey(key)
.setTextValue(value);
}
private void updateWidget(DbSession session, WidgetDto widget) {
dbClient.widgetDao().update(session,
widget.setWidgetKey(getReplacementWidgetKey(session, widget))
.setUpdatedAt(new Date(system.now()))
.setConfigured(true));
}
private String getReplacementWidgetKey(DbSession session, WidgetDto widget) {
DashboardDto dashboard = dbClient.dashboardDao().selectById(session, widget.getDashboardId());
if (dashboard == null) {
LOGGER.warn(String.format("Widget with ID=%d is not displayed on any dashboard, updating nevertheless", widget.getId()));
}
return widget.getResourceId() == null ? WIDGET_ISSUE_FILTER : WIDGET_PROJECT_ISSUE_FILTER;
}
@Override
public void stop() {
// do nothing
}
}

View File

@ -1,197 +0,0 @@
/*
* SonarQube
* Copyright (C) 2009-2016 SonarSource SA
* mailto:contact AT sonarsource DOT com
*
* This program 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.
*
* This program 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.startup;
import com.google.common.collect.Iterables;
import java.util.Arrays;
import java.util.Collection;
import java.util.List;
import org.hamcrest.BaseMatcher;
import org.junit.Before;
import org.junit.Test;
import org.mockito.ArgumentMatcher;
import org.sonar.api.web.Dashboard;
import org.sonar.api.web.DashboardLayout;
import org.sonar.api.web.DashboardTemplate;
import org.sonar.db.dashboard.ActiveDashboardDao;
import org.sonar.db.dashboard.ActiveDashboardDto;
import org.sonar.db.dashboard.DashboardDao;
import org.sonar.db.dashboard.DashboardDto;
import org.sonar.db.dashboard.WidgetDto;
import org.sonar.db.dashboard.WidgetPropertyDto;
import org.sonar.db.loadedtemplate.LoadedTemplateDao;
import org.sonar.db.loadedtemplate.LoadedTemplateDto;
import static org.assertj.core.api.Assertions.assertThat;
import static org.mockito.Matchers.any;
import static org.mockito.Matchers.argThat;
import static org.mockito.Matchers.eq;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.never;
import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.when;
public class RegisterDashboardsTest {
private RegisterDashboards task;
private DashboardDao dashboardDao;
private ActiveDashboardDao activeDashboardDao;
private LoadedTemplateDao loadedTemplateDao;
private DashboardTemplate fakeDashboardTemplate;
@Before
public void init() {
dashboardDao = mock(DashboardDao.class);
activeDashboardDao = mock(ActiveDashboardDao.class);
loadedTemplateDao = mock(LoadedTemplateDao.class);
fakeDashboardTemplate = mock(DashboardTemplate.class);
task = new RegisterDashboards(new DashboardTemplate[] {fakeDashboardTemplate}, dashboardDao,
activeDashboardDao, loadedTemplateDao, null);
}
@Test
public void testStart() {
when(fakeDashboardTemplate.createDashboard()).thenReturn(newGlobalDashboard());
task.start();
verify(dashboardDao).insert(any(DashboardDto.class));
verify(loadedTemplateDao).insert(any(LoadedTemplateDto.class));
verify(activeDashboardDao).insert(any(ActiveDashboardDto.class));
task.stop();
}
@Test
public void shouldNotRegister() {
when(loadedTemplateDao.countByTypeAndKey(LoadedTemplateDto.DASHBOARD_TYPE, "Fake")).thenReturn(1);
assertThat(task.shouldRegister("Fake")).isFalse();
}
@Test
public void shouldRegisterDashboard() {
when(loadedTemplateDao.countByTypeAndKey(LoadedTemplateDto.DASHBOARD_TYPE, "Fake")).thenReturn(0);
assertThat(task.shouldRegister("Fake")).isTrue();
}
@Test
public void should_register_and_activate_dashboard() {
when(fakeDashboardTemplate.createDashboard()).thenReturn(newGlobalDashboard());
DashboardDto dashboardDto = task.register("Fake", fakeDashboardTemplate.createDashboard());
verify(dashboardDao).insert(dashboardDto);
verify(loadedTemplateDao).insert(eq(new LoadedTemplateDto("Fake", LoadedTemplateDto.DASHBOARD_TYPE)));
}
@Test
public void should_activate_dashboard() {
when(fakeDashboardTemplate.createDashboard()).thenReturn(newGlobalDashboard());
task.start();
verify(activeDashboardDao).insert(any(ActiveDashboardDto.class));
}
@Test
public void should_not_activate_project_dashboards() {
Dashboard dashboard = Dashboard.create().setGlobal(false);
when(fakeDashboardTemplate.createDashboard()).thenReturn(dashboard);
task.start();
verify(activeDashboardDao, never()).insert(any(ActiveDashboardDto.class));
verify(loadedTemplateDao, never()).insert(any(LoadedTemplateDto.class));
}
@Test
public void should_disable_activation() {
Dashboard dashboard = newGlobalDashboard();
dashboard.setActivated(false);
when(fakeDashboardTemplate.createDashboard()).thenReturn(dashboard);
task.start();
verify(activeDashboardDao, never()).insert(any(ActiveDashboardDto.class));
}
@Test
public void shouldCreateDtoFromExtension() {
Dashboard dashboard = newGlobalDashboard()
.setLayout(DashboardLayout.TWO_COLUMNS_30_70);
Dashboard.Widget widget = dashboard.addWidget("fake-widget", 1);
widget.setProperty("fake-property", "fake_metric");
when(fakeDashboardTemplate.createDashboard()).thenReturn(dashboard);
DashboardDto dto = task.createDtoFromExtension("Fake", fakeDashboardTemplate.createDashboard());
assertThat(dto.getUserId()).isNull();
assertThat(dto.getName()).isEqualTo("Fake");
assertThat(dto.getDescription()).isNull();
assertThat(dto.getColumnLayout()).isEqualTo("30%-70%");
assertThat(dto.getShared()).isTrue();
assertThat(dto.getCreatedAt()).isNotNull();
assertThat(dto.getUpdatedAt()).isNotNull();
WidgetDto widgetDto = Iterables.getOnlyElement(dto.getWidgets());
assertThat(widgetDto.getWidgetKey()).isEqualTo("fake-widget");
assertThat(widgetDto.getDescription()).isNull();
assertThat(widgetDto.getColumnIndex()).isEqualTo(1);
assertThat(widgetDto.getRowIndex()).isEqualTo(1);
assertThat(widgetDto.getConfigured()).isTrue();
assertThat(widgetDto.getCreatedAt()).isNotNull();
assertThat(widgetDto.getUpdatedAt()).isNotNull();
Collection<WidgetPropertyDto> props = widgetDto.getWidgetProperties();
assertThat(props).hasSize(1);
WidgetPropertyDto prop = Iterables.getFirst(props, null);
assertThat(prop.getPropertyKey()).isEqualTo("fake-property");
assertThat(prop.getTextValue()).isEqualTo("fake_metric");
}
@Test
public void defaultDashboardShouldBeTheFirstActivatedDashboard() {
DashboardDto defaultDashboard = new DashboardDto().setId(10L).setName(RegisterDashboards.DEFAULT_DASHBOARD_NAME);
DashboardDto second = new DashboardDto().setId(11L).setName("Bar");
DashboardDto third = new DashboardDto().setId(12L).setName("Foo");
List<DashboardDto> dashboards = Arrays.asList(third, defaultDashboard, second);
task.activate(dashboards);
verify(activeDashboardDao).insert(argThat(matchActiveDashboardDto(10L, 1)));
verify(activeDashboardDao).insert(argThat(matchActiveDashboardDto(11L, 2)));
verify(activeDashboardDao).insert(argThat(matchActiveDashboardDto(12L, 3)));
}
private BaseMatcher<ActiveDashboardDto> matchActiveDashboardDto(final long dashboardId, final int orderId) {
return new ArgumentMatcher<ActiveDashboardDto>() {
@Override
public boolean matches(Object o) {
ActiveDashboardDto dto = (ActiveDashboardDto) o;
return dto.getDashboardId() == dashboardId && dto.getOrderIndex() == orderId;
}
};
}
private Dashboard newGlobalDashboard() {
return Dashboard.create().setGlobal(true);
}
}

View File

@ -1,94 +0,0 @@
/*
* SonarQube
* Copyright (C) 2009-2016 SonarSource SA
* mailto:contact AT sonarsource DOT com
*
* This program 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.
*
* This program 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.startup;
import java.util.Date;
import java.util.List;
import java.util.Map;
import org.junit.Rule;
import org.junit.Test;
import org.sonar.api.utils.DateUtils;
import org.sonar.api.utils.System2;
import org.sonar.db.DbClient;
import org.sonar.db.DbTester;
import org.sonar.db.dashboard.DashboardDao;
import org.sonar.db.dashboard.WidgetDao;
import org.sonar.db.dashboard.WidgetPropertyDao;
import org.sonar.db.issue.IssueFilterDao;
import org.sonar.db.loadedtemplate.LoadedTemplateDao;
import static org.assertj.core.api.Assertions.assertThat;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.when;
public class RenameIssueWidgetsTest {
@Rule
public DbTester dbTester = DbTester.create(System2.INSTANCE);
@Test
public void should_rename_widgets() {
dbTester.prepareDbUnit(this.getClass(), "before.xml");
doStart();
dbTester.assertDbUnit(this.getClass(), "after.xml", new String[] {"updated_at"}, "widgets", "widget_properties", "loaded_templates");
List<Map<String, Object>> results = dbTester.select("select updated_at as \"updatedAt\" from widgets");
assertThat(results).hasSize(6);
// First widget is not updated
assertThat(results.get(0).get("updatedAt")).isNull();
for (int i = 1; i < results.size(); i++) {
assertThat(results.get(i).get("updatedAt").toString()).startsWith("2003-03-2");
}
}
@Test
public void should_skip_when_already_executed() {
dbTester.prepareDbUnit(this.getClass(), "after.xml");
doStart();
dbTester.assertDbUnit(this.getClass(), "after.xml", "widgets", "widget_properties", "loaded_templates");
}
private void doStart() {
System2 system2 = mock(System2.class);
Date now = DateUtils.parseDateTime("2003-03-23T01:23:45+0100");
when(system2.now()).thenReturn(now.getTime());
RenameIssueWidgets task = new RenameIssueWidgets(
new DbClient(
dbTester.database(),
dbTester.myBatis(),
new WidgetDao(dbTester.myBatis()),
new WidgetPropertyDao(dbTester.myBatis()),
new IssueFilterDao(dbTester.myBatis()),
new LoadedTemplateDao(dbTester.myBatis()),
new DashboardDao(dbTester.myBatis())
),
system2,
null);
task.start();
task.stop();
}
}

View File

@ -1,115 +0,0 @@
<dataset>
<issue_filters
id="1"
name="Unresolved Issues"
user_login="[null]"
shared="[true]"
description="[null]"
data="resolved=false"
created_at="2011-04-25 01:15:00"
updated_at="2011-04-25 01:15:00" />
<issue_filters
id="2"
name="False Positive and Won't Fix Issues"
user_login="[null]"
shared="[true]"
description="[null]"
data="resolutions=FALSE-POSITIVE,WONTFIX"
created_at="2011-04-25 01:15:00"
updated_at="2011-04-25 01:15:00" />
<issue_filters
id="3"
name="My Unresolved Issues"
user_login="[null]"
shared="[true]"
description="[null]"
data="resolved=false|assignees=__me__"
created_at="2011-04-25 01:15:00"
updated_at="2011-04-25 01:15:00" />
<dashboards
id="1"
user_id="[null]"
name="[null]"
description="[null]"
column_layout="[null]"
shared="[true]"
created_at="[null]"
updated_at="[null]"
/>
<dashboards
id="2"
user_id="[null]"
name="[null]"
description="[null]"
column_layout="[null]"
shared="[true]"
created_at="[null]"
updated_at="[null]"
/>
<widgets id="1" dashboard_id="1" widget_key="polop" name="[null]" description="[null]"
column_index="1" row_index="1" configured="[true]" created_at="[null]" updated_at="[null]" resource_id="[null]"/>
<widget_properties id="1" widget_id="1" kee="palap" text_value="pulup"/>
<!-- 'False Positive Issues' - replaced by project_issue_filter w/ 'False Positive and Won't Fix Issues' filter -->
<widgets id="2" dashboard_id="1" widget_key="issue_filter" name="[null]" description="[null]"
column_index="1" row_index="2" configured="[true]" created_at="[null]" updated_at="2003-03-23 01:23:45" resource_id="[null]"/>
<!-- filter = 'False Positive and Won't Fix Issues' -->
<widget_properties id="3" widget_id="2" kee="filter" text_value="2"/>
<!-- distributionAxis is 'resolutions' -->
<widget_properties id="4" widget_id="2" kee="distributionAxis" text_value="resolutions"/>
<!-- 'My Unresolved Issues' - replaced by project_issue_filter w/ 'My Unresolved Issues' filter -->
<widgets id="3" dashboard_id="1" widget_key="issue_filter" name="[null]" description="[null]"
column_index="1" row_index="3" configured="[true]" created_at="[null]" updated_at="2003-03-23 01:23:45" resource_id="[null]"/>
<!-- filter = 'My Unresolved Issues' -->
<widget_properties id="5" widget_id="3" kee="filter" text_value="3"/>
<!-- distributionAxis is 'severities' -->
<widget_properties id="6" widget_id="3" kee="distributionAxis" text_value="severities"/>
<!-- 'Unresolved Issues Per Developer' - on a global dashboard, replaced by project_issue_filter w/ 'Unresolved Issues' filter -->
<widgets id="4" dashboard_id="2" widget_key="project_issue_filter" name="[null]" description="[null]"
column_index="1" row_index="4" configured="[true]" created_at="[null]" updated_at="2003-03-23 01:23:45" resource_id="12345"/>
<!-- filter = 'Unresolved Issues' -->
<widget_properties id="7" widget_id="4" kee="filter" text_value="1"/>
<!-- distributionAxis is 'assignees' -->
<widget_properties id="8" widget_id="4" kee="distributionAxis" text_value="assignees"/>
<!-- 'Unresolved Issues Per Status' - on a global dashboard without resource_id, replaced by issue_filter w/ 'Unresolved Issues' filter -->
<widgets id="5" dashboard_id="2" widget_key="issue_filter" name="[null]" description="[null]"
column_index="1" row_index="5" configured="[true]" created_at="[null]" updated_at="2003-03-23 01:23:45" resource_id="[null]"/>
<!-- filter = 'Unresolved Issues' -->
<widget_properties id="9" widget_id="5" kee="filter" text_value="1"/>
<!-- distributionAxis is 'assignees' -->
<widget_properties id="10" widget_id="5" kee="distributionAxis" text_value="statuses"/>
<!-- 'Unresolved Issues Per Status' - dashboard not found, still replaced by issue_filter w/ 'Unresolved Issues' filter -->
<widgets id="6" dashboard_id="3" widget_key="issue_filter" name="[null]" description="[null]"
column_index="1" row_index="1" configured="[true]" created_at="[null]" updated_at="2003-03-23 01:23:45" resource_id="[null]"/>
<!-- filter = 'Unresolved Issues' -->
<widget_properties id="11" widget_id="6" kee="filter" text_value="1"/>
<!-- distributionAxis is 'assignees' -->
<widget_properties id="12" widget_id="6" kee="distributionAxis" text_value="statuses"/>
<loaded_templates id="1" template_type="ONE_SHOT_TASK" kee="RenameIssueWidgets"/>
</dataset>

View File

@ -1,92 +0,0 @@
<dataset>
<issue_filters
id="1"
name="Unresolved Issues"
user_login="[null]"
shared="[true]"
description="[null]"
data="resolved=false"
created_at="2011-04-25 01:15:00"
updated_at="2011-04-25 01:15:00" />
<issue_filters
id="2"
name="False Positive and Won't Fix Issues"
user_login="[null]"
shared="[true]"
description="[null]"
data="resolutions=FALSE-POSITIVE,WONTFIX"
created_at="2011-04-25 01:15:00"
updated_at="2011-04-25 01:15:00" />
<issue_filters
id="3"
name="My Unresolved Issues"
user_login="[null]"
shared="[true]"
description="[null]"
data="resolved=false|assignees=__me__"
created_at="2011-04-25 01:15:00"
updated_at="2011-04-25 01:15:00" />
<dashboards
id="1"
user_id="[null]"
name="[null]"
description="[null]"
column_layout="[null]"
shared="[true]"
created_at="[null]"
updated_at="[null]"
/>
<dashboards
id="2"
user_id="[null]"
name="[null]"
description="[null]"
column_layout="[null]"
shared="[true]"
created_at="[null]"
updated_at="[null]"
/>
<!-- Will not be modified -->
<widgets id="1" dashboard_id="1" widget_key="polop" name="[null]" description="[null]"
column_index="1" row_index="1" configured="[true]" created_at="[null]" updated_at="[null]" resource_id="[null]"/>
<widget_properties id="1" widget_id="1" kee="palap" text_value="pulup"/>
<!-- 'False Positive Issues' - replaced by project_issue_filter w/ 'False Positive and Won't Fix Issues' filter -->
<widgets id="2" dashboard_id="1" widget_key="false_positive_reviews" name="[null]" description="[null]"
column_index="1" row_index="2" configured="[true]" created_at="[null]" updated_at="[null]" resource_id="[null]"/>
<!-- 'My Unresolved Issues' - replaced by project_issue_filter w/ 'My Unresolved Issues' filter -->
<widgets id="3" dashboard_id="1" widget_key="my_reviews" name="[null]" description="[null]"
column_index="1" row_index="3" configured="[true]" created_at="[null]" updated_at="[null]" resource_id="[null]"/>
<!-- config for 'My Unresolved Issues' - will be deleted -->
<widget_properties id="2" widget_id="3" kee="numberOfLines" text_value="20"/>
<!-- 'Unresolved Issues Per Developer' - replaced by project_issue_filter w/ 'Unresolved Issues' filter -->
<widgets id="4" dashboard_id="2" widget_key="reviews_per_developer" name="[null]" description="[null]"
column_index="1" row_index="4" configured="[true]" created_at="[null]" updated_at="[null]" resource_id="12345"/>
<!-- 'Unresolved Issues Per Status' - on a global dashboard without resource_id, replaced by issue_filter w/ 'Unresolved Issues' filter -->
<widgets id="5" dashboard_id="2" widget_key="unresolved_issues_statuses" name="[null]" description="[null]"
column_index="1" row_index="5" configured="[true]" created_at="[null]" updated_at="[null]" resource_id="[null]"/>
<!-- 'Unresolved Issues Per Status' - dashboard not found, still replaced by issue_filter w/ 'Unresolved Issues' filter -->
<widgets id="6" dashboard_id="3" widget_key="unresolved_issues_statuses" name="[null]" description="[null]"
column_index="1" row_index="1" configured="[true]" created_at="[null]" updated_at="[null]" resource_id="[null]"/>
</dataset>