From 45d83ef1befaa596acff7da348892d36919dd7f8 Mon Sep 17 00:00:00 2001 From: Tomasz Godzik Date: Thu, 18 Apr 2024 11:55:49 +0200 Subject: [PATCH] [fix] Fix publishing warnings (#547) * bugfix: Fix publishing warnings Previously, no (Scala) warnings would be reported since they would come inside stderr in a progress build event. Now, they are handled via that event and cleared correctly when needed. * chore: Add tests for compilation --- MODULE.bazel | 3 +- MODULE.bazel.lock | 312 ++++++------------ .../bsp/bazel/BazelBspScalaProjectTest.kt | 40 ++- .../scala_targets/Example.scala | 11 +- .../bsp/bazel/server/bep/BepServer.kt | 31 +- .../server/diagnostics/DiagnosticsParser.kt | 8 +- .../server/diagnostics/DiagnosticsService.kt | 14 +- .../diagnostics/DiagnosticsServiceTest.kt | 8 +- 8 files changed, 169 insertions(+), 258 deletions(-) diff --git a/MODULE.bazel b/MODULE.bazel index 3001280c2..a3e4a9b33 100644 --- a/MODULE.bazel +++ b/MODULE.bazel @@ -24,9 +24,10 @@ bazel_dep( dev_dependency = True, repo_name = "testkit", ) + git_override( module_name = "bsp-testkit2", - commit = "a53e52ed415d087b63a40e796374c7819d9f76a7", + commit = "3462993c11559f36ab937286f035277692dd8cf4", remote = "https://github.com/build-server-protocol/bsp-testkit2.git", ) diff --git a/MODULE.bazel.lock b/MODULE.bazel.lock index cfc2b9c91..33401710f 100644 --- a/MODULE.bazel.lock +++ b/MODULE.bazel.lock @@ -1,6 +1,6 @@ { "lockFileVersion": 3, - "moduleFileHash": "95ee595fb035e62e71e7648d7f42de2d476a454db4e525113592df88de31df96", + "moduleFileHash": "8829e7114d500844ca4a27bad9a9f07a5dd07de48a195e15c66e9b3d8913c5f4", "flags": { "cmdRegistries": [ "https://bcr.bazel.build/" @@ -47,7 +47,7 @@ "usingModule": "", "location": { "file": "@@//:MODULE.bazel", - "line": 39, + "line": 40, "column": 31 }, "imports": { @@ -73,7 +73,7 @@ "devDependency": true, "location": { "file": "@@//:MODULE.bazel", - "line": 47, + "line": 48, "column": 24 } }, @@ -85,7 +85,7 @@ "devDependency": true, "location": { "file": "@@//:MODULE.bazel", - "line": 48, + "line": 49, "column": 24 } }, @@ -97,7 +97,7 @@ "devDependency": true, "location": { "file": "@@//:MODULE.bazel", - "line": 49, + "line": 50, "column": 24 } } @@ -111,7 +111,7 @@ "usingModule": "", "location": { "file": "@@//:MODULE.bazel", - "line": 70, + "line": 71, "column": 22 }, "imports": { @@ -159,7 +159,7 @@ "devDependency": false, "location": { "file": "@@//:MODULE.bazel", - "line": 71, + "line": 72, "column": 14 } } @@ -170,7 +170,7 @@ ], "deps": { "bazel_skylib": "bazel_skylib@1.5.0", - "rules_kotlin": "rules_kotlin@1.9.1", + "rules_kotlin": "rules_kotlin@1.9.5", "rules_java": "rules_java@7.5.0", "rules_proto": "rules_proto@5.3.0-21.7", "rules_cc": "rules_cc@0.0.9", @@ -214,10 +214,10 @@ } } }, - "rules_kotlin@1.9.1": { + "rules_kotlin@1.9.5": { "name": "rules_kotlin", - "version": "1.9.1", - "key": "rules_kotlin@1.9.1", + "version": "1.9.5", + "key": "rules_kotlin@1.9.5", "repoName": "rules_kotlin", "executionPlatformsToRegister": [], "toolchainsToRegister": [ @@ -227,14 +227,13 @@ { "extensionBzlFile": "@rules_kotlin//src/main/starlark/core/repositories:bzlmod_setup.bzl", "extensionName": "rules_kotlin_extensions", - "usingModule": "rules_kotlin@1.9.1", + "usingModule": "rules_kotlin@1.9.5", "location": { - "file": "https://bcr.bazel.build/modules/rules_kotlin/1.9.1/MODULE.bazel", + "file": "https://bcr.bazel.build/modules/rules_kotlin/1.9.5/MODULE.bazel", "line": 14, "column": 40 }, "imports": { - "buildkite_config": "buildkite_config", "com_github_google_ksp": "com_github_google_ksp", "com_github_jetbrains_kotlin": "com_github_jetbrains_kotlin", "com_github_pinterest_ktlint": "com_github_pinterest_ktlint", @@ -248,10 +247,10 @@ { "extensionBzlFile": "@bazel_tools//tools/android:android_extensions.bzl", "extensionName": "remote_android_tools_extensions", - "usingModule": "rules_kotlin@1.9.1", + "usingModule": "rules_kotlin@1.9.5", "location": { - "file": "https://bcr.bazel.build/modules/rules_kotlin/1.9.1/MODULE.bazel", - "line": 27, + "file": "https://bcr.bazel.build/modules/rules_kotlin/1.9.5/MODULE.bazel", + "line": 29, "column": 42 }, "imports": { @@ -262,67 +261,6 @@ "tags": [], "hasDevUseExtension": false, "hasNonDevUseExtension": true - }, - { - "extensionBzlFile": "@rules_jvm_external//:extensions.bzl", - "extensionName": "maven", - "usingModule": "rules_kotlin@1.9.1", - "location": { - "file": "https://bcr.bazel.build/modules/rules_kotlin/1.9.1/MODULE.bazel", - "line": 36, - "column": 22 - }, - "imports": { - "kotlin_rules_maven": "kotlin_rules_maven" - }, - "devImports": [], - "tags": [ - { - "tagName": "install", - "attributeValues": { - "name": "kotlin_rules_maven", - "artifacts": [ - "com.google.code.findbugs:jsr305:3.0.2", - "junit:junit:4.13-beta-3", - "com.google.protobuf:protobuf-java:3.6.0", - "com.google.protobuf:protobuf-java-util:3.6.0", - "com.google.guava:guava:27.1-jre", - "com.google.truth:truth:0.45", - "com.google.auto.service:auto-service:1.0.1", - "com.google.auto.service:auto-service-annotations:1.0.1", - "com.google.auto.value:auto-value:1.10.1", - "com.google.auto.value:auto-value-annotations:1.10.1", - "com.google.dagger:dagger:2.43.2", - "com.google.dagger:dagger-compiler:2.43.2", - "com.google.dagger:dagger-producers:2.43.2", - "javax.annotation:javax.annotation-api:1.3.2", - "javax.inject:javax.inject:1", - "org.pantsbuild:jarjar:1.7.2", - "org.jetbrains.kotlinx:atomicfu-js:0.15.2", - "org.jetbrains.kotlinx:kotlinx-serialization-runtime:1.0-M1-1.4.0-rc", - "dev.zacsweers.autoservice:auto-service-ksp:jar:1.1.0", - "com.squareup.moshi:moshi:1.15.0", - "com.squareup.moshi:moshi-kotlin:1.15.0", - "com.squareup.moshi:moshi-kotlin-codegen:1.15.0", - "com.google.auto.service:auto-service-annotations:jar:1.1.1" - ], - "fetch_sources": true, - "repositories": [ - "https://maven-central.storage.googleapis.com/repos/central/data/", - "https://maven.google.com", - "https://repo1.maven.org/maven2" - ] - }, - "devDependency": false, - "location": { - "file": "https://bcr.bazel.build/modules/rules_kotlin/1.9.1/MODULE.bazel", - "line": 37, - "column": 14 - } - } - ], - "hasDevUseExtension": false, - "hasNonDevUseExtension": true } ], "deps": { @@ -331,9 +269,6 @@ "rules_java": "rules_java@7.5.0", "rules_python": "rules_python@0.31.0", "rules_cc": "rules_cc@0.0.9", - "rules_jvm_external": "rules_jvm_external@_", - "rules_pkg": "rules_pkg@0.7.0", - "io_bazel_stardoc": "stardoc@0.5.6", "rules_proto": "rules_proto@5.3.0-21.7", "bazel_tools": "bazel_tools@_", "local_config_platform": "local_config_platform@_" @@ -342,14 +277,14 @@ "bzlFile": "@bazel_tools//tools/build_defs/repo:http.bzl", "ruleClassName": "http_archive", "attributes": { - "name": "rules_kotlin~1.9.1", + "name": "rules_kotlin~1.9.5", "urls": [ - "https://github.com/bazelbuild/rules_kotlin/releases/download/v1.9.1/rules_kotlin-v1.9.1.tar.gz" + "https://github.com/bazelbuild/rules_kotlin/releases/download/v1.9.5/rules_kotlin-v1.9.5.tar.gz" ], - "integrity": "sha256-2YmMMlDgRCQ27qveThlMMNbHakqX9RexjO/f1ONFclo=", + "integrity": "sha256-NOjANRdktx1492yHRumAY5ec4I3PGpFmbz87wpSaUz0=", "strip_prefix": "", "remote_patches": { - "https://bcr.bazel.build/modules/rules_kotlin/1.9.1/patches/module_dot_bazel_version.patch": "sha256-JNJ7cO0dqwPGSWBXTKQ93kwoF0xUXsTrIu9pronFqJI=" + "https://bcr.bazel.build/modules/rules_kotlin/1.9.5/patches/module_dot_bazel_version.patch": "sha256-tOrLxnNleAaGaQRSX2G0aTQ0kjwAvUGRuhEGMiHFvEo=" }, "remote_patch_strip": 1 } @@ -754,7 +689,7 @@ "deps": { "bazel_skylib": "bazel_skylib@1.5.0", "rules_java": "rules_java@7.5.0", - "rules_kotlin": "rules_kotlin@1.9.1", + "rules_kotlin": "rules_kotlin@1.9.5", "rules_jvm_external": "rules_jvm_external@_", "bazel_tools": "bazel_tools@_", "local_config_platform": "local_config_platform@_" @@ -1017,68 +952,6 @@ "bazel_tools": "bazel_tools@_" } }, - "rules_pkg@0.7.0": { - "name": "rules_pkg", - "version": "0.7.0", - "key": "rules_pkg@0.7.0", - "repoName": "rules_pkg", - "executionPlatformsToRegister": [], - "toolchainsToRegister": [], - "extensionUsages": [], - "deps": { - "rules_python": "rules_python@0.31.0", - "bazel_skylib": "bazel_skylib@1.5.0", - "rules_license": "rules_license@0.0.7", - "bazel_tools": "bazel_tools@_", - "local_config_platform": "local_config_platform@_" - }, - "repoSpec": { - "bzlFile": "@bazel_tools//tools/build_defs/repo:http.bzl", - "ruleClassName": "http_archive", - "attributes": { - "name": "rules_pkg~0.7.0", - "urls": [ - "https://github.com/bazelbuild/rules_pkg/releases/download/0.7.0/rules_pkg-0.7.0.tar.gz" - ], - "integrity": "sha256-iimOgydi7aGDBZfWT+fbWBeKqEzVkm121bdE1lWJQcI=", - "strip_prefix": "", - "remote_patches": { - "https://bcr.bazel.build/modules/rules_pkg/0.7.0/patches/module_dot_bazel.patch": "sha256-4OaEPZwYF6iC71ZTDg6MJ7LLqX7ZA0/kK4mT+4xKqiE=" - }, - "remote_patch_strip": 0 - } - } - }, - "stardoc@0.5.6": { - "name": "stardoc", - "version": "0.5.6", - "key": "stardoc@0.5.6", - "repoName": "stardoc", - "executionPlatformsToRegister": [], - "toolchainsToRegister": [], - "extensionUsages": [], - "deps": { - "bazel_skylib": "bazel_skylib@1.5.0", - "rules_java": "rules_java@7.5.0", - "rules_license": "rules_license@0.0.7", - "bazel_tools": "bazel_tools@_", - "local_config_platform": "local_config_platform@_" - }, - "repoSpec": { - "bzlFile": "@bazel_tools//tools/build_defs/repo:http.bzl", - "ruleClassName": "http_archive", - "attributes": { - "name": "stardoc~0.5.6", - "urls": [ - "https://github.com/bazelbuild/stardoc/releases/download/0.5.6/stardoc-0.5.6.tar.gz" - ], - "integrity": "sha256-37w2Sq7BQ99ebFL68fEWZ3WltECCQ/RF9EtmHP3DE08=", - "strip_prefix": "", - "remote_patches": {}, - "remote_patch_strip": 0 - } - } - }, "rules_license@0.0.7": { "name": "rules_license", "version": "0.0.7", @@ -1308,6 +1181,36 @@ } } }, + "stardoc@0.5.6": { + "name": "stardoc", + "version": "0.5.6", + "key": "stardoc@0.5.6", + "repoName": "stardoc", + "executionPlatformsToRegister": [], + "toolchainsToRegister": [], + "extensionUsages": [], + "deps": { + "bazel_skylib": "bazel_skylib@1.5.0", + "rules_java": "rules_java@7.5.0", + "rules_license": "rules_license@0.0.7", + "bazel_tools": "bazel_tools@_", + "local_config_platform": "local_config_platform@_" + }, + "repoSpec": { + "bzlFile": "@bazel_tools//tools/build_defs/repo:http.bzl", + "ruleClassName": "http_archive", + "attributes": { + "name": "stardoc~0.5.6", + "urls": [ + "https://github.com/bazelbuild/stardoc/releases/download/0.5.6/stardoc-0.5.6.tar.gz" + ], + "integrity": "sha256-37w2Sq7BQ99ebFL68fEWZ3WltECCQ/RF9EtmHP3DE08=", + "strip_prefix": "", + "remote_patches": {}, + "remote_patch_strip": 0 + } + } + }, "zlib@1.3": { "name": "zlib", "version": "1.3", @@ -1390,6 +1293,38 @@ } } }, + "rules_pkg@0.7.0": { + "name": "rules_pkg", + "version": "0.7.0", + "key": "rules_pkg@0.7.0", + "repoName": "rules_pkg", + "executionPlatformsToRegister": [], + "toolchainsToRegister": [], + "extensionUsages": [], + "deps": { + "rules_python": "rules_python@0.31.0", + "bazel_skylib": "bazel_skylib@1.5.0", + "rules_license": "rules_license@0.0.7", + "bazel_tools": "bazel_tools@_", + "local_config_platform": "local_config_platform@_" + }, + "repoSpec": { + "bzlFile": "@bazel_tools//tools/build_defs/repo:http.bzl", + "ruleClassName": "http_archive", + "attributes": { + "name": "rules_pkg~0.7.0", + "urls": [ + "https://github.com/bazelbuild/rules_pkg/releases/download/0.7.0/rules_pkg-0.7.0.tar.gz" + ], + "integrity": "sha256-iimOgydi7aGDBZfWT+fbWBeKqEzVkm121bdE1lWJQcI=", + "strip_prefix": "", + "remote_patches": { + "https://bcr.bazel.build/modules/rules_pkg/0.7.0/patches/module_dot_bazel.patch": "sha256-4OaEPZwYF6iC71ZTDg6MJ7LLqX7ZA0/kK4mT+4xKqiE=" + }, + "remote_patch_strip": 0 + } + } + }, "abseil-cpp@20211102.0": { "name": "abseil-cpp", "version": "20211102.0", @@ -4026,59 +3961,6 @@ "downloaded_file_path": "org/junit/jupiter/junit-jupiter-api/5.10.2/junit-jupiter-api-5.10.2.jar" } }, - "kotlin_rules_maven": { - "bzlFile": "@@rules_jvm_external~override//:coursier.bzl", - "ruleClassName": "coursier_fetch", - "attributes": { - "name": "rules_jvm_external~override~maven~kotlin_rules_maven", - "user_provided_name": "kotlin_rules_maven", - "repositories": [ - "{ \"repo_url\": \"https://maven-central.storage.googleapis.com/repos/central/data/\" }", - "{ \"repo_url\": \"https://maven.google.com\" }", - "{ \"repo_url\": \"https://repo1.maven.org/maven2\" }" - ], - "artifacts": [ - "{ \"group\": \"com.google.code.findbugs\", \"artifact\": \"jsr305\", \"version\": \"3.0.2\" }", - "{ \"group\": \"junit\", \"artifact\": \"junit\", \"version\": \"4.13-beta-3\" }", - "{ \"group\": \"com.google.protobuf\", \"artifact\": \"protobuf-java\", \"version\": \"3.6.0\" }", - "{ \"group\": \"com.google.protobuf\", \"artifact\": \"protobuf-java-util\", \"version\": \"3.6.0\" }", - "{ \"group\": \"com.google.guava\", \"artifact\": \"guava\", \"version\": \"27.1-jre\" }", - "{ \"group\": \"com.google.truth\", \"artifact\": \"truth\", \"version\": \"0.45\" }", - "{ \"group\": \"com.google.auto.service\", \"artifact\": \"auto-service\", \"version\": \"1.0.1\" }", - "{ \"group\": \"com.google.auto.service\", \"artifact\": \"auto-service-annotations\", \"version\": \"1.0.1\" }", - "{ \"group\": \"com.google.auto.value\", \"artifact\": \"auto-value\", \"version\": \"1.10.1\" }", - "{ \"group\": \"com.google.auto.value\", \"artifact\": \"auto-value-annotations\", \"version\": \"1.10.1\" }", - "{ \"group\": \"com.google.dagger\", \"artifact\": \"dagger\", \"version\": \"2.43.2\" }", - "{ \"group\": \"com.google.dagger\", \"artifact\": \"dagger-compiler\", \"version\": \"2.43.2\" }", - "{ \"group\": \"com.google.dagger\", \"artifact\": \"dagger-producers\", \"version\": \"2.43.2\" }", - "{ \"group\": \"javax.annotation\", \"artifact\": \"javax.annotation-api\", \"version\": \"1.3.2\" }", - "{ \"group\": \"javax.inject\", \"artifact\": \"javax.inject\", \"version\": \"1\" }", - "{ \"group\": \"org.pantsbuild\", \"artifact\": \"jarjar\", \"version\": \"1.7.2\" }", - "{ \"group\": \"org.jetbrains.kotlinx\", \"artifact\": \"atomicfu-js\", \"version\": \"0.15.2\" }", - "{ \"group\": \"org.jetbrains.kotlinx\", \"artifact\": \"kotlinx-serialization-runtime\", \"version\": \"1.0-M1-1.4.0-rc\" }", - "{ \"group\": \"dev.zacsweers.autoservice\", \"artifact\": \"auto-service-ksp\", \"version\": \"1.1.0\", \"packaging\": \"jar\" }", - "{ \"group\": \"com.squareup.moshi\", \"artifact\": \"moshi\", \"version\": \"1.15.0\" }", - "{ \"group\": \"com.squareup.moshi\", \"artifact\": \"moshi-kotlin\", \"version\": \"1.15.0\" }", - "{ \"group\": \"com.squareup.moshi\", \"artifact\": \"moshi-kotlin-codegen\", \"version\": \"1.15.0\" }", - "{ \"group\": \"com.google.auto.service\", \"artifact\": \"auto-service-annotations\", \"version\": \"1.1.1\", \"packaging\": \"jar\" }" - ], - "fail_on_missing_checksum": true, - "fetch_sources": true, - "fetch_javadoc": false, - "excluded_artifacts": [], - "generate_compat_repositories": false, - "version_conflict_policy": "default", - "override_targets": {}, - "strict_visibility": false, - "strict_visibility_value": [ - "@@//visibility:private" - ], - "resolve_timeout": 600, - "use_starlark_android_rules": false, - "aar_import_bzl_label": "@build_bazel_rules_android//android:rules.bzl", - "duplicate_version_warning": "warn" - } - }, "unpinned_maven": { "bzlFile": "@@rules_jvm_external~override//:coursier.bzl", "ruleClassName": "coursier_fetch", @@ -7044,9 +6926,9 @@ "recordedRepoMappingEntries": [] } }, - "@@rules_kotlin~1.9.1//src/main/starlark/core/repositories:bzlmod_setup.bzl%rules_kotlin_extensions": { + "@@rules_kotlin~1.9.5//src/main/starlark/core/repositories:bzlmod_setup.bzl%rules_kotlin_extensions": { "general": { - "bzlTransitiveDigest": "LE+QUTVTwppoAoZuVHfoNmyjA8HGWJdHmYvHJwFswd0=", + "bzlTransitiveDigest": "ZIJvXHuEmZVzPuEoOBnuZfBDhARLL27d329xeBvhebY=", "accumulatedFileDigests": {}, "envVariables": {}, "generatedRepoSpecs": { @@ -7054,7 +6936,7 @@ "bzlFile": "@@bazel_tools//tools/build_defs/repo:http.bzl", "ruleClassName": "http_archive", "attributes": { - "name": "rules_kotlin~1.9.1~rules_kotlin_extensions~rules_android", + "name": "rules_kotlin~1.9.5~rules_kotlin_extensions~rules_android", "sha256": "cd06d15dd8bb59926e4d65f9003bfc20f9da4b2519985c27e190cddc8b7a7806", "strip_prefix": "rules_android-0.1.1", "urls": [ @@ -7066,7 +6948,7 @@ "bzlFile": "@@bazel_tools//tools/build_defs/repo:http.bzl", "ruleClassName": "http_file", "attributes": { - "name": "rules_kotlin~1.9.1~rules_kotlin_extensions~com_github_pinterest_ktlint", + "name": "rules_kotlin~1.9.5~rules_kotlin_extensions~com_github_pinterest_ktlint", "sha256": "2b3f6f674a944d25bb8d283c3539947bbe86074793012909a55de4b771f74bcc", "urls": [ "https://github.com/pinterest/ktlint/releases/download/0.49.1/ktlint" @@ -7074,21 +6956,11 @@ "executable": true } }, - "buildkite_config": { - "bzlFile": "@@bazel_tools//tools/build_defs/repo:http.bzl", - "ruleClassName": "http_archive", - "attributes": { - "name": "rules_kotlin~1.9.1~rules_kotlin_extensions~buildkite_config", - "urls": [ - "https://storage.googleapis.com/rbe-toolchain/bazel-configs/rbe-ubuntu1604/latest/rbe_default.tar" - ] - } - }, "com_github_jetbrains_kotlin": { - "bzlFile": "@@rules_kotlin~1.9.1//src/main/starlark/core/repositories:compiler.bzl", + "bzlFile": "@@rules_kotlin~1.9.5//src/main/starlark/core/repositories:compiler.bzl", "ruleClassName": "kotlin_compiler_repository", "attributes": { - "name": "rules_kotlin~1.9.1~rules_kotlin_extensions~com_github_jetbrains_kotlin", + "name": "rules_kotlin~1.9.5~rules_kotlin_extensions~com_github_jetbrains_kotlin", "urls": [ "https://github.com/JetBrains/kotlin/releases/download/v1.9.22/kotlin-compiler-1.9.22.zip" ], @@ -7097,10 +6969,10 @@ } }, "com_github_google_ksp": { - "bzlFile": "@@rules_kotlin~1.9.1//src/main/starlark/core/repositories:ksp.bzl", + "bzlFile": "@@rules_kotlin~1.9.5//src/main/starlark/core/repositories:ksp.bzl", "ruleClassName": "ksp_compiler_plugin_repository", "attributes": { - "name": "rules_kotlin~1.9.1~rules_kotlin_extensions~com_github_google_ksp", + "name": "rules_kotlin~1.9.5~rules_kotlin_extensions~com_github_google_ksp", "urls": [ "https://github.com/google/ksp/releases/download/1.9.22-1.0.17/artifacts.zip" ], @@ -7111,7 +6983,7 @@ }, "recordedRepoMappingEntries": [ [ - "rules_kotlin~1.9.1", + "rules_kotlin~1.9.5", "bazel_tools", "bazel_tools" ] diff --git a/e2e/src/main/kotlin/org/jetbrains/bsp/bazel/BazelBspScalaProjectTest.kt b/e2e/src/main/kotlin/org/jetbrains/bsp/bazel/BazelBspScalaProjectTest.kt index a532a1afd..f43c51267 100644 --- a/e2e/src/main/kotlin/org/jetbrains/bsp/bazel/BazelBspScalaProjectTest.kt +++ b/e2e/src/main/kotlin/org/jetbrains/bsp/bazel/BazelBspScalaProjectTest.kt @@ -1,14 +1,9 @@ package org.jetbrains.bsp.bazel -import ch.epfl.scala.bsp4j.BuildTarget -import ch.epfl.scala.bsp4j.BuildTargetCapabilities -import ch.epfl.scala.bsp4j.BuildTargetIdentifier -import ch.epfl.scala.bsp4j.ScalacOptionsItem -import ch.epfl.scala.bsp4j.ScalacOptionsParams -import ch.epfl.scala.bsp4j.ScalacOptionsResult -import ch.epfl.scala.bsp4j.WorkspaceBuildTargetsResult +import ch.epfl.scala.bsp4j.* import org.jetbrains.bsp.bazel.base.BazelBspTestBaseScenario import org.jetbrains.bsp.bazel.base.BazelBspTestScenarioStep +import java.util.UUID import kotlin.time.Duration.Companion.seconds object BazelBspScalaProjectTest : BazelBspTestBaseScenario() { @@ -19,6 +14,7 @@ object BazelBspScalaProjectTest : BazelBspTestBaseScenario() { override fun scenarioSteps(): List = listOf( scalaOptionsResults(), + compileWithWarnings(), ) override fun expectedWorkspaceBuildTargetsResult(): WorkspaceBuildTargetsResult { @@ -51,12 +47,34 @@ object BazelBspScalaProjectTest : BazelBspTestBaseScenario() { } val expectedScalaOptionsResult = ScalacOptionsResult(expectedScalaOptionsItems) val scalaOptionsParams = ScalacOptionsParams(expectedTargetIdentifiers) - - return BazelBspTestScenarioStep( - "scalaOptions results" - ) { + return BazelBspTestScenarioStep("scalaOptions results") { testClient.testScalacOptions(60.seconds, scalaOptionsParams, expectedScalaOptionsResult) } } + private fun compileWithWarnings(): BazelBspTestScenarioStep { + val expectedTargetIdentifiers = expectedTargetIdentifiers().filter { it.uri != "bsp-workspace-root" } + val compileParams = CompileParams(expectedTargetIdentifiers); + compileParams.originId = UUID.randomUUID().toString() + + val expectedCompilerResult = CompileResult(StatusCode.OK) + val expectedDiagnostic = Diagnostic( + Range(Position(2, 4), Position(2, 4)), + "\"match may not be exhaustive.\\nIt would fail on the following input: C(_)\\n aa match {\\n ^\"" + ) + expectedDiagnostic.severity = DiagnosticSeverity.WARNING + val expectedDocumentId = TextDocumentIdentifier("file://\$WORKSPACE/scala_targets/Example.scala") + val expectedDiagnosticsParam = PublishDiagnosticsParams( + expectedDocumentId, + expectedTargetIdentifiers[0], + listOf(expectedDiagnostic), + true, + ) + expectedDiagnosticsParam.originId = compileParams.originId + + return BazelBspTestScenarioStep("compile results") { + testClient.testCompile(60.seconds, compileParams, expectedCompilerResult, listOf(expectedDiagnosticsParam)) + } + } + } diff --git a/e2e/test-resources/enabled-rules-project/scala_targets/Example.scala b/e2e/test-resources/enabled-rules-project/scala_targets/Example.scala index be31028b6..a0d10a201 100644 --- a/e2e/test-resources/enabled-rules-project/scala_targets/Example.scala +++ b/e2e/test-resources/enabled-rules-project/scala_targets/Example.scala @@ -1,3 +1,12 @@ package example -object Example extends App{} +object Example extends App{ + val aa: A = ??? + aa match { + case B(_) => + } +} + +sealed trait A +case class B(b: Int) extends A +case class C(c: Int) extends A diff --git a/server/src/main/kotlin/org/jetbrains/bsp/bazel/server/bep/BepServer.kt b/server/src/main/kotlin/org/jetbrains/bsp/bazel/server/bep/BepServer.kt index ae9780edf..af0073ad0 100644 --- a/server/src/main/kotlin/org/jetbrains/bsp/bazel/server/bep/BepServer.kt +++ b/server/src/main/kotlin/org/jetbrains/bsp/bazel/server/bep/BepServer.kt @@ -165,6 +165,9 @@ class BepServer( private fun processProgressEvent(event: BuildEventStreamProtos.BuildEvent) { if (event.hasProgress()) { + if (target != null) { + processDiagnosticText(event.progress.stderr, target.uri, true) + } // TODO https://youtrack.jetbrains.com/issue/BAZEL-622 // bepLogger.onProgress(event.getProgress()); } @@ -250,7 +253,7 @@ class BepServer( try { val path = Paths.get(URI.create(actionEvent.stderr.uri)) val stdErrText = Files.readString(path) - processDiagnosticText(stdErrText, label) + processDiagnosticText(stdErrText, label, false) } catch (e: FileSystemNotFoundException) { LOGGER.warn(e) } catch (e: IOException) { @@ -258,24 +261,26 @@ class BepServer( } } BuildEventStreamProtos.File.FileCase.CONTENTS -> { - processDiagnosticText(actionEvent.stderr.contents.toStringUtf8(), label) + processDiagnosticText(actionEvent.stderr.contents.toStringUtf8(), label, false) } else -> { - processDiagnosticText("", label) + processDiagnosticText("", label, false) } } } - private fun processDiagnosticText(stdErrText: String, targetLabel: String) { - val events = - diagnosticsService.extractDiagnostics( - stdErrText, targetLabel, startedEvents.first.value - ) - events.forEach(Consumer { publishDiagnosticsParams: PublishDiagnosticsParams? -> - bspClient.onBuildPublishDiagnostics( - publishDiagnosticsParams - ) - }) + private fun processDiagnosticText(stdErrText: String, targetLabel: String, diagnosticsFromProgress: Boolean) { + if (startedEvents.isNotEmpty() && stdErrText.isNotEmpty()) { + val events = + diagnosticsService.extractDiagnostics( + stdErrText, targetLabel, startedEvents.first.value, diagnosticsFromProgress + ) + events.forEach(Consumer { publishDiagnosticsParams: PublishDiagnosticsParams? -> + bspClient.onBuildPublishDiagnostics( + publishDiagnosticsParams + ) + }) + } } private fun consumeCompletedEvent(event: BuildEventStreamProtos.BuildEvent) { diff --git a/server/src/main/kotlin/org/jetbrains/bsp/bazel/server/diagnostics/DiagnosticsParser.kt b/server/src/main/kotlin/org/jetbrains/bsp/bazel/server/diagnostics/DiagnosticsParser.kt index 7a13ae670..b3d6ac920 100644 --- a/server/src/main/kotlin/org/jetbrains/bsp/bazel/server/diagnostics/DiagnosticsParser.kt +++ b/server/src/main/kotlin/org/jetbrains/bsp/bazel/server/diagnostics/DiagnosticsParser.kt @@ -2,9 +2,9 @@ package org.jetbrains.bsp.bazel.server.diagnostics class DiagnosticsParser { - fun parse(bazelOutput: String, target: String): List { + fun parse(bazelOutput: String, target: String, onlyKnownFiles: Boolean): List { val output = prepareOutput(bazelOutput, target) - val diagnostics = collectDiagnostics(output) + val diagnostics = collectDiagnostics(output, onlyKnownFiles) return deduplicate(diagnostics) } @@ -14,7 +14,7 @@ class DiagnosticsParser { return Output(relevantLines, target) } - private fun collectDiagnostics(output: Output): List { + private fun collectDiagnostics(output: Output, onlyKnownFiles: Boolean): List { val diagnostics = mutableListOf() while (output.nonEmpty()) { for (parser in Parsers) { @@ -26,7 +26,7 @@ class DiagnosticsParser { } } - if (diagnostics.isEmpty()) { + if (diagnostics.isEmpty() && !onlyKnownFiles) { diagnostics.add( Diagnostic( position = Position(0, 0), diff --git a/server/src/main/kotlin/org/jetbrains/bsp/bazel/server/diagnostics/DiagnosticsService.kt b/server/src/main/kotlin/org/jetbrains/bsp/bazel/server/diagnostics/DiagnosticsService.kt index 0bb999263..6e22186d4 100644 --- a/server/src/main/kotlin/org/jetbrains/bsp/bazel/server/diagnostics/DiagnosticsService.kt +++ b/server/src/main/kotlin/org/jetbrains/bsp/bazel/server/diagnostics/DiagnosticsService.kt @@ -1,11 +1,9 @@ package org.jetbrains.bsp.bazel.server.diagnostics import ch.epfl.scala.bsp4j.BuildTargetIdentifier -import ch.epfl.scala.bsp4j.Diagnostic import ch.epfl.scala.bsp4j.PublishDiagnosticsParams import ch.epfl.scala.bsp4j.TextDocumentIdentifier import java.nio.file.Path -import java.util.concurrent.ConcurrentHashMap import java.util.Collections /** @@ -17,16 +15,20 @@ class DiagnosticsService(workspaceRoot: Path, private val hasAnyProblems: Mutabl private val parser = DiagnosticsParser() private val mapper = DiagnosticBspMapper(workspaceRoot) + /* Warnings are reported before the target completed event, when everything is cleared. so we want to avoid removing them */ + private val updatedInThisRun = mutableSetOf() fun getBspState() = Collections.unmodifiableMap(hasAnyProblems) fun extractDiagnostics( bazelOutput: String, targetLabel: String, - originId: String? + originId: String?, + diagnosticsFromProgress: Boolean ): List { - val parsedDiagnostics = parser.parse(bazelOutput, targetLabel) + val parsedDiagnostics = parser.parse(bazelOutput, targetLabel, diagnosticsFromProgress) val events = mapper.createDiagnostics(parsedDiagnostics, originId) + if (diagnosticsFromProgress) updatedInThisRun.addAll(events) updateProblemState(events) return events } @@ -34,6 +36,10 @@ class DiagnosticsService(workspaceRoot: Path, private val hasAnyProblems: Mutabl fun clearFormerDiagnostics(targetLabel: String): List { val docs = hasAnyProblems[targetLabel] hasAnyProblems.remove(targetLabel) + if (updatedInThisRun.isNotEmpty()) { + hasAnyProblems[targetLabel] = updatedInThisRun.map { it.textDocument }.toSet() + updatedInThisRun.clear() + } return docs ?.map { PublishDiagnosticsParams(it, BuildTargetIdentifier(targetLabel), emptyList(), true)} .orEmpty() diff --git a/server/src/test/kotlin/org/jetbrains/bsp/bazel/server/diagnostics/DiagnosticsServiceTest.kt b/server/src/test/kotlin/org/jetbrains/bsp/bazel/server/diagnostics/DiagnosticsServiceTest.kt index d64666073..f970e8c6f 100644 --- a/server/src/test/kotlin/org/jetbrains/bsp/bazel/server/diagnostics/DiagnosticsServiceTest.kt +++ b/server/src/test/kotlin/org/jetbrains/bsp/bazel/server/diagnostics/DiagnosticsServiceTest.kt @@ -638,7 +638,7 @@ class DiagnosticsServiceTest { diagnosticsBeforeError.shouldBeEmpty() // Extract the diagnostics from BEP, there's an error in `Test.scala` of "//path/to/package:test". - service.extractDiagnostics(output, "//path/to/package:test", null) + service.extractDiagnostics(output, "//path/to/package:test", null, false) // Assert that state is updated service.getBspState().keys.shouldHaveSize(1) @@ -726,8 +726,8 @@ class DiagnosticsServiceTest { ) ) - service.extractDiagnostics(output1, "//path/to/package:test", null) - service.extractDiagnostics(output2, "//path/to/package2:test", null) + service.extractDiagnostics(output1, "//path/to/package:test", null, false) + service.extractDiagnostics(output2, "//path/to/package2:test", null, false) // Assert that state is updated service.getBspState().keys shouldContainExactlyInAnyOrder listOf( @@ -775,6 +775,6 @@ class DiagnosticsServiceTest { } private fun extractDiagnostics(output: String, buildTarget: String): List? { - return DiagnosticsService(workspacePath, ConcurrentHashMap()).extractDiagnostics(output, buildTarget, null) + return DiagnosticsService(workspacePath, ConcurrentHashMap()).extractDiagnostics(output, buildTarget, null, false) } }