Skip to content
This repository has been archived by the owner on Aug 5, 2024. It is now read-only.

Commit

Permalink
Integration test on github.com/bazelbuild/bazel data (#24)
Browse files Browse the repository at this point in the history
* Integration test on github.com/bazelbuild/bazel data

* Review suggestions applied

* Make sure BSP server is killed

Apart from this, bump Bazel repo to 5.4.0 and
increase project view size
  • Loading branch information
tpasternak authored Dec 16, 2022
1 parent a4325c7 commit a921baa
Show file tree
Hide file tree
Showing 7 changed files with 220 additions and 86 deletions.
2 changes: 1 addition & 1 deletion build.gradle.kts
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ fun properties(key: String) = project.findProperty(key).toString()

plugins {
// gradle-intellij-plugin - read more: https://github.com/JetBrains/gradle-intellij-plugin
id("org.jetbrains.intellij") version "1.10.0"
id("org.jetbrains.intellij") version "1.10.1"
// gradle-changelog-plugin - read more: https://github.com/JetBrains/gradle-changelog-plugin
id("org.jetbrains.changelog") version "1.3.1"

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,8 +4,6 @@ import ch.epfl.scala.bsp4j.BuildTarget
import ch.epfl.scala.bsp4j.BuildTargetIdentifier
import com.intellij.openapi.diagnostic.logger
import com.intellij.openapi.diagnostic.trace
import java.util.TreeMap
import kotlin.Comparator

/**
* ## Conflicting Targets Problem
Expand Down Expand Up @@ -46,10 +44,10 @@ import kotlin.Comparator
* 2. If step one did not provide any result, we just take a target that has the biggest number of conflicts
*
*/
internal object NonOverlappingTargets {
public object NonOverlappingTargets {
private val log = logger<NonOverlappingTargets>()

operator fun invoke(
public operator fun invoke(
allTargets: Set<BuildTarget>,
conflictGraph: Map<BuildTargetIdentifier, Set<BuildTargetIdentifier>>,
): Set<BuildTargetIdentifier> {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,11 +5,11 @@ import com.intellij.openapi.diagnostic.logger
import com.intellij.openapi.diagnostic.trace
import org.jetbrains.magicmetamodel.extensions.reduceSets

internal object OverlappingTargetsGraph {
public object OverlappingTargetsGraph {

private val log = logger<OverlappingTargetsGraph>()

operator fun invoke(
public operator fun invoke(
targetsDetailsForDocumentProvider: TargetsDetailsForDocumentProvider,
): Map<BuildTargetIdentifier, Set<BuildTargetIdentifier>> {
log.trace { "Calculating overlapping targets graph..." }
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -20,13 +20,13 @@ public data class TargetsDetailsForDocumentProviderState(
public var isFileMap4HACK: Map<String, Boolean> = emptyMap(),
)

internal class TargetsDetailsForDocumentProvider {
public class TargetsDetailsForDocumentProvider {

private val documentIdToTargetsIdsMap: Map<Path, Set<BuildTargetIdentifier>>
private val documentIdInTheSameDirectoryToTargetsIdsMapForHACK: Map<Path, Set<BuildTargetIdentifier>>
private val isFileMap4HACK: Map<String, Boolean>

constructor(sources: List<SourcesItem>) {
public constructor(sources: List<SourcesItem>) {
log.trace { "Initializing TargetsDetailsForDocumentProvider with $sources..." }

this.documentIdToTargetsIdsMap = DocumentIdToTargetsIdsMap(sources)
Expand All @@ -38,7 +38,7 @@ internal class TargetsDetailsForDocumentProvider {
log.trace { "Initializing TargetsDetailsForDocumentProvider done!" }
}

constructor(state: TargetsDetailsForDocumentProviderState) {
public constructor(state: TargetsDetailsForDocumentProviderState) {
this.documentIdToTargetsIdsMap =
state.documentIdToTargetsIdsMap.mapKeys { Path(it.key) }.mapValues { it.value.map { it.fromState() }.toSet() }
this.documentIdInTheSameDirectoryToTargetsIdsMapForHACK =
Expand All @@ -47,15 +47,15 @@ internal class TargetsDetailsForDocumentProvider {
this.isFileMap4HACK = state.isFileMap4HACK
}

fun getAllDocuments(): List<TextDocumentIdentifier> =
public fun getAllDocuments(): List<TextDocumentIdentifier> =
documentIdToTargetsIdsMap.keys
.map(this::mapPathToTextDocumentIdentifier)
.toList()

private fun mapPathToTextDocumentIdentifier(path: Path): TextDocumentIdentifier =
TextDocumentIdentifier(path.toUri().toString())

fun getTargetsDetailsForDocument(documentId: TextDocumentIdentifier): Set<BuildTargetIdentifier> {
public fun getTargetsDetailsForDocument(documentId: TextDocumentIdentifier): Set<BuildTargetIdentifier> {
val targets = generateAllDocumentSubdirectoriesIncludingDocument(documentId)
.flatMap { documentIdToTargetsIdsMap[it].orEmpty() }.toSet()

Expand Down Expand Up @@ -84,7 +84,7 @@ internal class TargetsDetailsForDocumentProvider {
private fun mapDocumentIdToAbsolutePath(documentId: TextDocumentIdentifier): Path =
URI.create(documentId.uri).toAbsolutePath()

fun toState(): TargetsDetailsForDocumentProviderState =
public fun toState(): TargetsDetailsForDocumentProviderState =
TargetsDetailsForDocumentProviderState(
documentIdToTargetsIdsMap.mapKeys { it.key.toString() }
.mapValues { it.value.map { it.toState() }.toSet() },
Expand All @@ -93,7 +93,7 @@ internal class TargetsDetailsForDocumentProvider {
isFileMap4HACK
)

companion object {
private companion object {
private val log = logger<TargetsDetailsForDocumentProvider>()
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -96,12 +96,17 @@ public class CollectProjectDetailsTask(project: Project, private val taskId: Any
UpdateMagicMetaModelInTheBackgroundTask(project, taskId) { collectModel() }

private fun collectModel(): ProjectDetails {
fun errorCallback(e: Throwable) {
bspSyncConsole.finishTask(taskId, "Failed", FailureResultImpl(e))
}

bspSyncConsole.startSubtask(taskId, importSubtaskId, "Collecting model...")

val initializeBuildResult = queryForInitialize(server).get()
val initializeBuildResult = queryForInitialize(server).catchSyncErrors { errorCallback(it) }.get()
server.onBuildInitialized()

val projectDetails = calculateProjectDetailsWithCapabilities(server, initializeBuildResult.capabilities)

val projectDetails = calculateProjectDetailsWithCapabilities(server, initializeBuildResult.capabilities) { errorCallback(it) }

bspSyncConsole.finishSubtask(importSubtaskId, "Collection model done!")

Expand All @@ -111,7 +116,7 @@ public class CollectProjectDetailsTask(project: Project, private val taskId: Any
private fun queryForInitialize(server: BspServer): CompletableFuture<InitializeBuildResult> {
val buildParams = createInitializeBuildParams()

return server.buildInitialize(buildParams).catchSyncErrors()
return server.buildInitialize(buildParams)
}

private fun createInitializeBuildParams(): InitializeBuildParams {
Expand All @@ -130,83 +135,82 @@ public class CollectProjectDetailsTask(project: Project, private val taskId: Any

return params
}
}

private fun calculateProjectDetailsWithCapabilities(
server: BspServer,
buildServerCapabilities: BuildServerCapabilities,
): ProjectDetails {
val workspaceBuildTargetsResult = queryForBuildTargets(server).get()

val allTargetsIds = calculateAllTargetsIds(workspaceBuildTargetsResult)

val sourcesFuture = queryForSourcesResult(server, allTargetsIds)
val resourcesFuture = queryForTargetResources(server, buildServerCapabilities, allTargetsIds)
val dependencySourcesFuture = queryForDependencySources(server, buildServerCapabilities, allTargetsIds)
val javacOptionsFuture = queryForJavacOptions(server, allTargetsIds)

return ProjectDetails(
targetsId = allTargetsIds,
targets = workspaceBuildTargetsResult.targets.toSet(),
sources = sourcesFuture.get().items,
resources = resourcesFuture?.get()?.items ?: emptyList(),
dependenciesSources = dependencySourcesFuture?.get()?.items ?: emptyList(),
// SBT seems not to support the javacOptions endpoint and seems just to hang when called,
// so it's just safer to add timeout here. This should not be called at all for SBT.
javacOptions = javacOptionsFuture.get()?.items ?: emptyList()
)
}

private fun queryForBuildTargets(server: BspServer): CompletableFuture<WorkspaceBuildTargetsResult> =
server.workspaceBuildTargets().catchSyncErrors()
public fun calculateProjectDetailsWithCapabilities(
server: BspServer,
buildServerCapabilities: BuildServerCapabilities,
errorCallback: (Throwable) -> Unit
): ProjectDetails {
val workspaceBuildTargetsResult = queryForBuildTargets(server).get()

val allTargetsIds = calculateAllTargetsIds(workspaceBuildTargetsResult)

val sourcesFuture = queryForSourcesResult(server, allTargetsIds).catchSyncErrors(errorCallback)
val resourcesFuture = queryForTargetResources(server, buildServerCapabilities, allTargetsIds)?.catchSyncErrors(errorCallback)
val dependencySourcesFuture = queryForDependencySources(server, buildServerCapabilities, allTargetsIds)?.catchSyncErrors(errorCallback)
val javacOptionsFuture = queryForJavacOptions(server, allTargetsIds).catchSyncErrors(errorCallback)

return ProjectDetails(
targetsId = allTargetsIds,
targets = workspaceBuildTargetsResult.targets.toSet(),
sources = sourcesFuture.get().items,
resources = resourcesFuture?.get()?.items ?: emptyList(),
dependenciesSources = dependencySourcesFuture?.get()?.items ?: emptyList(),
// SBT seems not to support the javacOptions endpoint and seems just to hang when called,
// so it's just safer to add timeout here. This should not be called at all for SBT.
javacOptions = javacOptionsFuture.get()?.items ?: emptyList()
)
}

private fun calculateAllTargetsIds(workspaceBuildTargetsResult: WorkspaceBuildTargetsResult): List<BuildTargetIdentifier> =
workspaceBuildTargetsResult.targets.map { it.id }

private fun queryForSourcesResult(
server: BspServer,
allTargetsIds: List<BuildTargetIdentifier>
): CompletableFuture<SourcesResult> {
val sourcesParams = SourcesParams(allTargetsIds)
private fun queryForBuildTargets(server: BspServer): CompletableFuture<WorkspaceBuildTargetsResult> =
server.workspaceBuildTargets()

return server.buildTargetSources(sourcesParams).catchSyncErrors()
}
private fun calculateAllTargetsIds(workspaceBuildTargetsResult: WorkspaceBuildTargetsResult): List<BuildTargetIdentifier> =
workspaceBuildTargetsResult.targets.map { it.id }

private fun queryForTargetResources(
server: BspServer,
capabilities: BuildServerCapabilities,
allTargetsIds: List<BuildTargetIdentifier>
): CompletableFuture<ResourcesResult>? {
val resourcesParams = ResourcesParams(allTargetsIds)
private fun queryForSourcesResult(
server: BspServer,
allTargetsIds: List<BuildTargetIdentifier>
): CompletableFuture<SourcesResult> {
val sourcesParams = SourcesParams(allTargetsIds)

return if (capabilities.resourcesProvider) server.buildTargetResources(resourcesParams).catchSyncErrors()
else null
}
return server.buildTargetSources(sourcesParams)
}

private fun queryForDependencySources(
server: BspServer,
capabilities: BuildServerCapabilities,
allTargetsIds: List<BuildTargetIdentifier>
): CompletableFuture<DependencySourcesResult>? {
val dependencySourcesParams = DependencySourcesParams(allTargetsIds)
private fun queryForTargetResources(
server: BspServer,
capabilities: BuildServerCapabilities,
allTargetsIds: List<BuildTargetIdentifier>
): CompletableFuture<ResourcesResult>? {
val resourcesParams = ResourcesParams(allTargetsIds)

return if (capabilities.dependencySourcesProvider) server.buildTargetDependencySources(dependencySourcesParams)
.catchSyncErrors()
else null
}
return if (capabilities.resourcesProvider) server.buildTargetResources(resourcesParams)
else null
}

private fun queryForJavacOptions(
server: BspServer,
allTargetsIds: List<BuildTargetIdentifier>
): CompletableFuture<JavacOptionsResult> {
val javacOptionsParams = JavacOptionsParams(allTargetsIds)
private fun queryForDependencySources(
server: BspServer,
capabilities: BuildServerCapabilities,
allTargetsIds: List<BuildTargetIdentifier>
): CompletableFuture<DependencySourcesResult>? {
val dependencySourcesParams = DependencySourcesParams(allTargetsIds)

return server.buildTargetJavacOptions(javacOptionsParams).catchSyncErrors()
}
return if (capabilities.dependencySourcesProvider) server.buildTargetDependencySources(dependencySourcesParams)
else null
}

private fun <T> CompletableFuture<T>.catchSyncErrors(): CompletableFuture<T> =
this.whenComplete { _, exception ->
exception?.let {
bspSyncConsole.finishTask(taskId, "Failed", FailureResultImpl(exception))
}
}
private fun queryForJavacOptions(
server: BspServer,
allTargetsIds: List<BuildTargetIdentifier>
): CompletableFuture<JavacOptionsResult> {
val javacOptionsParams = JavacOptionsParams(allTargetsIds)
return server.buildTargetJavacOptions(javacOptionsParams)
}


private fun <T> CompletableFuture<T>.catchSyncErrors(errorCallback: (Throwable) -> Unit): CompletableFuture<T> =
this.whenComplete { _, exception ->
exception?.let { errorCallback(it) }
}
2 changes: 1 addition & 1 deletion src/main/resources/META-INF/plugin.xml
Original file line number Diff line number Diff line change
Expand Up @@ -37,7 +37,7 @@
<projectService serviceImplementation="org.jetbrains.plugins.bsp.config.BspProjectPropertiesService"/>
<projectService serviceImplementation="org.jetbrains.plugins.bsp.config.ProjectPropertiesService"/>
<projectService serviceImplementation="org.jetbrains.plugins.bsp.ui.console.BspConsoleService"/>
<registryKey defaultValue="180" description="Timeout for BSP requests" key="bsp.request.timeout.seconds"/>
<registryKey defaultValue="300" description="Timeout for BSP requests" key="bsp.request.timeout.seconds"/>
</extensions>

<actions>
Expand Down
Loading

0 comments on commit a921baa

Please sign in to comment.