@@ -30,6 +30,8 @@ public class CeWsModule extends Module { | |||
ActivityStatusAction.class, | |||
CancelAction.class, | |||
CancelAllAction.class, | |||
ComponentAction.class, | |||
InfoAction.class, | |||
IsQueueEmptyWs.class, | |||
ComponentAction.class, | |||
SubmitAction.class, |
@@ -0,0 +1,76 @@ | |||
/* | |||
* SonarQube | |||
* Copyright (C) 2009-2018 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.server.ce.ws; | |||
import java.util.Optional; | |||
import org.sonar.api.server.ws.Request; | |||
import org.sonar.api.server.ws.Response; | |||
import org.sonar.api.server.ws.WebService; | |||
import org.sonar.ce.queue.CeQueue; | |||
import org.sonar.server.user.AbstractUserSession; | |||
import org.sonar.server.user.SystemPasscode; | |||
import org.sonar.server.user.SystemPasscodeImpl; | |||
import org.sonar.server.user.UserSession; | |||
import org.sonar.server.ws.WsUtils; | |||
import org.sonarqube.ws.Ce; | |||
public class InfoAction implements CeWsAction { | |||
private final UserSession userSession; | |||
private final SystemPasscode systemPasscode; | |||
private final CeQueue ceQueue; | |||
public InfoAction(UserSession userSession, SystemPasscode systemPasscode, CeQueue ceQueue) { | |||
this.userSession = userSession; | |||
this.systemPasscode = systemPasscode; | |||
this.ceQueue = ceQueue; | |||
} | |||
@Override | |||
public void define(WebService.NewController controller) { | |||
controller.createAction("info") | |||
.setDescription("Gets information about Compute Engine. Requires the system administration permission or " + | |||
"system passcode (see " + SystemPasscodeImpl.PASSCODE_CONF_PROPERTY + " in sonar.properties).") | |||
.setSince("7.2") | |||
.setHandler(this) | |||
.setResponseExample(getClass().getResource("info-example.json")); | |||
} | |||
@Override | |||
public void handle(Request request, Response response) throws Exception { | |||
if (!userSession.isSystemAdministrator() && !systemPasscode.isValid(request)) { | |||
throw AbstractUserSession.insufficientPrivilegesException(); | |||
} | |||
Ce.InfoWsResponse.Builder builder = Ce.InfoWsResponse.newBuilder(); | |||
Optional<CeQueue.WorkersPause> pause = ceQueue.getWorkersPause(); | |||
builder.setWorkersPaused(isPaused(pause)); | |||
builder.setWorkersPauseRequested(isPauseRequested(pause)); | |||
WsUtils.writeProtobuf(builder.build(), request, response); | |||
} | |||
private static boolean isPaused(Optional<CeQueue.WorkersPause> pause) { | |||
return pause.isPresent() && pause.get() == CeQueue.WorkersPause.PAUSED; | |||
} | |||
private static boolean isPauseRequested(Optional<CeQueue.WorkersPause> pause) { | |||
return pause.isPresent() && pause.get() == CeQueue.WorkersPause.PAUSING; | |||
} | |||
} |
@@ -0,0 +1,4 @@ | |||
{ | |||
"workersPaused": false, | |||
"workersPauseRequested": true | |||
} |
@@ -31,6 +31,6 @@ public class CeWsModuleTest { | |||
public void verify_count_of_added_components() { | |||
ComponentContainer container = new ComponentContainer(); | |||
new CeWsModule().configure(container); | |||
assertThat(container.size()).isEqualTo(12 + COMPONENTS_IN_EMPTY_COMPONENT_CONTAINER); | |||
assertThat(container.size()).isEqualTo(13 + COMPONENTS_IN_EMPTY_COMPONENT_CONTAINER); | |||
} | |||
} |
@@ -0,0 +1,129 @@ | |||
/* | |||
* SonarQube | |||
* Copyright (C) 2009-2018 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.server.ce.ws; | |||
import java.util.Optional; | |||
import org.junit.Rule; | |||
import org.junit.Test; | |||
import org.junit.rules.ExpectedException; | |||
import org.sonar.api.server.ws.WebService; | |||
import org.sonar.ce.queue.CeQueue; | |||
import org.sonar.server.exceptions.ForbiddenException; | |||
import org.sonar.server.tester.UserSessionRule; | |||
import org.sonar.server.user.SystemPasscode; | |||
import org.sonar.server.ws.WsActionTester; | |||
import org.sonarqube.ws.Ce; | |||
import static org.assertj.core.api.Assertions.assertThat; | |||
import static org.mockito.ArgumentMatchers.any; | |||
import static org.mockito.Mockito.mock; | |||
import static org.mockito.Mockito.when; | |||
public class InfoActionTest { | |||
@Rule | |||
public ExpectedException expectedException = ExpectedException.none(); | |||
@Rule | |||
public UserSessionRule userSession = UserSessionRule.standalone(); | |||
private SystemPasscode passcode = mock(SystemPasscode.class); | |||
private CeQueue ceQueue = mock(CeQueue.class); | |||
private InfoAction underTest = new InfoAction(userSession, passcode, ceQueue); | |||
private WsActionTester ws = new WsActionTester(underTest); | |||
@Test | |||
public void test_definition() { | |||
WebService.Action def = ws.getDef(); | |||
assertThat(def.key()).isEqualTo("info"); | |||
assertThat(def.isInternal()).isFalse(); | |||
assertThat(def.isPost()).isFalse(); | |||
assertThat(def.params()).isEmpty(); | |||
} | |||
@Test | |||
public void test_example_of_response() { | |||
userSession.logIn().setSystemAdministrator(); | |||
when(ceQueue.getWorkersPause()).thenReturn(Optional.of(CeQueue.WorkersPause.PAUSING)); | |||
ws.newRequest().execute().assertJson(ws.getDef().responseExampleAsString()); | |||
} | |||
@Test | |||
public void test_workers_in_pausing_state() { | |||
userSession.logIn().setSystemAdministrator(); | |||
when(ceQueue.getWorkersPause()).thenReturn(Optional.of(CeQueue.WorkersPause.PAUSING)); | |||
Ce.InfoWsResponse response = ws.newRequest().executeProtobuf(Ce.InfoWsResponse.class); | |||
assertThat(response.getWorkersPaused()).isFalse(); | |||
assertThat(response.getWorkersPauseRequested()).isTrue(); | |||
} | |||
@Test | |||
public void test_workers_in_paused_state() { | |||
userSession.logIn().setSystemAdministrator(); | |||
when(ceQueue.getWorkersPause()).thenReturn(Optional.of(CeQueue.WorkersPause.PAUSED)); | |||
Ce.InfoWsResponse response = ws.newRequest().executeProtobuf(Ce.InfoWsResponse.class); | |||
assertThat(response.getWorkersPaused()).isTrue(); | |||
assertThat(response.getWorkersPauseRequested()).isFalse(); | |||
} | |||
@Test | |||
public void test_workers_in_resumed_state() { | |||
userSession.logIn().setSystemAdministrator(); | |||
when(ceQueue.getWorkersPause()).thenReturn(Optional.empty()); | |||
Ce.InfoWsResponse response = ws.newRequest().executeProtobuf(Ce.InfoWsResponse.class); | |||
assertThat(response.getWorkersPaused()).isFalse(); | |||
assertThat(response.getWorkersPauseRequested()).isFalse(); | |||
} | |||
@Test | |||
public void throw_ForbiddenException_if_not_system_administrator() { | |||
userSession.logIn().setNonSystemAdministrator(); | |||
expectedException.expect(ForbiddenException.class); | |||
expectedException.expectMessage("Insufficient privileges"); | |||
ws.newRequest().execute(); | |||
} | |||
@Test | |||
public void throw_ForbiddenException_if_invalid_passcode() { | |||
userSession.anonymous(); | |||
when(passcode.isValid(any())).thenReturn(false); | |||
expectedException.expect(ForbiddenException.class); | |||
expectedException.expectMessage("Insufficient privileges"); | |||
ws.newRequest().execute(); | |||
} | |||
@Test | |||
public void authenticate_with_passcode() { | |||
userSession.anonymous(); | |||
when(passcode.isValid(any())).thenReturn(true); | |||
when(ceQueue.getWorkersPause()).thenReturn(Optional.empty()); | |||
Ce.InfoWsResponse response = ws.newRequest().executeProtobuf(Ce.InfoWsResponse.class); | |||
assertThat(response.getWorkersPaused()).isFalse(); | |||
assertThat(response.getWorkersPauseRequested()).isFalse(); | |||
} | |||
} |
@@ -29,6 +29,7 @@ import org.sonarqube.ws.client.WsConnector; | |||
import org.sonarqube.ws.Ce.ActivityResponse; | |||
import org.sonarqube.ws.Ce.ActivityStatusWsResponse; | |||
import org.sonarqube.ws.Ce.ComponentResponse; | |||
import org.sonarqube.ws.Ce.InfoWsResponse; | |||
import org.sonarqube.ws.Ce.SubmitResponse; | |||
import org.sonarqube.ws.Ce.TaskResponse; | |||
import org.sonarqube.ws.Ce.TaskTypesWsResponse; | |||
@@ -126,6 +127,17 @@ public class CeService extends BaseService { | |||
ComponentResponse.parser()); | |||
} | |||
/** | |||
* This is a GET request. | |||
* @see <a href="https://next.sonarqube.com/sonarqube/web_api/api/ce/info">Further information about this action online (including a response example)</a> | |||
* @since 7.2 | |||
*/ | |||
public InfoWsResponse info() { | |||
return call( | |||
new GetRequest(path("info")), | |||
InfoWsResponse.parser()); | |||
} | |||
/** | |||
* | |||
* This is part of the internal API. |
@@ -57,6 +57,12 @@ message ComponentResponse { | |||
optional Task current = 2; | |||
} | |||
// GET api/ce/info | |||
message InfoWsResponse { | |||
optional bool workersPaused = 1; | |||
optional bool workersPauseRequested = 2; | |||
} | |||
// GET api/ce/task_types | |||
message TaskTypesWsResponse { | |||
repeated string taskTypes = 1; |