Skip to content

Instantly share code, notes, and snippets.

@windymelt
Last active May 14, 2025 16:29
Show Gist options
  • Save windymelt/15b8ed410eeac54f0aafb05d0b006b52 to your computer and use it in GitHub Desktop.
Save windymelt/15b8ed410eeac54f0aafb05d0b006b52 to your computer and use it in GitHub Desktop.
Feedback for MCP server in Metals v1.5.3

Metals MCP Server Tools - Debug Report (Debugged with AI Agent)

1. Introduction

This report summarizes the results of an investigation into the behavior of tools provided by the Metals MCP server. The investigation was based on the information about MCP support found in the Metals release notes.

Test Environment:

  • JVM: OpenJDK 24
  • Metals Version: 1.5.3
  • Scala Version: 3.7.0
  • sbt Version: 1.10.11
  • Project Configuration: A standard sbt project with src/main/scala and src/test/scala. MUnit was used as the testing framework.
  • AI Agent: Roo Code

2. Summary of Verified MCP Tools and Results

The following table outlines the main MCP tools verified and a summary of their behavior.

Tool Name Stability/Accuracy Notes
compile-file Generally stable (no response, but no errors)
compile-full Generally stable (no response, but no errors)
test Unstable/Inconsistent Behavior varies significantly with package structure. See details below.
glob-search Stable
typed-glob-search Stable
inspect Discrepancy with documentation Information returned for objects and methods is limited. See details.
get-docs Stable Correctly retrieves Scaladoc comments.
get-usages Stable Correctly detects symbol usages.
import-build Generally stable (responds) Did not affect the unstable behavior of the test tool.

3. Detailed Issues

3.1. Unstable Behavior of the test Tool

Premise (from release notes, etc.):

  • The test tool is intended to run Scala test suites.
  • It accepts testClass (required), testFile (optional), and verbose (optional, default false) as arguments.

Expected Behavior:

  • The specified test class should be executed consistently, regardless of its package structure, and return a result.
  • The verbose argument should be optional as per documentation.

Actual Behavior:

  • Issue with verbose argument:
    • On initial execution, an error occurred stating the verbose argument was missing. It appears to be treated as a required argument. This can be circumvented by specifying verbose: false.
  • Inconsistent behavior based on package structure:
    • Unstable behavior was observed across multiple test cases, where the test tool would sometimes respond and sometimes not, depending on the test suite's package structure.
    • Observed Patterns:
      • For one test suite, placing it in the same package hierarchy as the code under test resulted in no response, while placing it in a sub-package of the code under test resulted in normal operation.
      • For another test suite, the opposite occurred: it operated normally when placed in the same package hierarchy as the code under test, but failed to respond when placed in a sub-package.
      • A further minimal test suite failed to respond in either package structure.
      • However, test suites located in the default package always operated normally.
    • This inconsistent behavior persisted even after restarting the Metals server or executing import-build.

Possible Causes:

  • Potential issues in the Metals server's internal logic for test detection, classpath resolution, or test runner invocation, possibly influenced by factors beyond package hierarchy, such as specific test suite names, file structures, or processing order.
  • Issues related to how files are handled when the same package name is used in src/main/scala and src/test/scala.

3.2. Discrepancy of the inspect Tool with Documentation

Premise (from release notes, etc.):

  • The inspect tool returns detailed information about Scala symbols.
    • For packages, objects, and traits: a list of members.
    • For classes: a list of members and constructors.
    • For methods: signatures of all overloaded methods.

Expected Behavior:

  • Detailed information corresponding to the symbol type should be returned as described above.

Actual Behavior:

  • For objects (e.g., dev.capslock.metalsmcpexercise.Minimal):
    • Expected: A list of members, including the getOne method.
    • Actual: Only the symbol type and name were returned (e.g., object Minimal).
  • For methods (e.g., dev.capslock.metalsmcpexercise.Minimal.getOne):
    • Expected: The method signature.
    • Actual: No response.
  • This behavior was consistent for custom objects/methods within the project as well as for standard library classes (e.g., scala.collection.immutable.List).

Possible Causes:

  • The current implementation of the inspect tool may not yet provide the full range of information described in the documentation.

4. Summary and Suggestions

The Metals MCP server offers many useful information retrieval features and holds great potential for integration with AI agents. Tools like get-docs, get-usages, glob-search, and typed-glob-search performed stably.

However, the unstable behavior of the test tool and the lack of detailed information from the inspect tool present challenges in terms of reliability and usability. Addressing these points would significantly enhance the Metals MCP server.

Suggestions:

  1. Investigate and rectify the inconsistent behavior of the test tool concerning package structures.
  2. Enhance the inspect tool to provide detailed information as per its documentation.
  3. Update the documentation for the test tool's verbose argument to reflect its actual behavior (i.e., if it's mandatory).

We hope this report contributes to the quality improvement of Metals.

Additional feedback

General behaviour

LLM couldn't recognize tools frequently. I said "load build settings" (in Japanese), but LLM couldn't find tool.

IMO, More rich description is needed to reasonably select MCP tool for Agent. (When I wrote MCP framework in Scala in these days, it sometimes lost what to do if I provided few description.)

Lost connection

Sometimes MCP server is disconnected from Agent. When I refreshed connection, it started to work again.

Sometimes import-build didn't work

It timed out after about a minutes.

In addition, LLM didn't know "After modifying build.sbt, we should re-import build". Metals should tell this fact.

LLM is confused in compile-file / compile-full because it comes with no response

LLM couldn't decide whether it succeeded or failed.

IMHO MCP server should return some output.

Unstable behaviour with @main annotation (e.g. inspect)

It seems like there is mismatch between @main annotation and Metals's inner expression.

More description about get-docs is needed

It couldn't retrieve document for os.zip.apply (in os-lib) because LLM found os.zip and tried to find docs for os.zip.

IMO we should give some trick to LLM e.g. "It may have apply method, and it may have some docs".

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment