modelcontextprotocol / modelcontextprotocol/go-sdk

Proposal: Strong Typing for CallTool

Open
#735 5 comments 0 reactions 0 assignees View on GitHub

Nobody has claimed this yet.

needs community feedback
Dominant language
Go
Stars
5.1k
Forks
543
Avg merge
1d 17h
Merged PRs (30d)
37

Description

Is your feature request related to a problem? Please describe.
Currently the CallTool function only handles text output well.
If the Caller expects a specific type e.g. map[string]int or a struct then the Caller has to workaround the current state of the SDK.
This leads to unnecessary CPU and Memory Consumption and that despite of the server side of the SDK handling this scenario so well.

Describe the solution you'd like
There is a variant of my request with and without generics
Without generics, the CallTool function would allow to specify the output reference e.g.
CallTool(..., output any) error
The SDK would then directly unmarshal into the output reference.

Describe alternatives you've considered
So above is not a show stopper, as a workaround exists

Additional context
Here my workaround code:

	result, err := session.CallTool(c.context, &mcp.CallToolParams{
		Name:      toolName,
		Arguments: input,
		Meta:      mcp.Meta{"progressToken": progressToken},
	})
	if err != nil {
		return err
	}
	if result.IsError {
		var errMsg string
		for _, content := range result.Content {
			if tc, ok := content.(*mcp.TextContent); ok {
				if errMsg != "" {
					errMsg += "\n"
				}
				errMsg += tc.Text
			}
		}
		if errMsg == "" {
			errMsg = "tool call failed"
		}
		return errors.New(errMsg)
	}

	if output == nil {
		return nil
	}

	var textContent *mcp.TextContent
	for _, content := range result.Content {
		if tc, ok := content.(*mcp.TextContent); ok {
			textContent = tc
			break
		}
	}

	if textContent == nil {
		return errors.New("unexpected content type in tool result")
	}

	if output != nil {
		if err := json.Unmarshal([]byte(textContent.Text), output); err != nil {
			return err
		}
	}

Needless to say, I dont like it.

Contributor guide

Open the contributing guide

First steps

  1. Read the whole issue, then the project's contributing guide.
  2. Comment on the issue to say you are picking it up — it saves two people doing the same work.
  3. Fork the repository and make your change on a branch.
  4. Open a pull request that references the issue number.

Research direction

Start at the CallTool entry point in the Go SDK and trace how tool results and TextContent are handled. Compare the proposed output-reference and generic variants, then define the supported typed-output behavior and verify it with the SDK's existing tests; done means callers no longer need the shown JSON unmarshal workaround.

Written by the indexing model from the issue text.

Assessment

Tech stack
go
Domain
backend-api-design
Issue type
Feature
Difficulty
5/5
Estimated time
Over a week
Activity status
Stale
Clarity
Mostly clear
Newbie friendliness
35/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.