diff options
Diffstat (limited to 'server')
14 files changed, 87 insertions, 81 deletions
diff --git a/server/sonar-webserver-es/src/main/java/org/sonar/server/issue/index/IssueQueryFactory.java b/server/sonar-webserver-es/src/main/java/org/sonar/server/issue/index/IssueQueryFactory.java index f1d99c660b3..39e1189e5a6 100644 --- a/server/sonar-webserver-es/src/main/java/org/sonar/server/issue/index/IssueQueryFactory.java +++ b/server/sonar-webserver-es/src/main/java/org/sonar/server/issue/index/IssueQueryFactory.java @@ -31,7 +31,6 @@ import java.util.Arrays; import java.util.Collection; import java.util.Collections; import java.util.Date; -import java.util.EnumSet; import java.util.HashSet; import java.util.List; import java.util.Locale; @@ -46,7 +45,6 @@ import org.apache.commons.lang3.StringUtils; import org.jetbrains.annotations.NotNull; import org.slf4j.Logger; import org.slf4j.LoggerFactory; -import org.sonar.api.issue.impact.SoftwareQuality; import org.sonar.db.component.ComponentQualifiers; import org.sonar.api.rule.RuleKey; import org.sonar.core.rule.RuleType; @@ -71,8 +69,6 @@ import static java.lang.String.format; import static java.util.Collections.singleton; import static java.util.Collections.singletonList; import static org.sonar.api.issue.Issue.STATUSES; -import static org.sonar.api.issue.Issue.STATUS_CONFIRMED; -import static org.sonar.api.issue.Issue.STATUS_OPEN; import static org.sonar.api.issue.Issue.STATUS_REVIEWED; import static org.sonar.api.issue.Issue.STATUS_TO_REVIEW; import static org.sonar.api.measures.CoreMetrics.ANALYSIS_FROM_SONARQUBE_9_4_KEY; @@ -185,39 +181,6 @@ public class IssueQueryFactory { } } - public IssueQuery openIssueCountBySeverity( - String projectUuid, - String branchUuid, - String componentUuid, - boolean isMainBranch, - boolean newCode, - SoftwareQuality softwareQuality - ) { - var timeZone = clock.getZone(); - - var types = EnumSet.complementOf(EnumSet.of(RuleType.SECURITY_HOTSPOT)) - .stream() - .map(RuleType::name) - .toList(); - - var query = IssueQuery.builder() - .branchUuid(branchUuid) - .mainBranch(isMainBranch) - .issueStatuses(List.of(STATUS_OPEN, STATUS_CONFIRMED)) - .impactSoftwareQualities(List.of(softwareQuality.name())) - .projectUuids(List.of(projectUuid)) - .timeZone(timeZone) - .types(types); - - if (newCode) { - try (DbSession dbSession = dbClient.openSession(false)) { - setInNewCodePeriod(dbSession, query, componentUuid); - } - } - - return query.build(); - } - private Collection<String> collectIssueKeys(DbSession dbSession, SearchRequest request) { Collection<String> issueKeys = null; if (request.getFixedInPullRequest() != null) { diff --git a/server/sonar-webserver-monitoring/src/main/java/org/sonar/server/monitoring/ServerMonitoringMetrics.java b/server/sonar-webserver-monitoring/src/main/java/org/sonar/server/monitoring/ServerMonitoringMetrics.java index 9d6c9c9ebc5..39f91037d8c 100644 --- a/server/sonar-webserver-monitoring/src/main/java/org/sonar/server/monitoring/ServerMonitoringMetrics.java +++ b/server/sonar-webserver-monitoring/src/main/java/org/sonar/server/monitoring/ServerMonitoringMetrics.java @@ -37,6 +37,7 @@ public class ServerMonitoringMetrics { private final Gauge cePendingTasksTotal; private final Summary ceTasksRunningDuration; + private final Summary ceSystemTasksRunningDuration; private final Gauge elasticsearchDiskSpaceFreeBytesGauge; private final Gauge elasticSearchDiskSpaceTotalBytes; @@ -80,6 +81,12 @@ public class ServerMonitoringMetrics { .labelNames("task_type", "project_key") .register(); + ceSystemTasksRunningDuration = Summary.build() + .name("sonarqube_compute_engine_system_tasks_running_duration_seconds") + .help("Compute engine system task running time in seconds") + .labelNames("task_type") + .register(); + computeEngineGauge = Gauge.build() .name("sonarqube_health_compute_engine_status") .help("Tells whether Compute Engine is up (healthy, ready to take tasks) or down. 1 for up, 0 for down") @@ -165,8 +172,12 @@ public class ServerMonitoringMetrics { cePendingTasksTotal.set(numberOfPendingTasks); } - public void observeComputeEngineTaskDuration(long durationInSeconds, String taskType, String projectKey) { - ceTasksRunningDuration.labels(taskType, projectKey).observe(durationInSeconds); + public void observeComputeEngineTaskDuration(long durationInSeconds, String taskType, String label) { + ceTasksRunningDuration.labels(taskType, label).observe(durationInSeconds); + } + + public void observeComputeEngineSystemTaskDuration(long durationInSeconds, String taskType) { + ceSystemTasksRunningDuration.labels(taskType).observe(durationInSeconds); } public void setComputeEngineStatusToGreen() { diff --git a/server/sonar-webserver-monitoring/src/main/java/org/sonar/server/monitoring/ce/RecentTasksDurationTask.java b/server/sonar-webserver-monitoring/src/main/java/org/sonar/server/monitoring/ce/RecentTasksDurationTask.java index 74d3dd85387..5a4c22d15d8 100644 --- a/server/sonar-webserver-monitoring/src/main/java/org/sonar/server/monitoring/ce/RecentTasksDurationTask.java +++ b/server/sonar-webserver-monitoring/src/main/java/org/sonar/server/monitoring/ce/RecentTasksDurationTask.java @@ -22,11 +22,12 @@ package org.sonar.server.monitoring.ce; import java.util.Collection; import java.util.List; import java.util.Map; +import java.util.Objects; import java.util.stream.Collectors; -import org.sonar.api.config.Configuration; -import org.sonar.api.utils.System2; import org.slf4j.Logger; import org.slf4j.LoggerFactory; +import org.sonar.api.config.Configuration; +import org.sonar.api.utils.System2; import org.sonar.db.DbClient; import org.sonar.db.DbSession; import org.sonar.db.ce.CeActivityDto; @@ -56,6 +57,7 @@ public class RecentTasksDurationTask extends ComputeEngineMetricsTask { Collection<String> entityUuids = recentSuccessfulTasks.stream() .map(CeActivityDto::getEntityUuid) + .filter(Objects::nonNull) .toList(); List<EntityDto> entities = dbClient.entityDao().selectByUuids(dbSession, entityUuids); Map<String, String> entityUuidAndKeys = entities.stream() @@ -75,20 +77,22 @@ public class RecentTasksDurationTask extends ComputeEngineMetricsTask { private void reportObservedDurationForTasks(List<CeActivityDto> tasks, Map<String, String> entityUuidAndKeys) { for (CeActivityDto task : tasks) { - String mainComponentUuid = task.getEntityUuid(); + String entityUuid = task.getEntityUuid(); Long executionTimeMs = task.getExecutionTimeMs(); try { - requireNonNull(mainComponentUuid); requireNonNull(executionTimeMs); - String mainComponentKey = entityUuidAndKeys.get(mainComponentUuid); - requireNonNull(mainComponentKey); - - metrics.observeComputeEngineTaskDuration(executionTimeMs, task.getTaskType(), mainComponentKey); + if (entityUuid != null) { + String label = entityUuidAndKeys.get(entityUuid); + requireNonNull(label); + metrics.observeComputeEngineTaskDuration(executionTimeMs, task.getTaskType(), label); + } else { + metrics.observeComputeEngineSystemTaskDuration(executionTimeMs, task.getTaskType()); + } } catch (RuntimeException e) { - LOGGER.warn("Can't report metric data for a CE task with component uuid " + mainComponentUuid, e); + LOGGER.warn("Can't report metric data for a CE task with entity uuid " + entityUuid, e); } } - } + } diff --git a/server/sonar-webserver-monitoring/src/test/java/org/sonar/server/monitoring/ServerMonitoringMetricsTest.java b/server/sonar-webserver-monitoring/src/test/java/org/sonar/server/monitoring/ServerMonitoringMetricsTest.java index 8b0cbd624f0..ecacceefccb 100644 --- a/server/sonar-webserver-monitoring/src/test/java/org/sonar/server/monitoring/ServerMonitoringMetricsTest.java +++ b/server/sonar-webserver-monitoring/src/test/java/org/sonar/server/monitoring/ServerMonitoringMetricsTest.java @@ -158,6 +158,18 @@ public class ServerMonitoringMetricsTest { labelNames, labelValues)).isEqualTo(10); } + @Test + public void observeComputeEngineSystemTaskDurationTest() { + ServerMonitoringMetrics metrics = new ServerMonitoringMetrics(); + String[] labelNames = {"task_type"}; + String[] labelValues = {"AUDIT_PURGE"}; + + metrics.observeComputeEngineSystemTaskDuration(10, labelValues[0]); + + assertThat(CollectorRegistry.defaultRegistry.getSampleValue("sonarqube_compute_engine_system_tasks_running_duration_seconds_sum", + labelNames, labelValues)).isEqualTo(10); + } + private int sizeOfDefaultRegistry() { Enumeration<Collector.MetricFamilySamples> metrics = CollectorRegistry.defaultRegistry.metricFamilySamples(); return Collections.list(metrics).size(); diff --git a/server/sonar-webserver-monitoring/src/test/java/org/sonar/server/monitoring/ce/RecentTasksDurationTaskTest.java b/server/sonar-webserver-monitoring/src/test/java/org/sonar/server/monitoring/ce/RecentTasksDurationTaskTest.java index 5b5fc0a3570..7fdbfaa9dee 100644 --- a/server/sonar-webserver-monitoring/src/test/java/org/sonar/server/monitoring/ce/RecentTasksDurationTaskTest.java +++ b/server/sonar-webserver-monitoring/src/test/java/org/sonar/server/monitoring/ce/RecentTasksDurationTaskTest.java @@ -86,6 +86,22 @@ public class RecentTasksDurationTaskTest { } @Test + public void run_given1TaskWithEntityUuidAnd1Without_observeDurationFor2Tasks() { + RecentTasksDurationTask task = new RecentTasksDurationTask(dbClient, metrics, config, system); + List<CeActivityDto> recentTasks = createTasks(2, 0); + + recentTasks.get(0).setEntityUuid(null); + + when(entityDao.selectByUuids(any(), any())).thenReturn(createEntityDtos(1)); + when(ceActivityDao.selectNewerThan(any(), anyLong())).thenReturn(recentTasks); + + task.run(); + + verify(metrics, times(1)).observeComputeEngineTaskDuration(anyLong(), any(), any()); + verify(metrics, times(1)).observeComputeEngineSystemTaskDuration(anyLong(), any()); + } + + @Test public void run_givenNullExecutionTime_dontReportMetricData() { RecentTasksDurationTask task = new RecentTasksDurationTask(dbClient, metrics, config, system); List<CeActivityDto> recentTasks = createTasks(1, 0); diff --git a/server/sonar-webserver-webapi-v2/src/main/java/org/sonar/server/v2/api/email/config/controller/EmailConfigurationController.java b/server/sonar-webserver-webapi-v2/src/main/java/org/sonar/server/v2/api/email/config/controller/EmailConfigurationController.java index a62ec04c33a..8fb0f5e05a3 100644 --- a/server/sonar-webserver-webapi-v2/src/main/java/org/sonar/server/v2/api/email/config/controller/EmailConfigurationController.java +++ b/server/sonar-webserver-webapi-v2/src/main/java/org/sonar/server/v2/api/email/config/controller/EmailConfigurationController.java @@ -30,7 +30,6 @@ import org.sonar.server.v2.api.email.config.request.EmailConfigurationUpdateRest import org.sonar.server.v2.api.email.config.resource.EmailConfigurationResource; import org.sonar.server.v2.api.email.config.response.EmailConfigurationSearchRestResponse; import org.springframework.http.HttpStatus; -import org.springframework.http.MediaType; import org.springframework.web.bind.annotation.DeleteMapping; import org.springframework.web.bind.annotation.GetMapping; import org.springframework.web.bind.annotation.PatchMapping; @@ -44,6 +43,7 @@ import org.springframework.web.bind.annotation.RestController; import static org.sonar.server.v2.WebApiEndpoints.EMAIL_CONFIGURATION_ENDPOINT; import static org.sonar.server.v2.WebApiEndpoints.INTERNAL; import static org.sonar.server.v2.WebApiEndpoints.JSON_MERGE_PATCH_CONTENT_TYPE; +import static org.springframework.http.MediaType.APPLICATION_JSON_VALUE; @RequestMapping(EMAIL_CONFIGURATION_ENDPOINT) @RestController @@ -58,7 +58,7 @@ public interface EmailConfigurationController { extensions = @Extension(properties = {@ExtensionProperty(name = INTERNAL, value = "true")})) EmailConfigurationResource createEmailConfiguration(@Valid @RequestBody EmailConfigurationCreateRestRequest createRequest); - @GetMapping(path = "/{id}") + @GetMapping(path = "/{id}", produces = APPLICATION_JSON_VALUE) @ResponseStatus(HttpStatus.OK) @Operation(summary = "Fetch an email configuration", description = """ Fetch a Email configuration. Requires 'Administer System' permission. @@ -76,7 +76,7 @@ public interface EmailConfigurationController { extensions = @Extension(properties = {@ExtensionProperty(name = INTERNAL, value = "true")})) EmailConfigurationSearchRestResponse searchEmailConfigurations(); - @PatchMapping(path = "/{id}", consumes = JSON_MERGE_PATCH_CONTENT_TYPE, produces = MediaType.APPLICATION_JSON_VALUE) + @PatchMapping(path = "/{id}", consumes = JSON_MERGE_PATCH_CONTENT_TYPE, produces = APPLICATION_JSON_VALUE) @ResponseStatus(HttpStatus.OK) @Operation(summary = "Update an email configuration", description = """ Update an email configuration. Requires 'Administer System' permission. diff --git a/server/sonar-webserver-webapi-v2/src/main/java/org/sonar/server/v2/api/github/config/controller/GithubConfigurationController.java b/server/sonar-webserver-webapi-v2/src/main/java/org/sonar/server/v2/api/github/config/controller/GithubConfigurationController.java index dda8fdbc4b7..d246cb4af26 100644 --- a/server/sonar-webserver-webapi-v2/src/main/java/org/sonar/server/v2/api/github/config/controller/GithubConfigurationController.java +++ b/server/sonar-webserver-webapi-v2/src/main/java/org/sonar/server/v2/api/github/config/controller/GithubConfigurationController.java @@ -30,7 +30,6 @@ import org.sonar.server.v2.api.github.config.request.GithubConfigurationUpdateRe import org.sonar.server.v2.api.github.config.resource.GithubConfigurationResource; import org.sonar.server.v2.api.github.config.response.GithubConfigurationSearchRestResponse; import org.springframework.http.HttpStatus; -import org.springframework.http.MediaType; import org.springframework.web.bind.annotation.DeleteMapping; import org.springframework.web.bind.annotation.GetMapping; import org.springframework.web.bind.annotation.PatchMapping; @@ -44,12 +43,13 @@ import org.springframework.web.bind.annotation.RestController; import static org.sonar.server.v2.WebApiEndpoints.GITHUB_CONFIGURATION_ENDPOINT; import static org.sonar.server.v2.WebApiEndpoints.INTERNAL; import static org.sonar.server.v2.WebApiEndpoints.JSON_MERGE_PATCH_CONTENT_TYPE; +import static org.springframework.http.MediaType.APPLICATION_JSON_VALUE; @RequestMapping(GITHUB_CONFIGURATION_ENDPOINT) @RestController public interface GithubConfigurationController { - @GetMapping(path = "/{id}") + @GetMapping(path = "/{id}", produces = APPLICATION_JSON_VALUE) @ResponseStatus(HttpStatus.OK) @Operation(summary = "Fetch a GitHub configuration", description = """ Fetch a GitHub configuration. Requires 'Administer System' permission. @@ -67,7 +67,7 @@ public interface GithubConfigurationController { extensions = @Extension(properties = {@ExtensionProperty(name = INTERNAL, value = "true")})) GithubConfigurationSearchRestResponse searchGithubConfiguration(); - @PatchMapping(path = "/{id}", consumes = JSON_MERGE_PATCH_CONTENT_TYPE, produces = MediaType.APPLICATION_JSON_VALUE) + @PatchMapping(path = "/{id}", consumes = JSON_MERGE_PATCH_CONTENT_TYPE, produces = APPLICATION_JSON_VALUE) @ResponseStatus(HttpStatus.OK) @Operation(summary = "Update a GitHub configuration", description = """ Update a GitHub configuration. Requires 'Administer System' permission. diff --git a/server/sonar-webserver-webapi-v2/src/main/java/org/sonar/server/v2/api/gitlab/config/controller/GitlabConfigurationController.java b/server/sonar-webserver-webapi-v2/src/main/java/org/sonar/server/v2/api/gitlab/config/controller/GitlabConfigurationController.java index a00f7cd0891..b3ebde2230f 100644 --- a/server/sonar-webserver-webapi-v2/src/main/java/org/sonar/server/v2/api/gitlab/config/controller/GitlabConfigurationController.java +++ b/server/sonar-webserver-webapi-v2/src/main/java/org/sonar/server/v2/api/gitlab/config/controller/GitlabConfigurationController.java @@ -30,7 +30,6 @@ import org.sonar.server.v2.api.gitlab.config.request.GitlabConfigurationUpdateRe import org.sonar.server.v2.api.gitlab.config.resource.GitlabConfigurationResource; import org.sonar.server.v2.api.gitlab.config.response.GitlabConfigurationSearchRestResponse; import org.springframework.http.HttpStatus; -import org.springframework.http.MediaType; import org.springframework.web.bind.annotation.DeleteMapping; import org.springframework.web.bind.annotation.GetMapping; import org.springframework.web.bind.annotation.PatchMapping; @@ -44,12 +43,13 @@ import org.springframework.web.bind.annotation.RestController; import static org.sonar.server.v2.WebApiEndpoints.GITLAB_CONFIGURATION_ENDPOINT; import static org.sonar.server.v2.WebApiEndpoints.INTERNAL; import static org.sonar.server.v2.WebApiEndpoints.JSON_MERGE_PATCH_CONTENT_TYPE; +import static org.springframework.http.MediaType.APPLICATION_JSON_VALUE; @RequestMapping(GITLAB_CONFIGURATION_ENDPOINT) @RestController public interface GitlabConfigurationController { - @GetMapping(path = "/{id}") + @GetMapping(path = "/{id}", produces = APPLICATION_JSON_VALUE) @ResponseStatus(HttpStatus.OK) @Operation(summary = "Fetch a GitLab configuration", description = """ Fetch a GitLab configuration. Requires 'Administer System' permission. @@ -67,7 +67,7 @@ public interface GitlabConfigurationController { extensions = @Extension(properties = {@ExtensionProperty(name = INTERNAL, value = "true")})) GitlabConfigurationSearchRestResponse searchGitlabConfiguration(); - @PatchMapping(path = "/{id}", consumes = JSON_MERGE_PATCH_CONTENT_TYPE, produces = MediaType.APPLICATION_JSON_VALUE) + @PatchMapping(path = "/{id}", consumes = JSON_MERGE_PATCH_CONTENT_TYPE, produces = APPLICATION_JSON_VALUE) @ResponseStatus(HttpStatus.OK) @Operation(summary = "Update a Gitlab configuration", description = """ Update a Gitlab configuration. Requires 'Administer System' permission. diff --git a/server/sonar-webserver-webapi-v2/src/main/java/org/sonar/server/v2/api/group/controller/GroupController.java b/server/sonar-webserver-webapi-v2/src/main/java/org/sonar/server/v2/api/group/controller/GroupController.java index f6f6a149679..66bda515c44 100644 --- a/server/sonar-webserver-webapi-v2/src/main/java/org/sonar/server/v2/api/group/controller/GroupController.java +++ b/server/sonar-webserver-webapi-v2/src/main/java/org/sonar/server/v2/api/group/controller/GroupController.java @@ -35,7 +35,6 @@ import org.sonar.server.v2.api.group.response.GroupsSearchRestResponse; import org.sonar.server.v2.api.model.RestPage; import org.springdoc.core.annotations.ParameterObject; import org.springframework.http.HttpStatus; -import org.springframework.http.MediaType; import org.springframework.web.bind.annotation.DeleteMapping; import org.springframework.web.bind.annotation.GetMapping; import org.springframework.web.bind.annotation.PatchMapping; @@ -49,12 +48,13 @@ import org.springframework.web.bind.annotation.RestController; import static org.sonar.server.v2.WebApiEndpoints.GROUPS_ENDPOINT; import static org.sonar.server.v2.WebApiEndpoints.JSON_MERGE_PATCH_CONTENT_TYPE; +import static org.springframework.http.MediaType.APPLICATION_JSON_VALUE; @RequestMapping(GROUPS_ENDPOINT) @RestController public interface GroupController { - @GetMapping(produces = MediaType.APPLICATION_JSON_VALUE) + @GetMapping(produces = APPLICATION_JSON_VALUE) @ResponseStatus(HttpStatus.OK) @Operation(summary = "Group search", description = """ Get the list of groups. @@ -66,12 +66,12 @@ public interface GroupController { extensions = @Extension(properties = {@ExtensionProperty(name = "internal", value = "true")}), hidden = true) String excludedUserId, @Valid @ParameterObject RestPage restPage); - @GetMapping(path = "/{id}") + @GetMapping(path = "/{id}", produces = APPLICATION_JSON_VALUE) @ResponseStatus(HttpStatus.OK) @Operation(summary = "Fetch a single group", description = "Fetch a single group.") GroupRestResponse fetchGroup(@PathVariable("id") @Parameter(description = "The id of the group to fetch.", required = true, in = ParameterIn.PATH) String id); - @PostMapping(consumes = MediaType.APPLICATION_JSON_VALUE, produces = MediaType.APPLICATION_JSON_VALUE) + @PostMapping(consumes = APPLICATION_JSON_VALUE, produces = APPLICATION_JSON_VALUE) @ResponseStatus(HttpStatus.CREATED) @Operation(summary = "Create a new group", description = "Create a new group.") GroupRestResponse create(@Valid @RequestBody GroupCreateRestRequest request); @@ -81,7 +81,7 @@ public interface GroupController { @Operation(summary = "Deletes a group", description = "Deletes a group.") void deleteGroup(@PathVariable("id") @Parameter(description = "The ID of the group to delete.", required = true, in = ParameterIn.PATH) String id); - @PatchMapping(path = "/{id}", consumes = JSON_MERGE_PATCH_CONTENT_TYPE, produces = MediaType.APPLICATION_JSON_VALUE) + @PatchMapping(path = "/{id}", consumes = JSON_MERGE_PATCH_CONTENT_TYPE, produces = APPLICATION_JSON_VALUE) @ResponseStatus(HttpStatus.OK) @Operation(summary = "Update a group", description = """ Update a group name or description. diff --git a/server/sonar-webserver-webapi-v2/src/main/java/org/sonar/server/v2/api/mode/controller/ModeController.java b/server/sonar-webserver-webapi-v2/src/main/java/org/sonar/server/v2/api/mode/controller/ModeController.java index 336584a778a..3dec8655db4 100644 --- a/server/sonar-webserver-webapi-v2/src/main/java/org/sonar/server/v2/api/mode/controller/ModeController.java +++ b/server/sonar-webserver-webapi-v2/src/main/java/org/sonar/server/v2/api/mode/controller/ModeController.java @@ -34,12 +34,13 @@ import org.springframework.web.bind.annotation.RestController; import static org.sonar.server.v2.WebApiEndpoints.INTERNAL; import static org.sonar.server.v2.WebApiEndpoints.MODE_ENDPOINT; +import static org.springframework.http.MediaType.APPLICATION_JSON_VALUE; @RequestMapping(MODE_ENDPOINT) @RestController public interface ModeController { - @GetMapping(path = "") + @GetMapping(path = "", produces = APPLICATION_JSON_VALUE) @ResponseStatus(HttpStatus.OK) @Operation(summary = "Retrieve current instance Mode", description = """ Fetch the current instance mode. Can be Multi-Quality Rules (MQR) Mode or Standard Experience. diff --git a/server/sonar-webserver-webapi-v2/src/main/java/org/sonar/server/v2/api/projectbindings/controller/ProjectBindingsController.java b/server/sonar-webserver-webapi-v2/src/main/java/org/sonar/server/v2/api/projectbindings/controller/ProjectBindingsController.java index 64d3eda84b0..8a7ca41d895 100644 --- a/server/sonar-webserver-webapi-v2/src/main/java/org/sonar/server/v2/api/projectbindings/controller/ProjectBindingsController.java +++ b/server/sonar-webserver-webapi-v2/src/main/java/org/sonar/server/v2/api/projectbindings/controller/ProjectBindingsController.java @@ -37,12 +37,13 @@ import org.springframework.web.bind.annotation.RestController; import static org.sonar.server.v2.WebApiEndpoints.INTERNAL; import static org.sonar.server.v2.WebApiEndpoints.PROJECT_BINDINGS_ENDPOINT; +import static org.springframework.http.MediaType.APPLICATION_JSON_VALUE; @RequestMapping(PROJECT_BINDINGS_ENDPOINT) @RestController public interface ProjectBindingsController { - @GetMapping(path = "/{id}") + @GetMapping(path = "/{id}", produces = APPLICATION_JSON_VALUE) @Operation( operationId = "getProjectBinding", summary = "Fetch a single Project Binding", diff --git a/server/sonar-webserver-webapi-v2/src/main/java/org/sonar/server/v2/api/user/controller/UserController.java b/server/sonar-webserver-webapi-v2/src/main/java/org/sonar/server/v2/api/user/controller/UserController.java index 52563f6d997..1e478f0b602 100644 --- a/server/sonar-webserver-webapi-v2/src/main/java/org/sonar/server/v2/api/user/controller/UserController.java +++ b/server/sonar-webserver-webapi-v2/src/main/java/org/sonar/server/v2/api/user/controller/UserController.java @@ -35,7 +35,6 @@ import org.sonar.server.v2.api.user.response.UserRestResponse; import org.sonar.server.v2.api.user.response.UsersSearchRestResponse; import org.springdoc.core.annotations.ParameterObject; import org.springframework.http.HttpStatus; -import org.springframework.http.MediaType; import org.springframework.web.bind.annotation.DeleteMapping; import org.springframework.web.bind.annotation.GetMapping; import org.springframework.web.bind.annotation.PatchMapping; @@ -49,12 +48,13 @@ import org.springframework.web.bind.annotation.RestController; import static org.sonar.server.v2.WebApiEndpoints.JSON_MERGE_PATCH_CONTENT_TYPE; import static org.sonar.server.v2.WebApiEndpoints.USER_ENDPOINT; +import static org.springframework.http.MediaType.APPLICATION_JSON_VALUE; @RequestMapping(USER_ENDPOINT) @RestController public interface UserController { - @GetMapping(produces = MediaType.APPLICATION_JSON_VALUE) + @GetMapping(produces = APPLICATION_JSON_VALUE) @ResponseStatus(HttpStatus.OK) @Operation(summary = "Users search", description = """ Get a list of users. By default, only active users are returned. @@ -82,7 +82,7 @@ public interface UserController { @PathVariable("id") @Parameter(description = "The ID of the user to delete.", required = true, in = ParameterIn.PATH) String id, @RequestParam(value = "anonymize", required = false, defaultValue = "false") @Parameter(description = "Anonymize user in addition to deactivating it.") Boolean anonymize); - @GetMapping(path = "/{id}") + @GetMapping(path = "/{id}", produces = APPLICATION_JSON_VALUE) @ResponseStatus(HttpStatus.OK) @Operation(summary = "Fetch a single user", description = """ Fetch a single user. @@ -98,14 +98,14 @@ public interface UserController { """) UserRestResponse fetchUser(@PathVariable("id") @Parameter(description = "The id of the user to fetch.", required = true, in = ParameterIn.PATH) String id); - @PatchMapping(path = "/{id}", consumes = JSON_MERGE_PATCH_CONTENT_TYPE, produces = MediaType.APPLICATION_JSON_VALUE) + @PatchMapping(path = "/{id}", consumes = JSON_MERGE_PATCH_CONTENT_TYPE, produces = APPLICATION_JSON_VALUE) @ResponseStatus(HttpStatus.OK) @Operation(summary = "Update a user", description = """ Update users attributes. """) UserRestResponse updateUser(@PathVariable("id") String id, @Valid @RequestBody UserUpdateRestRequest updateRequest); - @PostMapping(consumes = MediaType.APPLICATION_JSON_VALUE, produces = MediaType.APPLICATION_JSON_VALUE) + @PostMapping(consumes = APPLICATION_JSON_VALUE, produces = APPLICATION_JSON_VALUE) @ResponseStatus(HttpStatus.OK) @Operation(summary = "User creation", description = """ Create a user. diff --git a/server/sonar-webserver/src/main/java/org/sonar/server/platform/web/CspFilter.java b/server/sonar-webserver/src/main/java/org/sonar/server/platform/web/CspFilter.java index 7015b1a0b46..195aa01c6bf 100644 --- a/server/sonar-webserver/src/main/java/org/sonar/server/platform/web/CspFilter.java +++ b/server/sonar-webserver/src/main/java/org/sonar/server/platform/web/CspFilter.java @@ -35,8 +35,6 @@ import jakarta.servlet.ServletResponse; import jakarta.servlet.http.HttpServletResponse; public class CspFilter implements Filter { - private static final String BEAMER_SRC = " https://*.getbeamer.com "; - private final List<String> cspHeaders = new ArrayList<>(); private String policies = null; @@ -48,13 +46,13 @@ public class CspFilter implements Filter { cspPolicies.add("default-src 'self'"); cspPolicies.add("base-uri 'none'"); cspPolicies.add("connect-src 'self' http: https:"); - cspPolicies.add("font-src 'self' data:" + BEAMER_SRC); - cspPolicies.add("frame-src" + BEAMER_SRC); + cspPolicies.add("font-src 'self' data:"); + cspPolicies.add("frame-src"); cspPolicies.add("img-src * data: blob:"); cspPolicies.add("object-src 'none'"); // the hash below corresponds to the window.__assetsPath script in index.html - cspPolicies.add("script-src 'self'" + BEAMER_SRC + getAssetsPathScriptCSPHash(filterConfig.getServletContext().getContextPath())); - cspPolicies.add("style-src 'self' 'unsafe-inline'" + BEAMER_SRC); + cspPolicies.add("script-src 'self' " + getAssetsPathScriptCSPHash(filterConfig.getServletContext().getContextPath())); + cspPolicies.add("style-src 'self' 'unsafe-inline'"); cspPolicies.add("worker-src 'self'"); this.policies = String.join("; ", cspPolicies).trim(); } diff --git a/server/sonar-webserver/src/test/java/org/sonar/server/platform/web/CspFilterTest.java b/server/sonar-webserver/src/test/java/org/sonar/server/platform/web/CspFilterTest.java index b2ef0146d4e..c4e0b3cfcd4 100644 --- a/server/sonar-webserver/src/test/java/org/sonar/server/platform/web/CspFilterTest.java +++ b/server/sonar-webserver/src/test/java/org/sonar/server/platform/web/CspFilterTest.java @@ -41,12 +41,12 @@ public class CspFilterTest { private static final String EXPECTED = "default-src 'self'; " + "base-uri 'none'; " + "connect-src 'self' http: https:; " + - "font-src 'self' data: https://*.getbeamer.com ; " + - "frame-src https://*.getbeamer.com ; " + + "font-src 'self' data:; " + + "frame-src; " + "img-src * data: blob:; " + "object-src 'none'; " + - "script-src 'self' https://*.getbeamer.com 'sha256-hK8SVWFNHY0UhP61DBzX/3fvT74EI8u6/jRQvUKeZoU='; " + - "style-src 'self' 'unsafe-inline' https://*.getbeamer.com ; " + + "script-src 'self' 'sha256-hK8SVWFNHY0UhP61DBzX/3fvT74EI8u6/jRQvUKeZoU='; " + + "style-src 'self' 'unsafe-inline'; " + "worker-src 'self'"; private final ServletContext servletContext = mock(ServletContext.class, RETURNS_MOCKS); private final HttpServletResponse response = mock(HttpServletResponse.class); @@ -75,7 +75,7 @@ public class CspFilterTest { doInit(); HttpServletRequest request = newRequest("/"); underTest.doFilter(request, response, chain); - verify(response).setHeader(eq("Content-Security-Policy"), contains("script-src 'self' https://*.getbeamer.com 'sha256-D1jaqcDDM2TM2STrzE42NNqyKR9PlptcHDe6tyaBcuM='; ")); + verify(response).setHeader(eq("Content-Security-Policy"), contains("script-src 'self' 'sha256-D1jaqcDDM2TM2STrzE42NNqyKR9PlptcHDe6tyaBcuM='; ")); verify(chain).doFilter(request, response); } |