MCP server that converts Markdown into PDF, Word, and PowerPoint documents
Server has 8 tools with complete input schemas and descriptions. Naming follows verb_noun convention (write_, read_, page_, get_, list_, search_, delete_). Descriptions are detailed (100-400 chars) and explain modes/prerequisites well. However, output schemas are not documented in code, responses are inferred from implementation. Parameter descriptions are thorough but some lack explicit constraints (enums, ranges). Error handling is minimal; no recovery guidance or actionable error messages visible. Security: no secrets in params (good), but no permission gates or audit logging evident. Composition is sound, tools chain via document_id. Overall: solid definitions with gaps in output documentation and error guidance.
Delete a document and its metadata sidecar from storage and registry.
Return metadata for a document: file name, format, type, page count, timestamps, storage location, template id, version history. No content. document_id: UUID from write_document, file_name from the response, or id from list_documents.
List documents known via the registry and optionally every ``*.meta.json`` sidecar under the local storage directory (scan_storage=True). Use the latter when registry.json is missing or files were created outside this server. Each summary includes 'id' (UUID), file_name, format, page_or_slide_count, created_at, storage_location. Optional filters: format_filter (pdf|docx|pptx), template_id, created_after, created_before (ISO datetime strings).
Replace or insert content at a specific page in an existing document. - Replace: provide (page) or (start_page, end_page) and new_content. - Insert: provide page, position='before'|'after', and content. document_id: The UUID returned by write_document(mode="create") or found via list_documents. Do NOT guess this value.
Read content from a previously created document. - mode="full": Return entire text content. - mode="page_count": Return the number of pages or slides. - mode="range": Return text for pages start_page..end_page (1-based). - mode="last_n": Return the last N pages (requires pages arg). document_id: The UUID from write_document(mode="create"), the file_name from the response (e.g. "report.pdf"), or an id from list_documents. Do NOT invent values; use list_documents when unsure.
Output schemas not documented. Tool descriptions explain what is returned (e.g., 'Returns matches: {page, match, context}') but no formal JSON Schema for responses. LLMs cannot reliably extract fields or plan downstream calls without documented output structure.
template_tool has ambiguous name. 'template_tool' does not start with a clear action verb. Should be 'manage_templates' or split into 'list_templates', 'get_template', 'instantiate_template' for clarity.
Error handling lacks recovery guidance. Code shows ValueError raises for invalid mode/args, but no structured error responses with actionable next steps (e.g., 'Call list_documents() to find valid document_id'). Agents cannot self-correct.
Inferred effective spec: <=2025-11-25.
| Scored | Grade | Overall | Spec posture | Rubric |
|---|---|---|---|---|
| 2026-09-23 | D | 56 | <=2025-11-25 | v2 |
Search the stored source Markdown for a document (sidecar ``source_markdown``). Returns ``matches``: a list of ``{page, match, context}`` where *page* is a 1-based index aligned with the server's page/slide numbering.
Manage DOCX/PPTX templates stored in the templates directory (default: ./templates/). - action="list": Returns available template files (optional type_filter: "document" or "presentation"). - action="get": Returns full template metadata (requires template_id = filename). - action="instantiate": Creates a new document from a template. Requires template_id (the template filename, e.g. "report.docx"), content (Markdown), and format ("docx", "pptx", or "pdf" with a .docx template). PDF needs LibreOffice headless (soffice) on PATH for Word headers/footers; otherwise falls back to a simple Markdown PDF. file_stem (action=instantiate): Preferred output file stem without extension (e.g. "quarterly_report" → "quarterly_report.docx"). Same as write_document's filename parameter; UUID remains document_id. You may use filename instead if your client prefers that name. placeholders (action=instantiate): Values for ``{{key}}`` in the template (Word: Jinja/docxtpl; PowerPoint: simple ``{{key}}`` in slide XML). Merged with ``markdown`` and ``body`` from the content argument. template_id is the filename of the template file inside the templates directory. Use action="list" first to see available templates.
Create or update a document from Markdown. Modes: - mode="create" (default): Creates a NEW document. Returns a unique document_id (UUID) in the response — save this ID, it is required for every subsequent operation (read, edit, append, metadata). - mode="append": Append content to an existing document. Requires document_id obtained from a prior write_document(mode="create") call or from list_documents. - mode="overwrite_pages": Replace pages start_page..end_page with new content. Requires document_id, start_page, end_page. filename (mode=create only): Optional output file stem (e.g. "report_q3"). The saved file becomes "<stem>.<ext>" while document_id remains a UUID. If omitted, the stem defaults to the document_id. read_document, get_metadata, and page_edit accept either the UUID or the saved file_name (e.g. "report_q3.pdf") when unique. template_id (mode=create): Optional Word (.docx) or PowerPoint (.pptx) template from ./templates/. For format="pdf", the template must be .docx; PDF is produced via LibreOffice (soffice on PATH) when available, otherwise a plain Markdown PDF. placeholders (mode=create, with template_id): Optional map of names to strings for ``{{name}}`` / Jinja placeholders in the template. Always includes ``markdown`` and ``body`` (full and trimmed Markdown) for use in Word templates via docxtpl. Output location: files are saved to the directory configured by MARKDOWN_MCP_STORAGE_LOCAL_PATH (default: ./markdown_mcp_output/). The response includes 'storage_location' with the full file path. IMPORTANT: Do NOT invent or guess document_id values. Always use the ID returned by this tool (mode=create) or retrieved via list_documents.
delete_document lacks confirmation/dry-run pattern. Destructive operation with no warning or confirmation step. Agents can accidentally delete documents without safeguard.
Parameter constraints not formalized as enums. 'mode' in write_document accepts 'create|append|overwrite_pages' but is a free-form string, not an enum. 'format' accepts 'pdf|docx|pptx' but no enum constraint. LLMs may hallucinate invalid values.