Thanks to visit codestin.com
Credit goes to github.com

Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
63 changes: 36 additions & 27 deletions cmd/mcptools/commands/call.go
Original file line number Diff line number Diff line change
Expand Up @@ -33,33 +33,7 @@ func CallCmd() *cobra.Command {
os.Exit(1)
}

cmdArgs := args
parsedArgs := []string{}
entityName := ""

i := 0
entityExtracted := false

for i < len(cmdArgs) {
switch {
case (cmdArgs[i] == FlagFormat || cmdArgs[i] == FlagFormatShort) && i+1 < len(cmdArgs):
FormatOption = cmdArgs[i+1]
i += 2
case (cmdArgs[i] == FlagParams || cmdArgs[i] == FlagParamsShort) && i+1 < len(cmdArgs):
ParamsString = cmdArgs[i+1]
i += 2
case !entityExtracted:
entityName = cmdArgs[i]
entityExtracted = true
i++
case cmdArgs[i] == FlagServerLogs:
ShowServerLogs = true
i++
default:
parsedArgs = append(parsedArgs, cmdArgs[i])
i++
}
}
parsedArgs, entityName := parseCallArguments(args)

if entityName == "" {
fmt.Fprintln(os.Stderr, "Error: entity name is required")
Expand Down Expand Up @@ -148,3 +122,38 @@ func CallCmd() *cobra.Command {
},
}
}

// fix cyclomatic complexity.
func parseCallArguments(args []string) ([]string, string) {
cmdArgs := args
parsedArgs := []string{}
entityName := ""

i := 0
entityExtracted := false

for i < len(cmdArgs) {
switch {
case (cmdArgs[i] == FlagFormat || cmdArgs[i] == FlagFormatShort) && i+1 < len(cmdArgs):
FormatOption = cmdArgs[i+1]
i += 2
case (cmdArgs[i] == FlagParams || cmdArgs[i] == FlagParamsShort) && i+1 < len(cmdArgs):
ParamsString = cmdArgs[i+1]
i += 2
case !entityExtracted:
entityName = cmdArgs[i]
entityExtracted = true
i++
case cmdArgs[i] == FlagServerLogs:
ShowServerLogs = true
i++
case cmdArgs[i] == FlagVerbose || cmdArgs[i] == FlagVerboseShort:
Verbose = true
i++
default:
parsedArgs = append(parsedArgs, cmdArgs[i])
i++
}
}
return parsedArgs, entityName
}
3 changes: 3 additions & 0 deletions cmd/mcptools/commands/get_prompt.go
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,9 @@ func GetPromptCmd() *cobra.Command {
case cmdArgs[i] == FlagServerLogs:
ShowServerLogs = true
i++
case args[i] == FlagVerbose || args[i] == FlagVerboseShort:
Verbose = true
i++
case !promptExtracted:
promptName = cmdArgs[i]
promptExtracted = true
Expand Down
35 changes: 35 additions & 0 deletions cmd/mcptools/commands/http.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
package commands

import (
"fmt"
"net/http"
"os"
)

var verbose = &http.Client{
Transport: verbosed{http.DefaultTransport},
}

type verbosed struct {
impl http.RoundTripper
}

func verboseHeader(dir byte, header map[string][]string) {
for k, a := range header {
for _, v := range a {
fmt.Fprintf(os.Stderr, "%c %s: %s\n", dir, k, v)
}
}
}

func (v verbosed) RoundTrip(req *http.Request) (*http.Response, error) {
verboseHeader('>', req.Header)
fmt.Fprintf(os.Stderr, "> \n")
resp, err := v.impl.RoundTrip(req)
if resp != nil {
verboseHeader('<', resp.Header)
fmt.Fprintf(os.Stderr, "< \n")
}
fmt.Fprintf(os.Stderr, "\n")
return resp, err
}
5 changes: 5 additions & 0 deletions cmd/mcptools/commands/root.go
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@

// flags.
const (
FlagFormat = "--format"

Check failure on line 12 in cmd/mcptools/commands/root.go

View workflow job for this annotation

GitHub Actions / Run golangci-lint

File is not properly formatted (gofmt)
FlagFormatShort = "-f"
FlagParams = "--params"
FlagParamsShort = "-p"
Expand All @@ -17,6 +17,8 @@
FlagHelpShort = "-h"
FlagServerLogs = "--server-logs"
FlagTransport = "--transport"
FlagVerbose = "--verbose"
FlagVerboseShort = "-v"
)

// entity types.
Expand All @@ -35,6 +37,8 @@
ParamsString string
// ShowServerLogs is a flag to show server logs.
ShowServerLogs bool
// Verbose show http verbose info.
Verbose bool
// TransportOption is the transport option for HTTP connections, valid values are "sse" and "http".
// Default is "http" (streamable HTTP).
TransportOption = "http"
Expand All @@ -52,6 +56,7 @@
cmd.PersistentFlags().StringVarP(&FormatOption, "format", "f", "table", "Output format (table, json, pretty)")
cmd.PersistentFlags().
StringVarP(&ParamsString, "params", "p", "{}", "JSON string of parameters to pass to the tool (for call command)")
cmd.PersistentFlags().BoolVarP(&Verbose, "verbose", "v", false, "Show http verbose info")
cmd.PersistentFlags().StringVar(&TransportOption, "transport", "http", "HTTP transport type (http, sse)")

return cmd
Expand Down
4 changes: 3 additions & 1 deletion cmd/mcptools/commands/shell.go
Original file line number Diff line number Diff line change
Expand Up @@ -231,7 +231,9 @@ func callCommand(thisCmd *cobra.Command, mcpClient *client.Client, commandArgs [
var toolResponse *mcp.CallToolResult
request := mcp.CallToolRequest{}
request.Params.Name = entityName
request.Params.Arguments = params
if len(params) > 0 {
request.Params.Arguments = params // fix unittest "tool_name without params"
}
toolResponse, execErr = mcpClient.CallTool(context.Background(), request)
if execErr == nil && toolResponse != nil {
resp = ConvertJSONToMap(toolResponse)
Expand Down
28 changes: 28 additions & 0 deletions cmd/mcptools/commands/trace.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
package commands

import (
"context"
"crypto/rand"

"github.com/mark3labs/mcp-go/client"
"github.com/mark3labs/mcp-go/client/transport"
"go.opentelemetry.io/otel/propagation"
"go.opentelemetry.io/otel/trace"
)

func generateTraceID() [16]byte {
var traceID [16]byte
_, _ = rand.Read(traceID[:])
return traceID
}

func injectTrace(ctx context.Context) transport.ClientOption {
sc := trace.NewSpanContext(trace.SpanContextConfig{
TraceID: generateTraceID(),
SpanID: trace.SpanID([8]byte{255}),
})
ctx = trace.ContextWithRemoteSpanContext(ctx, sc)
carrier := propagation.MapCarrier{}
propagation.TraceContext{}.Inject(ctx, carrier)
return client.WithHeaders(carrier)
}
11 changes: 9 additions & 2 deletions cmd/mcptools/commands/utils.go
Original file line number Diff line number Diff line change
Expand Up @@ -11,8 +11,8 @@
"github.com/f/mcptools/pkg/alias"
"github.com/f/mcptools/pkg/jsonutils"
"github.com/mark3labs/mcp-go/client"
"github.com/mark3labs/mcp-go/client/transport"
"github.com/mark3labs/mcp-go/mcp"

"github.com/spf13/cobra"
)

Expand Down Expand Up @@ -47,13 +47,17 @@
var err error

if len(args) == 1 && IsHTTP(args[0]) {
opts := []transport.ClientOption{injectTrace(context.Background())}
if Verbose {
opts = append(opts, transport.WithHTTPClient(verbose))
}
// Validate transport option for HTTP URLs
if TransportOption != "http" && TransportOption != "sse" {
return nil, fmt.Errorf("invalid transport option: %s (supported: http, sse)", TransportOption)
}

Check failure on line 58 in cmd/mcptools/commands/utils.go

View workflow job for this annotation

GitHub Actions / Run golangci-lint

File is not properly formatted (gofmt)
if TransportOption == "sse" {
c, err = client.NewSSEMCPClient(args[0])
c, err = client.NewSSEMCPClient(args[0], opts...)
} else {
// Default to streamable HTTP
c, err = client.NewStreamableHttpClient(args[0])
Expand Down Expand Up @@ -121,6 +125,9 @@
case args[i] == FlagServerLogs:
ShowServerLogs = true
i++
case args[i] == FlagVerbose || args[i] == FlagVerboseShort:
Verbose = true
i++
default:
parsedArgs = append(parsedArgs, args[i])
i++
Expand Down
2 changes: 1 addition & 1 deletion cmd/mcptools/commands/version.go
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ import (
// Version information placeholder.
var Version = "dev"

// getHomeDirectory returns the user's home directory
// getHomeDirectory returns the user's home directory.
// Tries HOME first, then falls back to USERPROFILE for Windows.
func getHomeDirectory() string {
homeDir := os.Getenv("HOME")
Expand Down
6 changes: 3 additions & 3 deletions cmd/mcptools/commands/web.go
Original file line number Diff line number Diff line change
Expand Up @@ -1269,20 +1269,20 @@ func handleCall(cache *MCPClientCache) http.HandlerFunc {
defer cache.mutex.Unlock()

switch requestData.Type {
case "tool":
case EntityTypeTool:
var toolResponse *mcp.CallToolResult
request := mcp.CallToolRequest{}
request.Params.Name = requestData.Name
request.Params.Arguments = requestData.Params
toolResponse, callErr = cache.client.CallTool(context.Background(), request)
resp = ConvertJSONToMap(toolResponse)
case "resource":
case EntityTypeRes:
var resourceResponse *mcp.ReadResourceResult
request := mcp.ReadResourceRequest{}
request.Params.URI = requestData.Name
resourceResponse, callErr = cache.client.ReadResource(context.Background(), request)
resp = ConvertJSONToMap(resourceResponse)
case "prompt":
case EntityTypePrompt:
var promptResponse *mcp.GetPromptResult
request := mcp.GetPromptRequest{}
request.Params.Name = requestData.Name
Expand Down
7 changes: 6 additions & 1 deletion go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -3,18 +3,22 @@ module github.com/f/mcptools
go 1.24.1

require (
github.com/mark3labs/mcp-go v0.24.1
github.com/mark3labs/mcp-go v0.32.0
github.com/peterh/liner v1.2.2
github.com/spf13/cobra v1.9.1
github.com/spf13/viper v1.20.1
github.com/stretchr/testify v1.10.0
go.opentelemetry.io/otel v1.29.0
go.opentelemetry.io/otel/trace v1.29.0
golang.org/x/term v0.30.0
golang.org/x/text v0.23.0
)

require (
github.com/davecgh/go-spew v1.1.1 // indirect
github.com/fsnotify/fsnotify v1.8.0 // indirect
github.com/go-logr/logr v1.4.2 // indirect
github.com/go-logr/stdr v1.2.2 // indirect
github.com/go-viper/mapstructure/v2 v2.2.1 // indirect
github.com/google/uuid v1.6.0 // indirect
github.com/inconshreveable/mousetrap v1.1.0 // indirect
Expand All @@ -30,6 +34,7 @@ require (
github.com/spf13/pflag v1.0.6 // indirect
github.com/subosito/gotenv v1.6.0 // indirect
github.com/yosida95/uritemplate/v3 v3.0.2 // indirect
go.opentelemetry.io/otel/metric v1.29.0 // indirect
go.uber.org/atomic v1.9.0 // indirect
go.uber.org/multierr v1.9.0 // indirect
golang.org/x/sys v0.31.0 // indirect
Expand Down
15 changes: 13 additions & 2 deletions go.sum
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,11 @@ github.com/frankban/quicktest v1.14.6 h1:7Xjx+VpznH+oBnejlPUj8oUpdxnVs4f8XU8WnHk
github.com/frankban/quicktest v1.14.6/go.mod h1:4ptaffx2x8+WTWXmUCuVU6aPUX1/Mz7zb5vbUoiM6w0=
github.com/fsnotify/fsnotify v1.8.0 h1:dAwr6QBTBZIkG8roQaJjGof0pp0EeF+tNV7YBP3F/8M=
github.com/fsnotify/fsnotify v1.8.0/go.mod h1:8jBTzvmWwFyi3Pb8djgCCO5IBqzKJ/Jwo8TRcHyHii0=
github.com/go-logr/logr v1.2.2/go.mod h1:jdQByPbusPIv2/zmleS9BjJVeZ6kBagPoEUsqbVz/1A=
github.com/go-logr/logr v1.4.2 h1:6pFjapn8bFcIbiKo3XT4j/BhANplGihG6tvd+8rYgrY=
github.com/go-logr/logr v1.4.2/go.mod h1:9T104GzyrTigFIr8wt5mBrctHMim0Nb2HLGrmQ40KvY=
github.com/go-logr/stdr v1.2.2 h1:hSWxHoqTgW2S2qGc0LTAI563KZ5YKYRhT3MFKZMbjag=
github.com/go-logr/stdr v1.2.2/go.mod h1:mMo/vtBO5dYbehREoey6XUKy/eSumjCCveDpRre4VKE=
github.com/go-viper/mapstructure/v2 v2.2.1 h1:ZAaOCxANMuZx5RCeg0mBdEZk7DZasvvZIxtHqx8aGss=
github.com/go-viper/mapstructure/v2 v2.2.1/go.mod h1:oJDH3BJKyqBA2TXFhDsKDGDTlndYOZ6rGS0BRZIxGhM=
github.com/google/go-cmp v0.6.0 h1:ofyhxvXcZhMsU5ulbFiLKl/XBFqE1GSq7atu8tAmTRI=
Expand All @@ -18,10 +23,10 @@ github.com/kr/pretty v0.3.1 h1:flRD4NNwYAUpkphVc1HcthR4KEIFJ65n8Mw5qdRn3LE=
github.com/kr/pretty v0.3.1/go.mod h1:hoEshYVHaxMs3cyo3Yncou5ZscifuDolrwPKZanG3xk=
github.com/kr/text v0.2.0 h1:5Nx0Ya0ZqY2ygV366QzturHI13Jq95ApcVaJBhpS+AY=
github.com/kr/text v0.2.0/go.mod h1:eLer722TekiGuMkidMxC/pM04lWEeraHUUmBw8l2grE=
github.com/mark3labs/mcp-go v0.23.1 h1:RzTzZ5kJ+HxwnutKA4rll8N/pKV6Wh5dhCmiJUu5S9I=
github.com/mark3labs/mcp-go v0.23.1/go.mod h1:rXqOudj/djTORU/ThxYx8fqEVj/5pvTuuebQ2RC7uk4=
github.com/mark3labs/mcp-go v0.24.1 h1:YV+5X/+W4oBdERLWgiA1uR7AIvenlKJaa5V4hqufI7E=
github.com/mark3labs/mcp-go v0.24.1/go.mod h1:rXqOudj/djTORU/ThxYx8fqEVj/5pvTuuebQ2RC7uk4=
github.com/mark3labs/mcp-go v0.32.0 h1:fgwmbfL2gbd67obg57OfV2Dnrhs1HtSdlY/i5fn7MU8=
github.com/mark3labs/mcp-go v0.32.0/go.mod h1:rXqOudj/djTORU/ThxYx8fqEVj/5pvTuuebQ2RC7uk4=
github.com/mattn/go-runewidth v0.0.3/go.mod h1:LwmH8dsx7+W8Uxz3IHJYH5QSwggIsqBzpuz5H//U1FU=
github.com/mattn/go-runewidth v0.0.16 h1:E5ScNMtiwvlvB5paMFdw9p4kSQzbXFikJ5SQO6TULQc=
github.com/mattn/go-runewidth v0.0.16/go.mod h1:Jdepj2loyihRzMpdS35Xk/zdY8IAYHsh153qUoGf23w=
Expand Down Expand Up @@ -59,6 +64,12 @@ github.com/subosito/gotenv v1.6.0 h1:9NlTDc1FTs4qu0DDq7AEtTPNw6SVm7uBMsUCUjABIf8
github.com/subosito/gotenv v1.6.0/go.mod h1:Dk4QP5c2W3ibzajGcXpNraDfq2IrhjMIvMSWPKKo0FU=
github.com/yosida95/uritemplate/v3 v3.0.2 h1:Ed3Oyj9yrmi9087+NczuL5BwkIc4wvTb5zIM+UJPGz4=
github.com/yosida95/uritemplate/v3 v3.0.2/go.mod h1:ILOh0sOhIJR3+L/8afwt/kE++YT040gmv5BQTMR2HP4=
go.opentelemetry.io/otel v1.29.0 h1:PdomN/Al4q/lN6iBJEN3AwPvUiHPMlt93c8bqTG5Llw=
go.opentelemetry.io/otel v1.29.0/go.mod h1:N/WtXPs1CNCUEx+Agz5uouwCba+i+bJGFicT8SR4NP8=
go.opentelemetry.io/otel/metric v1.29.0 h1:vPf/HFWTNkPu1aYeIsc98l4ktOQaL6LeSoeV2g+8YLc=
go.opentelemetry.io/otel/metric v1.29.0/go.mod h1:auu/QWieFVWx+DmQOUMgj0F8LHWdgalxXqvp7BII/W8=
go.opentelemetry.io/otel/trace v1.29.0 h1:J/8ZNK4XgR7a21DZUAsbF8pZ5Jcw1VhACmnYt39JTi4=
go.opentelemetry.io/otel/trace v1.29.0/go.mod h1:eHl3w0sp3paPkYstJOmAimxhiFXPg+MMTlEh3nsQgWQ=
go.uber.org/atomic v1.9.0 h1:ECmE8Bn/WFTYwEW/bpKD3M8VtR/zQVbavAoalC1PYyE=
go.uber.org/atomic v1.9.0/go.mod h1:fEN4uk6kAWBTFdckzkM89CLk9XfWZrxpCo0nPH17wJc=
go.uber.org/multierr v1.9.0 h1:7fIwc/ZtS0q++VgcfqFDxSBZVv/Xo49/SYnDFupUwlI=
Expand Down
Loading