"Thin" LSP Servers


During the LSP and build summit/allhands/mind-meld earlier this year, I promised folks a more concrete “thin” LSP proposal. Unfortunately, I’ve been very busy this quarter and didn’t get it to a point where I was really happy with it… I’m also not particularly likely to be able to work on it anytime soon.

Nonetheless, it exists, so might as well share it:

Interested in your thoughts!


Thank you @stuhood for starting this discussion and sharing your proposal!

Overall, I agree with the premise that there is an overlap between language servers and build tools. I think it’s an interesting idea to push more responsibility into the build tool and with that approach a language server won’t have to reimplement functionality of a build tool.

However, how you envision that different build tools can collaborate and reuse thin language servers?

From the perspective of a tooling developer, this proposal falls short in addressing the challenge of making tools like Scalafix available in the editor to as many users as possible regardless of what build tool they use. For better or worse, there are at least 6-8 different build tools that support compiling Scala projects. With this proposal, it seems every build tool will need to reimplement integrations with a wide range of different tools such as the Scala presentation compiler, Scalafix, Scalafmt, symbol indices, editor plugins and more. Integrating with each of these technologies requires a non-trivial amount of engineering and heavily stresses the public APIs of tools like Scalafix. I am concerned that under the thin LSP model certain build tools will miss the train on LSP because they don’t have dedicated resources to implement all of these integrations.

BSP addresses this challenge by specifying a protocol for triggering services and querying information that is readily available in most build tool. I’d like to stress that under the BSP model, a language server is not expected to batch compile source files. The BSP is primarily intended to enable a language server to:

  1. trigger batch compilation in the build tool. Symbol index creation can happen during batch compilation in the build tool using a similar architecture as “Index-While-Building” in Xcode 9 (great talk on the topic: https://youtu.be/jGJhnIT-D2M).
  2. query the build tool for compilation information (such as classpaths) to interactively compile open buffers. In the case of Scala, the compilation information to interactively compile an open buffer is in essence not that much: compiler version and flags (including -classpath). From that information it’s possible to provide code intelligence such as completions, diagnostics, and refactoring as you type. Note that a BSP BuildTarget does not include dependencies on other build targets because it is the responsibility of the build tool to batch compile dependent targets.