diff --git a/docs/plans/2026-03-21-mcp-sdk-migration.md b/docs/plans/2026-03-21-mcp-sdk-migration.md new file mode 100644 index 0000000..4bcda7c --- /dev/null +++ b/docs/plans/2026-03-21-mcp-sdk-migration.md @@ -0,0 +1,414 @@ +# Migration Plan: Official MCP SDK → mcp-go + +**Date:** 2026-03-21 +**Status:** Draft +**Motivation:** The official SDK (`github.com/modelcontextprotocol/go-sdk`) has unexported fields that make custom notifications impossible. We need `claude/channel` support (experimental capability) so the server can push events (inbox messages, dispatch completions, webhook events) into a running Claude Code session. `mcp-go` (`github.com/mark3labs/mcp-go`) exposes `SendNotificationToClient` and `SendNotificationToAllClients` plus full session management. + +**Breaking change risk:** 2 consumers (`agent`, `ide`) import `forge.lthn.ai/core/mcp` — both expose the `Subsystem` interface which references `*mcp.Server`. + +--- + +## 1. SDK Comparison — Key Differences + +### Package layout + +| Concept | Official SDK | mcp-go | +|---------|-------------|--------| +| Types import | `github.com/modelcontextprotocol/go-sdk/mcp` | `github.com/mark3labs/mcp-go/mcp` | +| Server import | same package | `github.com/mark3labs/mcp-go/server` | +| JSON-RPC | `github.com/modelcontextprotocol/go-sdk/jsonrpc` | Not exported (internal) | + +### Server creation + +| | Official SDK | mcp-go | +|-|-------------|--------| +| Constructor | `mcp.NewServer(&mcp.Implementation{Name, Version}, nil)` | `server.NewMCPServer("name", "version", ...options)` | +| Return type | `*mcp.Server` | `*server.MCPServer` | +| Capabilities | Set via `ServerOptions` (2nd arg) | `server.WithToolCapabilities(bool)`, `server.WithRecovery()`, etc. | + +### Tool definition + +| | Official SDK | mcp-go | +|-|-------------|--------| +| Struct | `&mcp.Tool{Name: "...", Description: "..."}` | `mcp.NewTool("name", mcp.WithDescription("..."), mcp.WithString("param", mcp.Required()), ...)` | +| Schema | Auto-generated from Go struct tags via reflection (our `addToolRecorded` pattern) | Must be declared explicitly with `WithString`/`WithNumber`/`WithBoolean`/`WithObject`/`WithArray` builders, OR supply raw `InputSchema` | + +### Tool registration + +| | Official SDK | mcp-go | +|-|-------------|--------| +| Function | `mcp.AddTool(server, tool, handler)` — package-level generic function | `s.AddTool(tool, handler)` — method on `*server.MCPServer` | +| Handler signature | `func(ctx, *mcp.CallToolRequest, In) (*mcp.CallToolResult, Out, error)` — 3 returns, generic typed input | `func(ctx, mcp.CallToolRequest) (*mcp.CallToolResult, error)` — 2 returns, untyped input | +| Input access | Auto-deserialized into typed `In` struct | `request.RequireString("name")`, `request.GetString("name", default)`, or manual `request.Params.Arguments["key"]` | +| Result helpers | Return `*mcp.CallToolResult` with `Content` slice | `mcp.NewToolResultText("...")`, `mcp.NewToolResultError("...")` | + +### Transports + +| | Official SDK | mcp-go | +|-|-------------|--------| +| Stdio | `server.Run(ctx, &mcp.StdioTransport{})` | `server.ServeStdio(s)` — top-level function | +| HTTP | `mcp.NewStreamableHTTPHandler(factory, opts)` | `server.NewStreamableHTTPServer(s, opts...)` | +| SSE | N/A | `server.NewSSEServer(s, opts...)` | +| TCP | Custom `Transport`/`Connection` impl | No built-in TCP — must implement or wrap | + +### Session & Notifications (the reason for migration) + +| | Official SDK | mcp-go | +|-|-------------|--------| +| Session access | Not exposed | `server.ClientSessionFromContext(ctx)`, `server.GetSessionID(ctx)` | +| Server from handler | Not available | `server.ServerFromContext(ctx)` | +| Push to client | Not possible (unexported) | `mcpServer.SendNotificationToClient(ctx, method, params)` | +| Broadcast | Not possible | `mcpServer.SendNotificationToAllClients(method, params)` | +| Session hooks | None | `hooks.AddOnRegisterSession(...)`, `hooks.AddOnUnregisterSession(...)` | +| Per-session tools | None | `s.AddSessionTool(sessionID, tool, handler)`, `s.DeleteSessionTools(...)` | + +--- + +## 2. Architectural Decisions + +### 2a. Handler signature adapter + +The biggest change: every tool handler must change from 3-return generic to 2-return untyped. Two approaches: + +**Option A — Direct rewrite:** Change every handler to `func(ctx, mcp.CallToolRequest) (*mcp.CallToolResult, error)`. Manually unmarshal input from `request.Params.Arguments` and marshal output via `mcp.NewToolResultText(json)`. + +**Option B — Adapter pattern (recommended):** Write a generic adapter that preserves the current handler signatures: + +```go +// adaptHandler wraps a typed handler for use with mcp-go. +func adaptHandler[In, Out any](h func(ctx context.Context, req mcp.CallToolRequest, input In) (*mcp.CallToolResult, Out, error)) server.ToolHandler { + return func(ctx context.Context, req mcp.CallToolRequest) (*mcp.CallToolResult, error) { + var input In + data, _ := json.Marshal(req.Params.Arguments) + if err := json.Unmarshal(data, &input); err != nil { + return mcp.NewToolResultError("invalid input: " + err.Error()), nil + } + result, output, err := h(ctx, req, input) + if err != nil { + return nil, err + } + if result != nil { + return result, nil + } + // Marshal output to JSON text result + outJSON, _ := json.Marshal(output) + return mcp.NewToolResultText(string(outJSON)), nil + } +} +``` + +This lets us keep every handler's current signature (including the REST bridge) and migrates only the registration layer. The handler `req` param changes from `*mcp.CallToolRequest` (pointer) to `mcp.CallToolRequest` (value) — a minor type change. + +### 2b. Tool schema declaration + +Current approach uses `addToolRecorded` with reflection-based `structSchema()`. With mcp-go, two options: + +**Option A — Builder API:** Rewrite each tool's schema using `mcp.WithString(...)`, `mcp.WithNumber(...)`, etc. Tedious (40+ tools) but idiomatic. + +**Option B — Raw InputSchema (recommended):** `mcp.NewTool` accepts a raw `InputSchema` option. Feed the existing `structSchema()` output directly: + +```go +mcp.NewTool("file_read", + mcp.WithDescription("Read the contents of a file"), + mcp.WithRawSchema(structSchema(new(ReadFileInput))), +) +``` + +If `WithRawSchema` doesn't exist, the `mcp.Tool` struct likely has an `InputSchema` field we can set after construction. This preserves the reflection-based schema generation. + +### 2c. REST bridge (`addToolRecorded`) + +The `addToolRecorded` generic function currently: +1. Calls `mcp.AddTool(server, tool, handler)` — registers with MCP +2. Creates a `RESTHandler` closure — for the REST bridge +3. Reflects `In`/`Out` types for JSON Schema — for API docs + +With mcp-go, step 1 changes to `s.AddTool(tool, adaptHandler(h))`. Steps 2 and 3 remain unchanged. The `ToolRecord` struct and `RESTHandler` pattern are internal to our code, not SDK types. + +### 2d. TCP transport + +The official SDK exposes `mcp.Transport` and `mcp.Connection` interfaces. Our `connTransport` implements these. mcp-go doesn't have equivalent interfaces. Options: + +**Option A — Wrap stdio over TCP:** Pipe TCP conn's reader/writer into mcp-go's stdio transport. + +**Option B — Use StreamableHTTP:** Replace TCP with HTTP transport (mcp-go has built-in support). This is architecturally cleaner for multi-client scenarios. + +**Option C — Implement custom transport:** mcp-go's `server` package may expose transport interfaces. Investigate at implementation time. + +### 2e. Subsystem interface + +The `Subsystem` interface exposes `RegisterTools(server *mcp.Server)`. This must change to `RegisterTools(server *server.MCPServer)`. This is a **breaking change for consumers** (`agent`, `ide`). + +--- + +## 3. File-by-File Migration Plan + +### Phase 1 — Core types and registration (foundation) + +#### `go.mod` +- **Remove:** `github.com/modelcontextprotocol/go-sdk v1.4.1` +- **Add:** `github.com/mark3labs/mcp-go v1.x.x` (latest stable) +- **Remove:** `github.com/modelcontextprotocol/go-sdk/jsonrpc` indirect (if present) + +#### `pkg/mcp/subsystem.go` +- **Old import:** `github.com/modelcontextprotocol/go-sdk/mcp` +- **New imports:** `github.com/mark3labs/mcp-go/mcp` + `github.com/mark3labs/mcp-go/server` +- **Change:** `RegisterTools(server *mcp.Server)` → `RegisterTools(server *server.MCPServer)` +- **Impact:** Breaking change for `Subsystem` interface consumers (`agent`, `ide` modules) + +#### `pkg/mcp/registry.go` +- **Old import:** `github.com/modelcontextprotocol/go-sdk/mcp` +- **New imports:** `github.com/mark3labs/mcp-go/mcp` + `github.com/mark3labs/mcp-go/server` +- **Changes:** + - `addToolRecorded[In, Out]()` signature: `server *mcp.Server` → `server *server.MCPServer` + - Replace `mcp.AddTool(server, t, h)` → `server.AddTool(tool, adaptHandler(h))` + - Tool construction: `&mcp.Tool{Name, Description}` → `mcp.NewTool(name, mcp.WithDescription(desc))` with schema attached + - `mcp.ToolHandlerFor[In, Out]` type param → custom type alias (mcp-go has no generic handler type) + - `RESTHandler` closure stays (internal to our code, not SDK) + - `structSchema()` stays (used for REST bridge schema generation) + +#### `pkg/mcp/mcp.go` +- **Old import:** `github.com/modelcontextprotocol/go-sdk/mcp` +- **New imports:** `github.com/mark3labs/mcp-go/mcp` + `github.com/mark3labs/mcp-go/server` +- **Changes:** + - `Service.server` field: `*mcp.Server` → `*server.MCPServer` + - `New()`: replace `mcp.NewServer(impl, nil)` → `server.NewMCPServer("core-cli", "0.1.0", server.WithToolCapabilities(true))` + - `Server()` return type: `*mcp.Server` → `*server.MCPServer` + - `Run()`: replace `s.server.Run(ctx, &mcp.StdioTransport{})` → `server.ServeStdio(s.server)` + - `registerTools()` param: `server *mcp.Server` → `server *server.MCPServer` + - All `addToolRecorded(s, server, group, &mcp.Tool{...}, handler)` calls → updated tool construction + - All handler signatures: `*mcp.CallToolRequest` → `mcp.CallToolRequest` (pointer → value) + +### Phase 2 — Transports + +#### `pkg/mcp/transport_stdio.go` +- **Old import:** `github.com/modelcontextprotocol/go-sdk/mcp` +- **New import:** `github.com/mark3labs/mcp-go/server` +- **Change:** `s.server.Run(ctx, &mcp.StdioTransport{})` → `server.ServeStdio(s.server)` +- **Note:** `ServeStdio` is a blocking function, same as `Run`. Context cancellation may need different handling (investigate mcp-go's stdio shutdown). + +#### `pkg/mcp/transport_http.go` +- **Old import:** `github.com/modelcontextprotocol/go-sdk/mcp` +- **New import:** `github.com/mark3labs/mcp-go/server` +- **Changes:** + - Replace `mcp.NewStreamableHTTPHandler(factory, opts)` → `server.NewStreamableHTTPServer(s.server, opts...)` + - mcp-go's HTTP server may handle auth differently — investigate built-in auth options vs keeping our `withAuth` wrapper + - `StreamableHTTPOptions{SessionTimeout}` → check mcp-go equivalent options + - The factory function `func(r *http.Request) *mcp.Server` pattern may not exist — mcp-go likely uses a single server instance + +#### `pkg/mcp/transport_tcp.go` +- **Old imports:** `github.com/modelcontextprotocol/go-sdk/jsonrpc` + `github.com/modelcontextprotocol/go-sdk/mcp` +- **New imports:** `github.com/mark3labs/mcp-go/server` (+ potentially mcp-go internals) +- **Changes:** + - **Critical:** `connTransport` implements `mcp.Transport` interface — no equivalent in mcp-go + - **Critical:** `connConnection` implements `mcp.Connection` with `Read`/`Write`/`Close`/`SessionID` — no equivalent + - `handleConnection()` creates per-connection `mcp.NewServer` + registers tools — must use mcp-go equivalent + - `jsonrpc.DecodeMessage`/`jsonrpc.EncodeMessage` — no public equivalent in mcp-go + - **Decision needed:** Replace TCP with HTTP transport, OR implement custom transport adapter + - Per-connection server instances: `mcp.NewServer()` → `server.NewMCPServer()` + re-register tools + - `mcp.Implementation{Name, Version}` struct literal → string args to `NewMCPServer` + +#### `pkg/mcp/transport_unix.go` +- **No direct SDK import** — delegates to `handleConnection()` from `transport_tcp.go` +- **Impact:** Inherits whatever transport approach we choose for TCP +- **No changes** if we keep the `handleConnection()` pattern + +### Phase 3 — Tool files (mechanical changes) + +All tool files follow the same pattern. For each: +1. Change import from `github.com/modelcontextprotocol/go-sdk/mcp` → `github.com/mark3labs/mcp-go/mcp` + `github.com/mark3labs/mcp-go/server` +2. Change handler param `*mcp.CallToolRequest` → `mcp.CallToolRequest` (pointer → value) +3. Change registration calls from `mcp.AddTool(server, &mcp.Tool{...}, handler)` → `server.AddTool(tool, adaptedHandler)` +4. Change `registerXTools(server *mcp.Server)` → `registerXTools(server *server.MCPServer)` + +#### `pkg/mcp/tools_metrics.go` +- `registerMetricsTools(server *mcp.Server)` → `registerMetricsTools(server *server.MCPServer)` +- 2 tool registrations: `metrics_record`, `metrics_query` +- Uses `mcp.AddTool` directly (not `addToolRecorded`) — change to `server.AddTool` + +#### `pkg/mcp/tools_process.go` +- `registerProcessTools(server *mcp.Server) bool` → `registerProcessTools(server *server.MCPServer) bool` +- 6 tool registrations: `process_start`, `process_stop`, `process_kill`, `process_list`, `process_output`, `process_input` +- Uses `mcp.AddTool` directly + +#### `pkg/mcp/tools_rag.go` +- `registerRAGTools(server *mcp.Server)` → `registerRAGTools(server *server.MCPServer)` +- 3 tool registrations: `rag_query`, `rag_ingest`, `rag_collections` +- Uses `mcp.AddTool` directly + +#### `pkg/mcp/tools_webview.go` +- `registerWebviewTools(server *mcp.Server)` → `registerWebviewTools(server *server.MCPServer)` +- 10 tool registrations: `webview_connect` through `webview_wait` +- Uses `mcp.AddTool` directly + +#### `pkg/mcp/tools_ws.go` +- `registerWSTools(server *mcp.Server) bool` → `registerWSTools(server *server.MCPServer) bool` +- 2 tool registrations: `ws_start`, `ws_info` +- Uses `mcp.AddTool` directly + +### Phase 4 — Subsystem packages + +#### `pkg/mcp/ide/ide.go` +- **Old import:** `github.com/modelcontextprotocol/go-sdk/mcp` +- **New imports:** `github.com/mark3labs/mcp-go/mcp` + `github.com/mark3labs/mcp-go/server` +- `RegisterTools(server *mcp.Server)` → `RegisterTools(server *server.MCPServer)` + +#### `pkg/mcp/ide/tools_build.go` +- `registerBuildTools(server *mcp.Server)` → `registerBuildTools(server *server.MCPServer)` +- 3 tools, handler signatures change `*mcp.CallToolRequest` → `mcp.CallToolRequest` + +#### `pkg/mcp/ide/tools_chat.go` +- `registerChatTools(server *mcp.Server)` → `registerChatTools(server *server.MCPServer)` +- 5 tools, handler signatures change + +#### `pkg/mcp/ide/tools_dashboard.go` +- `registerDashboardTools(server *mcp.Server)` → `registerDashboardTools(server *server.MCPServer)` +- 3 tools, handler signatures change + +#### `pkg/mcp/brain/brain.go` +- `RegisterTools(server *mcp.Server)` → `RegisterTools(server *server.MCPServer)` + +#### `pkg/mcp/brain/tools.go` +- `registerBrainTools(server *mcp.Server)` → `registerBrainTools(server *server.MCPServer)` +- 4 tools: `brain_remember`, `brain_recall`, `brain_forget`, `brain_list` +- Handler signatures change + +#### `pkg/mcp/brain/direct.go` +- `RegisterTools(server *mcp.Server)` → `RegisterTools(server *server.MCPServer)` +- 3 tools: `brain_remember`, `brain_recall`, `brain_forget` +- Handler signatures change + +### Phase 5 — Agentic subsystem + +#### `pkg/mcp/agentic/prep.go` +- `RegisterTools(server *mcp.Server)` → `RegisterTools(server *server.MCPServer)` +- Registers `agentic_prep_workspace` + `agentic_scan` + delegates to sub-registration functions +- Handler signatures change + +#### `pkg/mcp/agentic/dispatch.go` +- `registerDispatchTool(server *mcp.Server)` → `registerDispatchTool(server *server.MCPServer)` +- 1 tool: `agentic_dispatch` + +#### `pkg/mcp/agentic/status.go` +- `registerStatusTool(server *mcp.Server)` → `registerStatusTool(server *server.MCPServer)` +- 1 tool: `agentic_status` + +#### `pkg/mcp/agentic/scan.go` +- Handler signature change only (registration is in `prep.go`) + +#### `pkg/mcp/agentic/resume.go` +- `registerResumeTool(server *mcp.Server)` → `registerResumeTool(server *server.MCPServer)` +- 1 tool: `agentic_resume` + +#### `pkg/mcp/agentic/plan.go` +- `registerPlanTools(server *mcp.Server)` → `registerPlanTools(server *server.MCPServer)` +- 5 tools: `agentic_plan_create`, `agentic_plan_read`, `agentic_plan_update`, `agentic_plan_delete`, `agentic_plan_list` + +#### `pkg/mcp/agentic/pr.go` +- `registerCreatePRTool(server *mcp.Server)` → `registerCreatePRTool(server *server.MCPServer)` +- `registerListPRsTool(server *mcp.Server)` → `registerListPRsTool(server *server.MCPServer)` +- 2 tools: `agentic_create_pr`, `agentic_list_prs` + +#### `pkg/mcp/agentic/epic.go` +- `registerEpicTool(server *mcp.Server)` → `registerEpicTool(server *server.MCPServer)` +- 1 tool: `agentic_create_epic` + +### Phase 6 — Bridge (no SDK changes) + +#### `pkg/mcp/bridge.go` +- **No MCP SDK import** — uses `gin` and `api` only +- **No changes needed** — the REST bridge consumes `ToolRecord` which is our own type + +### Phase 7 — Tests + +All test files that import the SDK need the same import swap and type changes. Key test files: +- `pkg/mcp/subsystem_test.go` — references `*mcp.Server` +- `pkg/mcp/registry_test.go` — tests `addToolRecorded` +- `pkg/mcp/mcp_test.go` — creates `Service` +- `pkg/mcp/bridge_test.go` — tests REST bridge +- `pkg/mcp/transport_tcp_test.go` — tests TCP transport +- `pkg/mcp/transport_e2e_test.go` — end-to-end transport tests +- `pkg/mcp/tools_*_test.go` — tool handler tests +- `pkg/mcp/ide/bridge_test.go`, `pkg/mcp/ide/tools_test.go` +- `pkg/mcp/brain/brain_test.go` + +--- + +## 4. Breaking Changes & Risks + +### No direct equivalent + +| Feature | Official SDK | mcp-go | Mitigation | +|---------|-------------|--------|------------| +| Generic typed handlers | `ToolHandlerFor[In, Out]` | None — untyped `ToolHandler` | Write `adaptHandler[In, Out]()` adapter (section 2a) | +| Auto input schema from structs | Via `addToolRecorded` reflection | Must declare or supply raw schema | Keep `structSchema()` + attach via raw schema option (section 2b) | +| TCP transport interfaces | `mcp.Transport`, `mcp.Connection` | Not exposed | Replace TCP with HTTP, or implement adapter (section 2d) | +| JSON-RPC codec | `jsonrpc.DecodeMessage`/`EncodeMessage` | Not exposed | Only needed for TCP — goes away if TCP is replaced | +| Per-connection server instances | `mcp.NewServer()` per TCP conn | Single `MCPServer` with sessions | Use mcp-go's session model (section 2d) | +| `*mcp.CallToolRequest` (pointer) | Used in all handlers | `mcp.CallToolRequest` (value) | Mechanical change in all handler signatures | + +### Consumer impact + +The `Subsystem` interface change (`*mcp.Server` → `*server.MCPServer`) breaks: +- `agent` module — must update its subsystem implementations +- `ide` module — must update its subsystem implementations + +**Mitigation:** Coordinate the migration. Update `forge.lthn.ai/core/mcp` first, then update consumers to match. + +### New capabilities unlocked + +After migration, the following become possible: +- `server.ServerFromContext(ctx)` — access server from any tool handler +- `SendNotificationToClient(ctx, "claude/channel", payload)` — push events to Claude Code +- `SendNotificationToAllClients("claude/channel", payload)` — broadcast to all sessions +- Session hooks for connection tracking and cleanup +- Per-session tool registration (different tools for different clients) + +--- + +## 5. Migration Order (Recommended) + +1. **Phase 1:** Core types (`subsystem.go`, `registry.go`, `mcp.go`) — establishes the foundation +2. **Phase 2:** Transports (`transport_stdio.go`, `transport_http.go`, `transport_tcp.go`) — the riskiest phase +3. **Phase 3:** Tool files (mechanical, low risk) — `tools_metrics.go`, `tools_process.go`, `tools_rag.go`, `tools_webview.go`, `tools_ws.go` +4. **Phase 4:** IDE subsystem (`ide/`) +5. **Phase 5:** Brain subsystem (`brain/`) +6. **Phase 6:** Agentic subsystem (`agentic/`) +7. **Phase 7:** Tests — update in parallel with each phase +8. **Phase 8:** Consumer modules (`agent`, `ide`) — update after core module is published + +Each phase should be a separate commit. Build must pass after each phase. + +--- + +## 6. Estimated Scope + +| Category | Files | Tools | +|----------|-------|-------| +| Core (mcp.go, registry.go, subsystem.go) | 3 | — | +| Transports | 4 | — | +| Tool files (pkg/mcp/) | 5 | 23 tools | +| IDE subsystem | 4 | 11 tools | +| Brain subsystem | 3 | 7 tools | +| Agentic subsystem | 8 | 14 tools | +| Tests | ~12 | — | +| **Total** | **~39 files** | **55 tools** | + +--- + +## 7. Checklist + +- [ ] Verify `mcp-go` latest version supports `InputSchema` raw attachment +- [ ] Confirm `mcp-go`'s `CallToolRequest` field layout matches our assumptions +- [ ] Investigate mcp-go's stdio shutdown/context cancellation behaviour +- [ ] Decide: TCP transport → HTTP replacement or custom adapter +- [ ] Investigate mcp-go's HTTP server auth options (keep `withAuth` or use built-in) +- [ ] Write `adaptHandler[In, Out]()` generic adapter +- [ ] Write tool schema attachment helper (raw JSON Schema → `mcp.NewTool`) +- [ ] Update `addToolRecorded` to use new registration API +- [ ] Migrate all 55 tool registrations +- [ ] Update all handler signatures (`*mcp.CallToolRequest` → `mcp.CallToolRequest`) +- [ ] Update `Subsystem` interface + all implementations +- [ ] Update consumer modules (`agent`, `ide`) +- [ ] Run full test suite +- [ ] Add notification support (the whole point of the migration) diff --git a/go.mod b/go.mod index e053acd..e231f69 100644 --- a/go.mod +++ b/go.mod @@ -3,16 +3,16 @@ module forge.lthn.ai/core/mcp go 1.26.0 require ( - forge.lthn.ai/core/api v0.1.3 - forge.lthn.ai/core/cli v0.3.5 - forge.lthn.ai/core/go v0.3.1 - forge.lthn.ai/core/go-ai v0.1.11 - forge.lthn.ai/core/go-io v0.1.5 + forge.lthn.ai/core/api v0.1.5 + forge.lthn.ai/core/cli v0.3.7 + forge.lthn.ai/core/go v0.3.3 + forge.lthn.ai/core/go-ai v0.1.12 + forge.lthn.ai/core/go-io v0.1.7 forge.lthn.ai/core/go-log v0.0.4 - forge.lthn.ai/core/go-process v0.2.7 - forge.lthn.ai/core/go-rag v0.1.9 - forge.lthn.ai/core/go-webview v0.1.5 - forge.lthn.ai/core/go-ws v0.2.3 + forge.lthn.ai/core/go-process v0.2.9 + forge.lthn.ai/core/go-rag v0.1.11 + forge.lthn.ai/core/go-webview v0.1.6 + forge.lthn.ai/core/go-ws v0.2.5 github.com/gin-gonic/gin v1.12.0 github.com/gorilla/websocket v1.5.3 github.com/modelcontextprotocol/go-sdk v1.4.1 @@ -21,8 +21,8 @@ require ( ) require ( - forge.lthn.ai/core/go-i18n v0.1.5 // indirect - forge.lthn.ai/core/go-inference v0.1.4 // indirect + forge.lthn.ai/core/go-i18n v0.1.7 // indirect + forge.lthn.ai/core/go-inference v0.1.6 // indirect github.com/99designs/gqlgen v0.17.88 // indirect github.com/KyleBanks/depth v1.2.1 // indirect github.com/agnivade/levenshtein v1.2.1 // indirect @@ -31,7 +31,7 @@ require ( github.com/bahlo/generic-list-go v0.2.0 // indirect github.com/bmatcuk/doublestar/v4 v4.10.0 // indirect github.com/buger/jsonparser v1.1.1 // indirect - github.com/bytedance/gopkg v0.1.3 // indirect + github.com/bytedance/gopkg v0.1.4 // indirect github.com/bytedance/sonic v1.15.0 // indirect github.com/bytedance/sonic/loader v0.5.0 // indirect github.com/casbin/casbin/v2 v2.135.0 // indirect @@ -103,7 +103,7 @@ require ( github.com/muesli/ansi v0.0.0-20230316100256-276c6243b2f6 // indirect github.com/muesli/cancelreader v0.2.2 // indirect github.com/muesli/termenv v0.16.0 // indirect - github.com/ollama/ollama v0.18.0 // indirect + github.com/ollama/ollama v0.18.1 // indirect github.com/pelletier/go-toml/v2 v2.2.4 // indirect github.com/pmezard/go-difflib v1.0.1-0.20181226105442-5d4384ee4fb2 // indirect github.com/qdrant/go-client v1.17.1 // indirect diff --git a/go.sum b/go.sum index db1806e..cba2eb1 100644 --- a/go.sum +++ b/go.sum @@ -1,27 +1,27 @@ -forge.lthn.ai/core/api v0.1.3 h1:iYmNP6zK5SiNRunYEsXPvjppTh3bQADkMyoCC8lEs48= -forge.lthn.ai/core/api v0.1.3/go.mod h1:dBOZc6DS0HdnTfCJZ8FkZxWJio2cIf0d1UrCAlDanrA= -forge.lthn.ai/core/cli v0.3.5 h1:P7yK0DmSA1QnUMFuCjJZf/fk/akKPIxopQ6OwD8Sar8= -forge.lthn.ai/core/cli v0.3.5/go.mod h1:SeArHx+hbpX5iZqgASCD7Q1EDoc6uaaGiGBotmNzIx4= -forge.lthn.ai/core/go v0.3.1 h1:5FMTsUhLcxSr07F9q3uG0Goy4zq4eLivoqi8shSY4UM= -forge.lthn.ai/core/go v0.3.1/go.mod h1:gE6c8h+PJ2287qNhVUJ5SOe1kopEwHEquvinstpuyJc= -forge.lthn.ai/core/go-ai v0.1.11 h1:EJ3XIVg7NcLSPoOCX8I1YGso+uxtVVujafRyShXPAEA= -forge.lthn.ai/core/go-ai v0.1.11/go.mod h1:5Pc9lszxgkO7Aj2Z3dtq4L9Xk9l/VNN+Baj1t///OCM= -forge.lthn.ai/core/go-i18n v0.1.5 h1:B4hV4eTl63akZiplM8lswuttctrcSOCWyFSGBZmu6Nc= -forge.lthn.ai/core/go-i18n v0.1.5/go.mod h1:hJsUxmqdPly73i3VkTDxvmbrpjxSd65hQVQqWA3+fnM= -forge.lthn.ai/core/go-inference v0.1.4 h1:fuAgWbqsEDajHniqAKyvHYbRcBrkGEiGSqR2pfTMRY0= -forge.lthn.ai/core/go-inference v0.1.4/go.mod h1:jfWz+IJX55wAH98+ic6FEqqGB6/P31CHlg7VY7pxREw= -forge.lthn.ai/core/go-io v0.1.5 h1:+XJ1YhaGGFLGtcNbPtVlndTjk+pO0Ydi2hRDj5/cHOM= -forge.lthn.ai/core/go-io v0.1.5/go.mod h1:FRtXSsi8W+U9vewCU+LBAqqbIj3wjXA4dBdSv3SAtWI= +forge.lthn.ai/core/api v0.1.5 h1:NwZrcOyBjaiz5/cn0n0tnlMUodi8Or6FHMx59C7Kv2o= +forge.lthn.ai/core/api v0.1.5/go.mod h1:PBnaWyOVXSOGy+0x2XAPUFMYJxQ2CNhppia/D06ZPII= +forge.lthn.ai/core/cli v0.3.7 h1:1GrbaGg0wDGHr6+klSbbGyN/9sSbHvFbdySJznymhwg= +forge.lthn.ai/core/cli v0.3.7/go.mod h1:DBUppJkA9P45ZFGgI2B8VXw1rAZxamHoI/KG7fRvTNs= +forge.lthn.ai/core/go v0.3.3 h1:kYYZ2nRYy0/Be3cyuLJspRjLqTMxpckVyhb/7Sw2gd0= +forge.lthn.ai/core/go v0.3.3/go.mod h1:Cp4ac25pghvO2iqOu59t1GyngTKVOzKB5/VPdhRi9CQ= +forge.lthn.ai/core/go-ai v0.1.12 h1:OHt0bUABlyhvgxZxyMwueRoh8rS3YKWGFY6++zCAwC8= +forge.lthn.ai/core/go-ai v0.1.12/go.mod h1:5Pc9lszxgkO7Aj2Z3dtq4L9Xk9l/VNN+Baj1t///OCM= +forge.lthn.ai/core/go-i18n v0.1.7 h1:aHkAoc3W8fw3RPNvw/UszQbjyFWXHszzbZgty3SwyAA= +forge.lthn.ai/core/go-i18n v0.1.7/go.mod h1:0VDjwtY99NSj2iqwrI09h5GUsJeM9s48MLkr+/Dn4G8= +forge.lthn.ai/core/go-inference v0.1.6 h1:ce42zC0zO8PuISUyAukAN1NACEdWp5wF1mRgnh5+58E= +forge.lthn.ai/core/go-inference v0.1.6/go.mod h1:jfWz+IJX55wAH98+ic6FEqqGB6/P31CHlg7VY7pxREw= +forge.lthn.ai/core/go-io v0.1.7 h1:Tdb6sqh+zz1lsGJaNX9RFWM6MJ/RhSAyxfulLXrJsbk= +forge.lthn.ai/core/go-io v0.1.7/go.mod h1:8lRLFk4Dnp5cR/Cyzh9WclD5566TbpdRgwcH7UZLWn4= forge.lthn.ai/core/go-log v0.0.4 h1:KTuCEPgFmuM8KJfnyQ8vPOU1Jg654W74h8IJvfQMfv0= forge.lthn.ai/core/go-log v0.0.4/go.mod h1:r14MXKOD3LF/sI8XUJQhRk/SZHBE7jAFVuCfgkXoZPw= -forge.lthn.ai/core/go-process v0.2.7 h1:yl7jOxzDqWpJd/ZvJ/Ff6bHgPFLA1ZYU5UDcsz3AzLM= -forge.lthn.ai/core/go-process v0.2.7/go.mod h1:I6x11UNaZbU3k0FWUaSlPRTE4YZk/lWIjiODm/8Jr9c= -forge.lthn.ai/core/go-rag v0.1.9 h1:uI0STgiSJiboAK22J59vf8vgwY4NfFruopoFphzWr7U= -forge.lthn.ai/core/go-rag v0.1.9/go.mod h1:eUimVDmTbb8zp78W6ijEWICjetBsoW1L80QphE6rLN8= -forge.lthn.ai/core/go-webview v0.1.5 h1:tr6HJvDLfrF6GoDo0aT/kIdKtZCV9Qky6xI0TI4vEH8= -forge.lthn.ai/core/go-webview v0.1.5/go.mod h1:5n1tECD1wBV/uFZRY9ZjfPFO5TYZrlaR3mQFwvO2nek= -forge.lthn.ai/core/go-ws v0.2.3 h1:qTeMtJQjtTdTwfPvtbOBdch2Dmbde+Aso8Ow1qvg/bk= -forge.lthn.ai/core/go-ws v0.2.3/go.mod h1:C3riJyLLcV6QhLvYlq3P/XkGTsN598qQeGBoLdoHBU4= +forge.lthn.ai/core/go-process v0.2.9 h1:Wql+5TUF+lfU2oJ9I+S764MkTqJhBsuyMM0v1zsfZC4= +forge.lthn.ai/core/go-process v0.2.9/go.mod h1:NIzZOF5IVYYCjHkcNIGcg1mZH+bzGoie4SlZUDYOKIM= +forge.lthn.ai/core/go-rag v0.1.11 h1:KXTOtnOdrx8YKmvnj0EOi2EI/+cKjE8w2PpJCQIrSd8= +forge.lthn.ai/core/go-rag v0.1.11/go.mod h1:vIlOKVD1SdqqjkJ2XQyXPuKPtiajz/STPLCaDpqOzk8= +forge.lthn.ai/core/go-webview v0.1.6 h1:szXQxRJf2bOZJKh3v1P01B1Vf9mgXaBCXzh0EZu9aoc= +forge.lthn.ai/core/go-webview v0.1.6/go.mod h1:5n1tECD1wBV/uFZRY9ZjfPFO5TYZrlaR3mQFwvO2nek= +forge.lthn.ai/core/go-ws v0.2.5 h1:ZIV7Yrv01R/xpJUogA5vrfP9yB9li1w7EV3eZFMt8h0= +forge.lthn.ai/core/go-ws v0.2.5/go.mod h1:C3riJyLLcV6QhLvYlq3P/XkGTsN598qQeGBoLdoHBU4= github.com/99designs/gqlgen v0.17.88 h1:neMQDgehMwT1vYIOx/w5ZYPUU/iMNAJzRO44I5Intoc= github.com/99designs/gqlgen v0.17.88/go.mod h1:qeqYFEgOeSKqWedOjogPizimp2iu4E23bdPvl4jTYic= github.com/KyleBanks/depth v1.2.1 h1:5h8fQADFrWtarTdtDudMmGsC7GPbOAu6RVB3ffsVFHc= @@ -51,8 +51,8 @@ github.com/bsm/gomega v1.27.10 h1:yeMWxP2pV2fG3FgAODIY8EiRE3dy0aeFYt4l7wh6yKA= github.com/bsm/gomega v1.27.10/go.mod h1:JyEr/xRbxbtgWNi8tIEVPUYZ5Dzef52k01W3YH0H+O0= github.com/buger/jsonparser v1.1.1 h1:2PnMjfWD7wBILjqQbt530v576A/cAbQvEW9gGIpYMUs= github.com/buger/jsonparser v1.1.1/go.mod h1:6RYKKt7H4d4+iWqouImQ9R2FZql3VbhNgx27UK13J/0= -github.com/bytedance/gopkg v0.1.3 h1:TPBSwH8RsouGCBcMBktLt1AymVo2TVsBVCY4b6TnZ/M= -github.com/bytedance/gopkg v0.1.3/go.mod h1:576VvJ+eJgyCzdjS+c4+77QF3p7ubbtiKARP3TxducM= +github.com/bytedance/gopkg v0.1.4 h1:oZnQwnX82KAIWb7033bEwtxvTqXcYMxDBaQxo5JJHWM= +github.com/bytedance/gopkg v0.1.4/go.mod h1:v1zWfPm21Fb+OsyXN2VAHdL6TBb2L88anLQgdyje6R4= github.com/bytedance/sonic v1.15.0 h1:/PXeWFaR5ElNcVE84U0dOHjiMHQOwNIx3K4ymzh/uSE= github.com/bytedance/sonic v1.15.0/go.mod h1:tFkWrPz0/CUCLEF4ri4UkHekCIcdnkqXw9VduqpJh0k= github.com/bytedance/sonic/loader v0.5.0 h1:gXH3KVnatgY7loH5/TkeVyXPfESoqSBSBEiDd5VjlgE= @@ -233,8 +233,8 @@ github.com/muesli/cancelreader v0.2.2 h1:3I4Kt4BQjOR54NavqnDogx/MIoWBFa0StPA8ELU github.com/muesli/cancelreader v0.2.2/go.mod h1:3XuTXfFS2VjM+HTLZY9Ak0l6eUKfijIfMUZ4EgX0QYo= github.com/muesli/termenv v0.16.0 h1:S5AlUN9dENB57rsbnkPyfdGuWIlkmzJjbFf0Tf5FWUc= github.com/muesli/termenv v0.16.0/go.mod h1:ZRfOIKPFDYQoDFF4Olj7/QJbW60Ol/kL1pU3VfY/Cnk= -github.com/ollama/ollama v0.18.0 h1:loPvswLB07Cn3SnRy5E9tZziGS4nqfnoVllSKO68vX8= -github.com/ollama/ollama v0.18.0/go.mod h1:tCX4IMV8DHjl3zY0THxuEkpWDZSOchJpzTuLACpMwFw= +github.com/ollama/ollama v0.18.1 h1:7K6anW64C2keASpToYfuOa00LuP8aCmofLKcT2c1mlY= +github.com/ollama/ollama v0.18.1/go.mod h1:tCX4IMV8DHjl3zY0THxuEkpWDZSOchJpzTuLACpMwFw= github.com/pelletier/go-toml/v2 v2.2.4 h1:mye9XuhQ6gvn5h28+VilKrrPoQVanw5PMw/TB0t5Ec4= github.com/pelletier/go-toml/v2 v2.2.4/go.mod h1:2gIqNv+qfxSVS7cM2xJQKtLSTLUE9V8t9Stt+h56mCY= github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4=