Add MCP server, note mutation endpoint, and updated_at tracking (v3.0.0)

New MCP server (mcp/) exposes kb operations as native MCP tools over
Streamable HTTP with Bearer token auth. Supports collections via tag
conventions, chunked file uploads, and agent-side search patterns.

Engine gains PATCH /api/v1/notes/{id} for in-place note updates with
transactional re-chunk/re-embed, and updated_at column on documents.

Go client adds updatenote command and Patch HTTP method.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
2026-04-02 21:34:55 +01:00
parent adeba21712
commit e7136a4a20
32 changed files with 1679 additions and 8 deletions
@@ -0,0 +1,90 @@
## 1. Engine: Schema Migration & updated_at
- [x] 1.1 Add `updated_at TEXT` column migration to `init_schema()` in `kb/database.py` (same pattern as existing `ALTER TABLE` migrations)
- [x] 1.2 Update `insert_document()` to include `updated_at` in returned/stored fields
- [x] 1.3 Update document list endpoint (`GET /api/v1/documents`) to include `updated_at` in response and use `COALESCE(updated_at, created_at)` for date sorting
- [x] 1.4 Update document detail endpoint (`GET /api/v1/documents/{id}`) to include `updated_at` in response
- [x] 1.5 Update tag management endpoint (`PUT /api/v1/documents/{id}/tags`) to set `updated_at = current_timestamp` on tag changes
## 2. Engine: Note Mutation Endpoint
- [x] 2.1 Create `kb/routes/notes.py` with `PATCH /api/v1/notes/{id}` endpoint
- [x] 2.2 Implement validation: document must exist and have `doc_type = 'note'` (404 / 422 on failure)
- [x] 2.3 Implement note update logic: delete old chunks/embeddings, run note chunking pipeline, re-embed, insert new chunks, update `content_hash` and `updated_at` — all in a single transaction
- [x] 2.4 Register the notes router in `engine/main.py`
- [x] 2.5 Test: update a note and verify chunks, embeddings, FTS index, and `updated_at` are all correctly updated
- [x] 2.6 Test: verify rollback on embedding failure preserves original note
## 3. Engine: Version Bump
- [x] 3.1 Update `engine/VERSION` to `3.0.0`
## 4. Go Client: Update Note Command
- [x] 4.1 Add `PATCH /api/v1/notes/{id}` method to `internal/api/client.go`
- [x] 4.2 Create `cmd/updatenote.go` — takes document ID and text as positional args, calls PATCH endpoint, formats output (human/json)
- [x] 4.3 Handle error cases: 404 (not found), 422 (not a note), missing arguments
- [x] 4.4 Update `cmd/examples.go` to include `updatenote` usage
## 5. Go Client: Version Bump
- [x] 5.1 Update `client/VERSION` to `3.0.0`
- [x] 5.2 Update `client/MIN_ENGINE_VERSION` to `3.0.0`
## 6. MCP Server: Project Setup
- [x] 6.1 Create `mcp/` directory at repo root with Python package structure
- [x] 6.2 Add `mcp` SDK and `httpx` as dependencies (requirements.txt or pyproject.toml)
- [x] 6.3 Implement config: read `KB_ENGINE_URL`, `KB_API_KEY`, `KB_MCP_API_KEY` from environment
- [x] 6.4 Implement Streamable HTTP transport setup using `mcp` SDK
- [x] 6.5 Implement Bearer token authentication for incoming agent connections (`KB_MCP_API_KEY`)
## 7. MCP Server: Core Tools
- [x] 7.1 Implement `kb_search` tool — proxy to engine search API, translate `collection` param to `collection:*` tag filter, strip `collection:*` tags from results and add `collection` field
- [x] 7.2 Implement `kb_addnote` tool — proxy to engine jobs API, apply `collection:<name>` tag (default `collection:documents`)
- [x] 7.3 Implement `kb_update_note` tool — proxy to engine `PATCH /api/v1/notes/{id}`
- [x] 7.4 Implement `kb_get` tool — proxy to engine documents API, support lookup by ID or source_path, strip collection tags from response
- [x] 7.5 Implement `kb_status` tool — proxy to engine status API
- [x] 7.6 Implement `kb_jobs` tool — proxy to engine jobs API with optional status filter
## 8. MCP Server: Chunked File Upload
- [x] 8.1 Implement `kb_upload_start` tool — generate UUID, create temp staging directory, store upload metadata (filename, tags, collection) in memory
- [x] 8.2 Implement `kb_upload_chunk` tool — validate upload_id exists, decode base64, write chunk to staging directory by chunk_index
- [x] 8.3 Implement `kb_upload_finish` tool — reassemble chunks in order, forward as multipart upload to engine `POST /api/v1/jobs` with tags (including `collection:*`), return job ID, clean up staging
- [x] 8.4 Implement abandoned upload cleanup — background task that removes uploads older than 10 minutes
- [x] 8.5 Test: upload a multi-chunk file and verify it arrives at the engine correctly
## 9. MCP Server: Collection Management
- [x] 9.1 Implement exclusive collection enforcement — on addnote/addfile, query document tags, remove any existing `collection:*` tags via engine tag API before applying new one
- [x] 9.2 Implement collection tag stripping in all tool responses (search results, document details)
## 10. MCP Server: Tool Descriptions
- [x] 10.1 Write `kb_search` tool description including query expansion and reranking guidance
- [x] 10.2 Write descriptions for all other tools with parameter documentation and usage examples
- [x] 10.3 Include chunked upload usage example in `kb_upload_start` description
## 11. MCP Server: Docker & Compose
- [x] 11.1 Create `mcp/Dockerfile` — Python base image, install dependencies, run MCP server
- [x] 11.2 Add MCP server service to Docker Compose file(s) — connect to engine via Docker network, expose Streamable HTTP port
- [x] 11.3 Document environment variables (`KB_ENGINE_URL`, `KB_API_KEY`, `KB_MCP_API_KEY`) in compose file
## 12. Integration Testing
- [x] 12.1 Test: MCP search with collection filter returns only matching documents
- [x] 12.2 Test: MCP addnote with collection applies correct tag and enforces exclusivity
- [x] 12.3 Test: MCP update note preserves document ID and tags, updates content and `updated_at`
- [x] 12.4 Test: chunked file upload end-to-end (start → chunk × N → finish → verify job created)
- [x] 12.5 Test: MCP server rejects unauthenticated connections when `KB_MCP_API_KEY` is set
## 13. Release
- [x] 13.1 Build and tag engine Docker images (`engine-v3.0.0-*`)
- [x] 13.2 Build and tag MCP server Docker image
- [x] 13.3 Build Go client binaries for all platforms
- [x] 13.4 Create git tags: `engine-v3.0.0`, `client-v3.0.0`
- [x] 13.5 Update SKILL.md to reference MCP server as primary agent integration path