]> source.dussan.org Git - sonarqube.git/commitdiff
SONAR-21204 Add info message to /api/ce/activity
authorAurelien Poscia <aurelien.poscia@sonarsource.com>
Thu, 7 Dec 2023 09:19:52 +0000 (10:19 +0100)
committersonartech <sonartech@sonarsource.com>
Fri, 22 Dec 2023 20:03:02 +0000 (20:03 +0000)
server/sonar-webserver-webapi/src/it/java/org/sonar/server/ce/ws/ActivityActionIT.java
server/sonar-webserver-webapi/src/main/java/org/sonar/server/ce/ws/ActivityAction.java
server/sonar-webserver-webapi/src/main/java/org/sonar/server/ce/ws/TaskFormatter.java
server/sonar-webserver-webapi/src/main/resources/org/sonar/server/ce/ws/activity-example.json
server/sonar-webserver-webapi/src/test/java/org/sonar/server/ce/ws/TaskFormatterTest.java
sonar-ws/src/main/protobuf/ws-ce.proto

index faeb14c405b08a288f1e974b3d3a940ab1ae79ea..411dc6a45014e5682e9eb468c8fda119956f25c0 100644 (file)
@@ -250,9 +250,9 @@ public class ActivityActionIT {
     insertActivity("T1", project1, SUCCESS);
     insertActivity("T2", project2, FAILED);
     insertQueue("T3", project1, IN_PROGRESS);
-    List<String> messagesT1 = insertMessages("T1", 2);
-    List<String> messagesT2 = insertMessages("T2", 1);
-    insertMessages("T3", 5);
+    List<String> messagesT1 = insertMessages(MessageType.GENERIC,"T1", 2);
+    List<String> messagesT2 = insertMessages(MessageType.GENERIC,"T2", 1);
+    insertMessages(MessageType.GENERIC,"T3", 5);
 
     ActivityResponse activityResponse = call(ws.newRequest()
       .setParam(Param.PAGE_SIZE, Integer.toString(10))
@@ -262,13 +262,33 @@ public class ActivityActionIT {
       .containsOnly(tuple("T1", messagesT1.size(), messagesT1), tuple("T2", messagesT2.size(), messagesT2), tuple("T3", 0, emptyList()));
   }
 
-  private List<String> insertMessages(String taskUuid, int messageCount) {
+  @Test
+  public void return_infoMessages() {
+    logInAsSystemAdministrator();
+    ProjectData project1 = db.components().insertPrivateProject();
+    ProjectData project2 = db.components().insertPrivateProject();
+    insertActivity("T1", project1, SUCCESS);
+    insertActivity("T2", project2, FAILED);
+    insertQueue("T3", project1, IN_PROGRESS);
+    List<String> messagesT1 = insertMessages(MessageType.INFO,"T1", 2);
+    List<String> messagesT2 = insertMessages(MessageType.INFO,"T2", 1);
+    insertMessages(MessageType.INFO,"T3", 5);
+
+    ActivityResponse activityResponse = call(ws.newRequest()
+      .setParam(Param.PAGE_SIZE, Integer.toString(10))
+      .setParam(PARAM_STATUS, "SUCCESS,FAILED,CANCELED,IN_PROGRESS,PENDING"));
+    assertThat(activityResponse.getTasksList())
+      .extracting(Task::getId, Task::getInfoMessagesList)
+      .containsOnly(tuple("T1",  messagesT1), tuple("T2",  messagesT2), tuple("T3",  emptyList()));
+  }
+
+  private List<String> insertMessages(MessageType messageType, String taskUuid, int messageCount) {
     List<CeTaskMessageDto> ceTaskMessageDtos = IntStream.range(0, messageCount)
       .mapToObj(i -> new CeTaskMessageDto()
         .setUuid("uuid_" + taskUuid + "_" + i)
         .setTaskUuid(taskUuid)
         .setMessage("m_" + taskUuid + "_" + i)
-        .setType(MessageType.GENERIC)
+        .setType(messageType)
         .setCreatedAt(taskUuid.hashCode() + i))
       .toList();
 
index e9b72c81f61cc11a9ac53353fbf80276ba9a8b32..1de49c9da31c73b1952a37ef7cc23b98cd8f3602 100644 (file)
@@ -113,7 +113,8 @@ public class ActivityAction implements CeWsAction {
         new Change("8.8", "field \"logs\" is dropped"),
         new Change("10.0", "Remove deprecated field 'componentId'"),
         new Change("10.1", String.format("The use of module keys in parameter '%s' is removed", PARAM_COMPONENT)),
-        new Change("10.1", "Warnings field will be now be filled (it was always empty in the past).")
+        new Change("10.1", "Warnings field will be now be filled (it was always empty in the past)."),
+        new Change("10.4", "field \"infoMessages\" added to response")
       )
       .setSince("5.2");
 
index 673cbe2f36357175fd1b5ef9920533dca0cffc98..10523235792543bdd31244d68cdddf0cdadae12f 100644 (file)
@@ -21,6 +21,7 @@ package org.sonar.server.ce.ws;
 
 import com.google.common.collect.Multimap;
 import java.util.Collection;
+import java.util.Comparator;
 import java.util.Date;
 import java.util.List;
 import java.util.Map;
@@ -41,6 +42,7 @@ import org.sonar.db.ce.CeQueueDto;
 import org.sonar.db.ce.CeTaskCharacteristicDto;
 import org.sonar.db.ce.CeTaskMessageDto;
 import org.sonar.db.component.ComponentDto;
+import org.sonar.db.dismissmessage.MessageType;
 import org.sonar.db.user.UserDto;
 import org.sonarqube.ws.Ce;
 import org.sonarqube.ws.Common;
@@ -129,6 +131,9 @@ public class TaskFormatter {
     builder.setWarningCount(warnings.size());
     warnings.forEach(builder::addWarnings);
 
+    List<String> infoMessages = extractInfoMessages(activityDto);
+    builder.addAllInfoMessages(infoMessages);
+
     return builder.build();
   }
 
@@ -168,6 +173,14 @@ public class TaskFormatter {
       .toList();
   }
 
+  private static List<String> extractInfoMessages(CeActivityDto activityDto) {
+    return activityDto.getCeTaskMessageDtos().stream()
+      .filter(ceTaskMessageDto -> MessageType.INFO.equals(ceTaskMessageDto.getType()))
+      .sorted(Comparator.comparing(CeTaskMessageDto::getCreatedAt))
+      .map(CeTaskMessageDto::getMessage)
+      .toList();
+  }
+
   private static class DtoCache {
     private final Map<String, ComponentDto> componentsByUuid;
     private final Multimap<String, CeTaskCharacteristicDto> characteristicsByTaskUuid;
index 65cb3713b4d247f77017aa2c546ce76e82c8cc4a..7d858fa24799e3bca8fd7429c57690962bec10ec 100644 (file)
       "warnings": [
         "The properties \u0027sonar.login\u0027 and \u0027sonar.password\u0027 are deprecated and will be removed in the future. Please pass a token with the \u0027sonar.token\u0027 property instead.",
         "Missing blame information for 2 files. This may lead to some features not working correctly. Please check the analysis logs and refer to \u003ca href\u003d\"https://docs.sonarsource.com/sonarqube/latest/analyzing-source-code/scm-integration/\" rel\u003d\"noopener noreferrer\" target\u003d\"_blank\"\u003ethe documentation\u003c/a\u003e."
+      ] ,
+      "infoMessages": [
+        "Successfully synchronized 5 users.",
+        "Other information message"
       ]
     },
     {
index e8d1bec6d2261d064f1695a3a13c6057532720f9..33bcd0e383996769b5a9e9c12d45850c2f2d886a 100644 (file)
@@ -23,6 +23,7 @@ import java.util.ArrayList;
 import java.util.Collections;
 import java.util.Date;
 import java.util.List;
+import java.util.Set;
 import java.util.stream.IntStream;
 import javax.annotation.Nullable;
 import org.junit.Rule;
@@ -45,6 +46,7 @@ import static org.mockito.Mockito.mock;
 import static org.mockito.Mockito.when;
 import static org.sonar.db.ce.CeQueueTesting.makeInProgress;
 import static org.sonar.db.dismissmessage.MessageType.INFO;
+import static org.sonar.db.dismissmessage.MessageType.PROJECT_NCD_PAGE_90;
 
 public class TaskFormatterTest {
 
@@ -186,6 +188,7 @@ public class TaskFormatterTest {
     assertThat(wsTask.hasScannerContext()).isFalse();
     assertThat(wsTask.getWarningCount()).isZero();
     assertThat(wsTask.getWarningsList()).isEmpty();
+    assertThat(wsTask.getInfoMessagesList()).isEmpty();
   }
 
   @Test
@@ -200,7 +203,7 @@ public class TaskFormatterTest {
   }
 
   @Test
-  public void formatActivity_filterNonWarnings_andSetMessagesAndCount() {
+  public void formatActivity_filterWarnings_andSetWarningsAndCount() {
     TestActivityDto dto = newActivity("UUID", "COMPONENT_UUID", CeActivityDto.Status.FAILED, null);
     CeTaskMessageDto warning1 = createCeTaskMessageDto(1998, MessageType.GENERIC);
     CeTaskMessageDto warning2 = createCeTaskMessageDto(1999, MessageType.GENERIC);
@@ -216,6 +219,24 @@ public class TaskFormatterTest {
     assertThat(wsTask.getWarningsList()).hasSameElementsAs(getMessagesText(List.of(warning1, warning2)));
   }
 
+  @Test
+  public void formatActivity_filterInformation_andSetInformationMessages() {
+    TestActivityDto dto = newActivity("UUID", "COMPONENT_UUID", CeActivityDto.Status.FAILED, null);
+    CeTaskMessageDto nonInfo1 = createCeTaskMessageDto(1998, MessageType.SUGGEST_DEVELOPER_EDITION_UPGRADE);
+    CeTaskMessageDto nonInfo2 = createCeTaskMessageDto(1999, MessageType.GENERIC);
+    CeTaskMessageDto nonInfo3 = createCeTaskMessageDto(2000, MessageType.BRANCH_NCD_90);
+    CeTaskMessageDto info2 = createCeTaskMessageDto(2002, INFO);
+    CeTaskMessageDto info1 = createCeTaskMessageDto(2001, INFO);
+
+    List<CeTaskMessageDto> ceTaskMessageDtos = new ArrayList<>(dto.getCeTaskMessageDtos());
+    ceTaskMessageDtos.addAll(Set.of(nonInfo1, nonInfo2, nonInfo3, info1, info2));
+    dto.setCeTaskMessageDtos(ceTaskMessageDtos);
+
+    Ce.Task wsTask = underTest.formatActivity(db.getSession(), dto, null);
+
+    assertThat(wsTask.getInfoMessagesList()).hasSameElementsAs(getMessagesText(List.of(info1, info2)));
+  }
+
   private static List<String> getMessagesText(List<CeTaskMessageDto> ceTaskMessageDtos) {
     return ceTaskMessageDtos.stream().map(CeTaskMessageDto::getMessage).toList();
   }
@@ -282,7 +303,7 @@ public class TaskFormatterTest {
     TestActivityDto testActivityDto = new TestActivityDto(queueDto);
 
     List<CeTaskMessageDto> ceTaskMessageDtos = IntStream.range(0, WARNING_COUNT)
-      .mapToObj(i -> createCeTaskMessageDto(i, INFO))
+      .mapToObj(i -> createCeTaskMessageDto(i, PROJECT_NCD_PAGE_90))
       .toList();
     testActivityDto.setCeTaskMessageDtos(ceTaskMessageDtos);
     return (TestActivityDto) testActivityDto
index 3c19f02a691ca3488490f1115b5c3c02780238de..ab51fba97caaf0f0d82828549957bfbecd876c6b 100644 (file)
@@ -136,6 +136,7 @@ message Task {
   optional int32 warningCount = 26;
   repeated string warnings = 27;
   optional string nodeName = 28;
+  repeated string infoMessages = 29;
 }
 
 enum TaskStatus {