Skip to content

Make server instructions reflect disabled categories#579

Open
drtootsie wants to merge 4 commits intografana:mainfrom
drtootsie:fix-server-instructions-clarity
Open

Make server instructions reflect disabled categories#579
drtootsie wants to merge 4 commits intografana:mainfrom
drtootsie:fix-server-instructions-clarity

Conversation

@drtootsie
Copy link
Copy Markdown

@drtootsie drtootsie commented Feb 15, 2026

Addresses #552

Problem

The MCP server instructions were hardcoded and always listed all capabilities, even when categories were disabled. This caused AI clients to repeatedly attempt using disabled features.

Solution

Made instructions dynamic - they now reflect only enabled categories.

Changes

  • Added buildInstructions() method to dynamically build instructions
  • Added isEnabled() helper to check category status
  • Prometheus & Loki line now adapts based on what's enabled
  • Disabled categories are completely omitted

Examples

With --disable-loki:

  • Before: "Prometheus & Loki: Run PromQL and LogQL queries..."
  • After: "Prometheus: Run PromQL queries..."

With --disable-loki --disable-oncall --disable-incident:
Only enabled categories appear in the instructions.

Impact

AI clients now receive accurate capability information upfront, preventing wasted attempts to use disabled features.


Note

Medium Risk
Moderate risk because it refactors tool-category registration into a centralized map and changes how server WithInstructions is generated, which could inadvertently omit/incorrectly describe capabilities if the mapping drifts from flags.

Overview
Server instructions are no longer hardcoded; they’re now built dynamically from the configured enabled-tools list and --disable-* flags via disabledTools.buildInstructions(), omitting disabled categories and adapting the Prometheus/Loki capability line based on what’s enabled.

Tool registration is refactored to use a single toolCategories() source-of-truth (including category metadata/instruction text) and addTools() now iterates that list instead of calling maybeAddTools per-category.

Written by Cursor Bugbot for commit 9d1d0cd. This will update automatically on new commits. Configure here.

@drtootsie drtootsie requested a review from a team as a code owner February 15, 2026 20:03
@CLAassistant
Copy link
Copy Markdown

CLAassistant commented Feb 15, 2026

CLA assistant check
Thank you for your submission! We really appreciate it. Like many open source projects, we ask that you all sign our Contributor License Agreement before we can accept your contribution.
1 out of 2 committers have signed the CLA.

✅ sd2k
❌ drtootsie
You have signed the CLA already but the status is still pending? Let us recheck it.

Copy link
Copy Markdown
Collaborator

@sd2k sd2k left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I agree that we should do this but I don't like defining another isEnabled function with lots of untyped strings. We already do 'stuff' conditional on each flag being enabled in addTools. I think we could change that to processTools, and wrap each call to maybeAddTools in a function that also builds up the instruction string; that way we only have a single place mapping fields of disabledTools to strings representing the flag.

Addresses grafana#552

The MCP server instructions are now dynamically built based on which
tool categories are actually enabled, preventing AI clients from
repeatedly attempting to use disabled features.

Changes:
- Added buildInstructions() method to disabledTools
- Added isEnabled() helper to check if a category is enabled
- Dynamically builds Prometheus & Loki line based on what's enabled
- Omits disabled categories from instructions entirely

Example: With --disable-loki, instructions now say:
  'Prometheus: Run PromQL queries...'
instead of:
  'Prometheus & Loki: Run PromQL and LogQL queries...'

This significantly improves the client experience by providing accurate
capability information upfront.
@drtootsie drtootsie force-pushed the fix-server-instructions-clarity branch from 02ee4a2 to 2a7a0a1 Compare March 11, 2026 02:50
@zarko-a
Copy link
Copy Markdown

zarko-a commented Mar 18, 2026

Any chance this can move forward?

The issue affects users who have multiple MCP servers in their environment and tooling might be conflicting. For example, ElasticSearch is advertised through Grafana MCP even though the tool is disabled, all along we have another MCP server that offers working ElasticSearch tool. Agents tend to go for the one in Grafana MCP.

sd2k and others added 2 commits March 18, 2026 21:29
Replace the duplicate isEnabled switch and separate buildInstructions
with a shared toolCategories() method that both addTools and
buildInstructions use. This ensures the mapping from disabled flags
to category strings is defined in exactly one place, preventing
the kind of drift the Cursor Bugbot flagged (missing "examples" case).

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Resolve conflicts by incorporating new tool categories from main
(elasticsearch, cloudwatch, runpanelquery) and other changes
(maxLokiLogLimit) into the unified toolCategories() approach.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Copy link
Copy Markdown

@cursor cursor bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Cursor Bugbot has reviewed your changes and found 1 potential issue.

Fix All in Cursor

Bugbot Autofix is ON, but it could not run because the branch was deleted or merged before autofix could start.

Add proxied category to toolCategories() with nil addFunc (since
proxied tools are registered separately in newServer), so the
instruction text appears when proxied tools are enabled. Skip nil
addFunc entries in addTools.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
@sd2k
Copy link
Copy Markdown
Collaborator

sd2k commented Mar 19, 2026

@drtootsie could you please sign the CLA and I can get this merged in? thanks!

@sd2k sd2k added the cla: no Contributor License Agreement is not signed label Mar 26, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

cla: no Contributor License Agreement is not signed

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants