aboutsummaryrefslogtreecommitdiffstats
path: root/server
diff options
context:
space:
mode:
authorJean-Baptiste Lievremont <jean-baptiste.lievremont@sonarsource.com>2015-03-12 17:56:46 +0100
committerJean-Baptiste Lievremont <jean-baptiste.lievremont@sonarsource.com>2015-03-18 13:19:47 +0100
commit94ab0b3fb528418dbe747d0ab7f59b8dbb7bf177 (patch)
tree2960ae3b226b83f9c7221197d16b814df03e634d /server
parent15772b15068d3fb54032aac52889172b9329fc2c (diff)
downloadsonarqube-94ab0b3fb528418dbe747d0ab7f59b8dbb7bf177.tar.gz
sonarqube-94ab0b3fb528418dbe747d0ab7f59b8dbb7bf177.zip
SONAR-6236 Migrate existing dashboards to use the new issue widgets
Diffstat (limited to 'server')
-rw-r--r--server/sonar-server/src/main/java/org/sonar/server/dashboard/db/WidgetDao.java10
-rw-r--r--server/sonar-server/src/main/java/org/sonar/server/dashboard/db/WidgetPropertyDao.java11
-rw-r--r--server/sonar-server/src/main/java/org/sonar/server/db/DbClient.java7
-rw-r--r--server/sonar-server/src/main/java/org/sonar/server/platform/ServerComponents.java1
-rw-r--r--server/sonar-server/src/main/java/org/sonar/server/startup/RegisterDashboards.java14
-rw-r--r--server/sonar-server/src/main/java/org/sonar/server/startup/RenameIssueWidgets.java151
-rw-r--r--server/sonar-server/src/test/java/org/sonar/server/startup/RegisterDashboardsTest.java9
-rw-r--r--server/sonar-server/src/test/java/org/sonar/server/startup/RenameIssueWidgetsTest.java84
-rw-r--r--server/sonar-server/src/test/resources/org/sonar/server/startup/RenameIssueWidgetsTest/after.xml81
-rw-r--r--server/sonar-server/src/test/resources/org/sonar/server/startup/RenameIssueWidgetsTest/before.xml65
-rw-r--r--server/sonar-server/src/test/resources/org/sonar/server/startup/RenameIssueWidgetsTest/empty.xml3
11 files changed, 420 insertions, 16 deletions
diff --git a/server/sonar-server/src/main/java/org/sonar/server/dashboard/db/WidgetDao.java b/server/sonar-server/src/main/java/org/sonar/server/dashboard/db/WidgetDao.java
index ca7b10d9e5f..d6d12e4c0f5 100644
--- a/server/sonar-server/src/main/java/org/sonar/server/dashboard/db/WidgetDao.java
+++ b/server/sonar-server/src/main/java/org/sonar/server/dashboard/db/WidgetDao.java
@@ -38,7 +38,17 @@ public class WidgetDao extends BaseDao<WidgetMapper, WidgetDto, Long> {
return mapper(session).selectById(widgetId);
}
+ @Override
+ protected WidgetDto doUpdate(DbSession session, WidgetDto item) {
+ mapper(session).update(item);
+ return item;
+ }
+
public Collection<WidgetDto> findByDashboard(DbSession session, long dashboardKey) {
return mapper(session).selectByDashboard(dashboardKey);
}
+
+ public Collection<WidgetDto> findAll(DbSession session) {
+ return mapper(session).selectAll();
+ }
}
diff --git a/server/sonar-server/src/main/java/org/sonar/server/dashboard/db/WidgetPropertyDao.java b/server/sonar-server/src/main/java/org/sonar/server/dashboard/db/WidgetPropertyDao.java
index ae85a6fd386..9aeead48d6a 100644
--- a/server/sonar-server/src/main/java/org/sonar/server/dashboard/db/WidgetPropertyDao.java
+++ b/server/sonar-server/src/main/java/org/sonar/server/dashboard/db/WidgetPropertyDao.java
@@ -26,6 +26,7 @@ import org.sonar.core.persistence.DbSession;
import org.sonar.server.db.BaseDao;
import java.util.Collection;
+import java.util.List;
public class WidgetPropertyDao extends BaseDao<WidgetPropertyMapper, WidgetPropertyDto, Long> {
@@ -34,6 +35,12 @@ public class WidgetPropertyDao extends BaseDao<WidgetPropertyMapper, WidgetPrope
}
@Override
+ protected WidgetPropertyDto doInsert(DbSession session, WidgetPropertyDto item) {
+ mapper(session).insert(item);
+ return item;
+ }
+
+ @Override
protected WidgetPropertyDto doGetNullableByKey(DbSession session, Long propertyId) {
return mapper(session).selectById(propertyId);
}
@@ -42,4 +49,8 @@ public class WidgetPropertyDao extends BaseDao<WidgetPropertyMapper, WidgetPrope
return mapper(session).selectByDashboard(dashboardKey);
}
+ public void deleteByWidgetIds(DbSession session, List<Long> widgetIdsWithPropertiesToDelete) {
+ mapper(session).deleteByWidgetIds(widgetIdsWithPropertiesToDelete);
+ }
+
}
diff --git a/server/sonar-server/src/main/java/org/sonar/server/db/DbClient.java b/server/sonar-server/src/main/java/org/sonar/server/db/DbClient.java
index a0056e42064..fe5106cc7d6 100644
--- a/server/sonar-server/src/main/java/org/sonar/server/db/DbClient.java
+++ b/server/sonar-server/src/main/java/org/sonar/server/db/DbClient.java
@@ -22,6 +22,7 @@ package org.sonar.server.db;
import org.sonar.api.ServerComponent;
import org.sonar.core.issue.db.ActionPlanDao;
import org.sonar.core.issue.db.IssueChangeDao;
+import org.sonar.core.issue.db.IssueFilterDao;
import org.sonar.core.persistence.DaoComponent;
import org.sonar.core.persistence.Database;
import org.sonar.core.persistence.DbSession;
@@ -82,6 +83,7 @@ public class DbClient implements ServerComponent {
private final UserDao userDao;
private final GroupDao groupDao;
private final IssueDao issueDao;
+ private final IssueFilterDao issueFilterDao;
private final IssueChangeDao issueChangeDao;
private final ActionPlanDao actionPlanDao;
private final AnalysisReportDao analysisReportDao;
@@ -118,6 +120,7 @@ public class DbClient implements ServerComponent {
userDao = getDao(map, UserDao.class);
groupDao = getDao(map, GroupDao.class);
issueDao = getDao(map, IssueDao.class);
+ issueFilterDao = getDao(map, IssueFilterDao.class);
issueChangeDao = getDao(map, IssueChangeDao.class);
actionPlanDao = getDao(map, ActionPlanDao.class);
analysisReportDao = getDao(map, AnalysisReportDao.class);
@@ -151,6 +154,10 @@ public class DbClient implements ServerComponent {
return issueDao;
}
+ public IssueFilterDao issueFilterDao() {
+ return issueFilterDao;
+ }
+
public IssueChangeDao issueChangeDao() {
return issueChangeDao;
}
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 6542ea824c6..1d9da7f47f4 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
@@ -709,6 +709,7 @@ class ServerComponents {
startupContainer.addSingleton(RegisterServletFilters.class);
startupContainer.addSingleton(CopyRequirementsFromCharacteristicsToRules.class);
startupContainer.addSingleton(ReportQueueCleaner.class);
+ startupContainer.addSingleton(RenameIssueWidgets.class);
DoPrivileged.execute(new DoPrivileged.Task() {
@Override
diff --git a/server/sonar-server/src/main/java/org/sonar/server/startup/RegisterDashboards.java b/server/sonar-server/src/main/java/org/sonar/server/startup/RegisterDashboards.java
index baea633bb32..084820d0a64 100644
--- a/server/sonar-server/src/main/java/org/sonar/server/startup/RegisterDashboards.java
+++ b/server/sonar-server/src/main/java/org/sonar/server/startup/RegisterDashboards.java
@@ -27,14 +27,10 @@ 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.core.dashboard.ActiveDashboardDao;
-import org.sonar.core.dashboard.ActiveDashboardDto;
-import org.sonar.core.dashboard.DashboardDao;
-import org.sonar.core.dashboard.DashboardDto;
-import org.sonar.core.dashboard.WidgetDto;
-import org.sonar.core.dashboard.WidgetPropertyDto;
+import org.sonar.core.dashboard.*;
import org.sonar.core.template.LoadedTemplateDao;
import org.sonar.core.template.LoadedTemplateDto;
+import org.sonar.server.issue.filter.RegisterIssueFilters;
import java.io.Serializable;
import java.util.Date;
@@ -55,7 +51,7 @@ public class RegisterDashboards implements Startable {
private final LoadedTemplateDao loadedTemplateDao;
public RegisterDashboards(DashboardTemplate[] dashboardTemplatesArray, DashboardDao dashboardDao,
- ActiveDashboardDao activeDashboardDao, LoadedTemplateDao loadedTemplateDao) {
+ ActiveDashboardDao activeDashboardDao, LoadedTemplateDao loadedTemplateDao, RegisterIssueFilters startupDependency) {
this.dashboardTemplates = Lists.newArrayList(dashboardTemplatesArray);
this.dashboardDao = dashboardDao;
this.activeDashboardDao = activeDashboardDao;
@@ -65,8 +61,8 @@ public class RegisterDashboards implements Startable {
/**
* Used when no plugin is defining some DashboardTemplate
*/
- public RegisterDashboards(DashboardDao dashboardDao, ActiveDashboardDao activeDashboardDao, LoadedTemplateDao loadedTemplateDao) {
- this(new DashboardTemplate[] {}, dashboardDao, activeDashboardDao, loadedTemplateDao);
+ public RegisterDashboards(DashboardDao dashboardDao, ActiveDashboardDao activeDashboardDao, LoadedTemplateDao loadedTemplateDao, RegisterIssueFilters registerIssueFilters) {
+ this(new DashboardTemplate[] {}, dashboardDao, activeDashboardDao, loadedTemplateDao, registerIssueFilters);
}
@Override
diff --git a/server/sonar-server/src/main/java/org/sonar/server/startup/RenameIssueWidgets.java b/server/sonar-server/src/main/java/org/sonar/server/startup/RenameIssueWidgets.java
new file mode 100644
index 00000000000..e0fbf821209
--- /dev/null
+++ b/server/sonar-server/src/main/java/org/sonar/server/startup/RenameIssueWidgets.java
@@ -0,0 +1,151 @@
+/*
+ * 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.startup;
+
+import com.google.common.collect.Lists;
+import org.picocontainer.Startable;
+import org.sonar.api.utils.log.Loggers;
+import org.sonar.core.dashboard.WidgetDto;
+import org.sonar.core.dashboard.WidgetPropertyDto;
+import org.sonar.core.issue.db.IssueFilterDto;
+import org.sonar.core.persistence.DbSession;
+import org.sonar.core.persistence.MyBatis;
+import org.sonar.core.template.LoadedTemplateDto;
+import org.sonar.server.db.DbClient;
+
+import java.util.List;
+
+public class RenameIssueWidgets implements Startable {
+
+ private static final String PROJECT_ISSUE_FILTER_WIDGET_KEY = "project_issue_filter";
+ private static final String FILTER_PROPERTY = "filter";
+ private static final String DISTRIBUTION_AXIS_PROPERTY = "distributionAxis";
+
+ private final DbClient dbClient;
+
+ public RenameIssueWidgets(DbClient dbClient) {
+ this.dbClient = dbClient;
+ }
+
+ @Override
+ public void start() {
+ DbSession session = dbClient.openSession(false);
+
+ try {
+ if (dbClient.loadedTemplateDao().countByTypeAndKey(LoadedTemplateDto.ONE_SHOT_TASK_TYPE, getClass().getSimpleName()) != 0) {
+ // Already done
+ return;
+ }
+
+ 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");
+
+ if (unresolvedIssues == null || hiddenDebt == null || myUnresolvedIssues == null) {
+ // One of the filter has been deleted, no need to do anything
+ return;
+ }
+
+ Loggers.get(getClass()).info("Replacing issue related widgets with issue filter widgets");
+
+ List<Long> widgetIdsWithPropertiesToDelete = Lists.newArrayList();
+ List<WidgetPropertyDto> widgetPropertiesToCreate = Lists.newArrayList();
+
+ for (WidgetDto widget : dbClient.widgetDao().findAll(session)) {
+ switch (widget.getWidgetKey()) {
+ case "false_positive_reviews":
+ widgetPropertiesToCreate.add(
+ new WidgetPropertyDto()
+ .setWidgetId(widget.getId())
+ .setPropertyKey(FILTER_PROPERTY)
+ .setTextValue(hiddenDebt.getId().toString()));
+ widgetPropertiesToCreate.add(
+ new WidgetPropertyDto()
+ .setWidgetId(widget.getId())
+ .setPropertyKey(DISTRIBUTION_AXIS_PROPERTY)
+ .setTextValue("resolutions"));
+ updateWidget(session, widgetIdsWithPropertiesToDelete, widget);
+ break;
+ case "my_reviews":
+ widgetPropertiesToCreate.add(
+ new WidgetPropertyDto()
+ .setWidgetId(widget.getId())
+ .setPropertyKey(FILTER_PROPERTY)
+ .setTextValue(myUnresolvedIssues.getId().toString()));
+ updateWidget(session, widgetIdsWithPropertiesToDelete, widget);
+ break;
+ case "reviews_per_developer":
+ widgetPropertiesToCreate.add(
+ new WidgetPropertyDto()
+ .setWidgetId(widget.getId())
+ .setPropertyKey(FILTER_PROPERTY)
+ .setTextValue(unresolvedIssues.getId().toString()));
+ widgetPropertiesToCreate.add(
+ new WidgetPropertyDto()
+ .setWidgetId(widget.getId())
+ .setPropertyKey(DISTRIBUTION_AXIS_PROPERTY)
+ .setTextValue("assignees"));
+ updateWidget(session, widgetIdsWithPropertiesToDelete, widget);
+ break;
+ case "unresolved_issues_statuses":
+ widgetPropertiesToCreate.add(
+ new WidgetPropertyDto()
+ .setWidgetId(widget.getId())
+ .setPropertyKey(FILTER_PROPERTY)
+ .setTextValue(unresolvedIssues.getId().toString()));
+ widgetPropertiesToCreate.add(
+ new WidgetPropertyDto()
+ .setWidgetId(widget.getId())
+ .setPropertyKey(DISTRIBUTION_AXIS_PROPERTY)
+ .setTextValue("statuses"));
+ updateWidget(session, widgetIdsWithPropertiesToDelete, widget);
+ break;
+ default:
+ // Nothing to do, move along
+ break;
+ }
+ }
+
+ dbClient.widgetPropertyDao().deleteByWidgetIds(session, widgetIdsWithPropertiesToDelete);
+ dbClient.widgetPropertyDao().insert(session, widgetPropertiesToCreate);
+
+ dbClient.loadedTemplateDao().insert(new LoadedTemplateDto()
+ .setType(LoadedTemplateDto.ONE_SHOT_TASK_TYPE)
+ .setKey(getClass().getSimpleName()), session);
+
+ session.commit();
+ } finally {
+ MyBatis.closeQuietly(session);
+ }
+ }
+
+ private void updateWidget(DbSession session, List<Long> widgetIdsWithPropertiesToDelete, WidgetDto widget) {
+ dbClient.widgetDao().update(session,
+ widget.setWidgetKey(PROJECT_ISSUE_FILTER_WIDGET_KEY)
+ .setConfigured(true));
+ widgetIdsWithPropertiesToDelete.add(widget.getId());
+ }
+
+ @Override
+ public void stop() {
+ // do nothing
+ }
+
+}
diff --git a/server/sonar-server/src/test/java/org/sonar/server/startup/RegisterDashboardsTest.java b/server/sonar-server/src/test/java/org/sonar/server/startup/RegisterDashboardsTest.java
index 64988ba63bd..5ababc6e721 100644
--- a/server/sonar-server/src/test/java/org/sonar/server/startup/RegisterDashboardsTest.java
+++ b/server/sonar-server/src/test/java/org/sonar/server/startup/RegisterDashboardsTest.java
@@ -27,12 +27,7 @@ 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.core.dashboard.ActiveDashboardDao;
-import org.sonar.core.dashboard.ActiveDashboardDto;
-import org.sonar.core.dashboard.DashboardDao;
-import org.sonar.core.dashboard.DashboardDto;
-import org.sonar.core.dashboard.WidgetDto;
-import org.sonar.core.dashboard.WidgetPropertyDto;
+import org.sonar.core.dashboard.*;
import org.sonar.core.template.LoadedTemplateDao;
import org.sonar.core.template.LoadedTemplateDto;
@@ -64,7 +59,7 @@ public class RegisterDashboardsTest {
fakeDashboardTemplate = mock(DashboardTemplate.class);
task = new RegisterDashboards(new DashboardTemplate[]{fakeDashboardTemplate}, dashboardDao,
- activeDashboardDao, loadedTemplateDao);
+ activeDashboardDao, loadedTemplateDao, null);
}
@Test
diff --git a/server/sonar-server/src/test/java/org/sonar/server/startup/RenameIssueWidgetsTest.java b/server/sonar-server/src/test/java/org/sonar/server/startup/RenameIssueWidgetsTest.java
new file mode 100644
index 00000000000..95047b5c59b
--- /dev/null
+++ b/server/sonar-server/src/test/java/org/sonar/server/startup/RenameIssueWidgetsTest.java
@@ -0,0 +1,84 @@
+/*
+ * 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.startup;
+
+import org.junit.Rule;
+import org.junit.Test;
+import org.junit.experimental.categories.Category;
+import org.sonar.api.utils.DateUtils;
+import org.sonar.api.utils.System2;
+import org.sonar.core.issue.db.IssueFilterDao;
+import org.sonar.core.persistence.DbTester;
+import org.sonar.core.template.LoadedTemplateDao;
+import org.sonar.server.dashboard.db.WidgetDao;
+import org.sonar.server.dashboard.db.WidgetPropertyDao;
+import org.sonar.server.db.DbClient;
+import org.sonar.test.DbTests;
+
+import static org.mockito.Mockito.mock;
+import static org.mockito.Mockito.when;
+
+@Category(DbTests.class)
+public class RenameIssueWidgetsTest {
+
+ @Rule
+ public DbTester dbTester = new DbTester();
+
+ @Test
+ public void should_rename_widgets() throws Exception {
+ dbTester.prepareDbUnit(this.getClass(), "before.xml");
+
+ doStart();
+
+ dbTester.assertDbUnit(this.getClass(), "after.xml", "widgets", "widget_properties", "loaded_templates");
+ }
+
+ @Test
+ public void should_skip_when_filter_removed() throws Exception {
+ dbTester.prepareDbUnit(this.getClass(), "empty.xml");
+
+ doStart();
+ }
+
+ @Test
+ public void should_skip_when_already_executed() throws Exception {
+ dbTester.prepareDbUnit(this.getClass(), "after.xml");
+
+ doStart();
+ }
+
+ private void doStart() {
+ System2 system2 = mock(System2.class);
+ when(system2.now()).thenReturn(DateUtils.parseDateTime("2003-03-23T01:23:45+0100").getTime());
+
+ RenameIssueWidgets task = new RenameIssueWidgets(
+ new DbClient(
+ dbTester.database(),
+ dbTester.myBatis(),
+ new WidgetDao(system2),
+ new WidgetPropertyDao(system2),
+ new IssueFilterDao(dbTester.myBatis()),
+ new LoadedTemplateDao(dbTester.myBatis())
+ ));
+
+ task.start();
+ task.stop();
+ }
+}
diff --git a/server/sonar-server/src/test/resources/org/sonar/server/startup/RenameIssueWidgetsTest/after.xml b/server/sonar-server/src/test/resources/org/sonar/server/startup/RenameIssueWidgetsTest/after.xml
new file mode 100644
index 00000000000..ab8310df45a
--- /dev/null
+++ b/server/sonar-server/src/test/resources/org/sonar/server/startup/RenameIssueWidgetsTest/after.xml
@@ -0,0 +1,81 @@
+<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" />
+
+
+ <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="project_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="project_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 'default', no other config -->
+
+
+ <!-- 'Unresolved Issues Per Developer' - replaced by project_issue_filter w/ 'Unresolved Issues' filter -->
+ <widgets id="4" dashboard_id="1" 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="[null]"/>
+
+ <!-- filter = 'Unresolved Issues' -->
+ <widget_properties id="6" widget_id="4" kee="filter" text_value="1"/>
+ <!-- distributionAxis is 'assignees' -->
+ <widget_properties id="7" widget_id="4" kee="distributionAxis" text_value="assignees"/>
+
+
+ <!-- 'Unresolved Issues Per Status' - replaced by project_issue_filter w/ 'Unresolved Issues' filter -->
+ <widgets id="5" dashboard_id="1" widget_key="project_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="8" widget_id="5" kee="filter" text_value="1"/>
+ <!-- distributionAxis is 'assignees' -->
+ <widget_properties id="9" widget_id="5" kee="distributionAxis" text_value="statuses"/>
+
+
+ <loaded_templates id="1" template_type="ONE_SHOT_TASK" kee="RenameIssueWidgets"/>
+
+</dataset>
diff --git a/server/sonar-server/src/test/resources/org/sonar/server/startup/RenameIssueWidgetsTest/before.xml b/server/sonar-server/src/test/resources/org/sonar/server/startup/RenameIssueWidgetsTest/before.xml
new file mode 100644
index 00000000000..d22705c26af
--- /dev/null
+++ b/server/sonar-server/src/test/resources/org/sonar/server/startup/RenameIssueWidgetsTest/before.xml
@@ -0,0 +1,65 @@
+<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" />
+
+
+ <!-- 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="1" 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="[null]"/>
+
+
+ <!-- 'Unresolved Issues Per Status' - replaced by project_issue_filter w/ 'Unresolved Issues' filter -->
+ <widgets id="5" dashboard_id="1" 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]"/>
+
+
+</dataset>
diff --git a/server/sonar-server/src/test/resources/org/sonar/server/startup/RenameIssueWidgetsTest/empty.xml b/server/sonar-server/src/test/resources/org/sonar/server/startup/RenameIssueWidgetsTest/empty.xml
new file mode 100644
index 00000000000..871dedcb5e9
--- /dev/null
+++ b/server/sonar-server/src/test/resources/org/sonar/server/startup/RenameIssueWidgetsTest/empty.xml
@@ -0,0 +1,3 @@
+<dataset>
+
+</dataset>