From 039308979d3a3cd8841d9abdf8453ba4014575f0 Mon Sep 17 00:00:00 2001 From: Simon Brandhof Date: Sun, 14 Apr 2013 23:39:12 +0200 Subject: [PATCH] SONAR-3755 add authorization to search of issues --- .../sonar/core/issue/DefaultIssueFinder.java | 86 ++++++++++++------- .../java/org/sonar/core/issue/IssueDao.java | 11 ++- .../org/sonar/core/persistence/DaoUtils.java | 2 + .../org/sonar/core/persistence/MyBatis.java | 1 + .../org/sonar/core/user/AuthorizationDao.java | 68 +++++++++++++++ .../org/sonar/core/issue/IssueMapper.xml | 22 +++-- .../core/issue/DefaultIssueFinderTest.java | 38 ++++++-- .../java/org/sonar/api/issue/Issuable.java | 5 -- .../java/org/sonar/api/issue/IssueFinder.java | 4 +- .../java/org/sonar/api/issue/IssueQuery.java | 2 + .../java/org/sonar/api/issue/JRubyIssues.java | 4 +- .../{ui => issue}/DefaultJRubyIssues.java | 7 +- .../org/sonar/server/platform/Platform.java | 1 + .../org/sonar/server/ui/JRubyFacades.java | 2 +- .../app/controllers/api/issues_controller.rb | 6 +- .../app/controllers/issues_controller.rb | 3 +- .../{ui => issue}/DefaultJRubyIssuesTest.java | 8 +- .../org/sonar/server/ui/JRubyFacadesTest.java | 1 + 18 files changed, 199 insertions(+), 72 deletions(-) create mode 100644 sonar-core/src/main/java/org/sonar/core/user/AuthorizationDao.java rename sonar-server/src/main/java/org/sonar/server/{ui => issue}/DefaultJRubyIssues.java (92%) rename sonar-server/src/test/java/org/sonar/server/{ui => issue}/DefaultJRubyIssuesTest.java (94%) diff --git a/sonar-core/src/main/java/org/sonar/core/issue/DefaultIssueFinder.java b/sonar-core/src/main/java/org/sonar/core/issue/DefaultIssueFinder.java index 3689c541f60..12d965cfdef 100644 --- a/sonar-core/src/main/java/org/sonar/core/issue/DefaultIssueFinder.java +++ b/sonar-core/src/main/java/org/sonar/core/issue/DefaultIssueFinder.java @@ -25,6 +25,7 @@ import com.google.common.collect.ImmutableList; import com.google.common.collect.Iterables; import com.google.common.collect.Maps; import com.google.common.collect.Sets; +import org.apache.ibatis.session.SqlSession; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.sonar.api.issue.Issue; @@ -33,8 +34,12 @@ import org.sonar.api.issue.IssueQuery; import org.sonar.api.rules.Rule; import org.sonar.api.rules.RuleFinder; import org.sonar.api.utils.KeyValueFormat; +import org.sonar.core.persistence.MyBatis; import org.sonar.core.resource.ResourceDao; import org.sonar.core.resource.ResourceDto; +import org.sonar.core.user.AuthorizationDao; + +import javax.annotation.Nullable; import java.util.List; import java.util.Map; @@ -47,53 +52,70 @@ public class DefaultIssueFinder implements IssueFinder { private static final Logger LOG = LoggerFactory.getLogger(DefaultIssueFinder.class); + /** + * The role required to access issues + */ + private static final String ROLE = "user"; + + private final MyBatis myBatis; private final IssueDao issueDao; private final ResourceDao resourceDao; + private final AuthorizationDao authorizationDao; private final RuleFinder ruleFinder; - public DefaultIssueFinder(IssueDao issueDao, ResourceDao resourceDao, RuleFinder ruleFinder) { + public DefaultIssueFinder(MyBatis myBatis, IssueDao issueDao, ResourceDao resourceDao, + AuthorizationDao authorizationDao, RuleFinder ruleFinder) { + this.myBatis = myBatis; this.issueDao = issueDao; this.resourceDao = resourceDao; + this.authorizationDao = authorizationDao; this.ruleFinder = ruleFinder; } - public Results find(IssueQuery query) { + public Results find(IssueQuery query, @Nullable Integer currentUserId) { LOG.debug("IssueQuery : {}", query); - List dtoList = issueDao.select(query); - - final Set componentIds = Sets.newLinkedHashSet(); - final Set ruleIds = Sets.newLinkedHashSet(); - for (IssueDto dto : dtoList) { - componentIds.add(dto.getResourceId()); - ruleIds.add(dto.getRuleId()); - } - final Map rules = Maps.newHashMap(); - for (Integer ruleId : ruleIds) { - Rule rule = ruleFinder.findById(ruleId); - if (rule != null) { - rules.put(rule.getId(), rule); + SqlSession sqlSession = myBatis.openSession(); + try { + List issueDtos = issueDao.select(query, sqlSession); + + Set componentIds = Sets.newLinkedHashSet(); + Set ruleIds = Sets.newLinkedHashSet(); + for (IssueDto issueDto : issueDtos) { + componentIds.add(issueDto.getResourceId()); + ruleIds.add(issueDto.getRuleId()); } - } - final Map resources = Maps.newHashMap(); - for (Integer componentId : componentIds) { - ResourceDto resource = resourceDao.getResource(componentId); - if (resource != null) { - resources.put(resource.getId().intValue(), resource); - } - } - // TODO verify authorization + componentIds = authorizationDao.keepAuthorizedComponentIds(componentIds, currentUserId, ROLE, sqlSession); - List issues = ImmutableList.copyOf(Iterables.transform(dtoList, new Function() { - @Override - public Issue apply(IssueDto dto) { - Rule rule = rules.get(dto.getRuleId()); - ResourceDto resource = resources.get(dto.getResourceId()); - return toIssue(dto, rule, resource); + final Map rules = Maps.newHashMap(); + for (Integer ruleId : ruleIds) { + Rule rule = ruleFinder.findById(ruleId); + if (rule != null) { + rules.put(rule.getId(), rule); + } + } + final Map resources = Maps.newHashMap(); + for (Integer componentId : componentIds) { + // TODO replace N+1 SQL requests by a single one + ResourceDto resource = resourceDao.getResource(componentId); + if (resource != null) { + resources.put(resource.getId().intValue(), resource); + } } - })); - return new DefaultResults(issues); + List issues = ImmutableList.copyOf(Iterables.transform(issueDtos, new Function() { + @Override + public Issue apply(IssueDto dto) { + Rule rule = rules.get(dto.getRuleId()); + ResourceDto resource = resources.get(dto.getResourceId()); + return toIssue(dto, rule, resource); + } + })); + + return new DefaultResults(issues); + } finally { + MyBatis.closeQuietly(sqlSession); + } } public Issue findByKey(String key) { diff --git a/sonar-core/src/main/java/org/sonar/core/issue/IssueDao.java b/sonar-core/src/main/java/org/sonar/core/issue/IssueDao.java index 2962518a8c4..c1691a7a3f9 100644 --- a/sonar-core/src/main/java/org/sonar/core/issue/IssueDao.java +++ b/sonar-core/src/main/java/org/sonar/core/issue/IssueDao.java @@ -88,13 +88,16 @@ public class IssueDao implements BatchComponent, ServerComponent { public List select(IssueQuery query) { SqlSession session = mybatis.openSession(); try { - // TODO support ordering - - return session.selectList("org.sonar.core.issue.IssueMapper.select", query, new RowBounds(query.offset(), query.limit())); - + return select(query, session); } finally { MyBatis.closeQuietly(session); } } + public List select(IssueQuery query, SqlSession session) { + // TODO support ordering + + return session.selectList("org.sonar.core.issue.IssueMapper.select", query, new RowBounds(query.offset(), query.limit())); + } + } diff --git a/sonar-core/src/main/java/org/sonar/core/persistence/DaoUtils.java b/sonar-core/src/main/java/org/sonar/core/persistence/DaoUtils.java index 8cc38c58d83..5c2ddfb0ac9 100644 --- a/sonar-core/src/main/java/org/sonar/core/persistence/DaoUtils.java +++ b/sonar-core/src/main/java/org/sonar/core/persistence/DaoUtils.java @@ -37,6 +37,7 @@ import org.sonar.core.rule.RuleDao; import org.sonar.core.source.jdbc.SnapshotDataDao; import org.sonar.core.template.LoadedTemplateDao; import org.sonar.core.user.AuthorDao; +import org.sonar.core.user.AuthorizationDao; import org.sonar.core.user.UserDao; import java.util.List; @@ -51,6 +52,7 @@ public final class DaoUtils { return ImmutableList.of( ActiveDashboardDao.class, AuthorDao.class, + AuthorizationDao.class, DashboardDao.class, DuplicationDao.class, GraphDao.class, diff --git a/sonar-core/src/main/java/org/sonar/core/persistence/MyBatis.java b/sonar-core/src/main/java/org/sonar/core/persistence/MyBatis.java index b337376e9ec..05706a7303d 100644 --- a/sonar-core/src/main/java/org/sonar/core/persistence/MyBatis.java +++ b/sonar-core/src/main/java/org/sonar/core/persistence/MyBatis.java @@ -134,6 +134,7 @@ public class MyBatis implements BatchComponent, ServerComponent { }; loadMappers(conf, mappers); loadMapper(conf, "org.sonar.core.issue.IssueMapper"); + loadMapper(conf, "org.sonar.core.user.AuthorizationMapper"); configureLogback(mappers); sessionFactory = new SqlSessionFactoryBuilder().build(conf); diff --git a/sonar-core/src/main/java/org/sonar/core/user/AuthorizationDao.java b/sonar-core/src/main/java/org/sonar/core/user/AuthorizationDao.java new file mode 100644 index 00000000000..9c1cbdda59d --- /dev/null +++ b/sonar-core/src/main/java/org/sonar/core/user/AuthorizationDao.java @@ -0,0 +1,68 @@ +/* + * Sonar, open source software quality management tool. + * Copyright (C) 2008-2012 SonarSource + * mailto:contact AT sonarsource DOT com + * + * Sonar 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. + * + * Sonar 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 Sonar; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02 + */ +package org.sonar.core.user; + +import com.google.common.collect.ImmutableMap; +import com.google.common.collect.Sets; +import org.apache.ibatis.session.SqlSession; +import org.sonar.api.ServerComponent; +import org.sonar.core.persistence.MyBatis; + +import javax.annotation.Nullable; + +import java.util.Collections; +import java.util.Map; +import java.util.Set; + +public class AuthorizationDao implements ServerComponent { + + private final MyBatis mybatis; + + public AuthorizationDao(MyBatis mybatis) { + this.mybatis = mybatis; + } + + public Set keepAuthorizedComponentIds(Set componentIds, @Nullable Integer userId, String role) { + SqlSession session = mybatis.openSession(); + try { + return keepAuthorizedComponentIds(componentIds, userId, role, session); + + } finally { + MyBatis.closeQuietly(session); + } + } + + public Set keepAuthorizedComponentIds(Set componentIds, @Nullable Integer userId, String role, SqlSession session) { + if (componentIds.isEmpty()) { + return Collections.emptySet(); + } + String sql; + Map params; + if (userId == null) { + sql = "keepAuthorizedComponentIdsForAnonymous"; + params = ImmutableMap.of("role", role, "componentIds", componentIds); + } else { + sql = "keepAuthorizedComponentIdsForUser"; + params = ImmutableMap.of("userId", userId, "role", role, "componentIds", componentIds); + } + + return Sets.newHashSet(session.selectList(sql, params)); + } +} diff --git a/sonar-core/src/main/resources/org/sonar/core/issue/IssueMapper.xml b/sonar-core/src/main/resources/org/sonar/core/issue/IssueMapper.xml index c3b04c76b8a..e916edbc1a7 100644 --- a/sonar-core/src/main/resources/org/sonar/core/issue/IssueMapper.xml +++ b/sonar-core/src/main/resources/org/sonar/core/issue/IssueMapper.xml @@ -28,7 +28,7 @@ i.closed_at as closedAt - + INSERT INTO issues (uuid, resource_id, rule_id, severity, manual_severity, manual_issue, title, message, line, cost, status, resolution, checksum, user_login, assignee_login, person_id, data, created_at, updated_at, closed_at) VALUES (#{uuid}, #{resourceId}, #{ruleId}, #{severity}, #{manualSeverity}, #{manualIssue}, #{title}, #{message}, #{line}, #{cost}, #{status}, @@ -36,8 +36,8 @@ - - + + select issues_seq.NEXTVAL from DUAL INSERT INTO issues (id, uuid, resource_id, rule_id, severity, manual_severity, manual_issue, title, message, line, cost, status, @@ -71,19 +71,27 @@ + + + from issues i , projects p, snapshots root, snapshots s @@ -140,7 +148,7 @@ - + diff --git a/sonar-core/src/test/java/org/sonar/core/issue/DefaultIssueFinderTest.java b/sonar-core/src/test/java/org/sonar/core/issue/DefaultIssueFinderTest.java index c1a2447894d..a5e5be2a719 100644 --- a/sonar-core/src/test/java/org/sonar/core/issue/DefaultIssueFinderTest.java +++ b/sonar-core/src/test/java/org/sonar/core/issue/DefaultIssueFinderTest.java @@ -19,53 +19,67 @@ */ package org.sonar.core.issue; +import org.apache.ibatis.session.SqlSession; import org.junit.Before; import org.junit.Test; +import org.mockito.invocation.InvocationOnMock; +import org.mockito.stubbing.Answer; import org.sonar.api.issue.Issue; import org.sonar.api.issue.IssueFinder; import org.sonar.api.issue.IssueQuery; import org.sonar.api.rules.Rule; import org.sonar.api.rules.RuleFinder; +import org.sonar.core.persistence.MyBatis; import org.sonar.core.resource.ResourceDao; import org.sonar.core.resource.ResourceDto; +import org.sonar.core.user.AuthorizationDao; import java.util.List; import static com.google.common.collect.Lists.newArrayList; import static org.fest.assertions.Assertions.assertThat; +import static org.mockito.Matchers.any; import static org.mockito.Matchers.anyInt; +import static org.mockito.Matchers.anySet; +import static org.mockito.Matchers.anyString; +import static org.mockito.Matchers.eq; import static org.mockito.Mockito.mock; import static org.mockito.Mockito.when; public class DefaultIssueFinderTest { - private DefaultIssueFinder finder; - private IssueDao issueDao; - private ResourceDao resourceDao; - private RuleFinder ruleFinder; + MyBatis mybatis; + DefaultIssueFinder finder; + IssueDao issueDao; + ResourceDao resourceDao; + RuleFinder ruleFinder; + AuthorizationDao authorizationDao; @Before public void before() { + mybatis = mock(MyBatis.class); issueDao = mock(IssueDao.class); resourceDao = mock(ResourceDao.class); ruleFinder = mock(RuleFinder.class); - finder = new DefaultIssueFinder(issueDao, resourceDao, ruleFinder); + authorizationDao = mock(AuthorizationDao.class); + finder = new DefaultIssueFinder(mybatis, issueDao, resourceDao, authorizationDao, ruleFinder); } @Test public void should_find_issues() { + grantAccessRights(); IssueQuery issueQuery = mock(IssueQuery.class); IssueDto issue1 = new IssueDto().setId(1L).setRuleId(50).setResourceId(123); IssueDto issue2 = new IssueDto().setId(2L).setRuleId(50).setResourceId(123); List dtoList = newArrayList(issue1, issue2); - when(issueDao.select(issueQuery)).thenReturn(dtoList); + when(issueDao.select(eq(issueQuery), any(SqlSession.class))).thenReturn(dtoList); Rule rule = Rule.create("repo", "key"); rule.setId(50); when(ruleFinder.findById(anyInt())).thenReturn(rule); when(resourceDao.getResource(anyInt())).thenReturn(new ResourceDto().setKey("componentKey").setId(123L)); - IssueFinder.Results results = finder.find(issueQuery); + IssueFinder.Results results = finder.find(issueQuery, null); assertThat(results.issues()).hasSize(2); Issue issue = results.issues().iterator().next(); assertThat(issue.componentKey()).isEqualTo("componentKey"); @@ -86,4 +100,14 @@ public class DefaultIssueFinderTest { assertThat(issue.ruleKey()).isEqualTo("key"); assertThat(issue.ruleRepositoryKey()).isEqualTo("repo"); } + + private void grantAccessRights() { + when(authorizationDao.keepAuthorizedComponentIds(anySet(), anyInt(), anyString(), any(SqlSession.class))) + .thenAnswer(new Answer() { + @Override + public Object answer(InvocationOnMock invocationOnMock) throws Throwable { + return invocationOnMock.getArguments()[0]; + } + }); + } } diff --git a/sonar-plugin-api/src/main/java/org/sonar/api/issue/Issuable.java b/sonar-plugin-api/src/main/java/org/sonar/api/issue/Issuable.java index ecc8dc4cfeb..0daa5a692ee 100644 --- a/sonar-plugin-api/src/main/java/org/sonar/api/issue/Issuable.java +++ b/sonar-plugin-api/src/main/java/org/sonar/api/issue/Issuable.java @@ -20,7 +20,6 @@ package org.sonar.api.issue; -import org.sonar.api.component.Component; import org.sonar.api.component.Perspective; import java.util.Collection; @@ -51,8 +50,4 @@ public interface Issuable extends Perspective { IssueBuilder newIssue(); Collection issues(); - - @Override - Component component(); - } diff --git a/sonar-plugin-api/src/main/java/org/sonar/api/issue/IssueFinder.java b/sonar-plugin-api/src/main/java/org/sonar/api/issue/IssueFinder.java index a71f62a8c84..e158c6a1d24 100644 --- a/sonar-plugin-api/src/main/java/org/sonar/api/issue/IssueFinder.java +++ b/sonar-plugin-api/src/main/java/org/sonar/api/issue/IssueFinder.java @@ -24,6 +24,8 @@ import org.sonar.api.ServerComponent; import org.sonar.api.component.Component; import org.sonar.api.rules.Rule; +import javax.annotation.Nullable; + import java.util.Collection; import java.util.List; @@ -36,7 +38,7 @@ public interface IssueFinder extends ServerComponent { List issues(); } - Results find(IssueQuery issueQuery); + Results find(IssueQuery issueQuery, @Nullable Integer currentUserId); Issue findByKey(String key); diff --git a/sonar-plugin-api/src/main/java/org/sonar/api/issue/IssueQuery.java b/sonar-plugin-api/src/main/java/org/sonar/api/issue/IssueQuery.java index e34b867a1c4..c227aed75ba 100644 --- a/sonar-plugin-api/src/main/java/org/sonar/api/issue/IssueQuery.java +++ b/sonar-plugin-api/src/main/java/org/sonar/api/issue/IssueQuery.java @@ -26,6 +26,8 @@ import org.apache.commons.lang.builder.ReflectionToStringBuilder; import java.util.List; /** + * TODO add javadoc + * * @since 3.6 */ public class IssueQuery { diff --git a/sonar-plugin-api/src/main/java/org/sonar/api/issue/JRubyIssues.java b/sonar-plugin-api/src/main/java/org/sonar/api/issue/JRubyIssues.java index 3cb966e800a..af3a0a0bffc 100644 --- a/sonar-plugin-api/src/main/java/org/sonar/api/issue/JRubyIssues.java +++ b/sonar-plugin-api/src/main/java/org/sonar/api/issue/JRubyIssues.java @@ -37,7 +37,7 @@ public interface JRubyIssues extends ServerComponent { * Search for issues. * *

- * Ruby: Api.issues.find(hash) + * Ruby: Api.issues.find(hash_of_parameters, current_user.id) *

* *

Parameters

@@ -45,6 +45,6 @@ public interface JRubyIssues extends ServerComponent { * TODO document parameters * */ - IssueFinder.Results find(Map parameters); + IssueFinder.Results find(Map parameters, Integer currentUserId); } diff --git a/sonar-server/src/main/java/org/sonar/server/ui/DefaultJRubyIssues.java b/sonar-server/src/main/java/org/sonar/server/issue/DefaultJRubyIssues.java similarity index 92% rename from sonar-server/src/main/java/org/sonar/server/ui/DefaultJRubyIssues.java rename to sonar-server/src/main/java/org/sonar/server/issue/DefaultJRubyIssues.java index 2c5f3718be5..a441ee6a3c8 100644 --- a/sonar-server/src/main/java/org/sonar/server/ui/DefaultJRubyIssues.java +++ b/sonar-server/src/main/java/org/sonar/server/issue/DefaultJRubyIssues.java @@ -17,13 +17,14 @@ * License along with Sonar; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02 */ -package org.sonar.server.ui; +package org.sonar.server.issue; import com.google.common.base.Splitter; import com.google.common.collect.Lists; import org.sonar.api.issue.IssueFinder; import org.sonar.api.issue.IssueQuery; import org.sonar.api.issue.JRubyIssues; +import org.sonar.server.ui.JRubyFacades; import java.util.List; import java.util.Map; @@ -42,8 +43,8 @@ public class DefaultJRubyIssues implements JRubyIssues { JRubyFacades.setIssues(this); } - public IssueFinder.Results find(Map params) { - return finder.find(newQuery(params)); + public IssueFinder.Results find(Map params, Integer currentUserId) { + return finder.find(newQuery(params), currentUserId); } IssueQuery newQuery(Map props) { diff --git a/sonar-server/src/main/java/org/sonar/server/platform/Platform.java b/sonar-server/src/main/java/org/sonar/server/platform/Platform.java index 2603f435907..8928ec685a8 100644 --- a/sonar-server/src/main/java/org/sonar/server/platform/Platform.java +++ b/sonar-server/src/main/java/org/sonar/server/platform/Platform.java @@ -75,6 +75,7 @@ import org.sonar.server.charts.ChartFactory; import org.sonar.server.configuration.Backup; import org.sonar.server.configuration.ProfilesManager; import org.sonar.server.database.EmbeddedDatabaseFactory; +import org.sonar.server.issue.DefaultJRubyIssues; import org.sonar.server.macro.MacroInterpreter; import org.sonar.server.notifications.NotificationCenter; import org.sonar.server.notifications.NotificationService; diff --git a/sonar-server/src/main/java/org/sonar/server/ui/JRubyFacades.java b/sonar-server/src/main/java/org/sonar/server/ui/JRubyFacades.java index 71add311036..23e6efbb65f 100644 --- a/sonar-server/src/main/java/org/sonar/server/ui/JRubyFacades.java +++ b/sonar-server/src/main/java/org/sonar/server/ui/JRubyFacades.java @@ -31,7 +31,7 @@ public class JRubyFacades implements ServerComponent { private static JRubyIssues issues = null; - static void setIssues(JRubyIssues i) { + public static void setIssues(JRubyIssues i) { JRubyFacades.issues = i; } diff --git a/sonar-server/src/main/webapp/WEB-INF/app/controllers/api/issues_controller.rb b/sonar-server/src/main/webapp/WEB-INF/app/controllers/api/issues_controller.rb index 408ba110f37..ebeda15122e 100644 --- a/sonar-server/src/main/webapp/WEB-INF/app/controllers/api/issues_controller.rb +++ b/sonar-server/src/main/webapp/WEB-INF/app/controllers/api/issues_controller.rb @@ -22,16 +22,12 @@ class Api::IssuesController < Api::ApiController # GET /api/issues/search? def search - results = find_issues(params) + results = Api.issues.find(params, current_user.id) render :json => jsonp(issues_to_json(results.issues)) end private - def find_issues(map) - Api.issues.find(map) - end - def issues_to_json(issues) json = [] issues.each do |issue| diff --git a/sonar-server/src/main/webapp/WEB-INF/app/controllers/issues_controller.rb b/sonar-server/src/main/webapp/WEB-INF/app/controllers/issues_controller.rb index 3b87bffa64f..27c0bfa50fb 100644 --- a/sonar-server/src/main/webapp/WEB-INF/app/controllers/issues_controller.rb +++ b/sonar-server/src/main/webapp/WEB-INF/app/controllers/issues_controller.rb @@ -24,11 +24,10 @@ class IssuesController < ApplicationController @issues = find_issues({}).issues end - protected def find_issues(map) - Api.issues.find(map) + Api.issues.find(map, current_user.id) end end \ No newline at end of file diff --git a/sonar-server/src/test/java/org/sonar/server/ui/DefaultJRubyIssuesTest.java b/sonar-server/src/test/java/org/sonar/server/issue/DefaultJRubyIssuesTest.java similarity index 94% rename from sonar-server/src/test/java/org/sonar/server/ui/DefaultJRubyIssuesTest.java rename to sonar-server/src/test/java/org/sonar/server/issue/DefaultJRubyIssuesTest.java index 0febd52cace..ecfcbe7dfcd 100644 --- a/sonar-server/src/test/java/org/sonar/server/ui/DefaultJRubyIssuesTest.java +++ b/sonar-server/src/test/java/org/sonar/server/issue/DefaultJRubyIssuesTest.java @@ -17,7 +17,7 @@ * License along with Sonar; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02 */ -package org.sonar.server.ui; +package org.sonar.server.issue; import com.google.common.collect.ImmutableMap; import com.google.common.collect.Lists; @@ -25,6 +25,7 @@ import org.junit.Test; import org.mockito.ArgumentMatcher; import org.sonar.api.issue.IssueFinder; import org.sonar.api.issue.IssueQuery; +import org.sonar.server.issue.DefaultJRubyIssues; import java.util.Map; @@ -32,6 +33,7 @@ import static com.google.common.collect.Lists.newArrayList; import static com.google.common.collect.Maps.newHashMap; import static org.fest.assertions.Assertions.assertThat; import static org.mockito.Matchers.argThat; +import static org.mockito.Matchers.eq; import static org.mockito.Mockito.mock; import static org.mockito.Mockito.verify; import static org.mockito.Mockito.verifyZeroInteractions; @@ -43,13 +45,13 @@ public class DefaultJRubyIssuesTest { @Test public void test_find() throws Exception { - facade.find(ImmutableMap.of("keys", Lists.newArrayList("ABCDE"))); + facade.find(ImmutableMap.of("keys", Lists.newArrayList("ABCDE")), 123); verify(finder).find(argThat(new ArgumentMatcher() { @Override public boolean matches(Object o) { return ((IssueQuery) o).keys().contains("ABCDE"); } - })); + }), eq(123)); } @Test diff --git a/sonar-server/src/test/java/org/sonar/server/ui/JRubyFacadesTest.java b/sonar-server/src/test/java/org/sonar/server/ui/JRubyFacadesTest.java index ec0d68f7d9f..d02ffc79f5c 100644 --- a/sonar-server/src/test/java/org/sonar/server/ui/JRubyFacadesTest.java +++ b/sonar-server/src/test/java/org/sonar/server/ui/JRubyFacadesTest.java @@ -20,6 +20,7 @@ package org.sonar.server.ui; import org.junit.Test; +import org.sonar.server.issue.DefaultJRubyIssues; import static org.fest.assertions.Assertions.assertThat; import static org.mockito.Mockito.mock; -- 2.39.5