/* * SonarQube * Copyright (C) 2009-2017 SonarSource SA * mailto:info AT sonarsource DOT com * * This program is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation; either * version 3 of the License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public License * along with this program; if not, write to the Free Software Foundation, * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ package org.sonar.scanner.rule; import com.google.common.collect.ImmutableSortedMap; import java.io.ByteArrayInputStream; import java.io.IOException; import java.io.InputStream; import java.util.Collection; import java.util.stream.IntStream; import org.junit.Before; import org.junit.Test; import org.sonar.api.rule.RuleKey; import org.sonar.api.rule.Severity; import org.sonar.scanner.WsTestUtil; import org.sonar.scanner.bootstrap.ScannerWsClient; import org.sonarqube.ws.Rules; import org.sonarqube.ws.Rules.Active; import org.sonarqube.ws.Rules.ActiveList; import org.sonarqube.ws.Rules.Actives; import org.sonarqube.ws.Rules.Rule; import org.sonarqube.ws.Rules.SearchResponse; import org.sonarqube.ws.Rules.SearchResponse.Builder; import static org.assertj.core.api.Assertions.assertThat; import static org.mockito.Mockito.mock; import static org.mockito.Mockito.verifyNoMoreInteractions; public class DefaultActiveRulesLoaderTest { private static final int PAGE_SIZE_1 = 150; private static final int PAGE_SIZE_2 = 76; private static final RuleKey EXAMPLE_KEY = RuleKey.of("squid", "S108"); private static final String FORMAT_KEY = "format"; private static final String FORMAT_VALUE = "^[a-z][a-zA-Z0-9]*$"; private static final String SEVERITY_VALUE = Severity.MINOR; private DefaultActiveRulesLoader loader; private ScannerWsClient wsClient; @Before public void setUp() { wsClient = mock(ScannerWsClient.class); loader = new DefaultActiveRulesLoader(wsClient); } @Test public void feed_real_response_encode_qp() throws IOException { int total = PAGE_SIZE_1 + PAGE_SIZE_2; WsTestUtil.mockStream(wsClient, urlOfPage(1), responseOfSize(PAGE_SIZE_1, total)); WsTestUtil.mockStream(wsClient, urlOfPage(2), responseOfSize(PAGE_SIZE_2, total)); Collection<LoadedActiveRule> activeRules = loader.load("c+-test_c+-values-17445"); assertThat(activeRules).hasSize(total); assertThat(activeRules) .filteredOn(r -> r.getRuleKey().equals(EXAMPLE_KEY)) .extracting(LoadedActiveRule::getParams) .extracting(p -> p.get(FORMAT_KEY)) .containsExactly(FORMAT_VALUE); assertThat(activeRules) .filteredOn(r -> r.getRuleKey().equals(EXAMPLE_KEY)) .extracting(LoadedActiveRule::getSeverity) .containsExactly(SEVERITY_VALUE); WsTestUtil.verifyCall(wsClient, urlOfPage(1)); WsTestUtil.verifyCall(wsClient, urlOfPage(2)); verifyNoMoreInteractions(wsClient); } private String urlOfPage(int page) { return "/api/rules/search.protobuf?f=repo,name,severity,lang,internalKey,templateKey,params,actives,createdAt&activation=true&qprofile=c%2B-test_c%2B-values-17445&p=" + page + "&ps=500"; } /** * Generates an imaginary protobuf result. * * @param numberOfRules the number of rules, that the response should contain * @param total the number of results on all pages * @return the binary stream */ private InputStream responseOfSize(int numberOfRules, int total) { Builder rules = SearchResponse.newBuilder(); Actives.Builder actives = Actives.newBuilder(); IntStream.rangeClosed(1, numberOfRules) .mapToObj(i -> RuleKey.of("squid", "S" + i)) .forEach(key -> { Rule.Builder ruleBuilder = Rule.newBuilder(); ruleBuilder.setKey(key.toString()); rules.addRules(ruleBuilder); Active.Builder activeBuilder = Active.newBuilder(); activeBuilder.setCreatedAt("2014-05-27T15:50:45+0100"); if (EXAMPLE_KEY.equals(key)) { activeBuilder.addParams(Rules.Active.Param.newBuilder().setKey(FORMAT_KEY).setValue(FORMAT_VALUE)); activeBuilder.setSeverity(SEVERITY_VALUE); } ActiveList activeList = Rules.ActiveList.newBuilder().addActiveList(activeBuilder).build(); actives.putAllActives(ImmutableSortedMap.of(key.toString(), activeList)); }); rules.setActives(actives); rules.setPs(numberOfRules); rules.setTotal(total); return new ByteArrayInputStream(rules.build().toByteArray()); } }