From e355b1927914aec7e22b4c3da98d9e75c48a57d5 Mon Sep 17 00:00:00 2001 From: Serhat Yenican <104850907+serhat-yenican-sonarsource@users.noreply.github.com> Date: Thu, 14 Nov 2024 16:45:11 +0100 Subject: [PATCH] CODEFIX-192 Add ai code fix enablement to audit logs (#12238) --- .../org/sonar/db/project/ProjectDaoIT.java | 12 +++-- .../db/audit/model/ComponentNewValue.java | 7 +-- .../sonar/db/audit/model/ProjectNewValue.java | 48 +++++++++++++++++++ .../java/org/sonar/db/project/ProjectDao.java | 6 +-- .../db/audit/model/ProjectNewValueTest.java | 48 +++++++++++++++++++ .../config/AiCodeFixEnablementConstants.java | 28 +++++++++++ 6 files changed, 136 insertions(+), 13 deletions(-) create mode 100644 server/sonar-db-dao/src/main/java/org/sonar/db/audit/model/ProjectNewValue.java create mode 100644 server/sonar-db-dao/src/test/java/org/sonar/db/audit/model/ProjectNewValueTest.java create mode 100644 sonar-core/src/main/java/org/sonar/core/config/AiCodeFixEnablementConstants.java diff --git a/server/sonar-db-dao/src/it/java/org/sonar/db/project/ProjectDaoIT.java b/server/sonar-db-dao/src/it/java/org/sonar/db/project/ProjectDaoIT.java index 228bb206b34..4b1e31c4f16 100644 --- a/server/sonar-db-dao/src/it/java/org/sonar/db/project/ProjectDaoIT.java +++ b/server/sonar-db-dao/src/it/java/org/sonar/db/project/ProjectDaoIT.java @@ -43,6 +43,7 @@ import org.sonar.db.DbTester; import org.sonar.db.Pagination; import org.sonar.db.audit.AuditPersister; import org.sonar.db.audit.NoOpAuditPersister; +import org.sonar.db.audit.model.ProjectNewValue; import org.sonar.db.component.BranchDto; import org.sonar.db.component.BranchType; import org.sonar.db.component.ComponentDto; @@ -53,6 +54,7 @@ import static java.util.Collections.emptySet; import static org.assertj.core.api.Assertions.assertThat; import static org.assertj.core.api.Assertions.tuple; import static org.mockito.ArgumentMatchers.any; +import static org.mockito.ArgumentMatchers.argThat; import static org.mockito.Mockito.mock; import static org.mockito.Mockito.times; import static org.mockito.Mockito.verify; @@ -387,20 +389,22 @@ class ProjectDaoIT { @Test void insert_withTrack_shouldCallAuditPersister() { - ProjectDto dto1 = createProject("o1", "p1"); + var dto1 = createProject("o1", "p1").setAiCodeFixEnabled(true); projectDaoWithAuditPersister.insert(db.getSession(), dto1, true); - verify(auditPersister, times(1)).addComponent(any(), any()); + verify(auditPersister, times(1)).addComponent(any(), + argThat(componentNewValue -> ((ProjectNewValue) componentNewValue).isAiCodeFixEnabled())); } @Test void update_shouldCallAuditPersister() { - ProjectDto dto1 = createProject("o1", "p1"); + var dto1 = createProject("o1", "p1").setAiCodeFixEnabled(true); projectDaoWithAuditPersister.update(db.getSession(), dto1); - verify(auditPersister, times(1)).updateComponent(any(), any()); + verify(auditPersister, times(1)).updateComponent(any(), + argThat(componentNewValue -> ((ProjectNewValue) componentNewValue).isAiCodeFixEnabled())); } @Test diff --git a/server/sonar-db-dao/src/main/java/org/sonar/db/audit/model/ComponentNewValue.java b/server/sonar-db-dao/src/main/java/org/sonar/db/audit/model/ComponentNewValue.java index c3ad625f4b9..8d711a3af55 100644 --- a/server/sonar-db-dao/src/main/java/org/sonar/db/audit/model/ComponentNewValue.java +++ b/server/sonar-db-dao/src/main/java/org/sonar/db/audit/model/ComponentNewValue.java @@ -23,7 +23,6 @@ import java.util.Objects; import javax.annotation.CheckForNull; import javax.annotation.Nullable; import org.sonar.db.component.ComponentDto; -import org.sonar.db.project.ProjectDto; import static java.util.Objects.requireNonNull; @@ -42,10 +41,6 @@ public class ComponentNewValue extends NewValue { private Boolean isEnabled; private String path; - public ComponentNewValue(ProjectDto project) { - this(project.getUuid(), project.getName(), project.getKey(), project.isPrivate(), project.getDescription(), project.getQualifier()); - } - public ComponentNewValue(ComponentDto component) { this(component.uuid(), component.name(), component.getKey(), component.isPrivate(), component.description(), component.qualifier()); } @@ -68,7 +63,7 @@ public class ComponentNewValue extends NewValue { this(uuid, name, key, isPrivate, description, qualifier); } - private ComponentNewValue(String uuid, String name, String key, @Nullable Boolean isPrivate, @Nullable String description, String qualifier) { + ComponentNewValue(String uuid, String name, String key, @Nullable Boolean isPrivate, @Nullable String description, String qualifier) { this.componentUuid = requireNonNull(uuid); this.componentName = name; this.componentKey = key; diff --git a/server/sonar-db-dao/src/main/java/org/sonar/db/audit/model/ProjectNewValue.java b/server/sonar-db-dao/src/main/java/org/sonar/db/audit/model/ProjectNewValue.java new file mode 100644 index 00000000000..dc95cb10c4d --- /dev/null +++ b/server/sonar-db-dao/src/main/java/org/sonar/db/audit/model/ProjectNewValue.java @@ -0,0 +1,48 @@ +/* + * SonarQube + * Copyright (C) 2009-2024 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.db.audit.model; + +import java.util.Objects; +import org.sonar.db.project.ProjectDto; + +public class ProjectNewValue extends ComponentNewValue { + + private final boolean aiCodeFixEnabled; + + public ProjectNewValue(ProjectDto project) { + super(project.getUuid(), project.getName(), project.getKey(), Boolean.valueOf(project.isPrivate()), project.getDescription(), project.getQualifier()); + this.aiCodeFixEnabled = project.getAiCodeFixEnabled(); + } + + @Override + public String toString() { + var sb = new StringBuilder(super.toString()); + var length = sb.length(); + sb.replace(length - 1, length, ", "); + addField(sb, "\"aiCodeFixEnabled\": ", Objects.toString(this.aiCodeFixEnabled, "false"), false); + endString(sb); + + return sb.toString(); + } + + public boolean isAiCodeFixEnabled() { + return aiCodeFixEnabled; + } +} diff --git a/server/sonar-db-dao/src/main/java/org/sonar/db/project/ProjectDao.java b/server/sonar-db-dao/src/main/java/org/sonar/db/project/ProjectDao.java index 7b8583787c6..c34f26ff0fc 100644 --- a/server/sonar-db-dao/src/main/java/org/sonar/db/project/ProjectDao.java +++ b/server/sonar-db-dao/src/main/java/org/sonar/db/project/ProjectDao.java @@ -29,7 +29,7 @@ import org.sonar.db.Dao; import org.sonar.db.DbSession; import org.sonar.db.Pagination; import org.sonar.db.audit.AuditPersister; -import org.sonar.db.audit.model.ComponentNewValue; +import org.sonar.db.audit.model.ProjectNewValue; import static java.util.Collections.emptyList; import static org.sonar.db.DatabaseUtils.executeLargeInputs; @@ -49,7 +49,7 @@ public class ProjectDao implements Dao { public void insert(DbSession session, ProjectDto project, boolean track) { if (track) { - auditPersister.addComponent(session, new ComponentNewValue(project)); + auditPersister.addComponent(session, new ProjectNewValue(project)); } mapper(session).insert(project); } @@ -132,7 +132,7 @@ public class ProjectDao implements Dao { } public void update(DbSession session, ProjectDto project) { - auditPersister.updateComponent(session, new ComponentNewValue(project)); + auditPersister.updateComponent(session, new ProjectNewValue(project)); mapper(session).update(project); } diff --git a/server/sonar-db-dao/src/test/java/org/sonar/db/audit/model/ProjectNewValueTest.java b/server/sonar-db-dao/src/test/java/org/sonar/db/audit/model/ProjectNewValueTest.java new file mode 100644 index 00000000000..fa95e45897c --- /dev/null +++ b/server/sonar-db-dao/src/test/java/org/sonar/db/audit/model/ProjectNewValueTest.java @@ -0,0 +1,48 @@ +/* + * SonarQube + * Copyright (C) 2009-2024 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.db.audit.model; + +import org.json.simple.JSONObject; +import org.json.simple.parser.JSONParser; +import org.json.simple.parser.ParseException; +import org.junit.jupiter.api.Test; +import org.sonar.db.project.ProjectDto; + +import static org.assertj.core.api.Assertions.assertThat; + +class ProjectNewValueTest { + + @Test + void toString_generatesValidJson() throws ParseException { + var project = new ProjectDto() + .setUuid("uuid") + .setName("name") + .setKey("key") + .setPrivate(true) + .setDescription("description") + .setQualifier("TRK") + .setAiCodeFixEnabled(true); + ProjectNewValue newValue = new ProjectNewValue(project); + + JSONObject jsonObject = (JSONObject) new JSONParser().parse(newValue.toString()); + + assertThat(jsonObject).hasSize(7); + } +} diff --git a/sonar-core/src/main/java/org/sonar/core/config/AiCodeFixEnablementConstants.java b/sonar-core/src/main/java/org/sonar/core/config/AiCodeFixEnablementConstants.java new file mode 100644 index 00000000000..6e4ee5ca133 --- /dev/null +++ b/sonar-core/src/main/java/org/sonar/core/config/AiCodeFixEnablementConstants.java @@ -0,0 +1,28 @@ +/* + * SonarQube + * Copyright (C) 2009-2024 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.core.config; + +public final class AiCodeFixEnablementConstants { + public static final String SUGGESTION_FEATURE_ENABLED_PROPERTY = "sonar.ai.suggestions.enabled"; + + private AiCodeFixEnablementConstants() { + } + +} -- 2.39.5