Skip to main content

Metals v0.8.0 - Cobalt

· 19 min read

We are excited to announce the release of Metals v0.8.0, codename Cobalt. This release includes a large number of new features and improvements, which have been under development since September 2019.

Commits since last release772
Merged PRs214
Closed issues84
New features8

For full details:

Metals is a language server for Scala that works with VS Code, Vim, Emacs, Sublime Text, Atom and Eclipse. Metals is developed at the Scala Center and VirtusLab along with contributors from the community. Recently, Metals has also gained support from Lunatech with the contributions from @ckipp01. We are extremely grateful for the growing support from the community and businesses alike, which shows in the number of new contributions and their quality.


Check out and give Metals a try!

  • run and debug for tests and main methods
  • go to implementations
  • rename symbol
  • first code action - import missing symbol
  • worksheet support
  • improvements for Bloop integration
  • better support for Vim via coc-metals
  • completion to add all abstract members
  • scaladoc auto completion on type /**


It is now possible to run and test directly from VS Code using the new "Run", "Test", "Debug" and "Debug test" buttons. The debug buttons support debugging with breakpoints. It's possible to insert breakpoints in Java and Scala sources for both workspace sources as well as library dependency sources.


To support other editors please take a look into the documentation on the Metals website.

Known breakpoints limitations we are working on:

  • debugging is only supported in VS Code at this moment, we hope to increase the editor support in the future. To support debugging, editors need to implement the Debug Adapter Protocol
  • breakpoints may not work as expected in all source locations (example: inner classes, ambiguous names, lambdas). Please share your feedback by reporting issues!

Go to implementations

Metals now implements the textDocument/implementations LSP endpoint, which enables all supported editors to display a list of all implementations of abstract classes or members.


Finding implementations also works for symbols outside of the workspace, at the price of a small performance penalty for the first invocation.

The work done for this feature was also instrumental for implementing the Rename refactor (see below).


Refactoring support is one of the most requested features in Metals. In this release, we started by implementing the most commonly used refactors: rename and import missing symbol.

We plan to add more common refactors along the way. Make sure to check out the ones that have already been proposed and consider suggesting other refactors that are essential in your development workflow.

Rename symbol

Thanks to the implementation of the Go to implementations feature, we were able to work on a proper rename for any workspace symbol that will rename all occurrences of a symbol even if that symbol is a part of a class hierarchy.


There are a couple of cases in which rename might behave differently based on the particular symbol being renamed:

  • renaming an overriden symbol will rename all occurrences for both parent and all children overriding that symbol
  • java symbols are not renamed
  • renaming "hashCode", "unapply", "unary_!", "!" is not supported, since they change the semantics
  • methods starting with : can only be renamed to ones with the same first character to make sure code compiles afterwards
  • renaming apply will change all occurrences with just () to a full name .newname()
  • if renaming a class with the same name as the file, the file's name will also be renamed
  • companion objects will also be renamed along with their companion classes

Import missing symbol

Another refactor that is commonly requested is the ability to fix a compilation error by auto-importing a symbol present on the classpath.

This was previously possible in Metals only during completions, but we were lacking what LSP calls a code action.

Code actions are context-sensitive actions that are proposed to the user in order to fix an error or to perform a relevant refactor.

Thanks to the work of @gabro we now have a basic architecture in place for supporting code actions and we were able to implement this feature.


Worksheet support

Thanks to great work by @olafurpg and some additional refinements by @alekseiAlefirov, worksheets are now available in all supported editors.

Worksheets are a way to evaluate code in real time to test and prototype any new features in a simple way. To create a worksheet all that is needed is to create a file with the extension within the source directory of your workspace (like /src/main/scala) and Metals will take care of the rest.

There are two ways worksheets are implemented for different editors. One is with an additional extension to LSP called Decoration extension and it's used by Visual Studio Code and coc-metals.

Visual Studio Code:


The other way worksheets are implemented for all other editors that don't support the Decoration extension is using workspace/applyEdits and comments with hover for larger results.



Build tools

In order to make the integration between Bloop and Metals a smoother experience, several new improvements are included in this release. There're based on feedback from users as well us our own experiences while working with Metals and should make the overall experience of importing the build and compiling much better.

SemanticDB is resolved inside Bloop

Metals requires the SemanticDB compiler plugin for a number of features to function properly. Because of that it was quite difficult to add it automatically in all supported build tools even if those supported Bloop itself. Perfect examples are Seed and Fury, which use Bloop to compile code, however adding a plugin automatically would require changes to their core code.

Currently, thanks to recent changes, Metals can send information about the SemanticDB version, which Bloop uses to automatically download and configure the SemanticDB scalac plugin. Thanks to that no changes in the build tool itself are needed. Particular changes in regards to build tools are:

  • Gradle - predef script code used in automatic import is now simplified a lot and works with even more customized workspaces. The only thing it needs to do is add the Bloop plugin and run bloopInstall, which can easily also be done manually by the user.
  • Maven - no manual configuration is now needed. To import automatically just the plugin is needed to be invoked with a setting for downloading sources.
  • Sbt - the metals-sbt plugin is now removed and the Bloop plugin is now added via automatically generated ./project/metals.sbt file and ran when imported automatically. Thanks to this solution it should be possible to reuse Metals compilation in the upcoming feature for offloading compilation in Sbt.
  • Mill - logic for adding semanticDB plugin is removed from Mill.
  • Fury, Seed - no changes were needed for the semanticDB integration and should work out of the box.

Switch to to using Bloop Launcher

Instead of using internal Metals logic, we now use the Bloop Launcher, which enables us to either connect to an existing Bsp server or start a new Bloop instance with the specified version if none is running. This greatly simplified the connection to Bloop and enabled us to work on further improvements.

Restart Bloop automatically if newer version is needed

Whenever Metals is started and connects to the Bloop build server it receives information about the version it is running. We compare that version to the one needed by Metals to make sure everything is properly working. If the current running version is older we offer to automatically restart it with the newer version. However, this may not work if Bloop was installed manually.

Automatically reconnect to Bsp/Bloop if connection is broken

There were numerous issues reported that the connection to Bps or Bloop was being lost, which causes Metals to behave erratically due to no compilation being run. To solve this, we now detect if the connection is closed and offer the user the option of automatic reconnection. This works both when the build server was down and when the connection was just interrupted. It should also solve the issues on MacOs with dropped connection.


Completion to add all abstract members

In the past when you were implementing an abstract member in a concrete class, you'd see the completion option to override the member. However, if you wanted to implement all of the abstract members, you'd need to do each one individually. Now you'll see a new completion option in the scenario to Implement all members which will implement all the members at once.


Support scaladoc auto completion on type /**

Thanks to recent work by tanishiking Metals now supports auto completing scaladoc for method definition and class definition on typing /**. More details about it can be found in the pull request.


Better support for Vim via coc-metals

In order to better support the Vim experience with Metals, coc-metals extension was created which is an extension for coc.nvim, the most popular LSP client for Vim and Neovim. With this new extension comes a whole bunch of new features for Metals + Vim users.

  • automated installation
  • easier configuration options
  • easier workspace commands
  • embedded doctor
  • input box support
  • implementation of the decoration protocol (Neovim only)


Support for java 11

Thanks to @isomarcte we now also run all tests on JDK 11, which enables us to be more confident about the support for it. With some additional changes to the documentation we now can fully claim that support for JDK 11 is available.

Other changes

This version includes approximately 25% of the Metals git commit log, which makes it impossible to explain every possible improvement in these release notes. Some other features and fixes that we should mention are:

  • fix for handling abstract var overrides
  • add an empty line after the package declaration before import
  • sort auto-completed exhaustive matches by declaration order
  • encode the workspace path directory in build digests
  • tone down "No SemanticDB" warning
  • send Tree View update notification on first no-op compilation.
  • enable goToDefinition when cursor is at end of symbol
  • prioritize build targets with supported Scala versions.
  • add automatic formatting of multi-line stripMargin strings on paste
  • remove support for 2.12.7


Big thanks to everybody who contributed to this release!

We had a lot of new contributors that provided us with some amazing new features and with some amazing quality.

$ git shortlog -sn --no-merges v0.7.6..v0.8.0
Ólafur Páll Geirsson
Tomasz Godzik
Marek Żarnowski
Scala Steward
Gabriele Petronella
Chris Kipp
Rikito Taniguchi
Szymon Świstun
David Strawn
Ayoub Benali
Aleksei Alefirov
Ashwin Bhaskar
Alexandre Archambault
Andy Czerwonka
Enrique Molina
Marc A. Saegesser
Soham Rohankar
Chris Birchall

Merged PRs

v0.8.0 (2020-01-10)

Full Changelog

Merged pull requests: