From 6dc2cc9ff6340e6588b7608ed90354aa6767fcdf Mon Sep 17 00:00:00 2001 From: Michal Duda Date: Tue, 22 Sep 2020 13:02:01 +0200 Subject: [PATCH] SONAR-13862 Do not display dismissed warnings in api/ce/analysis_status --- .../org/sonar/db/ce/CeTaskMessageDao.java | 7 ++++ .../org/sonar/db/ce/CeTaskMessageMapper.java | 2 ++ .../org/sonar/db/ce/CeTaskMessageMapper.xml | 16 ++++++++++ .../org/sonar/db/ce/CeTaskMessageDaoTest.java | 27 ++++++++++++++++ .../server/ce/ws/AnalysisStatusAction.java | 24 ++++++++------ .../ce/ws/AnalysisStatusActionTest.java | 32 ++++++++++++++----- 6 files changed, 91 insertions(+), 17 deletions(-) diff --git a/server/sonar-db-dao/src/main/java/org/sonar/db/ce/CeTaskMessageDao.java b/server/sonar-db-dao/src/main/java/org/sonar/db/ce/CeTaskMessageDao.java index 39c4b8e2fad..5cd9f8e93ad 100644 --- a/server/sonar-db-dao/src/main/java/org/sonar/db/ce/CeTaskMessageDao.java +++ b/server/sonar-db-dao/src/main/java/org/sonar/db/ce/CeTaskMessageDao.java @@ -40,6 +40,13 @@ public class CeTaskMessageDao implements Dao { return getMapper(dbSession).selectByTask(taskUuid); } + /** + * @return the non dismissed messages for the specific task and specific user, if any, in ascending order of column {@code CREATED_AT}. + */ + public List selectNonDismissedByUserAndTask(DbSession dbSession, String taskUuid, String userUuid) { + return getMapper(dbSession).selectNonDismissedByUserAndTask(taskUuid, userUuid); + } + public void deleteByType(DbSession session, CeTaskMessageType type) { getMapper(session).deleteByType(type.name()); } diff --git a/server/sonar-db-dao/src/main/java/org/sonar/db/ce/CeTaskMessageMapper.java b/server/sonar-db-dao/src/main/java/org/sonar/db/ce/CeTaskMessageMapper.java index 619cd743310..b63349f7c06 100644 --- a/server/sonar-db-dao/src/main/java/org/sonar/db/ce/CeTaskMessageMapper.java +++ b/server/sonar-db-dao/src/main/java/org/sonar/db/ce/CeTaskMessageMapper.java @@ -30,5 +30,7 @@ public interface CeTaskMessageMapper { List selectByTask(@Param("taskUuid") String taskUuid); + List selectNonDismissedByUserAndTask(@Param("taskUuid") String taskUuid, @Param("userUuid") String userUuid); + void deleteByType(@Param("ceMessageType") String ceMessageType); } diff --git a/server/sonar-db-dao/src/main/resources/org/sonar/db/ce/CeTaskMessageMapper.xml b/server/sonar-db-dao/src/main/resources/org/sonar/db/ce/CeTaskMessageMapper.xml index 360ac4425c1..9666696891b 100644 --- a/server/sonar-db-dao/src/main/resources/org/sonar/db/ce/CeTaskMessageMapper.xml +++ b/server/sonar-db-dao/src/main/resources/org/sonar/db/ce/CeTaskMessageMapper.xml @@ -31,6 +31,22 @@ ctm.created_at asc + + insert into ce_task_message ( diff --git a/server/sonar-db-dao/src/test/java/org/sonar/db/ce/CeTaskMessageDaoTest.java b/server/sonar-db-dao/src/test/java/org/sonar/db/ce/CeTaskMessageDaoTest.java index 4ad7e016454..6f14b690c20 100644 --- a/server/sonar-db-dao/src/test/java/org/sonar/db/ce/CeTaskMessageDaoTest.java +++ b/server/sonar-db-dao/src/test/java/org/sonar/db/ce/CeTaskMessageDaoTest.java @@ -28,6 +28,8 @@ import org.junit.rules.ExpectedException; import org.sonar.api.utils.System2; import org.sonar.db.DbSession; import org.sonar.db.DbTester; +import org.sonar.db.project.ProjectDto; +import org.sonar.db.user.UserDto; import static org.apache.commons.lang.RandomStringUtils.randomAlphabetic; import static org.assertj.core.api.Assertions.assertThat; @@ -127,6 +129,31 @@ public class CeTaskMessageDaoTest { .containsExactlyInAnyOrder(messages[0].getUuid(), messages[2].getUuid()); } + @Test + public void selectNonDismissedByUserAndTask_returns_empty_on_empty_table() { + UserDto user = dbTester.users().insertUser(); + String taskUuid = "17ae66e6-fe83-4c80-b704-4b04e9c5abe8"; + + List dto = underTest.selectNonDismissedByUserAndTask(dbTester.getSession(), taskUuid, user.getUuid()); + + assertThat(dto).isEmpty(); + } + + @Test + public void selectNonDismissedByUserAndTask_returns_non_dismissed_messages() { + UserDto user = dbTester.users().insertUser(); + ProjectDto project = dbTester.components().insertPrivateProjectDto(); + dbTester.users().insertUserDismissedMessage(user, project, CeTaskMessageType.SUGGEST_DEVELOPER_EDITION_UPGRADE); + String taskUuid = "17ae66e6-fe83-4c80-b704-4b04e9c5abe8"; + CeTaskMessageDto msg1 = insertMessage(taskUuid, 1, 1_222_333L); + insertMessage(taskUuid, 2, 1_222_334L, CeTaskMessageType.SUGGEST_DEVELOPER_EDITION_UPGRADE); + CeTaskMessageDto msg3 = insertMessage(taskUuid, 3, 1_222_335L); + List messages = underTest.selectNonDismissedByUserAndTask(dbTester.getSession(), taskUuid, user.getUuid()); + + assertThat(messages).hasSize(2); + assertThat(messages).extracting(CeTaskMessageDto::getUuid).containsExactlyInAnyOrder(msg1.getUuid(), msg3.getUuid()); + } + private CeTaskMessageDto insertMessage(String taskUuid, int i, long createdAt) { return insertMessage(taskUuid, i, createdAt, CeTaskMessageType.GENERIC); } diff --git a/server/sonar-webserver-webapi/src/main/java/org/sonar/server/ce/ws/AnalysisStatusAction.java b/server/sonar-webserver-webapi/src/main/java/org/sonar/server/ce/ws/AnalysisStatusAction.java index 55b49a97127..5825ebbfcbc 100644 --- a/server/sonar-webserver-webapi/src/main/java/org/sonar/server/ce/ws/AnalysisStatusAction.java +++ b/server/sonar-webserver-webapi/src/main/java/org/sonar/server/ce/ws/AnalysisStatusAction.java @@ -29,6 +29,7 @@ import org.sonar.api.web.UserRole; import org.sonar.db.DbClient; import org.sonar.db.DbSession; import org.sonar.db.ce.CeActivityDto; +import org.sonar.db.ce.CeTaskMessageDto; import org.sonar.db.ce.CeTaskTypes; import org.sonar.db.component.BranchDto; import org.sonar.db.project.ProjectDto; @@ -109,7 +110,6 @@ public class AnalysisStatusAction implements CeWsAction { private AnalysisStatusWsResponse.Component formatComponent(DbSession dbSession, ProjectDto project, @Nullable CeActivityDto lastActivity, @Nullable String branchKey, @Nullable String pullRequestKey) { - AnalysisStatusWsResponse.Component.Builder builder = AnalysisStatusWsResponse.Component.newBuilder() .setOrganization(getOrganizationKey(dbSession, project)) .setKey(project.getKey()) @@ -124,16 +124,22 @@ public class AnalysisStatusAction implements CeWsAction { if (lastActivity == null) { return builder.build(); } - List warnings = dbClient.ceTaskMessageDao().selectByTask(dbSession, lastActivity.getUuid()).stream() - .map(dto -> AnalysisStatusWsResponse.Warning.newBuilder() - .setKey(dto.getUuid()) - .setMessage(dto.getMessage()) - .setDismissable(dto.getType().isDismissible()) - .build()) - .collect(Collectors.toList()); - builder.addAllWarnings(warnings); + List warnings; + String userUuid = userSession.getUuid(); + if (userUuid != null) { + warnings = dbClient.ceTaskMessageDao().selectNonDismissedByUserAndTask(dbSession, lastActivity.getUuid(), userUuid); + } else { + warnings = dbClient.ceTaskMessageDao().selectByTask(dbSession, lastActivity.getUuid()); + } + List result = warnings.stream().map(dto -> AnalysisStatusWsResponse.Warning.newBuilder() + .setKey(dto.getUuid()) + .setMessage(dto.getMessage()) + .setDismissable(dto.getType().isDismissible()) + .build()) + .collect(Collectors.toList()); + builder.addAllWarnings(result); return builder.build(); } diff --git a/server/sonar-webserver-webapi/src/test/java/org/sonar/server/ce/ws/AnalysisStatusActionTest.java b/server/sonar-webserver-webapi/src/test/java/org/sonar/server/ce/ws/AnalysisStatusActionTest.java index 62b473c1122..56460ab7531 100644 --- a/server/sonar-webserver-webapi/src/test/java/org/sonar/server/ce/ws/AnalysisStatusActionTest.java +++ b/server/sonar-webserver-webapi/src/test/java/org/sonar/server/ce/ws/AnalysisStatusActionTest.java @@ -66,7 +66,7 @@ public class AnalysisStatusActionTest { @Rule public ExpectedException expectedException = ExpectedException.none(); @Rule - public UserSessionRule userSession = UserSessionRule.standalone().logIn().setSystemAdministrator(); + public UserSessionRule userSession = UserSessionRule.standalone(); @Rule public DbTester db = DbTester.create(System2.INSTANCE); @@ -76,7 +76,7 @@ public class AnalysisStatusActionTest { @Test public void no_errors_no_warnings() { ComponentDto project = db.components().insertPrivateProject(); - userSession.addProjectPermission(UserRole.USER, project); + userSession.logIn().setSystemAdministrator().addProjectPermission(UserRole.USER, project); Ce.AnalysisStatusWsResponse response = ws.newRequest() .setParam(PARAM_COMPONENT, project.getKey()) @@ -85,10 +85,26 @@ public class AnalysisStatusActionTest { assertThat(response.getComponent().getWarningsList()).isEmpty(); } + @Test + public void allows_unauthenticated_access() { + ComponentDto project = db.components().insertPublicProject(db.getDefaultOrganization()); + userSession.registerComponents(project); + SnapshotDto analysis = db.components().insertSnapshot(project); + CeActivityDto activity = insertActivity("task-uuid" + counter++, project, SUCCESS, analysis, REPORT); + createTaskMessage(activity, WARNING_IN_MAIN); + createTaskMessage(activity, "Dismissible warning", CeTaskMessageType.SUGGEST_DEVELOPER_EDITION_UPGRADE); + + Ce.AnalysisStatusWsResponse response = ws.newRequest() + .setParam(PARAM_COMPONENT, project.getKey()) + .executeProtobuf(Ce.AnalysisStatusWsResponse.class); + + assertThat(response.getComponent().getWarningsList()).hasSize(2); + } + @Test public void return_warnings_for_last_analysis_of_main() { ComponentDto project = db.components().insertPrivateProject(); - userSession.addProjectPermission(UserRole.USER, project); + userSession.logIn().setSystemAdministrator().addProjectPermission(UserRole.USER, project); SnapshotDto analysis = db.components().insertSnapshot(project); CeActivityDto activity = insertActivity("task-uuid" + counter++, project, SUCCESS, analysis, REPORT); @@ -119,7 +135,7 @@ public class AnalysisStatusActionTest { @Test public void return_warnings_for_last_analysis_of_branch() { ComponentDto project = db.components().insertPrivateProject(); - userSession.addProjectPermission(UserRole.USER, project); + userSession.logIn().setSystemAdministrator().addProjectPermission(UserRole.USER, project); ComponentDto branch = db.components().insertProjectBranch(project, b -> b.setKey(BRANCH_WITH_WARNING)); SnapshotDto analysis = db.components().insertSnapshot(branch); @@ -150,7 +166,7 @@ public class AnalysisStatusActionTest { @Test public void return_warnings_for_last_analysis_of_pull_request() { ComponentDto project = db.components().insertPrivateProject(); - userSession.addProjectPermission(UserRole.USER, project); + userSession.logIn().setSystemAdministrator().addProjectPermission(UserRole.USER, project); ComponentDto pullRequest = db.components().insertProjectBranch(project, b -> { b.setBranchType(BranchType.PULL_REQUEST); @@ -184,7 +200,7 @@ public class AnalysisStatusActionTest { @Test public void return_warnings_per_branch() { ComponentDto project = db.components().insertPrivateProject(); - userSession.addProjectPermission(UserRole.USER, project); + userSession.logIn().setSystemAdministrator().addProjectPermission(UserRole.USER, project); SnapshotDto analysis = db.components().insertSnapshot(project); CeActivityDto activity = insertActivity("task-uuid" + counter++, project, SUCCESS, analysis, REPORT); @@ -244,7 +260,7 @@ public class AnalysisStatusActionTest { @Test public void response_contains_branch_or_pullRequest_for_branch_or_pullRequest_only() { ComponentDto project = db.components().insertPrivateProject(); - userSession.addProjectPermission(UserRole.USER, project); + userSession.logIn().setSystemAdministrator().addProjectPermission(UserRole.USER, project); db.components().insertProjectBranch(project, b -> b.setKey(BRANCH_WITHOUT_WARNING)); @@ -294,7 +310,7 @@ public class AnalysisStatusActionTest { db.getDbClient().ceTaskMessageDao().insert(db.getSession(), ceTaskMessage); db.commit(); - userSession.addProjectPermission(UserRole.USER, project); + userSession.logIn().setSystemAdministrator().addProjectPermission(UserRole.USER, project); String result = ws.newRequest() .setParam(PARAM_COMPONENT, project.getKey()) -- 2.39.5