import type { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js"; import { z } from "zod"; import type { BetterNewsClient } from "../client.js"; import { handleTool } from "../utils.js"; export function registerCommentTools(server: McpServer, client: BetterNewsClient) { server.tool( "list_comments", "List comments on a news item. Moderators also see hidden comments. Requires news:read scope.", { newsItemId: z.string().uuid().describe("News item UUID"), page: z.number().int().positive().optional().describe("Page number (default 1)"), limit: z.number().int().min(1).max(100).optional().describe("Items per page (default 20)"), }, handleTool(async ({ newsItemId, page, limit }) => { const data = await client.get(`/api/news/${newsItemId}/comments`, { page, limit }); return JSON.stringify(data, null, 2); }), ); server.tool( "create_comment", "Post a comment on a published news item. Requires news:comment scope.", { newsItemId: z.string().uuid().describe("News item UUID"), content: z.string().min(1).max(2000).describe("Comment text"), }, handleTool(async ({ newsItemId, content }) => { const data = await client.post(`/api/news/${newsItemId}/comments`, { content }); return JSON.stringify(data, null, 2); }), ); server.tool( "delete_comment", "Delete a comment. Owners can delete their own; Mod/Admin can delete any. Requires news:comment scope.", { newsItemId: z.string().uuid().describe("News item UUID"), commentId: z.string().uuid().describe("Comment UUID"), }, handleTool(async ({ newsItemId, commentId }) => { const data = await client.delete(`/api/news/${newsItemId}/comments/${commentId}`); return JSON.stringify(data, null, 2); }), ); server.tool( "like_comment", "Toggle a like on a comment. Requires news:comment scope.", { newsItemId: z.string().uuid().describe("News item UUID"), commentId: z.string().uuid().describe("Comment UUID"), }, handleTool(async ({ newsItemId, commentId }) => { const data = await client.post(`/api/news/${newsItemId}/comments/${commentId}/like`); return JSON.stringify(data, null, 2); }), ); server.tool( "dislike_comment", "Toggle a dislike on a comment. Requires news:comment scope.", { newsItemId: z.string().uuid().describe("News item UUID"), commentId: z.string().uuid().describe("Comment UUID"), }, handleTool(async ({ newsItemId, commentId }) => { const data = await client.post(`/api/news/${newsItemId}/comments/${commentId}/dislike`); return JSON.stringify(data, null, 2); }), ); server.tool( "hide_comment", "Hide or unhide a comment. Hidden comments are invisible to regular users but still visible to Mod/Admin. Requires Mod/Admin role and news:moderate scope.", { newsItemId: z.string().uuid().describe("News item UUID"), commentId: z.string().uuid().describe("Comment UUID"), hidden: z.boolean().describe("True to hide, false to unhide"), }, handleTool(async ({ newsItemId, commentId, hidden }) => { const data = await client.patch(`/api/news/${newsItemId}/comments/${commentId}`, { hidden }); return JSON.stringify(data, null, 2); }), ); }