Skip to content

Commit 46d4204

Browse files
committed
move tool request to mcp_request.go
1 parent 85d7a14 commit 46d4204

File tree

2 files changed

+73
-52
lines changed

2 files changed

+73
-52
lines changed

cmd/src/mcp.go

Lines changed: 5 additions & 52 deletions
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,10 @@
11
package main
22

33
import (
4-
"bytes"
54
"context"
65
"encoding/json"
76
"flag"
87
"fmt"
9-
"io"
10-
"net/http"
118
"strings"
129

1310
"github.com/sourcegraph/src-cli/internal/api"
@@ -16,8 +13,6 @@ import (
1613
"github.com/sourcegraph/sourcegraph/lib/errors"
1714
)
1815

19-
const McpPath = ".api/mcp/v1"
20-
2116
func init() {
2217
flagSet := flag.NewFlagSet("mcp", flag.ExitOnError)
2318
commands = append(commands, &command{
@@ -51,14 +46,14 @@ func mcpMain(args []string) error {
5146
return printSchemas(tool)
5247
}
5348

54-
flags, vars, err := mcp.BuildToolFlagSet(tool)
49+
flags, vars, err := mcp.BuildArgFlagSet(tool)
5550
if err != nil {
5651
return err
5752
}
5853
if err := flags.Parse(flagArgs); err != nil {
5954
return err
6055
}
61-
sanitizeFlagValues(vars)
56+
mcp.DerefFlagValues(vars)
6257

6358
if err := validateToolArgs(tool.InputSchema, args, vars); err != nil {
6459
return err
@@ -97,58 +92,16 @@ func validateToolArgs(inputSchema mcp.Schema, args []string, vars map[string]any
9792
}
9893

9994
func handleMcpTool(ctx context.Context, client api.Client, tool *mcp.ToolDef, vars map[string]any) error {
100-
jsonRPC := struct {
101-
Version string `json:"jsonrpc"`
102-
ID int `json:"id"`
103-
Method string `json:"method"`
104-
Params any `json:"params"`
105-
}{
106-
Version: "2.0",
107-
ID: 1,
108-
Method: "tools/call",
109-
Params: struct {
110-
Name string `json:"name"`
111-
Arguments map[string]any `json:"arguments"`
112-
}{
113-
Name: tool.RawName,
114-
Arguments: vars,
115-
},
116-
}
117-
118-
buf := bytes.NewBuffer(nil)
119-
data, err := json.Marshal(jsonRPC)
120-
if err != nil {
121-
return err
122-
}
123-
buf.Write(data)
124-
125-
req, err := client.NewHTTPRequest(ctx, http.MethodPost, McpPath, buf)
95+
resp, err := mcp.DoToolRequest(ctx, client, tool, vars)
12696
if err != nil {
12797
return err
12898
}
129-
req.Header.Add("Content-Type", "application/json")
130-
req.Header.Add("Accept", "*/*")
13199

132-
resp, err := client.Do(req)
100+
data, err := mcp.ParseToolResponse(ctx, resp)
133101
if err != nil {
134102
return err
135103
}
136104

137-
jsonData, err := parseSSEResponse(data)
138-
if err != nil {
139-
return err
140-
}
141-
142-
fmt.Println(string(jsonData))
105+
fmt.Printf(string(data))
143106
return nil
144107
}
145-
146-
func parseSSEResponse(data []byte) ([]byte, error) {
147-
lines := bytes.SplitSeq(data, []byte("\n"))
148-
for line := range lines {
149-
if jsonData, ok := bytes.CutPrefix(line, []byte("data: ")); ok {
150-
return jsonData, nil
151-
}
152-
}
153-
return nil, errors.New("no data found in SSE response")
154-
}

internal/mcp/mcp_request.go

Lines changed: 68 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,68 @@
1+
package mcp
2+
3+
import (
4+
"bytes"
5+
"context"
6+
"encoding/json"
7+
"io"
8+
"net/http"
9+
10+
"github.com/sourcegraph/sourcegraph/lib/errors"
11+
"github.com/sourcegraph/src-cli/internal/api"
12+
)
13+
14+
const McpURLPath = ".api/mcp/v1"
15+
16+
func DoToolRequest(ctx context.Context, client api.Client, tool *ToolDef, vars map[string]any) (*http.Response, error) {
17+
jsonRPC := struct {
18+
Version string `json:"jsonrpc"`
19+
ID int `json:"id"`
20+
Method string `json:"method"`
21+
Params any `json:"params"`
22+
}{
23+
Version: "2.0",
24+
ID: 1,
25+
Method: "tools/call",
26+
Params: struct {
27+
Name string `json:"name"`
28+
Arguments map[string]any `json:"arguments"`
29+
}{
30+
Name: tool.RawName,
31+
Arguments: vars,
32+
},
33+
}
34+
35+
buf := bytes.NewBuffer(nil)
36+
data, err := json.Marshal(jsonRPC)
37+
if err != nil {
38+
return nil, err
39+
}
40+
buf.Write(data)
41+
42+
req, err := client.NewHTTPRequest(ctx, http.MethodPost, McpURLPath, buf)
43+
if err != nil {
44+
return nil, err
45+
}
46+
req.Header.Add("Content-Type", "application/json")
47+
req.Header.Add("Accept", "*/*")
48+
49+
return client.Do(req)
50+
}
51+
52+
func ParseToolResponse(ctx context.Context, resp *http.Response) ([]byte, error) {
53+
data, err := io.ReadAll(resp.Body)
54+
if err != nil {
55+
return nil, err
56+
}
57+
// The response is an SSE reponse
58+
// event:
59+
// data:
60+
lines := bytes.SplitSeq(data, []byte("\n"))
61+
for line := range lines {
62+
if jsonData, ok := bytes.CutPrefix(line, []byte("data: ")); ok {
63+
return jsonData, nil
64+
}
65+
}
66+
return nil, errors.New("no data found in SSE response")
67+
68+
}

0 commit comments

Comments
 (0)