Skip to content
Merged
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
5 changes: 5 additions & 0 deletions pkg/cli/mcp_server_http.go
Original file line number Diff line number Diff line change
Expand Up @@ -82,6 +82,11 @@ func runHTTPServer(server *mcp.Server, port int) error {
handler := mcp.NewStreamableHTTPHandler(func(req *http.Request) *mcp.Server {
return server
}, &mcp.StreamableHTTPOptions{
// Stateless mode is deliberately left disabled. Stateless servers opt into
// the 2026-07-28 protocol revision but drop session affinity, which the
// long-running logs/audit tools rely on for progress notifications over the
// lifetime of a session. Staying stateful lets the SDK negotiate down to
// 2025-11-25 for peers that still expect the initialize handshake.
SessionTimeout: 2 * time.Hour, // Close idle sessions after 2 hours
DisableLocalhostProtection: false, // Keep the SDK's localhost Host-header checks enabled.
Logger: logger.NewSlogLoggerWithHandler(mcpLog),
Expand Down
130 changes: 130 additions & 0 deletions scratchpad/mods/go-sdk.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,130 @@
# Module: github.com/modelcontextprotocol/go-sdk

## Overview

**go-sdk** is the official Go SDK for the Model Context Protocol (MCP). It provides
server-side primitives (`mcp.NewServer`, `mcp.AddTool`), client-side primitives
(`mcp.NewClient`), and a set of transports (stdio, in-memory, command, and
streamable HTTP).

**Key Characteristics:**

- Official MCP project, maintained jointly by the MCP community and Google
- Type-safe tool registration with automatic JSON-Schema generation (via `google/jsonschema-go`)
- Multiple transports: `StdioTransport`, `CommandTransport`, `InMemoryTransports`, streamable HTTP
- Protocol-revision negotiation with backward compatibility for older peers

## Version Used

Current version in `go.mod`: **v1.7.0** (latest release at time of review)

## Usage in gh-aw

### Files Using This Module

33 files, primarily:

- `pkg/cli/mcp_server.go` — server construction, capabilities, middleware wiring
- `pkg/cli/mcp_server_command.go` — stdio transport entry point
- `pkg/cli/mcp_server_http.go` — streamable HTTP handler and loopback binding
- `pkg/cli/mcp_tools_readonly.go`, `pkg/cli/mcp_tools_privileged.go`, `pkg/cli/mcp_tools_management.go` — tool registration
- `pkg/cli/mcp_argument_validation.go` — receiving middleware for schema-error rewriting
- `pkg/cli/mcp_inspect_mcp.go` — client-side usage for `gh aw mcp inspect`
- `pkg/parser/mcp.go` — MCP config parsing
- plus the corresponding `_test.go` files

### Key Roles

1. **Server** (`mcp_server.go`): builds the `gh aw` MCP server with a static tool set
(status, compile, logs, audit, audit-diff, checks, mcp-inspect, add, update, fix).
`Tools.ListChanged` is `false` because the tool set never changes.
2. **Transports**: `mcp.StdioTransport` for CLI mode and `mcp.NewStreamableHTTPHandler`
for `--http` mode, bound to `127.0.0.1` with a 2 hour `SessionTimeout`.
3. **Client**: `mcp.NewClient` with `CommandTransport` / `StreamableClientTransport` /
`InMemoryTransports` for the `mcp inspect` subcommand and end-to-end tests.
4. **Middleware**: `AddReceivingMiddleware` rewrites raw `additionalProperties` schema
errors into "did you mean?" suggestions.
5. **Progress reporting**: `notifyProgress()` uses `req.Params.GetProgressToken()` and
`Session.NotifyProgress` for long-running tools, no-oping when no token is supplied.
6. **Tool annotations**: `ReadOnlyHint` / `IdempotentHint` / `DestructiveHint` /
`OpenWorldHint` are set consistently on every tool.

## Research Summary

**Repository:** https://github.com/modelcontextprotocol/go-sdk

### Recent Updates (v1.7.0, protocol revision `2026-07-28`)

- **Stateless / sessionless mode** (SEP-2575) — the `initialize` handshake is replaced by
per-request `_meta` plus a `server/discover` RPC.
- **Multi-round-trip requests** (MRTR, SEP-2322) — sampling / elicitation / roots
server-initiated calls are replaced by `InputRequiredResult` + retry.
- **`subscriptions/listen`** — a unified stream replaces the four separate
`*/list_changed` notifications.
- **Cacheable list results** (`ttlMs` / `cacheScope`, SEP-2549).
- **HTTP header standardization** (`Mcp-Method`, `x-mcp-header` passthrough, SEP-2243).
- **Deprecation of roots, sampling, and logging** in the new revision — gh-aw uses none
of these, so there is nothing to migrate.
- Backward compatible: the SDK negotiates down to `2025-11-25` for stateful peers, which
is what gh-aw's HTTP server does today.
- Seven `MCPGODEBUG` escape-hatch flags exist for spec-compliance behavior changes and are
removed in v1.9.0. None are needed by gh-aw, because its usage already matches the new
defaults (for example bare `bool` `ReadOnlyHint` / `IdempotentHint` rather than `*bool`,
which avoids needing `hintomitempty=1`).

### Best Practices Already Observed in gh-aw

- `mcp_server.go` documents that schema caching is automatic in go-sdk v1.3.0+.
- `mcp_tools_privileged.go` explains why the `timeout` parameter deliberately has **no**
static schema default: the SDK would fill it in before the handler runs, short-circuiting
the per-request computed default.
- `mcp_server_http.go` binds to loopback only as defense in depth alongside the SDK's own
Host-header check, noting that the SDK dropped default cross-origin protection in v1.6.0.

## Improvement Opportunities

### Quick Wins

None required — the dependency is pinned to the latest release and usage patterns already
reflect v1.7.0-era defaults rather than legacy `MCPGODEBUG` opt-outs.

### Feature Opportunities

1. **Stateless HTTP mode** (`StreamableHTTPOptions.Stateless = true`) would opt the HTTP
server into the `2026-07-28` protocol revision. Given the deliberate 2 hour
`SessionTimeout` (session affinity for long-running `logs` / `audit` calls), staying
stateful remains the right call for now.
2. **Custom JSON-RPC method registration** (new in v1.7.0) — no current need, but available
if gh-aw ever wants a lightweight non-tool RPC endpoint.
3. **`x-mcp-header` passthrough** for `logs` / `audit` tool params — only relevant if the
HTTP server is ever placed behind a reverse proxy; the server is loopback-only today.

### Best Practice Alignment

- Correct annotation types (bare `bool` hints matching the v1.7.0 defaults)
- Deliberate avoidance of premature schema defaults
- In-code comments tracking SDK version-specific behavior

## Recommendations

1. No action needed this cycle — the module is current and usage is idiomatic.
2. Keep the `Stateless` HTTP mode decision on the radar if the MCP ecosystem drops support
for stateful sessions on newer protocol revisions.
3. Continue the practice of commenting *why* an SDK default is or is not used (for example
the `timeout` schema default) — it has already prevented a subtle bug class.

## References

- **Package Documentation:** https://pkg.go.dev/github.com/modelcontextprotocol/go-sdk/mcp
- **Repository:** https://github.com/modelcontextprotocol/go-sdk
- **Releases:** https://github.com/modelcontextprotocol/go-sdk/releases
- **MCP Specification:** https://modelcontextprotocol.io/specification

---

**Last Reviewed:** 2026-08-18
**Module Version:** v1.7.0
Comment on lines +125 to +126

---

*This summary was generated based on Go Fan analysis methodology. For the latest information, always check the upstream repository.*