"""MCP tools for Fable briefings and RSS feed management.""" from __future__ import annotations from typing import Any from fable_mcp.client import FableClient # ── RSS feeds ──────────────────────────────────────────────────────────────── async def list_rss_feeds(client: FableClient) -> dict[str, Any]: """List the user's RSS feeds.""" return await client.get("/api/briefing/feeds") async def add_rss_feed( client: FableClient, *, url: str, title: str | None = None, category: str | None = None, ) -> dict[str, Any]: """Add a new RSS feed. Title is optional — auto-populated from feed metadata.""" payload: dict[str, Any] = {"url": url} if title: payload["title"] = title if category: payload["category"] = category return await client.post("/api/briefing/feeds", json=payload) async def remove_rss_feed(client: FableClient, *, feed_id: int) -> dict[str, Any]: """Remove an RSS feed by ID.""" return await client.delete(f"/api/briefing/feeds/{feed_id}") # ── Briefings ──────────────────────────────────────────────────────────────── async def list_briefing_conversations(client: FableClient) -> dict[str, Any]: """List the user's briefing conversations, newest first.""" return await client.get("/api/briefing/conversations") async def get_today_briefing(client: FableClient) -> dict[str, Any]: """Fetch today's briefing conversation with all messages.""" return await client.get("/api/briefing/conversations/today") async def get_briefing_messages( client: FableClient, *, conversation_id: int, ) -> dict[str, Any]: """Fetch messages for a specific briefing conversation.""" return await client.get(f"/api/briefing/conversations/{conversation_id}/messages") async def trigger_briefing( client: FableClient, *, slot: str = "compilation", ) -> dict[str, Any]: """Manually trigger a briefing slot — fires data refresh and runs the pipeline. Slot is one of: compilation (full morning), morning, midday, afternoon. """ return await client.post("/api/briefing/trigger", json={"slot": slot}) async def reset_today_briefing( client: FableClient, *, run_compilation: bool = True, ) -> dict[str, Any]: """Delete all messages in today's briefing and optionally regenerate. Wipes the messages in today's briefing conversation (keeping the conversation row), then, if ``run_compilation`` is True, fires the compilation slot so a fresh briefing lands in its place. """ reset = await client.post("/api/briefing/reset-today") if not run_compilation: return {"reset": reset, "triggered": None} triggered = await client.post( "/api/briefing/trigger", json={"slot": "compilation"} ) return {"reset": reset, "triggered": triggered} # ── Generic conversations ─────────────────────────────────────────────────── async def get_conversation( client: FableClient, *, conversation_id: int, ) -> dict[str, Any]: """Fetch any conversation (chat or briefing) with all messages and tool calls.""" return await client.get(f"/api/chat/conversations/{conversation_id}")