Bahn: aisupport, Analyse-O2C-C2S, awesome-bahn-mcp-servers, beam-mcp,
Confluence_Bot, db-planet-mcp-server, O2C-Harness, project-audit,
Projekt-KIQ-HP, teamlandkarte-mcp
Dhive: Jury-Voting
Privat: CV, NoteGraph (NOTE: NoteGraph needs complete redo after consolidation)
Shared: AI-Orchestrator, OrgMyLife, power_skills_and_more
Shared/references: symphony (read-only)
Bahn repos remain available as independent remotes - this monorepo
pulls them in via subtree, the originals are untouched.
10 KiB
Implementation Plan: DB Planet MCP Tools Refactoring
Overview
Refactor the DB Planet MCP Server from a single monolithic SearchDBPlanet tool into ~28 focused, single-responsibility MCP tools organized across 9 registration modules. The implementation proceeds bottom-up: shared infrastructure first (error handler, enhanced client), then tool registration modules by capability area, then wiring everything together in the barrel and server entry point.
Tasks
-
1. Set up test infrastructure and shared utilities
-
1.1 Add vitest and fast-check dev dependencies
- Run
npm install --save-dev vitest fast-check - Add
"test": "vitest --run"script to package.json - Add vitest config if needed (ESM + TypeScript)
- Requirements: N/A (infrastructure)
- Run
-
1.2 Create the shared error handler at
src/errorHandler.ts- Implement
handleApiError(error: unknown): CallToolResult - Map 401 → authentication failed, 403 → insufficient permissions, 404 → not found, timeout → timed out, other → status + message
- All responses:
{ isError: true, content: [{ type: 'text', text: '[{status}] {message}' }] } - Requirements: 12.1, 12.2, 12.3, 12.4, 12.5
- Implement
-
* 1.3 Write property test for error handler (Property 3)
- Property 3: Error handler maps HTTP status to correct MCP error
- Generate arbitrary HTTP status codes and verify the output shape and message mapping
- Validates: Requirements 12.1, 12.2, 12.3, 12.4, 12.5
-
-
2. Enhance HaiiloClient with generic request method and 401 retry
-
2.1 Add generic
request<T>method tosrc/haiiloClient.ts- Accepts
{ method, path, params?, data? }config - Calls
getAccessToken(), makes request with Bearer token, returnsresponse.data - Requirements: 1.1, 1.2
- Accepts
-
2.2 Add Axios response interceptor for 401 retry
- On 401: clear
accessToken, re-authenticate, retry once using_retriedflag - If retry also 401, propagate error
- Requirements: 1.3
- On 401: clear
-
* 2.3 Write property test for token caching (Property 5)
- Property 5: Token caching — single authentication per session
- Mock OAuth endpoint, make N requests, verify exactly 1 token request
- Validates: Requirements 1.1, 1.2
-
* 2.4 Write property test for 401 retry logic (Property 10)
- Property 10: 401 retry — re-authenticate and retry once
- Mock API returning 401 then success, verify retry behavior and token refresh
- Validates: Requirements 1.3
-
* 2.5 Write property test for missing credentials (Property 6)
- Property 6: Missing credentials produce error
- Generate arbitrary subsets of missing credentials, verify MCP error response
- Validates: Requirements 1.4
-
-
3. Checkpoint — Ensure shared infrastructure tests pass
- Ensure all tests pass, ask the user if questions arise.
-
4. Implement search tool registration module
-
4.1 Create
src/tools/searchTools.tswithregisterSearchTools(server, client)- Register
Search_FullText: GET /api/search with query, page, pageSize params; return metadata only (id, title, type, excerpt, modified date) - Register
Search_QuickEntity: GET /api/quick-entity-search with query param - Register
Search_Grouped: GET /api/search/grouped with query param - All tools use Zod schemas with
.describe()annotations and delegate errors tohandleApiError - Requirements: 3.1, 3.2, 3.3, 3.4, 3.5
- Register
-
* 4.2 Write property test for pagination forwarding (Property 2)
- Property 2: Pagination parameter forwarding
- Generate optional page/pageSize values, verify they are forwarded as query params when present and omitted when absent
- Validates: Requirements 3.2, 5.2, 6.4, 9.2
-
* 4.3 Write property test for Search_FullText metadata only (Property 7)
- Property 7: Search_FullText returns metadata only
- Mock search response, verify result contains metadata fields and no full content
- Validates: Requirements 3.5
-
-
5. Implement workspace tool registration module
- 5.1 Create
src/tools/workspaceTools.tswithregisterWorkspaceTools(server, client)- Register
Workspace_List: GET /api/workspaces - Register
Workspace_Get: GET /api/workspaces/{id} - Register
Workspace_GetMembers: GET /api/workspaces/{id}/members - Register
Workspace_Join: PUT /api/workspaces/{id}/members/join - Register
Workspace_Create: POST /api/workspaces with name, description - Requirements: 4.1, 4.2, 4.3, 4.4, 4.5
- Register
- 5.1 Create
-
6. Implement news, people, and event tool registration modules
-
6.1 Create
src/tools/newsTools.tswithregisterNewsTools(server, client)- Register
News_GetFeed: GET /web/blog/newsfeed with optional page, pageSize - Requirements: 5.1, 5.2, 5.3
- Register
-
6.2 Create
src/tools/peopleTools.tswithregisterPeopleTools(server, client)- Register
People_GetMe: GET /api/users/me - Register
People_List: GET /api/users with optional page, pageSize - Register
People_Search: GET /api/users/chooser/search with query - Requirements: 6.1, 6.2, 6.3, 6.4
- Register
-
6.3 Create
src/tools/eventTools.tswithregisterEventTools(server, client)- Register
Event_Get: GET /api/events/{id} - Register
Event_GetMemberships: GET /api/events/{id}/memberships - Register
Event_UpdateStatus: PUT /api/events/{id}/memberships/status with id, status - Register
Event_Create: POST /api/events with title, description, startDate, endDate, location - Requirements: 7.1, 7.2, 7.3, 7.4
- Register
-
-
7. Implement social, notification, and page tool registration modules
-
7.1 Create
src/tools/socialTools.tswithregisterSocialTools(server, client)- Register
Social_GetComments: GET /api/comments with targetId - Register
Social_PostComment: POST /api/comments with targetId, body - Register
Social_GetLikes: GET /api/like-targets/{targetType}/{targetId} - Register
Social_ToggleLike: POST /api/like-targets/{targetType}/{targetId}/likes/{userId} - Requirements: 8.1, 8.2, 8.3, 8.4
- Register
-
7.2 Create
src/tools/notificationTools.tswithregisterNotificationTools(server, client)- Register
Notification_List: GET /api/notifications with optional page, pageSize - Register
Notification_GetStatus: GET /api/notifications/status - Register
Notification_MarkSeen: PUT /api/notifications/mark-seen - Requirements: 9.1, 9.2, 9.3, 9.4
- Register
-
7.3 Create
src/tools/pageTools.tswithregisterPageTools(server, client)- Register
Page_List: GET /api/pages - Register
Page_Get: GET /api/pages/{id} - Register
Page_GetMembers: GET /api/pages/{id}/members - Register
Page_Create: POST /api/pages with title, content - Requirements: 10.1, 10.2, 10.3, 10.4
- Register
-
-
8. Implement content fetching tool registration module
-
8.1 Create
src/tools/contentTools.tswithregisterContentTools(server, client)- Register
Content_GetFull: uses existinggetContentByType,fetchWidgetContent,extractTextFromWidgets,cleanHtmllogic from HaiiloClient - Accept contentId, contentType, optional appId, optional slug
- Support blog-article, wiki-article, page, workspace, app, timeline-item
- Return clean text extracted from widget HTML
- Return error for unsupported content types
- Requirements: 11.1, 11.2, 11.3, 11.4, 11.5
- Register
-
* 8.2 Write property test for HTML widget text extraction (Property 8)
- Property 8: HTML widget text extraction removes all tags
- Generate arbitrary HTML strings, verify output contains no
<...>sequences and entities are decoded - Validates: Requirements 11.3
-
* 8.3 Write property test for unsupported content type (Property 9)
- Property 9: Unsupported content type returns error
- Generate arbitrary strings not in the supported set, verify MCP error response
- Validates: Requirements 11.4
-
-
9. Checkpoint — Ensure all tool module tests pass
- Ensure all tests pass, ask the user if questions arise.
-
10. Wire everything together and update server entry point
-
10.1 Create
src/tools/index.tsbarrel withregisterAllTools(server, client)- Import and call all 9 registration functions in order
- Requirements: 2.1, 2.2
-
10.2 Update
src/getToolServer.tsto use new architecture- Create one
HaiiloClientinstance per session (not per tool call) - Call
registerAllTools(server, client)instead ofregisterHaiiloTools - Remove old import of
registerHaiiloTools - Requirements: 1.1, 2.2
- Create one
-
10.3 Remove old
src/tools/haiiloTools.ts- Delete the monolithic tool registration file
- Requirements: 2.1
-
* 10.4 Write property test for tool metadata completeness (Property 4)
- Property 4: Tool metadata completeness
- Instantiate McpServer, register all tools, verify each tool has
{Area}_{Action}name pattern, non-empty description, and Zod schema - Validates: Requirements 2.3, 2.4, 2.5
-
* 10.5 Write property test for tool-to-endpoint routing (Property 1)
- Property 1: Tool-to-endpoint routing correctness
- For each registered tool with arbitrary valid input, mock
client.request, invoke tool, verify correct HTTP method and path - Validates: Requirements 3.1, 3.3, 3.4, 4.1–4.5, 5.1, 6.1–6.3, 7.1–7.4, 8.1–8.4, 9.1, 9.3, 9.4, 10.1–10.4, 11.1
-
-
11. Verify backward compatibility
-
11.1 Verify
server.tsis unchanged- Confirm StreamableHTTP transport on
/servers/dbplanet/mcp, credentials viax-dbplanet-*headers, port 3000,/healthendpoint - Requirements: 13.1, 13.2, 13.3, 13.4
- Confirm StreamableHTTP transport on
-
* 11.2 Write unit tests for backward compatibility
- Test that server listens on port 3000, /health returns 200, all 28 tools are registered
- Requirements: 13.1, 13.2, 13.3, 13.4, 2.2
-
-
12. Final checkpoint — Ensure all tests pass
- Ensure all tests pass, ask the user if questions arise.
Notes
- Tasks marked with
*are optional and can be skipped for faster MVP - Each task references specific requirements for traceability
- Property tests validate universal correctness properties from the design document
- The existing
server.tsshould remain unchanged — onlygetToolServer.tsandsrc/tools/are modified - The
HaiiloClientcontent-fetching methods (getContentByType,fetchWidgetContent,extractTextFromWidgets,cleanHtml) need to be made accessible (public or package-internal) for use bycontentTools.ts