diff options
author | Simon Brandhof <simon.brandhof@sonarsource.com> | 2015-06-03 10:31:16 +0200 |
---|---|---|
committer | Simon Brandhof <simon.brandhof@sonarsource.com> | 2015-07-02 16:06:08 +0200 |
commit | bf4118d6a9ceb9ad24274cdc6537d4a607121815 (patch) | |
tree | 8f758ccb7a205da3eae96b05b74f79cade8ceae0 /sonar-batch | |
parent | 2f948758eebec934beb54701792cf2d558319251 (diff) | |
download | sonarqube-bf4118d6a9ceb9ad24274cdc6537d4a607121815.tar.gz sonarqube-bf4118d6a9ceb9ad24274cdc6537d4a607121815.zip |
SONAR-6623 extract issue tracking algorithm from batch
Diffstat (limited to 'sonar-batch')
52 files changed, 57 insertions, 2066 deletions
diff --git a/sonar-batch/src/main/java/org/sonar/batch/bootstrap/BatchComponents.java b/sonar-batch/src/main/java/org/sonar/batch/bootstrap/BatchComponents.java index d40e1c223f7..879ae9afb82 100644 --- a/sonar-batch/src/main/java/org/sonar/batch/bootstrap/BatchComponents.java +++ b/sonar-batch/src/main/java/org/sonar/batch/bootstrap/BatchComponents.java @@ -40,10 +40,7 @@ import org.sonar.batch.cpd.CpdComponents; import org.sonar.batch.debt.DebtDecorator; import org.sonar.batch.debt.IssueChangelogDebtCalculator; import org.sonar.batch.debt.NewDebtDecorator; -import org.sonar.batch.issue.tracking.InitialOpenIssuesSensor; -import org.sonar.batch.issue.tracking.IssueHandlers; import org.sonar.batch.issue.tracking.IssueTracking; -import org.sonar.batch.issue.tracking.IssueTrackingDecorator; import org.sonar.batch.language.LanguageDistributionDecorator; import org.sonar.batch.scan.report.ConsoleReport; import org.sonar.batch.scan.report.HtmlReport; @@ -92,11 +89,6 @@ public class BatchComponents { DebtDecorator.class, NewDebtDecorator.class, - // Issue tracking - IssueTrackingDecorator.class, - IssueHandlers.class, - InitialOpenIssuesSensor.class, - // to be moved to compute engine UnitTestDecorator.class, LineCoverageDecorator.class, diff --git a/sonar-batch/src/main/java/org/sonar/batch/debt/DebtDecorator.java b/sonar-batch/src/main/java/org/sonar/batch/debt/DebtDecorator.java index 5ddb7e45949..b339ead086a 100644 --- a/sonar-batch/src/main/java/org/sonar/batch/debt/DebtDecorator.java +++ b/sonar-batch/src/main/java/org/sonar/batch/debt/DebtDecorator.java @@ -38,7 +38,7 @@ import org.sonar.api.batch.rule.Rules; import org.sonar.api.component.ResourcePerspectives; import org.sonar.api.issue.Issuable; import org.sonar.api.issue.Issue; -import org.sonar.api.issue.internal.DefaultIssue; +import org.sonar.core.issue.DefaultIssue; import org.sonar.api.measures.CoreMetrics; import org.sonar.api.measures.Measure; import org.sonar.api.measures.MeasuresFilters; diff --git a/sonar-batch/src/main/java/org/sonar/batch/debt/IssueChangelogDebtCalculator.java b/sonar-batch/src/main/java/org/sonar/batch/debt/IssueChangelogDebtCalculator.java index fb882a7a0eb..5d34e8f89de 100644 --- a/sonar-batch/src/main/java/org/sonar/batch/debt/IssueChangelogDebtCalculator.java +++ b/sonar-batch/src/main/java/org/sonar/batch/debt/IssueChangelogDebtCalculator.java @@ -34,8 +34,8 @@ import javax.annotation.Nullable; import org.apache.commons.lang.time.DateUtils; import org.sonar.api.batch.BatchSide; import org.sonar.api.issue.Issue; -import org.sonar.api.issue.internal.DefaultIssue; -import org.sonar.api.issue.internal.FieldDiffs; +import org.sonar.core.issue.DefaultIssue; +import org.sonar.core.issue.FieldDiffs; import org.sonar.core.issue.IssueUpdater; import static com.google.common.collect.Lists.newArrayList; diff --git a/sonar-batch/src/main/java/org/sonar/batch/index/ScanPersister.java b/sonar-batch/src/main/java/org/sonar/batch/index/ScanPersister.java deleted file mode 100644 index 88b749ecb18..00000000000 --- a/sonar-batch/src/main/java/org/sonar/batch/index/ScanPersister.java +++ /dev/null @@ -1,29 +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.batch.index; - -import org.sonar.api.batch.BatchSide; - -@BatchSide -public interface ScanPersister { - - void persist(); - -} diff --git a/sonar-batch/src/main/java/org/sonar/batch/issue/DefaultIssuable.java b/sonar-batch/src/main/java/org/sonar/batch/issue/DefaultIssuable.java index 89561865d63..9dd268a8d22 100644 --- a/sonar-batch/src/main/java/org/sonar/batch/issue/DefaultIssuable.java +++ b/sonar-batch/src/main/java/org/sonar/batch/issue/DefaultIssuable.java @@ -23,7 +23,7 @@ import com.google.common.collect.Lists; import java.util.List; import org.sonar.api.issue.Issuable; import org.sonar.api.issue.Issue; -import org.sonar.api.issue.internal.DefaultIssue; +import org.sonar.core.issue.DefaultIssue; import org.sonar.api.resources.Project; import org.sonar.batch.index.BatchComponent; import org.sonar.core.issue.DefaultIssueBuilder; diff --git a/sonar-batch/src/main/java/org/sonar/batch/issue/DefaultProjectIssues.java b/sonar-batch/src/main/java/org/sonar/batch/issue/DefaultProjectIssues.java index 1cc682c0e34..ed9de9a5def 100644 --- a/sonar-batch/src/main/java/org/sonar/batch/issue/DefaultProjectIssues.java +++ b/sonar-batch/src/main/java/org/sonar/batch/issue/DefaultProjectIssues.java @@ -23,7 +23,7 @@ import com.google.common.base.Predicate; import com.google.common.collect.Iterables; import org.sonar.api.issue.Issue; import org.sonar.api.issue.ProjectIssues; -import org.sonar.api.issue.internal.DefaultIssue; +import org.sonar.core.issue.DefaultIssue; import javax.annotation.Nullable; diff --git a/sonar-batch/src/main/java/org/sonar/batch/issue/IssueCache.java b/sonar-batch/src/main/java/org/sonar/batch/issue/IssueCache.java index dc5daaaafb4..52a29fb7483 100644 --- a/sonar-batch/src/main/java/org/sonar/batch/issue/IssueCache.java +++ b/sonar-batch/src/main/java/org/sonar/batch/issue/IssueCache.java @@ -20,7 +20,7 @@ package org.sonar.batch.issue; import org.sonar.api.batch.BatchSide; -import org.sonar.api.issue.internal.DefaultIssue; +import org.sonar.core.issue.DefaultIssue; import org.sonar.batch.index.Cache; import org.sonar.batch.index.Caches; diff --git a/sonar-batch/src/main/java/org/sonar/batch/issue/IssueFilters.java b/sonar-batch/src/main/java/org/sonar/batch/issue/IssueFilters.java index 0e623246b50..70bd4d54d5b 100644 --- a/sonar-batch/src/main/java/org/sonar/batch/issue/IssueFilters.java +++ b/sonar-batch/src/main/java/org/sonar/batch/issue/IssueFilters.java @@ -21,7 +21,7 @@ package org.sonar.batch.issue; import org.sonar.api.batch.BatchSide; import org.sonar.api.issue.batch.IssueFilter; -import org.sonar.api.issue.internal.DefaultIssue; +import org.sonar.core.issue.DefaultIssue; @BatchSide public class IssueFilters { diff --git a/sonar-batch/src/main/java/org/sonar/batch/issue/ModuleIssues.java b/sonar-batch/src/main/java/org/sonar/batch/issue/ModuleIssues.java index 2586d4f898a..23fa523df44 100644 --- a/sonar-batch/src/main/java/org/sonar/batch/issue/ModuleIssues.java +++ b/sonar-batch/src/main/java/org/sonar/batch/issue/ModuleIssues.java @@ -28,7 +28,7 @@ import org.sonar.api.batch.rule.ActiveRules; import org.sonar.api.batch.rule.Rule; import org.sonar.api.batch.rule.Rules; import org.sonar.api.batch.rule.internal.DefaultActiveRule; -import org.sonar.api.issue.internal.DefaultIssue; +import org.sonar.core.issue.DefaultIssue; import org.sonar.api.resources.Project; import org.sonar.api.rule.RuleKey; import org.sonar.api.rules.Violation; diff --git a/sonar-batch/src/main/java/org/sonar/batch/issue/tracking/InitialOpenIssuesSensor.java b/sonar-batch/src/main/java/org/sonar/batch/issue/tracking/InitialOpenIssuesSensor.java deleted file mode 100644 index ef39e6b77e9..00000000000 --- a/sonar-batch/src/main/java/org/sonar/batch/issue/tracking/InitialOpenIssuesSensor.java +++ /dev/null @@ -1,93 +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.batch.issue.tracking; - -import java.util.Calendar; -import java.util.Date; -import org.apache.commons.lang.time.DateUtils; -import org.apache.ibatis.session.ResultContext; -import org.apache.ibatis.session.ResultHandler; -import org.sonar.api.batch.RequiresDB; -import org.sonar.api.batch.Sensor; -import org.sonar.api.batch.SensorContext; -import org.sonar.api.resources.Project; -import org.sonar.core.issue.db.IssueChangeDao; -import org.sonar.core.issue.db.IssueChangeDto; -import org.sonar.core.issue.db.IssueDao; -import org.sonar.core.issue.db.IssueDto; -import org.sonar.core.resource.ResourceDao; -import org.sonar.core.resource.ResourceDto; -import org.sonar.core.resource.ResourceQuery; - -/** - * Load all the issues referenced during the previous scan. - */ -@RequiresDB -public class InitialOpenIssuesSensor implements Sensor { - - private final InitialOpenIssuesStack initialOpenIssuesStack; - private final IssueDao issueDao; - private final IssueChangeDao issueChangeDao; - private final ResourceDao resourceDao; - - public InitialOpenIssuesSensor(InitialOpenIssuesStack initialOpenIssuesStack, IssueDao issueDao, IssueChangeDao issueChangeDao, ResourceDao resourceDao) { - this.initialOpenIssuesStack = initialOpenIssuesStack; - this.issueDao = issueDao; - this.issueChangeDao = issueChangeDao; - this.resourceDao = resourceDao; - } - - @Override - public boolean shouldExecuteOnProject(Project project) { - return true; - } - - @Override - public void analyse(Project project, SensorContext context) { - ResourceDto module = resourceDao.getResource(ResourceQuery.create().setKey(project.getEffectiveKey())); - if (module != null) { - long moduleId = module.getId(); - // Adding one second is a hack for resolving conflicts with concurrent user - // changes during issue persistence - final Date now = DateUtils.addSeconds(DateUtils.truncate(new Date(), Calendar.MILLISECOND), 1); - issueDao.selectNonClosedIssuesByModule(moduleId, new ResultHandler() { - @Override - public void handleResult(ResultContext rc) { - IssueDto dto = (IssueDto) rc.getResultObject(); - dto.setSelectedAt(now.getTime()); - initialOpenIssuesStack.addIssue(dto); - } - }); - - issueChangeDao.selectChangelogOnNonClosedIssuesByModuleAndType(moduleId, new ResultHandler() { - @Override - public void handleResult(ResultContext rc) { - IssueChangeDto dto = (IssueChangeDto) rc.getResultObject(); - initialOpenIssuesStack.addChangelog(dto); - } - }); - } - } - - @Override - public String toString() { - return getClass().getSimpleName(); - } -} diff --git a/sonar-batch/src/main/java/org/sonar/batch/issue/tracking/InitialOpenIssuesStack.java b/sonar-batch/src/main/java/org/sonar/batch/issue/tracking/InitialOpenIssuesStack.java deleted file mode 100644 index ea7b9fb6e95..00000000000 --- a/sonar-batch/src/main/java/org/sonar/batch/issue/tracking/InitialOpenIssuesStack.java +++ /dev/null @@ -1,86 +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.batch.issue.tracking; - -import org.sonar.api.batch.BatchSide; -import org.sonar.api.batch.InstantiationStrategy; -import org.sonar.batch.index.Cache; -import org.sonar.batch.index.Caches; -import org.sonar.core.issue.db.IssueChangeDto; -import org.sonar.core.issue.db.IssueDto; - -import java.util.ArrayList; -import java.util.Collections; -import java.util.List; - -import static com.google.common.collect.Lists.newArrayList; - -@BatchSide -@InstantiationStrategy(InstantiationStrategy.PER_BATCH) -public class InitialOpenIssuesStack { - - private final Cache<IssueDto> issuesCache; - private final Cache<ArrayList<IssueChangeDto>> issuesChangelogCache; - - public InitialOpenIssuesStack(Caches caches) { - issuesCache = caches.createCache("last-open-issues"); - issuesChangelogCache = caches.createCache("issues-changelog"); - } - - public InitialOpenIssuesStack addIssue(IssueDto issueDto) { - issuesCache.put(issueDto.getComponentKey(), issueDto.getKee(), issueDto); - return this; - } - - public List<ServerIssue> selectAndRemoveIssues(String componentKey) { - Iterable<IssueDto> issues = issuesCache.values(componentKey); - List<ServerIssue> result = newArrayList(); - for (IssueDto issue : issues) { - result.add(new ServerIssueFromDb(issue)); - } - issuesCache.clear(componentKey); - return result; - } - - public Iterable<IssueDto> selectAllIssues() { - return issuesCache.values(); - } - - public InitialOpenIssuesStack addChangelog(IssueChangeDto issueChangeDto) { - List<IssueChangeDto> changeDtos = issuesChangelogCache.get(issueChangeDto.getIssueKey()); - if (changeDtos == null) { - changeDtos = newArrayList(); - } - changeDtos.add(issueChangeDto); - issuesChangelogCache.put(issueChangeDto.getIssueKey(), newArrayList(changeDtos)); - return this; - } - - public List<IssueChangeDto> selectChangelog(String issueKey) { - List<IssueChangeDto> changeDtos = issuesChangelogCache.get(issueKey); - return changeDtos != null ? changeDtos : Collections.<IssueChangeDto>emptyList(); - } - - public void clear() { - issuesCache.clear(); - issuesChangelogCache.clear(); - } -} diff --git a/sonar-batch/src/main/java/org/sonar/batch/issue/tracking/IssueHandlers.java b/sonar-batch/src/main/java/org/sonar/batch/issue/tracking/IssueHandlers.java deleted file mode 100644 index c7ef0dd53c4..00000000000 --- a/sonar-batch/src/main/java/org/sonar/batch/issue/tracking/IssueHandlers.java +++ /dev/null @@ -1,141 +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.batch.issue.tracking; - -import org.sonar.api.batch.BatchSide; -import org.sonar.api.issue.Issue; -import org.sonar.api.issue.IssueHandler; -import org.sonar.api.issue.internal.DefaultIssue; -import org.sonar.api.issue.internal.IssueChangeContext; -import org.sonar.api.user.User; -import org.sonar.core.issue.IssueUpdater; -import org.sonar.core.user.DefaultUser; - -import javax.annotation.Nullable; - -@BatchSide -public class IssueHandlers { - private final IssueHandler[] handlers; - private final DefaultContext context; - - public IssueHandlers(IssueUpdater updater, IssueHandler[] handlers) { - this.handlers = handlers; - this.context = new DefaultContext(updater); - } - - public IssueHandlers(IssueUpdater updater) { - this(updater, new IssueHandler[0]); - } - - public void execute(DefaultIssue issue, IssueChangeContext changeContext) { - context.reset(issue, changeContext); - for (IssueHandler handler : handlers) { - handler.onIssue(context); - } - } - - static class DefaultContext implements IssueHandler.Context { - private final IssueUpdater updater; - private DefaultIssue issue; - private IssueChangeContext changeContext; - - private DefaultContext(IssueUpdater updater) { - this.updater = updater; - } - - private void reset(DefaultIssue i, IssueChangeContext changeContext) { - this.issue = i; - this.changeContext = changeContext; - } - - @Override - public Issue issue() { - return issue; - } - - @Override - public boolean isNew() { - return issue.isNew(); - } - - @Override - public boolean isEndOfLife() { - return issue.isEndOfLife(); - } - - @Override - public IssueHandler.Context setLine(@Nullable Integer line) { - updater.setLine(issue, line); - return this; - } - - @Override - public IssueHandler.Context setMessage(@Nullable String s) { - updater.setMessage(issue, s, changeContext); - return this; - } - - @Override - public IssueHandler.Context setSeverity(String severity) { - updater.setSeverity(issue, severity, changeContext); - return this; - } - - @Override - public IssueHandler.Context setAuthorLogin(@Nullable String login) { - updater.setAuthorLogin(issue, login, changeContext); - return this; - } - - @Override - public IssueHandler.Context setEffortToFix(@Nullable Double d) { - updater.setEffortToFix(issue, d, changeContext); - return this; - } - - @Override - public IssueHandler.Context setAttribute(String key, @Nullable String value) { - throw new UnsupportedOperationException("TODO"); - } - - @Override - public IssueHandler.Context assign(@Nullable String assignee) { - User user = null; - if (assignee != null) { - user = new DefaultUser().setLogin(assignee).setName(assignee); - } - updater.assign(issue, user, changeContext); - return this; - } - - @Override - public IssueHandler.Context assign(@Nullable User user) { - updater.assign(issue, user, changeContext); - return this; - } - - @Override - public IssueHandler.Context addComment(String text) { - updater.addComment(issue, text, changeContext); - return this; - } - } - -} diff --git a/sonar-batch/src/main/java/org/sonar/batch/issue/tracking/IssueTracking.java b/sonar-batch/src/main/java/org/sonar/batch/issue/tracking/IssueTracking.java index bd339571e51..ee089357320 100644 --- a/sonar-batch/src/main/java/org/sonar/batch/issue/tracking/IssueTracking.java +++ b/sonar-batch/src/main/java/org/sonar/batch/issue/tracking/IssueTracking.java @@ -29,7 +29,7 @@ import com.google.common.collect.Maps; import com.google.common.collect.Multimap; import org.sonar.api.batch.BatchSide; import org.sonar.api.batch.InstantiationStrategy; -import org.sonar.api.issue.internal.DefaultIssue; +import org.sonar.core.issue.DefaultIssue; import javax.annotation.Nullable; diff --git a/sonar-batch/src/main/java/org/sonar/batch/issue/tracking/IssueTrackingDecorator.java b/sonar-batch/src/main/java/org/sonar/batch/issue/tracking/IssueTrackingDecorator.java deleted file mode 100644 index 7c05341ffe1..00000000000 --- a/sonar-batch/src/main/java/org/sonar/batch/issue/tracking/IssueTrackingDecorator.java +++ /dev/null @@ -1,279 +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.batch.issue.tracking; - -import com.google.common.annotations.VisibleForTesting; -import com.google.common.base.Strings; -import com.google.common.collect.Lists; -import org.apache.commons.lang.StringUtils; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; -import org.sonar.api.batch.Decorator; -import org.sonar.api.batch.DecoratorBarriers; -import org.sonar.api.batch.DecoratorContext; -import org.sonar.api.batch.DependedUpon; -import org.sonar.api.batch.DependsUpon; -import org.sonar.api.batch.RequiresDB; -import org.sonar.api.batch.fs.InputFile; -import org.sonar.api.batch.fs.internal.DefaultInputFile; -import org.sonar.api.component.ResourcePerspectives; -import org.sonar.api.issue.Issuable; -import org.sonar.api.issue.Issue; -import org.sonar.api.issue.internal.DefaultIssue; -import org.sonar.api.issue.internal.IssueChangeContext; -import org.sonar.api.profiles.RulesProfile; -import org.sonar.api.resources.File; -import org.sonar.api.resources.Project; -import org.sonar.api.resources.Resource; -import org.sonar.api.resources.ResourceUtils; -import org.sonar.api.rules.ActiveRule; -import org.sonar.api.rules.Rule; -import org.sonar.api.rules.RuleFinder; -import org.sonar.api.utils.Duration; -import org.sonar.api.utils.KeyValueFormat; -import org.sonar.batch.issue.IssueCache; -import org.sonar.batch.scan.filesystem.InputPathCache; -import org.sonar.core.issue.IssueUpdater; -import org.sonar.core.issue.db.IssueChangeDto; -import org.sonar.core.issue.db.IssueDto; -import org.sonar.core.issue.workflow.IssueWorkflow; - -import java.util.Collection; - -@DependsUpon(DecoratorBarriers.ISSUES_ADDED) -@DependedUpon(DecoratorBarriers.ISSUES_TRACKED) -@RequiresDB -public class IssueTrackingDecorator implements Decorator { - - private static final Logger LOG = LoggerFactory.getLogger(IssueTrackingDecorator.class); - - private final IssueCache issueCache; - private final InitialOpenIssuesStack initialOpenIssues; - private final IssueTracking tracking; - private final ServerLineHashesLoader lastLineHashes; - private final IssueHandlers handlers; - private final IssueWorkflow workflow; - private final IssueUpdater updater; - private final IssueChangeContext changeContext; - private final ResourcePerspectives perspectives; - private final RulesProfile rulesProfile; - private final RuleFinder ruleFinder; - private final InputPathCache inputPathCache; - private final Project project; - - public IssueTrackingDecorator(IssueCache issueCache, InitialOpenIssuesStack initialOpenIssues, IssueTracking tracking, - ServerLineHashesLoader lastLineHashes, - IssueHandlers handlers, IssueWorkflow workflow, - IssueUpdater updater, - Project project, - ResourcePerspectives perspectives, - RulesProfile rulesProfile, - RuleFinder ruleFinder, InputPathCache inputPathCache) { - this.issueCache = issueCache; - this.initialOpenIssues = initialOpenIssues; - this.tracking = tracking; - this.lastLineHashes = lastLineHashes; - this.handlers = handlers; - this.workflow = workflow; - this.updater = updater; - this.project = project; - this.inputPathCache = inputPathCache; - this.changeContext = IssueChangeContext.createScan(project.getAnalysisDate()); - this.perspectives = perspectives; - this.rulesProfile = rulesProfile; - this.ruleFinder = ruleFinder; - } - - @Override - public boolean shouldExecuteOnProject(Project project) { - return true; - } - - @Override - public void decorate(Resource resource, DecoratorContext context) { - Issuable issuable = perspectives.as(Issuable.class, resource); - if (issuable != null) { - doDecorate(resource); - } - } - - @VisibleForTesting - void doDecorate(Resource resource) { - Collection<DefaultIssue> issues = Lists.newArrayList(); - for (Issue issue : issueCache.byComponent(resource.getEffectiveKey())) { - issues.add((DefaultIssue) issue); - } - issueCache.clear(resource.getEffectiveKey()); - // issues = all the issues created by rule engines during this module scan and not excluded by filters - - // all the issues that are not closed in db before starting this module scan, including manual issues - Collection<ServerIssue> dbOpenIssues = initialOpenIssues.selectAndRemoveIssues(resource.getEffectiveKey()); - - SourceHashHolder sourceHashHolder = null; - if (ResourceUtils.isFile(resource)) { - File sonarFile = (File) resource; - InputFile file = inputPathCache.getFile(project.getEffectiveKey(), sonarFile.getPath()); - if (file == null) { - throw new IllegalStateException("File " + resource + " was not found in InputPath cache"); - } - sourceHashHolder = new SourceHashHolder((DefaultInputFile) file, lastLineHashes); - } - - IssueTrackingResult trackingResult = tracking.track(sourceHashHolder, dbOpenIssues, issues); - - // unmatched = issues that have been resolved + issues on disabled/removed rules + manual issues - addUnmatched(trackingResult.unmatched(), sourceHashHolder, issues); - - mergeMatched(trackingResult); - - if (ResourceUtils.isProject(resource)) { - // issues that relate to deleted components - addIssuesOnDeletedComponents(issues); - } - - for (DefaultIssue issue : issues) { - workflow.doAutomaticTransition(issue, changeContext); - handlers.execute(issue, changeContext); - issueCache.put(issue); - } - } - - @VisibleForTesting - protected void mergeMatched(IssueTrackingResult result) { - for (DefaultIssue issue : result.matched()) { - IssueDto ref = ((ServerIssueFromDb) result.matching(issue)).getDto(); - - // invariant fields - issue.setKey(ref.getKee()); - issue.setCreationDate(ref.getIssueCreationDate()); - issue.setUpdateDate(ref.getIssueUpdateDate()); - issue.setCloseDate(ref.getIssueCloseDate()); - - // non-persisted fields - issue.setNew(false); - issue.setEndOfLife(false); - issue.setOnDisabledRule(false); - issue.setSelectedAt(ref.getSelectedAt()); - - // fields to update with old values - issue.setActionPlanKey(ref.getActionPlanKey()); - issue.setResolution(ref.getResolution()); - issue.setStatus(ref.getStatus()); - issue.setAssignee(ref.getAssignee()); - issue.setAuthorLogin(ref.getAuthorLogin()); - issue.setTags(ref.getTags()); - - if (ref.getIssueAttributes() != null) { - issue.setAttributes(KeyValueFormat.parse(ref.getIssueAttributes())); - } - - // populate existing changelog - Collection<IssueChangeDto> issueChangeDtos = initialOpenIssues.selectChangelog(issue.key()); - for (IssueChangeDto issueChangeDto : issueChangeDtos) { - issue.addChange(issueChangeDto.toFieldDiffs()); - } - - // fields to update with current values - if (ref.isManualSeverity()) { - issue.setManualSeverity(true); - issue.setSeverity(ref.getSeverity()); - } else { - updater.setPastSeverity(issue, ref.getSeverity(), changeContext); - } - updater.setPastLine(issue, ref.getLine()); - updater.setPastMessage(issue, ref.getMessage(), changeContext); - updater.setPastEffortToFix(issue, ref.getEffortToFix(), changeContext); - Long debtInMinutes = ref.getDebt(); - Duration previousTechnicalDebt = debtInMinutes != null ? Duration.create(debtInMinutes) : null; - updater.setPastTechnicalDebt(issue, previousTechnicalDebt, changeContext); - updater.setPastProject(issue, ref.getProjectKey(), changeContext); - } - } - - private void addUnmatched(Collection<ServerIssue> unmatchedIssues, SourceHashHolder sourceHashHolder, Collection<DefaultIssue> issues) { - for (ServerIssue unmatchedIssue : unmatchedIssues) { - IssueDto unmatchedDto = ((ServerIssueFromDb) unmatchedIssue).getDto(); - DefaultIssue unmatched = unmatchedDto.toDefaultIssue(); - if (StringUtils.isNotBlank(unmatchedDto.getReporter()) && !Issue.STATUS_CLOSED.equals(unmatchedDto.getStatus())) { - relocateManualIssue(unmatched, unmatchedDto, sourceHashHolder); - } - updateUnmatchedIssue(unmatched, false /* manual issues can be kept open */); - issues.add(unmatched); - } - } - - private void addIssuesOnDeletedComponents(Collection<DefaultIssue> issues) { - for (IssueDto deadDto : initialOpenIssues.selectAllIssues()) { - DefaultIssue dead = deadDto.toDefaultIssue(); - updateUnmatchedIssue(dead, true); - issues.add(dead); - } - initialOpenIssues.clear(); - } - - private void updateUnmatchedIssue(DefaultIssue issue, boolean forceEndOfLife) { - issue.setNew(false); - - boolean manualIssue = !Strings.isNullOrEmpty(issue.reporter()); - Rule rule = ruleFinder.findByKey(issue.ruleKey()); - if (manualIssue) { - // Manual rules are not declared in Quality profiles, so no need to check ActiveRule - boolean isRemovedRule = rule == null || Rule.STATUS_REMOVED.equals(rule.getStatus()); - issue.setEndOfLife(forceEndOfLife || isRemovedRule); - issue.setOnDisabledRule(isRemovedRule); - } else { - ActiveRule activeRule = rulesProfile.getActiveRule(issue.ruleKey().repository(), issue.ruleKey().rule()); - issue.setEndOfLife(true); - issue.setOnDisabledRule(activeRule == null || rule == null || Rule.STATUS_REMOVED.equals(rule.getStatus())); - } - } - - private void relocateManualIssue(DefaultIssue newIssue, IssueDto oldIssue, SourceHashHolder sourceHashHolder) { - LOG.debug("Trying to relocate manual issue {}", oldIssue.getKee()); - - Integer previousLine = oldIssue.getLine(); - if (previousLine == null) { - LOG.debug("Cannot relocate issue at resource level"); - return; - } - - Collection<Integer> newLinesWithSameHash = sourceHashHolder.getNewLinesMatching(previousLine); - LOG.debug("Found the following lines with same hash: {}", newLinesWithSameHash); - if (newLinesWithSameHash.isEmpty()) { - if (previousLine > sourceHashHolder.getHashedSource().length()) { - LOG.debug("Old issue line {} is out of new source, closing and removing line number", previousLine); - newIssue.setLine(null); - updater.setStatus(newIssue, Issue.STATUS_CLOSED, changeContext); - updater.setResolution(newIssue, Issue.RESOLUTION_REMOVED, changeContext); - updater.setPastLine(newIssue, previousLine); - updater.setPastMessage(newIssue, oldIssue.getMessage(), changeContext); - updater.setPastEffortToFix(newIssue, oldIssue.getEffortToFix(), changeContext); - } - } else if (newLinesWithSameHash.size() == 1) { - Integer newLine = newLinesWithSameHash.iterator().next(); - LOG.debug("Relocating issue to line {}", newLine); - - newIssue.setLine(newLine); - updater.setPastLine(newIssue, previousLine); - updater.setPastMessage(newIssue, oldIssue.getMessage(), changeContext); - updater.setPastEffortToFix(newIssue, oldIssue.getEffortToFix(), changeContext); - } - } -} diff --git a/sonar-batch/src/main/java/org/sonar/batch/issue/tracking/IssueTrackingResult.java b/sonar-batch/src/main/java/org/sonar/batch/issue/tracking/IssueTrackingResult.java index 8fe3549e66b..e04cdc240b4 100644 --- a/sonar-batch/src/main/java/org/sonar/batch/issue/tracking/IssueTrackingResult.java +++ b/sonar-batch/src/main/java/org/sonar/batch/issue/tracking/IssueTrackingResult.java @@ -23,7 +23,7 @@ import com.google.common.collect.HashMultimap; import com.google.common.collect.Maps; import com.google.common.collect.Multimap; import org.apache.commons.lang.StringUtils; -import org.sonar.api.issue.internal.DefaultIssue; +import org.sonar.core.issue.DefaultIssue; import org.sonar.api.rule.RuleKey; import javax.annotation.Nullable; diff --git a/sonar-batch/src/main/java/org/sonar/batch/issue/tracking/LocalIssueTracking.java b/sonar-batch/src/main/java/org/sonar/batch/issue/tracking/LocalIssueTracking.java index a946c9f7dea..733e41d26a1 100644 --- a/sonar-batch/src/main/java/org/sonar/batch/issue/tracking/LocalIssueTracking.java +++ b/sonar-batch/src/main/java/org/sonar/batch/issue/tracking/LocalIssueTracking.java @@ -29,8 +29,8 @@ import org.sonar.api.batch.fs.internal.DefaultInputFile; import org.sonar.api.batch.rule.ActiveRule; import org.sonar.api.batch.rule.ActiveRules; import org.sonar.api.issue.Issue; -import org.sonar.api.issue.internal.DefaultIssue; -import org.sonar.api.issue.internal.IssueChangeContext; +import org.sonar.core.issue.DefaultIssue; +import org.sonar.core.issue.IssueChangeContext; import org.sonar.api.resources.Project; import org.sonar.api.resources.ResourceUtils; import org.sonar.api.rule.RuleKey; @@ -166,7 +166,7 @@ public class LocalIssueTracking { // non-persisted fields issue.setNew(false); - issue.setEndOfLife(false); + issue.setBeingClosed(false); issue.setOnDisabledRule(false); // fields to update with old values @@ -226,9 +226,9 @@ public class LocalIssueTracking { boolean manualIssue = issue.ruleKey().isManual(); boolean isRemovedRule = activeRule == null; if (manualIssue) { - issue.setEndOfLife(forceEndOfLife || isRemovedRule); + issue.setBeingClosed(forceEndOfLife || isRemovedRule); } else { - issue.setEndOfLife(true); + issue.setBeingClosed(true); } issue.setOnDisabledRule(isRemovedRule); } diff --git a/sonar-batch/src/main/java/org/sonar/batch/mediumtest/TaskResult.java b/sonar-batch/src/main/java/org/sonar/batch/mediumtest/TaskResult.java index 55502e9ba78..9b6ece676b1 100644 --- a/sonar-batch/src/main/java/org/sonar/batch/mediumtest/TaskResult.java +++ b/sonar-batch/src/main/java/org/sonar/batch/mediumtest/TaskResult.java @@ -37,7 +37,7 @@ import org.sonar.api.batch.sensor.duplication.Duplication; import org.sonar.api.batch.sensor.highlighting.TypeOfText; import org.sonar.api.batch.sensor.measure.internal.DefaultMeasure; import org.sonar.api.issue.Issue; -import org.sonar.api.issue.internal.DefaultIssue; +import org.sonar.core.issue.DefaultIssue; import org.sonar.api.measures.Measure; import org.sonar.batch.duplication.DuplicationCache; import org.sonar.batch.index.Cache.Entry; diff --git a/sonar-batch/src/main/java/org/sonar/batch/phases/PersisterExecutionEvent.java b/sonar-batch/src/main/java/org/sonar/batch/phases/PersisterExecutionEvent.java deleted file mode 100644 index cb6574591c7..00000000000 --- a/sonar-batch/src/main/java/org/sonar/batch/phases/PersisterExecutionEvent.java +++ /dev/null @@ -1,50 +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.batch.phases; - -import org.sonar.batch.index.ScanPersister; -import org.sonar.batch.phases.event.PersisterExecutionHandler; - -class PersisterExecutionEvent extends AbstractPhaseEvent<PersisterExecutionHandler> - implements PersisterExecutionHandler.PersisterExecutionEvent { - - private final ScanPersister persister; - - PersisterExecutionEvent(ScanPersister persister, boolean start) { - super(start); - this.persister = persister; - } - - @Override - public ScanPersister getPersister() { - return persister; - } - - @Override - public void dispatch(PersisterExecutionHandler handler) { - handler.onPersisterExecution(this); - } - - @Override - public Class getType() { - return PersisterExecutionHandler.class; - } - -} diff --git a/sonar-batch/src/main/java/org/sonar/batch/phases/PersistersExecutor.java b/sonar-batch/src/main/java/org/sonar/batch/phases/PersistersExecutor.java deleted file mode 100644 index 8e114b6ec31..00000000000 --- a/sonar-batch/src/main/java/org/sonar/batch/phases/PersistersExecutor.java +++ /dev/null @@ -1,65 +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.batch.phases; - -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; -import org.sonar.api.batch.BatchSide; -import org.sonar.batch.bootstrap.DefaultAnalysisMode; -import org.sonar.batch.events.EventBus; -import org.sonar.batch.index.ScanPersister; - -import java.util.Arrays; - -@BatchSide -public class PersistersExecutor { - - private static final Logger LOG = LoggerFactory.getLogger(PersistersExecutor.class); - - private final ScanPersister[] persisters; - private final DefaultAnalysisMode analysisMode; - private final EventBus eventBus; - - public PersistersExecutor(DefaultAnalysisMode analysisMode, EventBus eventBus, ScanPersister[] persisters) { - this.analysisMode = analysisMode; - this.eventBus = eventBus; - this.persisters = persisters; - } - - public PersistersExecutor(DefaultAnalysisMode analysisMode, EventBus eventBus) { - this(analysisMode, eventBus, new ScanPersister[0]); - } - - public void execute() { - if (analysisMode.isDb()) { - LOG.info("Store results in database"); - eventBus.fireEvent(new PersistersPhaseEvent(Arrays.asList(persisters), true)); - for (ScanPersister persister : persisters) { - LOG.debug("Execute {}", persister.getClass().getName()); - eventBus.fireEvent(new PersisterExecutionEvent(persister, true)); - persister.persist(); - eventBus.fireEvent(new PersisterExecutionEvent(persister, false)); - } - - eventBus.fireEvent(new PersistersPhaseEvent(Arrays.asList(persisters), false)); - } - } - -} diff --git a/sonar-batch/src/main/java/org/sonar/batch/phases/PersistersPhaseEvent.java b/sonar-batch/src/main/java/org/sonar/batch/phases/PersistersPhaseEvent.java deleted file mode 100644 index ad43c00ab36..00000000000 --- a/sonar-batch/src/main/java/org/sonar/batch/phases/PersistersPhaseEvent.java +++ /dev/null @@ -1,52 +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.batch.phases; - -import org.sonar.batch.index.ScanPersister; -import org.sonar.batch.phases.event.PersistersPhaseHandler; - -import java.util.List; - -class PersistersPhaseEvent extends AbstractPhaseEvent<PersistersPhaseHandler> - implements PersistersPhaseHandler.PersistersPhaseEvent { - - private final List<ScanPersister> persisters; - - PersistersPhaseEvent(List<ScanPersister> persisters, boolean start) { - super(start); - this.persisters = persisters; - } - - @Override - public List<ScanPersister> getPersisters() { - return persisters; - } - - @Override - protected void dispatch(PersistersPhaseHandler handler) { - handler.onPersistersPhase(this); - } - - @Override - protected Class getType() { - return PersistersPhaseHandler.class; - } - -} diff --git a/sonar-batch/src/main/java/org/sonar/batch/phases/PhaseExecutor.java b/sonar-batch/src/main/java/org/sonar/batch/phases/PhaseExecutor.java index af07cf80cb0..3a616e62465 100644 --- a/sonar-batch/src/main/java/org/sonar/batch/phases/PhaseExecutor.java +++ b/sonar-batch/src/main/java/org/sonar/batch/phases/PhaseExecutor.java @@ -44,7 +44,6 @@ public final class PhaseExecutor { private final SensorContext sensorContext; private final DefaultIndex index; private final ProjectInitializer pi; - private final PersistersExecutor persistersExecutor; private final FileSystemLogger fsLogger; private final DefaultModuleFileSystem fs; private final QProfileVerifier profileVerifier; @@ -57,7 +56,7 @@ public final class PhaseExecutor { InitializersExecutor initializersExecutor, PostJobsExecutor postJobsExecutor, SensorsExecutor sensorsExecutor, SensorContext sensorContext, DefaultIndex index, EventBus eventBus, ReportPublisher reportPublisher, ProjectInitializer pi, - PersistersExecutor persistersExecutor, FileSystemLogger fsLogger, IssuesReports jsonReport, DefaultModuleFileSystem fs, QProfileVerifier profileVerifier, + FileSystemLogger fsLogger, IssuesReports jsonReport, DefaultModuleFileSystem fs, QProfileVerifier profileVerifier, IssueExclusionsLoader issueExclusionsLoader, DefaultAnalysisMode analysisMode, LocalIssueTracking localIssueTracking) { this.decoratorsExecutor = decoratorsExecutor; this.postJobsExecutor = postJobsExecutor; @@ -68,7 +67,6 @@ public final class PhaseExecutor { this.eventBus = eventBus; this.reportPublisher = reportPublisher; this.pi = pi; - this.persistersExecutor = persistersExecutor; this.fsLogger = fsLogger; this.issuesReport = jsonReport; this.fs = fs; @@ -106,16 +104,11 @@ public final class PhaseExecutor { localIssueTracking(); } issuesReport(); - - if (!analysisMode.isPreview()) { - persistersExecutor.execute(); - } - publishReportJob(); postJobsExecutor.execute(sensorContext); } cleanMemory(); - eventBus.fireEvent(new ProjectAnalysisEvent(module, false)); + eventBus.fireEvent(new ProjectAnalysisEvent(module, false)); } private void publishReportJob() { diff --git a/sonar-batch/src/main/java/org/sonar/batch/phases/event/PersisterExecutionHandler.java b/sonar-batch/src/main/java/org/sonar/batch/phases/event/PersisterExecutionHandler.java deleted file mode 100644 index 7df8dae4ade..00000000000 --- a/sonar-batch/src/main/java/org/sonar/batch/phases/event/PersisterExecutionHandler.java +++ /dev/null @@ -1,45 +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.batch.phases.event; - -import org.sonar.api.batch.events.EventHandler; -import org.sonar.batch.index.ScanPersister; - -public interface PersisterExecutionHandler extends EventHandler { - - /** - * This interface is not intended to be implemented by clients. - */ - interface PersisterExecutionEvent { - - ScanPersister getPersister(); - - boolean isStart(); - - boolean isEnd(); - - } - - /** - * Called before and after execution of {@link ScanPersister}. - */ - void onPersisterExecution(PersisterExecutionEvent event); - -} diff --git a/sonar-batch/src/main/java/org/sonar/batch/phases/event/PersistersPhaseHandler.java b/sonar-batch/src/main/java/org/sonar/batch/phases/event/PersistersPhaseHandler.java deleted file mode 100644 index 087755bacab..00000000000 --- a/sonar-batch/src/main/java/org/sonar/batch/phases/event/PersistersPhaseHandler.java +++ /dev/null @@ -1,50 +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.batch.phases.event; - -import org.sonar.api.batch.events.EventHandler; -import org.sonar.batch.index.ScanPersister; - -import java.util.List; - -public interface PersistersPhaseHandler extends EventHandler { - - /** - * This interface is not intended to be implemented by clients. - */ - interface PersistersPhaseEvent { - - /** - * @return list of Persisters in the order of execution - */ - List<ScanPersister> getPersisters(); - - boolean isStart(); - - boolean isEnd(); - - } - - /** - * Called before and after execution of all {@link ScanPersister}s. - */ - void onPersistersPhase(PersistersPhaseEvent event); - -} diff --git a/sonar-batch/src/main/java/org/sonar/batch/phases/event/package-info.java b/sonar-batch/src/main/java/org/sonar/batch/phases/event/package-info.java deleted file mode 100644 index 6aefbe5b6bb..00000000000 --- a/sonar-batch/src/main/java/org/sonar/batch/phases/event/package-info.java +++ /dev/null @@ -1,23 +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. - */ -@ParametersAreNonnullByDefault -package org.sonar.batch.phases.event; - -import javax.annotation.ParametersAreNonnullByDefault; diff --git a/sonar-batch/src/main/java/org/sonar/batch/postjob/DefaultPostJobContext.java b/sonar-batch/src/main/java/org/sonar/batch/postjob/DefaultPostJobContext.java index 6f46c012ce9..7b1edddabec 100644 --- a/sonar-batch/src/main/java/org/sonar/batch/postjob/DefaultPostJobContext.java +++ b/sonar-batch/src/main/java/org/sonar/batch/postjob/DefaultPostJobContext.java @@ -28,7 +28,7 @@ import org.sonar.api.batch.postjob.PostJobContext; import org.sonar.api.batch.postjob.issue.Issue; import org.sonar.api.batch.rule.Severity; import org.sonar.api.config.Settings; -import org.sonar.api.issue.internal.DefaultIssue; +import org.sonar.core.issue.DefaultIssue; import org.sonar.api.rule.RuleKey; import org.sonar.batch.index.BatchComponent; import org.sonar.batch.index.BatchComponentCache; diff --git a/sonar-batch/src/main/java/org/sonar/batch/profiling/PhasesSumUpTimeProfiler.java b/sonar-batch/src/main/java/org/sonar/batch/profiling/PhasesSumUpTimeProfiler.java index 97e5c09dcdb..1da5585e762 100644 --- a/sonar-batch/src/main/java/org/sonar/batch/profiling/PhasesSumUpTimeProfiler.java +++ b/sonar-batch/src/main/java/org/sonar/batch/profiling/PhasesSumUpTimeProfiler.java @@ -48,16 +48,13 @@ import org.sonar.api.utils.System2; import org.sonar.api.utils.TimeUtils; import org.sonar.batch.bootstrap.BootstrapProperties; import org.sonar.batch.events.BatchStepHandler; -import org.sonar.batch.phases.event.PersisterExecutionHandler; -import org.sonar.batch.phases.event.PersistersPhaseHandler; import org.sonar.batch.util.BatchUtils; import static org.sonar.batch.profiling.AbstractTimeProfiling.sortByDescendingTotalTime; import static org.sonar.batch.profiling.AbstractTimeProfiling.truncate; public class PhasesSumUpTimeProfiler implements ProjectAnalysisHandler, SensorExecutionHandler, DecoratorExecutionHandler, PostJobExecutionHandler, DecoratorsPhaseHandler, - SensorsPhaseHandler, PostJobsPhaseHandler, InitializersPhaseHandler, InitializerExecutionHandler, BatchStepHandler, PersistersPhaseHandler, - PersisterExecutionHandler { + SensorsPhaseHandler, PostJobsPhaseHandler, InitializersPhaseHandler, InitializerExecutionHandler, BatchStepHandler { static final Logger LOG = LoggerFactory.getLogger(PhasesSumUpTimeProfiler.class); private static final int TEXT_RIGHT_PAD = 60; @@ -175,25 +172,6 @@ public class PhasesSumUpTimeProfiler implements ProjectAnalysisHandler, SensorEx } @Override - public void onPersistersPhase(PersistersPhaseEvent event) { - if (event.isStart()) { - currentModuleProfiling.addPhaseProfiling(Phase.PERSISTER); - } else { - currentModuleProfiling.getProfilingPerPhase(Phase.PERSISTER).stop(); - } - } - - @Override - public void onPersisterExecution(PersisterExecutionEvent event) { - PhaseProfiling profiling = currentModuleProfiling.getProfilingPerPhase(Phase.PERSISTER); - if (event.isStart()) { - profiling.newItemProfiling(event.getPersister()); - } else { - profiling.getProfilingPerItem(event.getPersister()).stop(); - } - } - - @Override public void onDecoratorExecution(DecoratorExecutionEvent event) { PhaseProfiling profiling = currentModuleProfiling.getProfilingPerPhase(Phase.DECORATOR); if (event.isStart()) { diff --git a/sonar-batch/src/main/java/org/sonar/batch/report/IssuesPublisher.java b/sonar-batch/src/main/java/org/sonar/batch/report/IssuesPublisher.java index 08be39df953..0377b3e0889 100644 --- a/sonar-batch/src/main/java/org/sonar/batch/report/IssuesPublisher.java +++ b/sonar-batch/src/main/java/org/sonar/batch/report/IssuesPublisher.java @@ -21,14 +21,8 @@ package org.sonar.batch.report; import com.google.common.base.Function; import com.google.common.collect.Iterables; -import java.util.Collection; -import java.util.Date; -import java.util.Iterator; -import javax.annotation.Nullable; import org.sonar.api.CoreProperties; import org.sonar.api.batch.bootstrap.ProjectDefinition; -import org.sonar.api.issue.internal.DefaultIssue; -import org.sonar.api.issue.internal.FieldDiffs; import org.sonar.api.resources.Project; import org.sonar.api.utils.KeyValueFormat; import org.sonar.batch.index.BatchComponent; @@ -38,6 +32,7 @@ import org.sonar.batch.protocol.Constants; import org.sonar.batch.protocol.output.BatchReport; import org.sonar.batch.protocol.output.BatchReportWriter; import org.sonar.batch.scan.ImmutableProjectReactor; +import org.sonar.core.issue.DefaultIssue; public class IssuesPublisher implements ReportPublisherStep { @@ -53,7 +48,6 @@ public class IssuesPublisher implements ReportPublisherStep { @Override public void publish(BatchReportWriter writer) { - Collection<Object> deletedComponentKeys = issueCache.componentKeys(); for (BatchComponent resource : componentCache.all()) { String componentKey = resource.resource().getEffectiveKey(); Iterable<DefaultIssue> issues = issueCache.byComponent(componentKey); @@ -65,23 +59,19 @@ public class IssuesPublisher implements ReportPublisherStep { return toReportIssue(builder, input); } })); - deletedComponentKeys.remove(componentKey); } - int count = exportIssuesOfDeletedComponents(deletedComponentKeys, writer); - - exportMetadata(writer, count); + exportMetadata(writer); } - private void exportMetadata(BatchReportWriter writer, int count) { + private void exportMetadata(BatchReportWriter writer) { ProjectDefinition root = reactor.getRoot(); BatchComponent rootProject = componentCache.getRoot(); BatchReport.Metadata.Builder builder = BatchReport.Metadata.newBuilder() .setAnalysisDate(((Project) rootProject.resource()).getAnalysisDate().getTime()) // Here we want key without branch .setProjectKey(root.getKey()) - .setRootComponentRef(rootProject.batchId()) - .setDeletedComponentsCount(count); + .setRootComponentRef(rootProject.batchId()); String branch = root.properties().get(CoreProperties.PROJECT_BRANCH_PROPERTY); if (branch != null) { builder.setBranch(branch); @@ -89,39 +79,14 @@ public class IssuesPublisher implements ReportPublisherStep { writer.writeMetadata(builder.build()); } - private int exportIssuesOfDeletedComponents(Collection<Object> deletedComponentKeys, BatchReportWriter writer) { - int deletedComponentCount = 0; - for (Object componentKey : deletedComponentKeys) { - deletedComponentCount++; - Iterable<DefaultIssue> issues = issueCache.byComponent(componentKey.toString()); - Iterator<DefaultIssue> iterator = issues.iterator(); - if (iterator.hasNext()) { - String componentUuid = iterator.next().componentUuid(); - writer.writeDeletedComponentIssues(deletedComponentCount, componentUuid, Iterables.transform(issues, new Function<DefaultIssue, BatchReport.Issue>() { - private BatchReport.Issue.Builder builder = BatchReport.Issue.newBuilder(); - - @Override - public BatchReport.Issue apply(DefaultIssue input) { - return toReportIssue(builder, input); - } - })); - } - } - return deletedComponentCount; - } - private BatchReport.Issue toReportIssue(BatchReport.Issue.Builder builder, DefaultIssue issue) { builder.clear(); // non-null fields - builder.setUuid(issue.key()); - builder.setIsNew(issue.isNew()); builder.setSeverity(Constants.Severity.valueOf(issue.severity())); builder.setRuleRepository(issue.ruleKey().repository()); builder.setRuleKey(issue.ruleKey().rule()); builder.setAttributes(KeyValueFormat.format(issue.attributes())); builder.addAllTag(issue.tags()); - builder.setMustSendNotification(issue.mustSendNotifications()); - builder.setIsChanged(issue.isChanged()); // nullable fields Integer line = issue.line(); @@ -136,65 +101,12 @@ public class IssuesPublisher implements ReportPublisherStep { if (effortToFix != null) { builder.setEffortToFix(effortToFix); } - Long debtInMinutes = issue.debtInMinutes(); if (debtInMinutes != null) { builder.setDebtInMinutes(debtInMinutes); } - String resolution = issue.resolution(); - if (resolution != null) { - builder.setResolution(resolution); - } - String status = issue.status(); - if (status != null) { - builder.setStatus(status); - } - String checksum = issue.checksum(); - if (checksum != null) { - builder.setChecksum(checksum); - } - builder.setManualSeverity(issue.manualSeverity()); - String reporter = issue.reporter(); - if (reporter != null) { - builder.setReporter(reporter); - } - String assignee = issue.assignee(); - if (assignee != null) { - builder.setAssignee(assignee); - } - String actionPlanKey = issue.actionPlanKey(); - if (actionPlanKey != null) { - builder.setActionPlanKey(actionPlanKey); - } - String authorLogin = issue.authorLogin(); - if (authorLogin != null) { - builder.setAuthorLogin(authorLogin); - } - String diff = diffsToString(issue.currentChange()); - if (diff != null) { - builder.setDiffFields(diff); - } - Date creationDate = issue.creationDate(); - if (creationDate != null) { - builder.setCreationDate(creationDate.getTime()); - } - Long selectedAt = issue.selectedAt(); - if (selectedAt != null) { - builder.setSelectedAt(selectedAt); - } - Date closeDate = issue.closeDate(); - if (closeDate != null) { - builder.setCloseDate(closeDate.getTime()); - } - Date updateDate = issue.updateDate(); - if (updateDate != null) { - builder.setUpdateDate(updateDate.getTime()); - } - return builder.build(); - } - private String diffsToString(@Nullable FieldDiffs diffs) { - return diffs != null ? diffs.toString() : null; + return builder.build(); } } diff --git a/sonar-batch/src/main/java/org/sonar/batch/scan/ModuleScanContainer.java b/sonar-batch/src/main/java/org/sonar/batch/scan/ModuleScanContainer.java index 4d4fb03fff9..c4524dca799 100644 --- a/sonar-batch/src/main/java/org/sonar/batch/scan/ModuleScanContainer.java +++ b/sonar-batch/src/main/java/org/sonar/batch/scan/ModuleScanContainer.java @@ -50,7 +50,6 @@ import org.sonar.batch.issue.ignore.scanner.IssueExclusionsLoader; import org.sonar.batch.issue.ignore.scanner.IssueExclusionsRegexpScanner; import org.sonar.batch.phases.DecoratorsExecutor; import org.sonar.batch.phases.InitializersExecutor; -import org.sonar.batch.phases.PersistersExecutor; import org.sonar.batch.phases.PhaseExecutor; import org.sonar.batch.phases.PostJobsExecutor; import org.sonar.batch.phases.ProjectInitializer; @@ -120,7 +119,6 @@ public class ModuleScanContainer extends ComponentContainer { PostJobsExecutor.class, DecoratorsExecutor.class, SensorsExecutor.class, - PersistersExecutor.class, InitializersExecutor.class, ProjectInitializer.class, moduleDefinition.getContainerExtensions(), diff --git a/sonar-batch/src/main/java/org/sonar/batch/scan/ProjectScanContainer.java b/sonar-batch/src/main/java/org/sonar/batch/scan/ProjectScanContainer.java index 1c3e864170d..83f24753ef4 100644 --- a/sonar-batch/src/main/java/org/sonar/batch/scan/ProjectScanContainer.java +++ b/sonar-batch/src/main/java/org/sonar/batch/scan/ProjectScanContainer.java @@ -53,7 +53,6 @@ import org.sonar.batch.index.Caches; import org.sonar.batch.index.DefaultIndex; import org.sonar.batch.issue.DefaultProjectIssues; import org.sonar.batch.issue.IssueCache; -import org.sonar.batch.issue.tracking.InitialOpenIssuesStack; import org.sonar.batch.issue.tracking.LocalIssueTracking; import org.sonar.batch.issue.tracking.ServerIssueRepository; import org.sonar.batch.mediumtest.ScanTaskObservers; @@ -217,10 +216,7 @@ public class ProjectScanContainer extends ComponentContainer { new DebtModelProvider(), // technical debt - DefaultTechnicalDebtModel.class, - - // Issue tracking - InitialOpenIssuesStack.class); + DefaultTechnicalDebtModel.class); } private void addBatchExtensions() { diff --git a/sonar-batch/src/main/java/org/sonar/batch/scan/report/ConsoleReport.java b/sonar-batch/src/main/java/org/sonar/batch/scan/report/ConsoleReport.java index e23e8a816e3..2634fdd9af9 100644 --- a/sonar-batch/src/main/java/org/sonar/batch/scan/report/ConsoleReport.java +++ b/sonar-batch/src/main/java/org/sonar/batch/scan/report/ConsoleReport.java @@ -25,7 +25,7 @@ import org.sonar.api.Properties; import org.sonar.api.Property; import org.sonar.api.PropertyType; import org.sonar.api.config.Settings; -import org.sonar.api.issue.internal.DefaultIssue; +import org.sonar.core.issue.DefaultIssue; import org.sonar.api.rule.Severity; import org.sonar.api.utils.log.Logger; import org.sonar.api.utils.log.Loggers; diff --git a/sonar-batch/src/main/java/org/sonar/batch/scan/report/IssuesReportBuilder.java b/sonar-batch/src/main/java/org/sonar/batch/scan/report/IssuesReportBuilder.java index 72c48f9bb7a..43e423e7fa7 100644 --- a/sonar-batch/src/main/java/org/sonar/batch/scan/report/IssuesReportBuilder.java +++ b/sonar-batch/src/main/java/org/sonar/batch/scan/report/IssuesReportBuilder.java @@ -23,7 +23,7 @@ import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.sonar.api.batch.BatchSide; import org.sonar.api.issue.Issue; -import org.sonar.api.issue.internal.DefaultIssue; +import org.sonar.core.issue.DefaultIssue; import org.sonar.api.resources.Project; import org.sonar.api.rule.RuleKey; import org.sonar.api.rules.Rule; diff --git a/sonar-batch/src/main/java/org/sonar/batch/scan/report/JSONReport.java b/sonar-batch/src/main/java/org/sonar/batch/scan/report/JSONReport.java index e2959d9352d..b13b5468d67 100644 --- a/sonar-batch/src/main/java/org/sonar/batch/scan/report/JSONReport.java +++ b/sonar-batch/src/main/java/org/sonar/batch/scan/report/JSONReport.java @@ -34,7 +34,7 @@ import org.sonar.api.batch.fs.internal.DefaultInputFile; import org.sonar.api.batch.rule.ActiveRules; import org.sonar.api.batch.rule.internal.DefaultActiveRule; import org.sonar.api.config.Settings; -import org.sonar.api.issue.internal.DefaultIssue; +import org.sonar.core.issue.DefaultIssue; import org.sonar.api.platform.Server; import org.sonar.api.resources.Project; import org.sonar.api.rule.RuleKey; diff --git a/sonar-batch/src/main/java/org/sonar/batch/sensor/DefaultSensorStorage.java b/sonar-batch/src/main/java/org/sonar/batch/sensor/DefaultSensorStorage.java index 0277408cbe4..4ddfe03452e 100644 --- a/sonar-batch/src/main/java/org/sonar/batch/sensor/DefaultSensorStorage.java +++ b/sonar-batch/src/main/java/org/sonar/batch/sensor/DefaultSensorStorage.java @@ -42,7 +42,7 @@ import org.sonar.api.batch.sensor.issue.Issue; import org.sonar.api.batch.sensor.measure.Measure; import org.sonar.api.batch.sensor.measure.internal.DefaultMeasure; import org.sonar.api.config.Settings; -import org.sonar.api.issue.internal.DefaultIssue; +import org.sonar.core.issue.DefaultIssue; import org.sonar.api.measures.Formula; import org.sonar.api.measures.Metric; import org.sonar.api.measures.PersistenceMode; diff --git a/sonar-batch/src/test/java/org/sonar/batch/debt/DebtDecoratorTest.java b/sonar-batch/src/test/java/org/sonar/batch/debt/DebtDecoratorTest.java index 5ce426696d5..94a58c79b0d 100644 --- a/sonar-batch/src/test/java/org/sonar/batch/debt/DebtDecoratorTest.java +++ b/sonar-batch/src/test/java/org/sonar/batch/debt/DebtDecoratorTest.java @@ -37,7 +37,7 @@ import org.sonar.api.batch.rule.internal.RulesBuilder; import org.sonar.api.component.ResourcePerspectives; import org.sonar.api.issue.Issuable; import org.sonar.api.issue.Issue; -import org.sonar.api.issue.internal.DefaultIssue; +import org.sonar.core.issue.DefaultIssue; import org.sonar.api.measures.CoreMetrics; import org.sonar.api.measures.Measure; import org.sonar.api.measures.MeasuresFilter; diff --git a/sonar-batch/src/test/java/org/sonar/batch/debt/IssueChangelogDebtCalculatorTest.java b/sonar-batch/src/test/java/org/sonar/batch/debt/IssueChangelogDebtCalculatorTest.java index 952075dec78..fb2bf2e90f5 100644 --- a/sonar-batch/src/test/java/org/sonar/batch/debt/IssueChangelogDebtCalculatorTest.java +++ b/sonar-batch/src/test/java/org/sonar/batch/debt/IssueChangelogDebtCalculatorTest.java @@ -24,8 +24,8 @@ import org.apache.commons.lang.time.DateUtils; import org.junit.Before; import org.junit.Test; import org.sonar.api.issue.Issue; -import org.sonar.api.issue.internal.DefaultIssue; -import org.sonar.api.issue.internal.FieldDiffs; +import org.sonar.core.issue.DefaultIssue; +import org.sonar.core.issue.FieldDiffs; import org.sonar.api.utils.Duration; import java.util.Date; diff --git a/sonar-batch/src/test/java/org/sonar/batch/debt/NewDebtDecoratorTest.java b/sonar-batch/src/test/java/org/sonar/batch/debt/NewDebtDecoratorTest.java index 8de52b074c2..8b00495711b 100644 --- a/sonar-batch/src/test/java/org/sonar/batch/debt/NewDebtDecoratorTest.java +++ b/sonar-batch/src/test/java/org/sonar/batch/debt/NewDebtDecoratorTest.java @@ -34,8 +34,8 @@ import org.sonar.api.component.ResourcePerspectives; import org.sonar.api.config.Settings; import org.sonar.api.issue.Issuable; import org.sonar.api.issue.Issue; -import org.sonar.api.issue.internal.DefaultIssue; -import org.sonar.api.issue.internal.FieldDiffs; +import org.sonar.core.issue.DefaultIssue; +import org.sonar.core.issue.FieldDiffs; import org.sonar.api.measures.CoreMetrics; import org.sonar.api.measures.Measure; import org.sonar.api.measures.Metric; diff --git a/sonar-batch/src/test/java/org/sonar/batch/issue/DefaultIssuableTest.java b/sonar-batch/src/test/java/org/sonar/batch/issue/DefaultIssuableTest.java index 42843ddd8ec..7f50a767efe 100644 --- a/sonar-batch/src/test/java/org/sonar/batch/issue/DefaultIssuableTest.java +++ b/sonar-batch/src/test/java/org/sonar/batch/issue/DefaultIssuableTest.java @@ -23,7 +23,7 @@ import java.util.Arrays; import java.util.List; import org.junit.Test; import org.sonar.api.issue.Issue; -import org.sonar.api.issue.internal.DefaultIssue; +import org.sonar.core.issue.DefaultIssue; import org.sonar.api.resources.Project; import org.sonar.batch.index.BatchComponent; diff --git a/sonar-batch/src/test/java/org/sonar/batch/issue/DefaultProjectIssuesTest.java b/sonar-batch/src/test/java/org/sonar/batch/issue/DefaultProjectIssuesTest.java index b46e3551a6d..99c6d5f7100 100644 --- a/sonar-batch/src/test/java/org/sonar/batch/issue/DefaultProjectIssuesTest.java +++ b/sonar-batch/src/test/java/org/sonar/batch/issue/DefaultProjectIssuesTest.java @@ -22,7 +22,7 @@ package org.sonar.batch.issue; import com.google.common.collect.Lists; import org.junit.Test; import org.sonar.api.issue.Issue; -import org.sonar.api.issue.internal.DefaultIssue; +import org.sonar.core.issue.DefaultIssue; import org.sonar.api.rule.RuleKey; import org.sonar.api.rule.Severity; diff --git a/sonar-batch/src/test/java/org/sonar/batch/issue/IssueCacheTest.java b/sonar-batch/src/test/java/org/sonar/batch/issue/IssueCacheTest.java index 25fefe6f13d..18e90aff802 100644 --- a/sonar-batch/src/test/java/org/sonar/batch/issue/IssueCacheTest.java +++ b/sonar-batch/src/test/java/org/sonar/batch/issue/IssueCacheTest.java @@ -26,7 +26,7 @@ import com.google.common.collect.Collections2; import com.google.common.collect.ImmutableList; import org.junit.Test; import org.sonar.api.issue.Issue; -import org.sonar.api.issue.internal.DefaultIssue; +import org.sonar.core.issue.DefaultIssue; import org.sonar.api.rule.Severity; import javax.annotation.Nullable; diff --git a/sonar-batch/src/test/java/org/sonar/batch/issue/IssueFiltersTest.java b/sonar-batch/src/test/java/org/sonar/batch/issue/IssueFiltersTest.java index 46aea62325c..b99aefe9bb8 100644 --- a/sonar-batch/src/test/java/org/sonar/batch/issue/IssueFiltersTest.java +++ b/sonar-batch/src/test/java/org/sonar/batch/issue/IssueFiltersTest.java @@ -21,7 +21,7 @@ package org.sonar.batch.issue; import org.junit.Test; import org.sonar.api.issue.Issue; -import org.sonar.api.issue.internal.DefaultIssue; +import org.sonar.core.issue.DefaultIssue; import static org.assertj.core.api.Assertions.assertThat; import static org.mockito.Matchers.any; diff --git a/sonar-batch/src/test/java/org/sonar/batch/issue/ModuleIssuesTest.java b/sonar-batch/src/test/java/org/sonar/batch/issue/ModuleIssuesTest.java index 2577ba98a41..f1157f16572 100644 --- a/sonar-batch/src/test/java/org/sonar/batch/issue/ModuleIssuesTest.java +++ b/sonar-batch/src/test/java/org/sonar/batch/issue/ModuleIssuesTest.java @@ -29,7 +29,7 @@ import org.mockito.runners.MockitoJUnitRunner; import org.sonar.api.batch.debt.DebtRemediationFunction; import org.sonar.api.batch.rule.internal.ActiveRulesBuilder; import org.sonar.api.batch.rule.internal.RulesBuilder; -import org.sonar.api.issue.internal.DefaultIssue; +import org.sonar.core.issue.DefaultIssue; import org.sonar.api.resources.File; import org.sonar.api.resources.Project; import org.sonar.api.resources.Resource; diff --git a/sonar-batch/src/test/java/org/sonar/batch/issue/tracking/InitialOpenIssuesSensorTest.java b/sonar-batch/src/test/java/org/sonar/batch/issue/tracking/InitialOpenIssuesSensorTest.java deleted file mode 100644 index 1b4a6adf544..00000000000 --- a/sonar-batch/src/test/java/org/sonar/batch/issue/tracking/InitialOpenIssuesSensorTest.java +++ /dev/null @@ -1,81 +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.batch.issue.tracking; - -import org.apache.ibatis.session.ResultHandler; -import org.junit.Test; -import org.sonar.api.resources.Project; -import org.sonar.core.issue.db.IssueChangeDao; -import org.sonar.core.issue.db.IssueDao; -import org.sonar.core.resource.ResourceDao; -import org.sonar.core.resource.ResourceDto; -import org.sonar.core.resource.ResourceQuery; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.mockito.Matchers.any; -import static org.mockito.Matchers.eq; -import static org.mockito.Mockito.mock; -import static org.mockito.Mockito.verify; -import static org.mockito.Mockito.verifyZeroInteractions; -import static org.mockito.Mockito.when; - -public class InitialOpenIssuesSensorTest { - - InitialOpenIssuesStack stack = mock(InitialOpenIssuesStack.class); - IssueDao issueDao = mock(IssueDao.class); - IssueChangeDao issueChangeDao = mock(IssueChangeDao.class); - ResourceDao resourceDao = mock(ResourceDao.class); - - InitialOpenIssuesSensor sensor = new InitialOpenIssuesSensor(stack, issueDao, issueChangeDao, resourceDao); - - @Test - public void should_select_module_open_issues() { - when(resourceDao.getResource(any(ResourceQuery.class))).thenReturn(new ResourceDto().setId(1L)); - - sensor.analyse(new Project("key"), null); - - verify(issueDao).selectNonClosedIssuesByModule(eq(1L), any(ResultHandler.class)); - } - - @Test - public void should_select_module_open_issues_changelog() { - when(resourceDao.getResource(any(ResourceQuery.class))).thenReturn(new ResourceDto().setId(1L)); - - sensor.analyse(new Project("key"), null); - - verify(issueChangeDao).selectChangelogOnNonClosedIssuesByModuleAndType(eq(1L), any(ResultHandler.class)); - } - - @Test - public void nothing_to_on_new_component() { - when(resourceDao.getResource(any(ResourceQuery.class))).thenReturn(null); - - sensor.analyse(new Project("key"), null); - - verifyZeroInteractions(issueDao); - verifyZeroInteractions(issueChangeDao); - } - - @Test - public void test_toString() throws Exception { - assertThat(sensor.toString()).isEqualTo("InitialOpenIssuesSensor"); - - } -} diff --git a/sonar-batch/src/test/java/org/sonar/batch/issue/tracking/InitialOpenIssuesStackTest.java b/sonar-batch/src/test/java/org/sonar/batch/issue/tracking/InitialOpenIssuesStackTest.java deleted file mode 100644 index c6f42f12b6a..00000000000 --- a/sonar-batch/src/test/java/org/sonar/batch/issue/tracking/InitialOpenIssuesStackTest.java +++ /dev/null @@ -1,120 +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.batch.issue.tracking; - -import org.sonar.batch.index.AbstractCachesTest; - -import org.junit.After; -import org.junit.Before; -import org.junit.Test; -import org.sonar.core.issue.db.IssueChangeDto; -import org.sonar.core.issue.db.IssueDto; - -import java.util.List; - -import static org.assertj.core.api.Assertions.assertThat; - -public class InitialOpenIssuesStackTest extends AbstractCachesTest { - - InitialOpenIssuesStack stack; - - @Before - public void before() { - stack = new InitialOpenIssuesStack(caches); - } - - @After - public void after() { - caches.stop(); - } - - @Test - public void get_and_remove_issues() { - IssueDto issueDto = new IssueDto().setComponentKey("org.struts.Action").setKee("ISSUE-1"); - stack.addIssue(issueDto); - - List<ServerIssue> issueDtos = stack.selectAndRemoveIssues("org.struts.Action"); - assertThat(issueDtos).hasSize(1); - assertThat(issueDtos.get(0).key()).isEqualTo("ISSUE-1"); - - assertThat(stack.selectAllIssues()).isEmpty(); - } - - @Test - public void get_and_remove_with_many_issues_on_same_resource() { - stack.addIssue(new IssueDto().setComponentKey("org.struts.Action").setKee("ISSUE-1")); - stack.addIssue(new IssueDto().setComponentKey("org.struts.Action").setKee("ISSUE-2")); - - List<ServerIssue> issueDtos = stack.selectAndRemoveIssues("org.struts.Action"); - assertThat(issueDtos).hasSize(2); - - assertThat(stack.selectAllIssues()).isEmpty(); - } - - @Test - public void get_and_remove_do_nothing_if_resource_not_found() { - stack.addIssue(new IssueDto().setComponentKey("org.struts.Action").setKee("ISSUE-1")); - - List<ServerIssue> issueDtos = stack.selectAndRemoveIssues("Other"); - assertThat(issueDtos).hasSize(0); - - assertThat(stack.selectAllIssues()).hasSize(1); - } - - @Test - public void select_changelog() { - stack.addChangelog(new IssueChangeDto().setKey("CHANGE-1").setIssueKey("ISSUE-1")); - stack.addChangelog(new IssueChangeDto().setKey("CHANGE-2").setIssueKey("ISSUE-1")); - - List<IssueChangeDto> issueChangeDtos = stack.selectChangelog("ISSUE-1"); - assertThat(issueChangeDtos).hasSize(2); - assertThat(issueChangeDtos.get(0).getKey()).isEqualTo("CHANGE-1"); - assertThat(issueChangeDtos.get(1).getKey()).isEqualTo("CHANGE-2"); - } - - @Test - public void return_empty_changelog() { - assertThat(stack.selectChangelog("ISSUE-1")).isEmpty(); - } - - @Test - public void clear_issues() { - stack.addIssue(new IssueDto().setComponentKey("org.struts.Action").setKee("ISSUE-1")); - - assertThat(stack.selectAllIssues()).hasSize(1); - - // issues are not removed - assertThat(stack.selectAllIssues()).hasSize(1); - - stack.clear(); - assertThat(stack.selectAllIssues()).isEmpty(); - } - - @Test - public void clear_issues_changelog() { - stack.addChangelog(new IssueChangeDto().setKey("CHANGE-1").setIssueKey("ISSUE-1")); - - assertThat(stack.selectChangelog("ISSUE-1")).hasSize(1); - - stack.clear(); - assertThat(stack.selectChangelog("ISSUE-1")).isEmpty(); - } -} diff --git a/sonar-batch/src/test/java/org/sonar/batch/issue/tracking/IssueHandlersTest.java b/sonar-batch/src/test/java/org/sonar/batch/issue/tracking/IssueHandlersTest.java deleted file mode 100644 index fe81ee2006b..00000000000 --- a/sonar-batch/src/test/java/org/sonar/batch/issue/tracking/IssueHandlersTest.java +++ /dev/null @@ -1,62 +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.batch.issue.tracking; - -import org.junit.Test; -import org.mockito.ArgumentMatcher; -import org.sonar.api.issue.IssueHandler; -import org.sonar.api.issue.internal.DefaultIssue; -import org.sonar.api.issue.internal.IssueChangeContext; -import org.sonar.core.issue.IssueUpdater; - -import java.util.Date; - -import static org.mockito.Matchers.argThat; -import static org.mockito.Mockito.mock; -import static org.mockito.Mockito.verify; -import static org.mockito.Mockito.verifyZeroInteractions; - -public class IssueHandlersTest { - @Test - public void should_execute_handlers() { - IssueHandler h1 = mock(IssueHandler.class); - IssueHandler h2 = mock(IssueHandler.class); - IssueUpdater updater = mock(IssueUpdater.class); - - IssueHandlers handlers = new IssueHandlers(updater, new IssueHandler[]{h1, h2}); - final DefaultIssue issue = new DefaultIssue(); - handlers.execute(issue, IssueChangeContext.createScan(new Date())); - - verify(h1).onIssue(argThat(new ArgumentMatcher<IssueHandler.Context>() { - @Override - public boolean matches(Object o) { - return ((IssueHandler.Context) o).issue() == issue; - } - })); - } - - @Test - public void test_no_handlers() { - IssueUpdater updater = mock(IssueUpdater.class); - IssueHandlers handlers = new IssueHandlers(updater); - handlers.execute(new DefaultIssue(), IssueChangeContext.createScan(new Date())); - verifyZeroInteractions(updater); - } -} diff --git a/sonar-batch/src/test/java/org/sonar/batch/issue/tracking/IssueTrackingDecoratorTest.java b/sonar-batch/src/test/java/org/sonar/batch/issue/tracking/IssueTrackingDecoratorTest.java deleted file mode 100644 index d09c7908d20..00000000000 --- a/sonar-batch/src/test/java/org/sonar/batch/issue/tracking/IssueTrackingDecoratorTest.java +++ /dev/null @@ -1,584 +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.batch.issue.tracking; - -import org.apache.commons.codec.digest.DigestUtils; -import org.apache.commons.io.FileUtils; -import org.apache.commons.lang.StringUtils; -import org.junit.Before; -import org.junit.Test; -import org.junit.rules.TemporaryFolder; -import org.mockito.ArgumentCaptor; -import org.mockito.ArgumentMatcher; -import org.sonar.api.batch.DecoratorContext; -import org.sonar.api.batch.fs.internal.DefaultInputFile; -import org.sonar.api.component.ResourcePerspectives; -import org.sonar.api.issue.Issue; -import org.sonar.api.issue.internal.DefaultIssue; -import org.sonar.api.issue.internal.IssueChangeContext; -import org.sonar.api.profiles.RulesProfile; -import org.sonar.api.resources.File; -import org.sonar.api.resources.Project; -import org.sonar.api.resources.Resource; -import org.sonar.api.rule.RuleKey; -import org.sonar.api.rules.Rule; -import org.sonar.api.rules.RuleFinder; -import org.sonar.api.utils.Duration; -import org.sonar.api.utils.System2; -import org.sonar.batch.issue.IssueCache; -import org.sonar.batch.scan.filesystem.InputPathCache; -import org.sonar.core.issue.IssueUpdater; -import org.sonar.core.issue.db.IssueChangeDto; -import org.sonar.core.issue.db.IssueDto; -import org.sonar.core.issue.workflow.IssueWorkflow; -import org.sonar.java.api.JavaClass; - -import java.io.IOException; -import java.nio.charset.StandardCharsets; -import java.util.Arrays; -import java.util.Collection; -import java.util.Collections; -import java.util.List; - -import static com.google.common.collect.Lists.newArrayList; -import static org.assertj.core.api.Assertions.assertThat; -import static org.mockito.Matchers.any; -import static org.mockito.Matchers.anyCollection; -import static org.mockito.Matchers.anyString; -import static org.mockito.Matchers.argThat; -import static org.mockito.Matchers.eq; -import static org.mockito.Matchers.isA; -import static org.mockito.Mockito.RETURNS_MOCKS; -import static org.mockito.Mockito.mock; -import static org.mockito.Mockito.never; -import static org.mockito.Mockito.times; -import static org.mockito.Mockito.verify; -import static org.mockito.Mockito.verifyZeroInteractions; -import static org.mockito.Mockito.when; - -public class IssueTrackingDecoratorTest { - - @org.junit.Rule - public TemporaryFolder temp = new TemporaryFolder(); - - IssueTrackingDecorator decorator; - IssueCache issueCache = mock(IssueCache.class, RETURNS_MOCKS); - InitialOpenIssuesStack initialOpenIssues = mock(InitialOpenIssuesStack.class); - IssueTracking tracking = mock(IssueTracking.class, RETURNS_MOCKS); - ServerLineHashesLoader lastSnapshots = mock(ServerLineHashesLoader.class); - IssueHandlers handlers = mock(IssueHandlers.class); - IssueWorkflow workflow = mock(IssueWorkflow.class); - IssueUpdater updater = mock(IssueUpdater.class); - ResourcePerspectives perspectives = mock(ResourcePerspectives.class); - RulesProfile profile = mock(RulesProfile.class); - RuleFinder ruleFinder = mock(RuleFinder.class); - InputPathCache inputPathCache = mock(InputPathCache.class); - - @Before - public void init() { - decorator = new IssueTrackingDecorator( - issueCache, - initialOpenIssues, - tracking, - lastSnapshots, - handlers, - workflow, - updater, - new Project("foo"), - perspectives, - profile, - ruleFinder, - inputPathCache); - } - - @Test - public void should_execute_on_project() { - Project project = mock(Project.class); - assertThat(decorator.shouldExecuteOnProject(project)).isTrue(); - } - - @Test - public void should_not_be_executed_on_classes_not_methods() { - DecoratorContext context = mock(DecoratorContext.class); - decorator.decorate(JavaClass.create("org.foo.Bar"), context); - verifyZeroInteractions(context, issueCache, tracking, handlers, workflow); - } - - @Test - public void should_process_open_issues() { - Resource file = File.create("Action.java").setEffectiveKey("struts:Action.java").setId(123); - final DefaultIssue issue = new DefaultIssue(); - - // INPUT : one issue, no open issues during previous scan, no filtering - when(issueCache.byComponent("struts:Action.java")).thenReturn(Arrays.asList(issue)); - List<ServerIssue> dbIssues = Collections.emptyList(); - when(initialOpenIssues.selectAndRemoveIssues("struts:Action.java")).thenReturn(dbIssues); - when(inputPathCache.getFile("foo", "Action.java")).thenReturn(mock(DefaultInputFile.class)); - decorator.doDecorate(file); - - // Apply filters, track, apply transitions, notify extensions then update cache - verify(tracking).track(isA(SourceHashHolder.class), eq(dbIssues), argThat(new ArgumentMatcher<Collection<DefaultIssue>>() { - @Override - public boolean matches(Object o) { - List<DefaultIssue> issues = (List<DefaultIssue>) o; - return issues.size() == 1 && issues.get(0) == issue; - } - })); - verify(workflow).doAutomaticTransition(eq(issue), any(IssueChangeContext.class)); - verify(handlers).execute(eq(issue), any(IssueChangeContext.class)); - verify(issueCache).put(issue); - } - - @Test - public void should_register_unmatched_issues_as_end_of_life() { - // "Unmatched" issues existed in previous scan but not in current one -> they have to be closed - Resource file = File.create("Action.java").setEffectiveKey("struts:Action.java").setId(123); - - // INPUT : one issue existing during previous scan - ServerIssue unmatchedIssue = new ServerIssueFromDb(new IssueDto().setKee("ABCDE").setResolution(null).setStatus("OPEN").setRuleKey("squid", "AvoidCycle")); - - IssueTrackingResult trackingResult = new IssueTrackingResult(); - trackingResult.addUnmatched(unmatchedIssue); - - when(tracking.track(isA(SourceHashHolder.class), anyCollection(), anyCollection())).thenReturn(trackingResult); - when(inputPathCache.getFile("foo", "Action.java")).thenReturn(mock(DefaultInputFile.class)); - - decorator.doDecorate(file); - - verify(workflow, times(1)).doAutomaticTransition(any(DefaultIssue.class), any(IssueChangeContext.class)); - verify(handlers, times(1)).execute(any(DefaultIssue.class), any(IssueChangeContext.class)); - - ArgumentCaptor<DefaultIssue> argument = ArgumentCaptor.forClass(DefaultIssue.class); - verify(issueCache).put(argument.capture()); - - DefaultIssue issue = argument.getValue(); - assertThat(issue.key()).isEqualTo("ABCDE"); - assertThat(issue.isNew()).isFalse(); - assertThat(issue.isEndOfLife()).isTrue(); - } - - @Test - public void manual_issues_should_be_moved_if_matching_line_found() throws Exception { - // INPUT : one issue existing during previous scan - ServerIssue unmatchedIssue = new ServerIssueFromDb(new IssueDto().setKee("ABCDE").setReporter("freddy").setLine(6).setStatus("OPEN").setRuleKey("manual", "Performance")); - when(ruleFinder.findByKey(RuleKey.of("manual", "Performance"))).thenReturn(new Rule("manual", "Performance")); - - IssueTrackingResult trackingResult = new IssueTrackingResult(); - trackingResult.addUnmatched(unmatchedIssue); - - String originalSource = "public interface Action {\n" - + " void method1();\n" - + " void method2();\n" - + " void method3();\n" - + " void method4();\n" - + " void method5();\n" // Original issue here - + "}"; - String newSource = "public interface Action {\n" - + " void method5();\n" // New issue here - + " void method1();\n" - + " void method2();\n" - + " void method3();\n" - + " void method4();\n" - + "}"; - Resource file = mockHashes(originalSource, newSource); - - when(tracking.track(isA(SourceHashHolder.class), anyCollection(), anyCollection())).thenReturn(trackingResult); - - decorator.doDecorate(file); - - verify(workflow, times(1)).doAutomaticTransition(any(DefaultIssue.class), any(IssueChangeContext.class)); - verify(handlers, times(1)).execute(any(DefaultIssue.class), any(IssueChangeContext.class)); - - ArgumentCaptor<DefaultIssue> argument = ArgumentCaptor.forClass(DefaultIssue.class); - verify(issueCache).put(argument.capture()); - - DefaultIssue issue = argument.getValue(); - assertThat(issue.line()).isEqualTo(2); - assertThat(issue.key()).isEqualTo("ABCDE"); - assertThat(issue.isNew()).isFalse(); - assertThat(issue.isEndOfLife()).isFalse(); - assertThat(issue.isOnDisabledRule()).isFalse(); - } - - private Resource mockHashes(String originalSource, String newSource) throws IOException { - DefaultInputFile inputFile = mock(DefaultInputFile.class); - java.io.File f = temp.newFile(); - when(inputFile.path()).thenReturn(f.toPath()); - when(inputFile.file()).thenReturn(f); - when(inputFile.charset()).thenReturn(StandardCharsets.UTF_8); - when(inputFile.lines()).thenReturn(StringUtils.countMatches(newSource, "\n") + 1); - FileUtils.write(f, newSource, StandardCharsets.UTF_8); - when(inputFile.key()).thenReturn("foo:Action.java"); - when(inputPathCache.getFile("foo", "Action.java")).thenReturn(inputFile); - when(lastSnapshots.getLineHashes("foo:Action.java")).thenReturn(computeHexHashes(originalSource)); - Resource file = File.create("Action.java"); - return file; - } - - @Test - public void manual_issues_should_be_untouched_if_already_closed() throws Exception { - - // INPUT : one issue existing during previous scan - ServerIssue unmatchedIssue = new ServerIssueFromDb(new IssueDto().setKee("ABCDE").setReporter("freddy").setLine(1).setStatus("CLOSED").setRuleKey("manual", "Performance")); - when(ruleFinder.findByKey(RuleKey.of("manual", "Performance"))).thenReturn(new Rule("manual", "Performance")); - - IssueTrackingResult trackingResult = new IssueTrackingResult(); - trackingResult.addUnmatched(unmatchedIssue); - - String originalSource = "public interface Action {}"; - Resource file = mockHashes(originalSource, originalSource); - - when(tracking.track(isA(SourceHashHolder.class), anyCollection(), anyCollection())).thenReturn(trackingResult); - - decorator.doDecorate(file); - - verify(workflow, times(1)).doAutomaticTransition(any(DefaultIssue.class), any(IssueChangeContext.class)); - verify(handlers, times(1)).execute(any(DefaultIssue.class), any(IssueChangeContext.class)); - - ArgumentCaptor<DefaultIssue> argument = ArgumentCaptor.forClass(DefaultIssue.class); - verify(issueCache).put(argument.capture()); - - DefaultIssue issue = argument.getValue(); - assertThat(issue.line()).isEqualTo(1); - assertThat(issue.key()).isEqualTo("ABCDE"); - assertThat(issue.isNew()).isFalse(); - assertThat(issue.isEndOfLife()).isFalse(); - assertThat(issue.isOnDisabledRule()).isFalse(); - assertThat(issue.status()).isEqualTo("CLOSED"); - } - - @Test - public void manual_issues_should_be_untouched_if_line_is_null() throws Exception { - - // INPUT : one issue existing during previous scan - ServerIssue unmatchedIssue = new ServerIssueFromDb(new IssueDto().setKee("ABCDE").setReporter("freddy").setLine(null).setStatus("OPEN").setRuleKey("manual", "Performance")); - when(ruleFinder.findByKey(RuleKey.of("manual", "Performance"))).thenReturn(new Rule("manual", "Performance")); - - IssueTrackingResult trackingResult = new IssueTrackingResult(); - trackingResult.addUnmatched(unmatchedIssue); - - String originalSource = "public interface Action {}"; - Resource file = mockHashes(originalSource, originalSource); - - when(tracking.track(isA(SourceHashHolder.class), anyCollection(), anyCollection())).thenReturn(trackingResult); - - decorator.doDecorate(file); - - verify(workflow, times(1)).doAutomaticTransition(any(DefaultIssue.class), any(IssueChangeContext.class)); - verify(handlers, times(1)).execute(any(DefaultIssue.class), any(IssueChangeContext.class)); - - ArgumentCaptor<DefaultIssue> argument = ArgumentCaptor.forClass(DefaultIssue.class); - verify(issueCache).put(argument.capture()); - - DefaultIssue issue = argument.getValue(); - assertThat(issue.line()).isEqualTo(null); - assertThat(issue.key()).isEqualTo("ABCDE"); - assertThat(issue.isNew()).isFalse(); - assertThat(issue.isEndOfLife()).isFalse(); - assertThat(issue.isOnDisabledRule()).isFalse(); - assertThat(issue.status()).isEqualTo("OPEN"); - } - - @Test - public void manual_issues_should_be_kept_if_matching_line_not_found() throws Exception { - // "Unmatched" issues existed in previous scan but not in current one -> they have to be closed - - // INPUT : one issue existing during previous scan - final int issueOnLine = 6; - ServerIssue unmatchedIssue = new ServerIssueFromDb(new IssueDto().setKee("ABCDE").setReporter("freddy").setLine(issueOnLine).setStatus("OPEN") - .setRuleKey("manual", "Performance")); - when(ruleFinder.findByKey(RuleKey.of("manual", "Performance"))).thenReturn(new Rule("manual", "Performance")); - - IssueTrackingResult trackingResult = new IssueTrackingResult(); - trackingResult.addUnmatched(unmatchedIssue); - - String originalSource = "public interface Action {\n" - + " void method1();\n" - + " void method2();\n" - + " void method3();\n" - + " void method4();\n" - + " void method5();\n" // Original issue here - + "}"; - String newSource = "public interface Action {\n" - + " void method1();\n" - + " void method2();\n" - + " void method3();\n" - + " void method4();\n" - + " void method6();\n" // Poof, no method5 anymore - + "}"; - - Resource file = mockHashes(originalSource, newSource); - - when(tracking.track(isA(SourceHashHolder.class), anyCollection(), anyCollection())).thenReturn(trackingResult); - - decorator.doDecorate(file); - - verify(workflow, times(1)).doAutomaticTransition(any(DefaultIssue.class), any(IssueChangeContext.class)); - verify(handlers, times(1)).execute(any(DefaultIssue.class), any(IssueChangeContext.class)); - - ArgumentCaptor<DefaultIssue> argument = ArgumentCaptor.forClass(DefaultIssue.class); - verify(issueCache).put(argument.capture()); - - DefaultIssue issue = argument.getValue(); - assertThat(issue.line()).isEqualTo(issueOnLine); - assertThat(issue.key()).isEqualTo("ABCDE"); - assertThat(issue.isNew()).isFalse(); - assertThat(issue.isEndOfLife()).isFalse(); - assertThat(issue.isOnDisabledRule()).isFalse(); - } - - @Test - public void manual_issues_should_be_kept_if_multiple_matching_lines_found() throws Exception { - // "Unmatched" issues existed in previous scan but not in current one -> they have to be closed - - // INPUT : one issue existing during previous scan - final int issueOnLine = 3; - ServerIssue unmatchedIssue = new ServerIssueFromDb(new IssueDto().setKee("ABCDE").setReporter("freddy").setLine(issueOnLine).setStatus("OPEN") - .setRuleKey("manual", "Performance")); - when(ruleFinder.findByKey(RuleKey.of("manual", "Performance"))).thenReturn(new Rule("manual", "Performance")); - - IssueTrackingResult trackingResult = new IssueTrackingResult(); - trackingResult.addUnmatched(unmatchedIssue); - - String originalSource = "public class Action {\n" - + " void method1() {\n" - + " notify();\n" // initial issue - + " }\n" - + "}"; - String newSource = "public class Action {\n" - + " \n" - + " void method1() {\n" // new issue will appear here - + " notify();\n" - + " }\n" - + " void method2() {\n" - + " notify();\n" - + " }\n" - + "}"; - Resource file = mockHashes(originalSource, newSource); - - when(tracking.track(isA(SourceHashHolder.class), anyCollection(), anyCollection())).thenReturn(trackingResult); - - decorator.doDecorate(file); - - verify(workflow, times(1)).doAutomaticTransition(any(DefaultIssue.class), any(IssueChangeContext.class)); - verify(handlers, times(1)).execute(any(DefaultIssue.class), any(IssueChangeContext.class)); - - ArgumentCaptor<DefaultIssue> argument = ArgumentCaptor.forClass(DefaultIssue.class); - verify(issueCache).put(argument.capture()); - - DefaultIssue issue = argument.getValue(); - assertThat(issue.line()).isEqualTo(issueOnLine); - assertThat(issue.key()).isEqualTo("ABCDE"); - assertThat(issue.isNew()).isFalse(); - assertThat(issue.isEndOfLife()).isFalse(); - assertThat(issue.isOnDisabledRule()).isFalse(); - } - - @Test - public void manual_issues_should_be_closed_if_manual_rule_is_removed() throws Exception { - // "Unmatched" issues existed in previous scan but not in current one -> they have to be closed - - // INPUT : one issue existing during previous scan - ServerIssue unmatchedIssue = new ServerIssueFromDb(new IssueDto().setKee("ABCDE").setReporter("freddy").setLine(1).setStatus("OPEN").setRuleKey("manual", "Performance")); - when(ruleFinder.findByKey(RuleKey.of("manual", "Performance"))).thenReturn(new Rule("manual", "Performance").setStatus(Rule.STATUS_REMOVED)); - - IssueTrackingResult trackingResult = new IssueTrackingResult(); - trackingResult.addUnmatched(unmatchedIssue); - - String source = "public interface Action {}"; - Resource file = mockHashes(source, source); - - when(tracking.track(isA(SourceHashHolder.class), anyCollection(), anyCollection())).thenReturn(trackingResult); - - decorator.doDecorate(file); - - verify(workflow, times(1)).doAutomaticTransition(any(DefaultIssue.class), any(IssueChangeContext.class)); - verify(handlers, times(1)).execute(any(DefaultIssue.class), any(IssueChangeContext.class)); - - ArgumentCaptor<DefaultIssue> argument = ArgumentCaptor.forClass(DefaultIssue.class); - verify(issueCache).put(argument.capture()); - - DefaultIssue issue = argument.getValue(); - assertThat(issue.key()).isEqualTo("ABCDE"); - assertThat(issue.isNew()).isFalse(); - assertThat(issue.isEndOfLife()).isTrue(); - assertThat(issue.isOnDisabledRule()).isTrue(); - } - - @Test - public void manual_issues_should_be_closed_if_manual_rule_is_not_found() throws Exception { - // "Unmatched" issues existed in previous scan but not in current one -> they have to be closed - - // INPUT : one issue existing during previous scan - ServerIssue unmatchedIssue = new ServerIssueFromDb(new IssueDto().setKee("ABCDE").setReporter("freddy").setLine(1).setStatus("OPEN").setRuleKey("manual", "Performance")); - when(ruleFinder.findByKey(RuleKey.of("manual", "Performance"))).thenReturn(null); - - IssueTrackingResult trackingResult = new IssueTrackingResult(); - trackingResult.addUnmatched(unmatchedIssue); - - String source = "public interface Action {}"; - Resource file = mockHashes(source, source); - - when(tracking.track(isA(SourceHashHolder.class), anyCollection(), anyCollection())).thenReturn(trackingResult); - - decorator.doDecorate(file); - - verify(workflow, times(1)).doAutomaticTransition(any(DefaultIssue.class), any(IssueChangeContext.class)); - verify(handlers, times(1)).execute(any(DefaultIssue.class), any(IssueChangeContext.class)); - - ArgumentCaptor<DefaultIssue> argument = ArgumentCaptor.forClass(DefaultIssue.class); - verify(issueCache).put(argument.capture()); - - DefaultIssue issue = argument.getValue(); - assertThat(issue.key()).isEqualTo("ABCDE"); - assertThat(issue.isNew()).isFalse(); - assertThat(issue.isEndOfLife()).isTrue(); - assertThat(issue.isOnDisabledRule()).isTrue(); - } - - @Test - public void manual_issues_should_be_closed_if_new_source_is_shorter() throws Exception { - // "Unmatched" issues existed in previous scan but not in current one -> they have to be closed - - // INPUT : one issue existing during previous scan - ServerIssue unmatchedIssue = new ServerIssueFromDb(new IssueDto().setKee("ABCDE").setReporter("freddy").setLine(6).setStatus("OPEN").setRuleKey("manual", "Performance")); - when(ruleFinder.findByKey(RuleKey.of("manual", "Performance"))).thenReturn(null); - - IssueTrackingResult trackingResult = new IssueTrackingResult(); - trackingResult.addUnmatched(unmatchedIssue); - - String originalSource = "public interface Action {\n" - + " void method1();\n" - + " void method2();\n" - + " void method3();\n" - + " void method4();\n" - + " void method5();\n" - + "}"; - String newSource = "public interface Action {\n" - + " void method1();\n" - + " void method2();\n" - + "}"; - Resource file = mockHashes(originalSource, newSource); - - when(tracking.track(isA(SourceHashHolder.class), anyCollection(), anyCollection())).thenReturn(trackingResult); - - decorator.doDecorate(file); - - verify(workflow, times(1)).doAutomaticTransition(any(DefaultIssue.class), any(IssueChangeContext.class)); - verify(handlers, times(1)).execute(any(DefaultIssue.class), any(IssueChangeContext.class)); - - ArgumentCaptor<DefaultIssue> argument = ArgumentCaptor.forClass(DefaultIssue.class); - verify(issueCache).put(argument.capture()); - - DefaultIssue issue = argument.getValue(); - verify(updater).setResolution(eq(issue), eq(Issue.RESOLUTION_REMOVED), any(IssueChangeContext.class)); - verify(updater).setStatus(eq(issue), eq(Issue.STATUS_CLOSED), any(IssueChangeContext.class)); - - assertThat(issue.key()).isEqualTo("ABCDE"); - assertThat(issue.isNew()).isFalse(); - assertThat(issue.isEndOfLife()).isTrue(); - assertThat(issue.isOnDisabledRule()).isTrue(); - } - - @Test - public void should_register_issues_on_deleted_components() { - Project project = new Project("struts"); - DefaultIssue openIssue = new DefaultIssue(); - when(issueCache.byComponent("struts")).thenReturn(Arrays.asList(openIssue)); - IssueDto deadIssue = new IssueDto().setKee("ABCDE").setResolution(null).setStatus("OPEN").setRuleKey("squid", "AvoidCycle"); - when(initialOpenIssues.selectAllIssues()).thenReturn(Arrays.asList(deadIssue)); - - decorator.doDecorate(project); - - // the dead issue must be closed -> apply automatic transition, notify handlers and add to cache - verify(workflow, times(2)).doAutomaticTransition(any(DefaultIssue.class), any(IssueChangeContext.class)); - verify(handlers, times(2)).execute(any(DefaultIssue.class), any(IssueChangeContext.class)); - verify(issueCache, times(2)).put(any(DefaultIssue.class)); - - verify(issueCache).put(argThat(new ArgumentMatcher<DefaultIssue>() { - @Override - public boolean matches(Object o) { - DefaultIssue dead = (DefaultIssue) o; - return "ABCDE".equals(dead.key()) && !dead.isNew() && dead.isEndOfLife(); - } - })); - } - - @Test - public void merge_matched_issue() { - ServerIssue previousIssue = new ServerIssueFromDb(new IssueDto().setKee("ABCDE").setResolution(null).setStatus("OPEN").setRuleKey("squid", "AvoidCycle") - .setLine(10).setSeverity("MAJOR").setMessage("Message").setEffortToFix(1.5).setDebt(1L).setProjectKey("sample")); - DefaultIssue issue = new DefaultIssue(); - - IssueTrackingResult trackingResult = mock(IssueTrackingResult.class); - when(trackingResult.matched()).thenReturn(newArrayList(issue)); - when(trackingResult.matching(eq(issue))).thenReturn(previousIssue); - decorator.mergeMatched(trackingResult); - - verify(updater).setPastSeverity(eq(issue), eq("MAJOR"), any(IssueChangeContext.class)); - verify(updater).setPastLine(eq(issue), eq(10)); - verify(updater).setPastMessage(eq(issue), eq("Message"), any(IssueChangeContext.class)); - verify(updater).setPastEffortToFix(eq(issue), eq(1.5), any(IssueChangeContext.class)); - verify(updater).setPastTechnicalDebt(eq(issue), eq(Duration.create(1L)), any(IssueChangeContext.class)); - verify(updater).setPastProject(eq(issue), eq("sample"), any(IssueChangeContext.class)); - } - - @Test - public void merge_matched_issue_on_manual_severity() { - ServerIssue previousIssue = new ServerIssueFromDb(new IssueDto().setKee("ABCDE").setResolution(null).setStatus("OPEN").setRuleKey("squid", "AvoidCycle") - .setLine(10).setManualSeverity(true).setSeverity("MAJOR").setMessage("Message").setEffortToFix(1.5).setDebt(1L)); - DefaultIssue issue = new DefaultIssue(); - - IssueTrackingResult trackingResult = mock(IssueTrackingResult.class); - when(trackingResult.matched()).thenReturn(newArrayList(issue)); - when(trackingResult.matching(eq(issue))).thenReturn(previousIssue); - decorator.mergeMatched(trackingResult); - - assertThat(issue.manualSeverity()).isTrue(); - assertThat(issue.severity()).isEqualTo("MAJOR"); - verify(updater, never()).setPastSeverity(eq(issue), anyString(), any(IssueChangeContext.class)); - } - - @Test - public void merge_issue_changelog_with_previous_changelog() { - when(initialOpenIssues.selectChangelog("ABCDE")).thenReturn(newArrayList(new IssueChangeDto().setIssueKey("ABCD").setCreatedAt(System2.INSTANCE.now()))); - - ServerIssue previousIssue = new ServerIssueFromDb(new IssueDto().setKee("ABCDE").setResolution(null).setStatus("OPEN").setRuleKey("squid", "AvoidCycle") - .setLine(10).setMessage("Message").setEffortToFix(1.5).setDebt(1L).setCreatedAt(System2.INSTANCE.now())); - DefaultIssue issue = new DefaultIssue(); - - IssueTrackingResult trackingResult = mock(IssueTrackingResult.class); - when(trackingResult.matched()).thenReturn(newArrayList(issue)); - when(trackingResult.matching(eq(issue))).thenReturn(previousIssue); - decorator.mergeMatched(trackingResult); - - assertThat(issue.changes()).hasSize(1); - } - - private String[] computeHexHashes(String source) { - String[] lines = source.split("\n"); - String[] hashes = new String[lines.length]; - for (int i = 0; i < lines.length; i++) { - hashes[i] = DigestUtils.md5Hex(lines[i].replaceAll("[\t ]", "")); - } - return hashes; - } - -} diff --git a/sonar-batch/src/test/java/org/sonar/batch/issue/tracking/IssueTrackingTest.java b/sonar-batch/src/test/java/org/sonar/batch/issue/tracking/IssueTrackingTest.java index 062c539b457..ae678c34bd3 100644 --- a/sonar-batch/src/test/java/org/sonar/batch/issue/tracking/IssueTrackingTest.java +++ b/sonar-batch/src/test/java/org/sonar/batch/issue/tracking/IssueTrackingTest.java @@ -32,7 +32,7 @@ import org.junit.rules.ExpectedException; import org.junit.rules.TemporaryFolder; import org.sonar.api.batch.fs.internal.DefaultInputFile; import org.sonar.api.issue.Issue; -import org.sonar.api.issue.internal.DefaultIssue; +import org.sonar.core.issue.DefaultIssue; import org.sonar.api.resources.Project; import org.sonar.api.resources.Resource; import org.sonar.api.rule.RuleKey; diff --git a/sonar-batch/src/test/java/org/sonar/batch/postjob/DefaultPostJobContextTest.java b/sonar-batch/src/test/java/org/sonar/batch/postjob/DefaultPostJobContextTest.java index 5db240ddeb5..081dcb968b5 100644 --- a/sonar-batch/src/test/java/org/sonar/batch/postjob/DefaultPostJobContextTest.java +++ b/sonar-batch/src/test/java/org/sonar/batch/postjob/DefaultPostJobContextTest.java @@ -26,7 +26,7 @@ import org.sonar.api.batch.fs.InputFile; import org.sonar.api.batch.postjob.issue.Issue; import org.sonar.api.batch.rule.Severity; import org.sonar.api.config.Settings; -import org.sonar.api.issue.internal.DefaultIssue; +import org.sonar.core.issue.DefaultIssue; import org.sonar.api.resources.File; import org.sonar.batch.index.BatchComponentCache; import org.sonar.batch.issue.IssueCache; diff --git a/sonar-batch/src/test/java/org/sonar/batch/profiling/PhasesSumUpTimeProfilerTest.java b/sonar-batch/src/test/java/org/sonar/batch/profiling/PhasesSumUpTimeProfilerTest.java index 0aa11588a8c..1ff8b82c9c4 100644 --- a/sonar-batch/src/test/java/org/sonar/batch/profiling/PhasesSumUpTimeProfilerTest.java +++ b/sonar-batch/src/test/java/org/sonar/batch/profiling/PhasesSumUpTimeProfilerTest.java @@ -20,6 +20,10 @@ package org.sonar.batch.profiling; import com.google.common.collect.Maps; +import java.util.Arrays; +import java.util.Collections; +import java.util.List; +import java.util.Map; import org.junit.Before; import org.junit.Rule; import org.junit.Test; @@ -48,14 +52,6 @@ import org.sonar.api.resources.Resource; import org.sonar.api.utils.System2; import org.sonar.batch.bootstrap.BootstrapProperties; import org.sonar.batch.events.BatchStepEvent; -import org.sonar.batch.index.ScanPersister; -import org.sonar.batch.phases.event.PersisterExecutionHandler; -import org.sonar.batch.phases.event.PersistersPhaseHandler; - -import java.util.Arrays; -import java.util.Collections; -import java.util.List; -import java.util.Map; import static org.assertj.core.api.Assertions.assertThat; import static org.mockito.Mockito.spy; @@ -88,7 +84,6 @@ public class PhasesSumUpTimeProfilerTest { assertThat(profiler.currentModuleProfiling.getProfilingPerPhase(Phase.INIT).getProfilingPerItem(new FakeInitializer()).totalTime()).isEqualTo(7L); assertThat(profiler.currentModuleProfiling.getProfilingPerPhase(Phase.SENSOR).getProfilingPerItem(new FakeSensor()).totalTime()).isEqualTo(10L); assertThat(profiler.currentModuleProfiling.getProfilingPerPhase(Phase.DECORATOR).getProfilingPerItem(new FakeDecorator1()).totalTime()).isEqualTo(20L); - assertThat(profiler.currentModuleProfiling.getProfilingPerPhase(Phase.PERSISTER).getProfilingPerItem(new FakeScanPersister()).totalTime()).isEqualTo(40L); assertThat(profiler.currentModuleProfiling.getProfilingPerPhase(Phase.POSTJOB).getProfilingPerItem(new FakePostJob()).totalTime()).isEqualTo(30L); assertThat(profiler.currentModuleProfiling.getProfilingPerBatchStep("Free memory").totalTime()).isEqualTo(9L); @@ -109,14 +104,12 @@ public class PhasesSumUpTimeProfilerTest { assertThat(profiler.currentModuleProfiling.getProfilingPerPhase(Phase.SENSOR).getProfilingPerItem(new FakeSensor()).totalTime()).isEqualTo(10L); assertThat(profiler.currentModuleProfiling.getProfilingPerPhase(Phase.DECORATOR).getProfilingPerItem(new FakeDecorator1()).totalTime()).isEqualTo(20L); assertThat(profiler.currentModuleProfiling.getProfilingPerPhase(Phase.DECORATOR).getProfilingPerItem(new FakeDecorator2()).totalTime()).isEqualTo(10L); - assertThat(profiler.currentModuleProfiling.getProfilingPerPhase(Phase.PERSISTER).getProfilingPerItem(new FakeScanPersister()).totalTime()).isEqualTo(40L); assertThat(profiler.currentModuleProfiling.getProfilingPerPhase(Phase.POSTJOB).getProfilingPerItem(new FakePostJob()).totalTime()).isEqualTo(30L); assertThat(profiler.totalProfiling.getProfilingPerPhase(Phase.INIT).getProfilingPerItem(new FakeInitializer()).totalTime()).isEqualTo(21L); assertThat(profiler.totalProfiling.getProfilingPerPhase(Phase.SENSOR).getProfilingPerItem(new FakeSensor()).totalTime()).isEqualTo(30L); assertThat(profiler.totalProfiling.getProfilingPerPhase(Phase.DECORATOR).getProfilingPerItem(new FakeDecorator1()).totalTime()).isEqualTo(60L); assertThat(profiler.totalProfiling.getProfilingPerPhase(Phase.DECORATOR).getProfilingPerItem(new FakeDecorator2()).totalTime()).isEqualTo(30L); - assertThat(profiler.totalProfiling.getProfilingPerPhase(Phase.PERSISTER).getProfilingPerItem(new FakeScanPersister()).totalTime()).isEqualTo(120L); assertThat(profiler.totalProfiling.getProfilingPerPhase(Phase.POSTJOB).getProfilingPerItem(new FakePostJob()).totalTime()).isEqualTo(90L); } @@ -164,7 +157,6 @@ public class PhasesSumUpTimeProfilerTest { initializerPhase(profiler); sensorPhase(profiler); decoratorPhase(profiler); - persistersPhase(profiler); postJobPhase(profiler); batchStep(profiler); // End of moduleA @@ -234,19 +226,6 @@ public class PhasesSumUpTimeProfilerTest { profiler.onSensorsPhase(sensorsEvent(false)); } - private void persistersPhase(PhasesSumUpTimeProfiler profiler) { - ScanPersister persister = new FakeScanPersister(); - // Start of persister phase - profiler.onPersistersPhase(persistersEvent(true)); - // Start of a ScanPersister - profiler.onPersisterExecution(persisterEvent(persister, true)); - clock.sleep(40); - // End of a ScanPersister - profiler.onPersisterExecution(persisterEvent(persister, false)); - // End of persister phase - profiler.onPersistersPhase(persistersEvent(false)); - } - private void postJobPhase(PhasesSumUpTimeProfiler profiler) { PostJob postJob = new FakePostJob(); // Start of sensor phase @@ -340,26 +319,6 @@ public class PhasesSumUpTimeProfilerTest { }; } - private PersisterExecutionHandler.PersisterExecutionEvent persisterEvent(final ScanPersister persister, final boolean start) { - return new PersisterExecutionHandler.PersisterExecutionEvent() { - - @Override - public boolean isStart() { - return start; - } - - @Override - public boolean isEnd() { - return !start; - } - - @Override - public ScanPersister getPersister() { - return persister; - } - }; - } - private SensorsPhaseEvent sensorsEvent(final boolean start) { return new SensorsPhaseHandler.SensorsPhaseEvent() { @@ -420,26 +379,6 @@ public class PhasesSumUpTimeProfilerTest { }; } - private PersistersPhaseHandler.PersistersPhaseEvent persistersEvent(final boolean start) { - return new PersistersPhaseHandler.PersistersPhaseEvent() { - - @Override - public boolean isStart() { - return start; - } - - @Override - public boolean isEnd() { - return !start; - } - - @Override - public List<ScanPersister> getPersisters() { - return null; - } - }; - } - private DecoratorsPhaseHandler.DecoratorsPhaseEvent decoratorsEvent(final boolean start) { return new DecoratorsPhaseHandler.DecoratorsPhaseEvent() { @@ -528,10 +467,4 @@ public class PhasesSumUpTimeProfilerTest { public void executeOn(Project project, SensorContext context) { } } - - public class FakeScanPersister implements ScanPersister { - @Override - public void persist() { - } - } } diff --git a/sonar-batch/src/test/java/org/sonar/batch/report/IssuesPublisherTest.java b/sonar-batch/src/test/java/org/sonar/batch/report/IssuesPublisherTest.java index 8e49ddb719f..fbe835369f3 100644 --- a/sonar-batch/src/test/java/org/sonar/batch/report/IssuesPublisherTest.java +++ b/sonar-batch/src/test/java/org/sonar/batch/report/IssuesPublisherTest.java @@ -30,8 +30,6 @@ import org.junit.rules.TemporaryFolder; import org.sonar.api.CoreProperties; import org.sonar.api.batch.bootstrap.ProjectDefinition; import org.sonar.api.database.model.Snapshot; -import org.sonar.api.issue.internal.DefaultIssue; -import org.sonar.api.issue.internal.FieldDiffs; import org.sonar.api.resources.Project; import org.sonar.api.rule.RuleKey; import org.sonar.api.utils.Duration; @@ -41,6 +39,8 @@ import org.sonar.batch.protocol.output.BatchReport.Metadata; import org.sonar.batch.protocol.output.BatchReportReader; import org.sonar.batch.protocol.output.BatchReportWriter; import org.sonar.batch.scan.ImmutableProjectReactor; +import org.sonar.core.issue.DefaultIssue; +import org.sonar.core.issue.FieldDiffs; import static org.assertj.core.api.Assertions.assertThat; import static org.mockito.Matchers.anyString; @@ -110,7 +110,6 @@ public class IssuesPublisherTest { Metadata metadata = reader.readMetadata(); assertThat(metadata.getAnalysisDate()).isEqualTo(1234567L); assertThat(metadata.getProjectKey()).isEqualTo("foo"); - assertThat(metadata.getDeletedComponentsCount()).isEqualTo(0); assertThat(reader.readComponentIssues(1)).hasSize(0); assertThat(reader.readComponentIssues(2)).hasSize(2); @@ -118,7 +117,7 @@ public class IssuesPublisherTest { } @Test - public void publishMatadataWithBranch() throws Exception { + public void publishMetadataWithBranch() throws Exception { root.properties().put(CoreProperties.PROJECT_BRANCH_PROPERTY, "myBranch"); p.setKey("foo:myBranch"); p.setEffectiveKey("foo:myBranch"); @@ -133,56 +132,6 @@ public class IssuesPublisherTest { assertThat(metadata.getAnalysisDate()).isEqualTo(1234567L); assertThat(metadata.getProjectKey()).isEqualTo("foo"); assertThat(metadata.getBranch()).isEqualTo("myBranch"); - assertThat(metadata.getDeletedComponentsCount()).isEqualTo(0); } - @Test - public void publishIssuesOfDeletedComponents() throws Exception { - - DefaultIssue issue1 = new DefaultIssue(); - issue1.setKey("uuid"); - issue1.setComponentUuid("deletedUuid"); - issue1.setSeverity("MAJOR"); - issue1.setRuleKey(RuleKey.of("repo", "rule")); - DefaultIssue issue2 = new DefaultIssue(); - issue2.setKey("uuid2"); - issue2.setComponentUuid("deletedUuid"); - issue2.setSeverity("MAJOR"); - issue2.setRuleKey(RuleKey.of("repo", "rule")); - issue2.setLine(2); - issue2.setMessage("msg"); - issue2.setEffortToFix(2d); - issue2.setDebt(Duration.create(2)); - issue2.setResolution("FIXED"); - issue2.setStatus("RESOLVED"); - issue2.setChecksum("checksum"); - issue2.setReporter("reporter"); - issue2.setAssignee("assignee"); - issue2.setActionPlanKey("action"); - issue2.setAuthorLogin("author"); - issue2.setCurrentChange(new FieldDiffs().setUserLogin("foo")); - issue2.setCreationDate(new Date()); - issue2.setUpdateDate(new Date()); - issue2.setCloseDate(new Date()); - issue2.setSelectedAt(1234L); - - when(issueCache.byComponent("foo:deleted.php")).thenReturn(Arrays.asList(issue1, issue2)); - - when(issueCache.componentKeys()).thenReturn(Arrays.<Object>asList("foo:deleted.php")); - - File outputDir = temp.newFolder(); - BatchReportWriter writer = new BatchReportWriter(outputDir); - - publisher.publish(writer); - - BatchReportReader reader = new BatchReportReader(outputDir); - Metadata metadata = reader.readMetadata(); - assertThat(metadata.getDeletedComponentsCount()).isEqualTo(1); - - assertThat(reader.readComponentIssues(1)).hasSize(0); - assertThat(reader.readComponentIssues(2)).hasSize(0); - assertThat(reader.readDeletedComponentIssues(1).getComponentUuid()).isEqualTo("deletedUuid"); - assertThat(reader.readDeletedComponentIssues(1).getIssueList()).hasSize(2); - - } } diff --git a/sonar-batch/src/test/java/org/sonar/batch/scan/report/ConsoleReportTest.java b/sonar-batch/src/test/java/org/sonar/batch/scan/report/ConsoleReportTest.java index f5a1482e608..fc3355952c0 100644 --- a/sonar-batch/src/test/java/org/sonar/batch/scan/report/ConsoleReportTest.java +++ b/sonar-batch/src/test/java/org/sonar/batch/scan/report/ConsoleReportTest.java @@ -25,7 +25,7 @@ import org.junit.Test; import org.sonar.api.batch.fs.InputFile; import org.sonar.api.batch.fs.internal.DefaultInputFile; import org.sonar.api.config.Settings; -import org.sonar.api.issue.internal.DefaultIssue; +import org.sonar.core.issue.DefaultIssue; import org.sonar.api.rule.Severity; import org.sonar.api.utils.log.LogTester; import org.sonar.batch.issue.IssueCache; diff --git a/sonar-batch/src/test/java/org/sonar/batch/scan/report/JSONReportTest.java b/sonar-batch/src/test/java/org/sonar/batch/scan/report/JSONReportTest.java index 0a346666ad5..afc0d4c39aa 100644 --- a/sonar-batch/src/test/java/org/sonar/batch/scan/report/JSONReportTest.java +++ b/sonar-batch/src/test/java/org/sonar/batch/scan/report/JSONReportTest.java @@ -33,7 +33,7 @@ import org.sonar.api.batch.rule.ActiveRules; import org.sonar.api.batch.rule.internal.ActiveRulesBuilder; import org.sonar.api.config.Settings; import org.sonar.api.issue.Issue; -import org.sonar.api.issue.internal.DefaultIssue; +import org.sonar.core.issue.DefaultIssue; import org.sonar.api.platform.Server; import org.sonar.api.resources.Project; import org.sonar.api.resources.Resource; diff --git a/sonar-batch/src/test/java/org/sonar/batch/sensor/DefaultSensorStorageTest.java b/sonar-batch/src/test/java/org/sonar/batch/sensor/DefaultSensorStorageTest.java index d62fd760616..69b176538a1 100644 --- a/sonar-batch/src/test/java/org/sonar/batch/sensor/DefaultSensorStorageTest.java +++ b/sonar-batch/src/test/java/org/sonar/batch/sensor/DefaultSensorStorageTest.java @@ -144,7 +144,7 @@ public class DefaultSensorStorageTest { public void shouldAddIssueOnFile() { InputFile file = new DefaultInputFile("foo", "src/Foo.php").setLines(4); - ArgumentCaptor<org.sonar.api.issue.internal.DefaultIssue> argumentCaptor = ArgumentCaptor.forClass(org.sonar.api.issue.internal.DefaultIssue.class); + ArgumentCaptor<org.sonar.core.issue.DefaultIssue> argumentCaptor = ArgumentCaptor.forClass(org.sonar.core.issue.DefaultIssue.class); sensorStorage.store(new DefaultIssue() .onFile(file) @@ -155,7 +155,7 @@ public class DefaultSensorStorageTest { verify(moduleIssues).initAndAddIssue(argumentCaptor.capture()); - org.sonar.api.issue.internal.DefaultIssue issue = argumentCaptor.getValue(); + org.sonar.core.issue.DefaultIssue issue = argumentCaptor.getValue(); assertThat(issue.ruleKey()).isEqualTo(RuleKey.of("foo", "bar")); assertThat(issue.message()).isEqualTo("Foo"); assertThat(issue.line()).isEqualTo(3); @@ -167,7 +167,7 @@ public class DefaultSensorStorageTest { public void shouldAddIssueOnDirectory() { InputDir dir = new DefaultInputDir("foo", "src"); - ArgumentCaptor<org.sonar.api.issue.internal.DefaultIssue> argumentCaptor = ArgumentCaptor.forClass(org.sonar.api.issue.internal.DefaultIssue.class); + ArgumentCaptor<org.sonar.core.issue.DefaultIssue> argumentCaptor = ArgumentCaptor.forClass(org.sonar.core.issue.DefaultIssue.class); sensorStorage.store(new DefaultIssue() .onDir(dir) @@ -177,7 +177,7 @@ public class DefaultSensorStorageTest { verify(moduleIssues).initAndAddIssue(argumentCaptor.capture()); - org.sonar.api.issue.internal.DefaultIssue issue = argumentCaptor.getValue(); + org.sonar.core.issue.DefaultIssue issue = argumentCaptor.getValue(); assertThat(issue.ruleKey()).isEqualTo(RuleKey.of("foo", "bar")); assertThat(issue.message()).isEqualTo("Foo"); assertThat(issue.line()).isNull(); @@ -187,7 +187,7 @@ public class DefaultSensorStorageTest { @Test public void shouldAddIssueOnProject() { - ArgumentCaptor<org.sonar.api.issue.internal.DefaultIssue> argumentCaptor = ArgumentCaptor.forClass(org.sonar.api.issue.internal.DefaultIssue.class); + ArgumentCaptor<org.sonar.core.issue.DefaultIssue> argumentCaptor = ArgumentCaptor.forClass(org.sonar.core.issue.DefaultIssue.class); sensorStorage.store(new DefaultIssue() .onProject() @@ -198,7 +198,7 @@ public class DefaultSensorStorageTest { verify(moduleIssues).initAndAddIssue(argumentCaptor.capture()); - org.sonar.api.issue.internal.DefaultIssue issue = argumentCaptor.getValue(); + org.sonar.core.issue.DefaultIssue issue = argumentCaptor.getValue(); assertThat(issue.ruleKey()).isEqualTo(RuleKey.of("foo", "bar")); assertThat(issue.message()).isEqualTo("Foo"); assertThat(issue.line()).isNull(); |