Skip to content

Allow configuring workspace type via flag #988

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 6 commits into from
Dec 12, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -18,13 +18,23 @@ public enum BuildConfiguration: Hashable, Codable {
case release
}

/// The type of workspace; default workspace type selection logic can be overridden.
///
/// **(LSP Extension)**
public enum WorkspaceType: Hashable, Codable {
case buildServer, compilationDatabase, swiftPM
}

/// Build settings that should be used for a workspace.
///
/// **(LSP Extension)**
public struct WorkspaceBuildSetup: Hashable, Codable {
/// The configuration that the workspace should be built in.
public let buildConfiguration: BuildConfiguration?

/// The default workspace type to use for this workspace.
public let defaultWorkspaceType: WorkspaceType?

/// The build directory for the workspace.
public let scratchPath: DocumentURI?

Expand All @@ -42,13 +52,15 @@ public struct WorkspaceBuildSetup: Hashable, Codable {

public init(
buildConfiguration: BuildConfiguration? = nil,
defaultWorkspaceType: WorkspaceType? = nil,
scratchPath: DocumentURI? = nil,
cFlags: [String]? = nil,
cxxFlags: [String]? = nil,
linkerFlags: [String]? = nil,
swiftFlags: [String]? = nil
) {
self.buildConfiguration = buildConfiguration
self.defaultWorkspaceType = defaultWorkspaceType
self.scratchPath = scratchPath
self.cFlags = cFlags
self.cxxFlags = cxxFlags
Expand Down
13 changes: 12 additions & 1 deletion Sources/SKCore/BuildSetup.swift
Original file line number Diff line number Diff line change
Expand Up @@ -21,21 +21,31 @@ public struct BuildSetup {
/// Default configuration
public static let `default` = BuildSetup(
configuration: nil,
defaultWorkspaceType: nil,
path: nil,
flags: BuildFlags()
)

/// Build configuration (debug|release).
public var configuration: BuildConfiguration?

/// Default workspace type (buildserver|compdb|swiftpm). Overrides workspace type selection logic.
public var defaultWorkspaceType: WorkspaceType?

/// Build artifacts directory path. If nil, the build system may choose a default value.
public var path: AbsolutePath?

/// Additional build flags
public var flags: BuildFlags

public init(configuration: BuildConfiguration?, path: AbsolutePath?, flags: BuildFlags) {
public init(
configuration: BuildConfiguration?,
defaultWorkspaceType: WorkspaceType?,
path: AbsolutePath?,
flags: BuildFlags
) {
self.configuration = configuration
self.defaultWorkspaceType = defaultWorkspaceType
self.path = path
self.flags = flags
}
Expand All @@ -49,6 +59,7 @@ public struct BuildSetup {
flags = flags.merging(other.flags)
return BuildSetup(
configuration: other.configuration ?? self.configuration,
defaultWorkspaceType: other.defaultWorkspaceType ?? self.defaultWorkspaceType,
path: other.path ?? self.path,
flags: flags
)
Expand Down
1 change: 1 addition & 0 deletions Sources/SKSupport/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ add_library(SKSupport STATIC
Random.swift
Result.swift
ThreadSafeBox.swift
WorkspaceType.swift
)
set_target_properties(SKSupport PROPERTIES
INTERFACE_INCLUDE_DIRECTORIES ${CMAKE_Swift_MODULE_DIRECTORY})
Expand Down
17 changes: 17 additions & 0 deletions Sources/SKSupport/WorkspaceType.swift
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
//===----------------------------------------------------------------------===//
//
// This source file is part of the Swift.org open source project
//
// Copyright (c) 2014 - 2021 Apple Inc. and the Swift project authors
// Licensed under Apache License v2.0 with Runtime Library Exception
//
// See https://swift.org/LICENSE.txt for license information
// See https://swift.org/CONTRIBUTORS.txt for the list of Swift project authors
//
//===----------------------------------------------------------------------===//

public enum WorkspaceType: String {
case buildServer
case compilationDatabase
case swiftPM
}
12 changes: 12 additions & 0 deletions Sources/SourceKitLSP/SourceKitServer.swift
Original file line number Diff line number Diff line change
Expand Up @@ -974,6 +974,17 @@ extension LanguageServerProtocol.BuildConfiguration {
}
}

private extension LanguageServerProtocol.WorkspaceType {
/// Convert `LanguageServerProtocol.WorkspaceType` to `SkSupport.WorkspaceType`.
var workspaceType: SKSupport.WorkspaceType {
switch self {
case .buildServer: return .buildServer
case .compilationDatabase: return .compilationDatabase
case .swiftPM: return .swiftPM
}
}
}

// MARK: - Request and notification handling

extension SourceKitServer {
Expand All @@ -991,6 +1002,7 @@ extension SourceKitServer {
}
return SKCore.BuildSetup(
configuration: buildParams?.buildConfiguration?.configuration,
defaultWorkspaceType: buildParams?.defaultWorkspaceType?.workspaceType,
path: scratchPath,
flags: BuildFlags(
cCompilerFlags: buildParams?.cFlags ?? [],
Expand Down
38 changes: 30 additions & 8 deletions Sources/SourceKitLSP/Workspace.swift
Original file line number Diff line number Diff line change
Expand Up @@ -108,20 +108,42 @@ public final class Workspace {
reloadPackageStatusCallback: @escaping (ReloadPackageStatus) async -> Void
) async throws {
var buildSystem: BuildSystem? = nil
if let rootUrl = rootUri.fileURL, let rootPath = try? AbsolutePath(validating: rootUrl.path) {
if let buildServer = await BuildServerBuildSystem(projectRoot: rootPath, buildSetup: buildSetup) {
buildSystem = buildServer
} else if let swiftpm = await SwiftPMWorkspace(

func buildSwiftPMWorkspace(rootUrl: URL) async -> SwiftPMWorkspace? {
return await SwiftPMWorkspace(
url: rootUrl,
toolchainRegistry: toolchainRegistry,
buildSetup: buildSetup,
reloadPackageStatusCallback: reloadPackageStatusCallback
) {
buildSystem = swiftpm
} else if let compdb = CompilationDatabaseBuildSystem(
)
}

func buildCompDBWorkspace(rootPath: AbsolutePath) -> CompilationDatabaseBuildSystem? {
return CompilationDatabaseBuildSystem(
projectRoot: rootPath,
searchPaths: compilationDatabaseSearchPaths
) {
)
}

func buildBuildServerWorkspace(rootPath: AbsolutePath) async -> BuildServerBuildSystem? {
return await BuildServerBuildSystem(projectRoot: rootPath, buildSetup: buildSetup)
}

if let rootUrl = rootUri.fileURL, let rootPath = try? AbsolutePath(validating: rootUrl.path) {
let defaultBuildSystem: BuildSystem? =
switch buildSetup.defaultWorkspaceType {
case .buildServer: await buildBuildServerWorkspace(rootPath: rootPath)
case .compilationDatabase: buildCompDBWorkspace(rootPath: rootPath)
case .swiftPM: await buildSwiftPMWorkspace(rootUrl: rootUrl)
case nil: nil
}
if let defaultBuildSystem {
buildSystem = defaultBuildSystem
} else if let buildServer = await buildBuildServerWorkspace(rootPath: rootPath) {
buildSystem = buildServer
} else if let swiftpm = await buildSwiftPMWorkspace(rootUrl: rootUrl) {
buildSystem = swiftpm
} else if let compdb = buildCompDBWorkspace(rootPath: rootPath) {
buildSystem = compdb
} else {
logger.error(
Expand Down
12 changes: 12 additions & 0 deletions Sources/sourcekit-lsp/SourceKitLSP.swift
Original file line number Diff line number Diff line change
Expand Up @@ -92,6 +92,12 @@ extension SKSupport.BuildConfiguration: ExpressibleByArgument {}
extension SKSupport.BuildConfiguration: @retroactive ExpressibleByArgument {}
#endif

#if swift(<5.10)
extension SKSupport.WorkspaceType: ExpressibleByArgument {}
#else
extension SKSupport.WorkspaceType: @retroactive ExpressibleByArgument {}
#endif

@main
struct SourceKitLSP: ParsableCommand {
static let configuration = CommandConfiguration(
Expand Down Expand Up @@ -169,6 +175,11 @@ struct SourceKitLSP: ParsableCommand {
)
var indexPrefixMappings = [PathPrefixMapping]()

@Option(
help: "Override default workspace type selection; one of 'swiftPM', 'compilationDatabase', or 'buildServer'"
)
var defaultWorkspaceType: SKSupport.WorkspaceType?

@Option(
name: .customLong("compilation-db-search-path"),
parsing: .singleValue,
Expand All @@ -191,6 +202,7 @@ struct SourceKitLSP: ParsableCommand {
var serverOptions = SourceKitServer.Options()

serverOptions.buildSetup.configuration = buildConfiguration
serverOptions.buildSetup.defaultWorkspaceType = defaultWorkspaceType
serverOptions.buildSetup.path = scratchPath
serverOptions.buildSetup.flags.cCompilerFlags = buildFlagsCc
serverOptions.buildSetup.flags.cxxCompilerFlags = buildFlagsCxx
Expand Down
5 changes: 5 additions & 0 deletions Tests/SKCoreTests/FallbackBuildSystemTests.swift
Original file line number Diff line number Diff line change
Expand Up @@ -58,6 +58,7 @@ final class FallbackBuildSystemTests: XCTestCase {

let buildSetup = BuildSetup(
configuration: .debug,
defaultWorkspaceType: nil,
path: nil,
flags: BuildFlags(swiftCompilerFlags: [
"-Xfrontend",
Expand Down Expand Up @@ -97,6 +98,7 @@ final class FallbackBuildSystemTests: XCTestCase {

let buildSetup = BuildSetup(
configuration: .debug,
defaultWorkspaceType: nil,
path: nil,
flags: BuildFlags(swiftCompilerFlags: [
"-sdk",
Expand Down Expand Up @@ -169,6 +171,7 @@ final class FallbackBuildSystemTests: XCTestCase {

let buildSetup = BuildSetup(
configuration: .debug,
defaultWorkspaceType: nil,
path: nil,
flags: BuildFlags(cxxCompilerFlags: [
"-v"
Expand Down Expand Up @@ -204,6 +207,7 @@ final class FallbackBuildSystemTests: XCTestCase {

let buildSetup = BuildSetup(
configuration: .debug,
defaultWorkspaceType: nil,
path: nil,
flags: BuildFlags(cxxCompilerFlags: [
"-isysroot",
Expand Down Expand Up @@ -254,6 +258,7 @@ final class FallbackBuildSystemTests: XCTestCase {

let buildSetup = BuildSetup(
configuration: .debug,
defaultWorkspaceType: nil,
path: nil,
flags: BuildFlags(cCompilerFlags: [
"-v"
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -186,6 +186,7 @@ final class SwiftPMWorkspaceTests: XCTestCase {

let config = BuildSetup(
configuration: .release,
defaultWorkspaceType: nil,
path: packageRoot.appending(component: "non_default_build_path"),
flags: BuildFlags(cCompilerFlags: ["-m32"], swiftCompilerFlags: ["-typecheck"])
)
Expand Down