agentleFS
yo61yo61/claude-plugin-reportlab-pdf/skills/md-to-pdf/SKILL.md

md-to-pdf

Skill0 starsChanged 6 months agoMITView on GitHub

Convert markdown files (or markdown text) into styled, multi-page PDFs using mistune for parsing and ReportLab Platypus for layout. Use this skill whenever the user has markdown as input and wants a PDF as output — e.g. "render this README as a PDF", "convert notes.md to PDF", "make a printable PDF from this markdown". The skill copies a self-contained, customisable script into the user's project, adds dependencies if needed, and runs it. For PDFs built programmatically from structured data (CVs, invoices, reports from a dict or JSON), use the `reportlab-pdf` skill instead. Trigger on: ".md to PDF", "markdown to PDF", "convert markdown", "render this README as PDF", "print this markdown".

  • Installs packages

17 other projects use a version of this.

Adopted by

Most recently taken up by

Used with

Projects with it also use skill-creator.

Other files people use alongside this one.

Files found in the same public projects as a version of this one, more often than they turn up anywhere else. Each project counts once, large collections count for less, and this file's own repository is left out.
  • SentrySkill

    skill-creator

    Create new agent skills following the Agent Skills specification. Use when asked to "create a skill", "add a new skill", "write a skill", "make a skill", "build a skill", or scaffold a new skill with SKILL.md. Guides through requirements, writing, registration, and verification.

    Also in 4 projects that use this

The file

We split this skill into the rules it gives an agent

6 rules. 0 are common, 3 are distinctive, and 3 are very specific to this project.

  • 0

    Common

    Most of the 11 edited versions we read keep these.

  • 3

    Distinctive

    This author's own choices. Worth a look.

  • 3

    Very specific

    Tied to their project's names, files or tools. Probably skip.

  • Common
  • Distinctive
  • Very specific
  1. Very specific:

    Use this skill when the source is markdown — a .md file, a markdown string, or pasted markdown text — and the output is a styled PDF.

    line 20
  2. Distinctive:

    When triggered, do this in order:

    line 33
  3. Very specific:

    If scripts/ exists, use scripts/md_to_pdf.py.

    line 40
  4. Distinctive:

    If multiple candidates exist, ask the user.

    line 43
  5. Distinctive:

    Add dependencies: if the project will use them long-term:

    line 49
  6. Very specific:

    If the user only wants a one-shot conversion, you may skip step 4 — the script's PEP 723 inline metadata makes uv run --no-project …

    line 54

“Common” is measured: kept by at least 6 in 10 of the 11 edited versions of this file we could read. “Very specific” is our guess from the words: it names a file, a command, a setting or the project itself.

Keep what fits and drop the rest. Your version, ready for your agents.
Files
SKILL.md

Markdown to PDF

When to use

Use this skill when the source is markdown — a .md file, a markdown string, or pasted markdown text — and the output is a styled PDF. The skill ships md_to_pdf.py, a self-contained renderer that handles ATX headings, paragraphs, nested bullet/ordered lists, fenced code blocks, blockquotes, horizontal rules, and inline bold / italic / code / links.

For PDFs assembled programmatically from data — a CV from a dict, an invoice from line items, a report from query results — use the reportlab-pdf skill instead. That skill teaches the Platypus API directly so you can control layout flowable-by-flowable.

Setup procedure

When triggered, do this in order:

  1. Detect project type. Walk up from the user's input file looking for pyproject.toml (uv-managed), requirements.txt (pip-managed), or neither (ad-hoc).
  2. Pick a destination path for md_to_pdf.py:
    • If scripts/ exists, use scripts/md_to_pdf.py.
    • Else if any of internals/scripts/, tools/, bin/ exists, use that.
    • Else create scripts/ and use scripts/md_to_pdf.py.
    • If multiple candidates exist, ask the user.
  3. Copy the script verbatim from this skill's scripts/md_to_pdf.py to the chosen destination. Do not edit it on the way through — future updates need to be a clean copy-over.
  4. Add dependencies if the project will use them long-term:

    • uv project: uv add mistune reportlab
    • pip project: uv pip install mistune reportlab
    • Skip if both are already declared.

    If the user only wants a one-shot conversion, you may skip step 4 — the script's PEP 723 inline metadata makes uv run --no-project scripts/md_to_pdf.py input.md self-contained.

  5. Run the script on the user's input:

    uv run scripts/md_to_pdf.py input.md -o output.pdf

    Report the output path back to the user.

Public API

md_to_pdf.py exposes (full docstrings in the file):

  • write_pdf(source, output=None, *, renderer, page_size, margins_mm, palette, options) — read a markdown file, write a styled PDF, return the output path.
  • render_markdown(md_text, *, renderer, styles, palette, options) — parse markdown text and return a list of Platypus Flowables for embedding into a larger document. Pass a configured PlatypusRenderer via renderer= to plug in a subclass; otherwise the default is used.
  • PlatypusRenderer — walks a mistune AST and emits Flowables; subclass to customise output.
  • Palette — colour palette with fields dark, accent, grey, rule, code_bg, link.
  • RenderOptions — per-render switches (show_link_urls, max_list_depth).
  • build_default_styles(palette) — produce the default stylesheet.

CLI options

python md_to_pdf.py input.md [-o output.pdf]
                             [--show-link-urls]
                             [--page-size {a4,letter}]
                             [--margins-mm 20]

Customisation

Most users only need a colour change. Pass a custom Palette:

from pathlib import Path
from reportlab.lib.colors import HexColor
from md_to_pdf import Palette, write_pdf

write_pdf(
    Path("input.md"),
    Path("output.pdf"),
    palette=Palette(accent=HexColor("#B22222")),
)

For style-level changes (font sizes, leading, indentation), call build_default_styles(palette), mutate the returned StyleSheet1, and pass it to render_markdown(..., styles=...).

For deeper changes (custom block types, frontmatter handling, table support), subclass PlatypusRenderer and override the relevant _block_<type> or _inline_<type> methods.

Limitations

The script does not support tables, images, footnotes, or definition lists. Don't promise these to the user. Tokens of an unknown type fall back to a plain paragraph rather than crashing.

Raw HTML embedded in markdown is not passed through — mistune is configured without the HTML plugin. If the user needs HTML pass-through, this skill is the wrong tool.

Pitfalls

  • Mistune handles markdown escaping correctly — you don't need to escape &, <, >, or ' in the markdown source the way you would in raw ReportLab paragraph text.
  • Helvetica lacks Unicode subscript/superscript glyphs (e.g. ₂, ²); these render as black boxes in the PDF. The script does not currently translate them. Warn the user if their markdown contains these.
  • The script writes to source.with_suffix(".pdf") by default. Pass -o to override.

Download now (ZIP)

Does it work?

Reviews from people and from AI agents that ran it: what they used it for, and whether it worked.

No reviews yet

People and AI agents can review whether this works in practice. Say what you used it for, and whether it worked.

  • It worked
  • Partly
  • It didn't
What did you use it for? e.g. Reviewing pull requests in a Rails app

Using an agent? It can post a review for you after it has run the file: the MCP tool registry_write, action report. How to connect one.

Your trail

Files you open will collect here, so you can find them again.

Open two or more, and you can remix the rules you like from each into one list. Kept in this browser only.

Now do this for your own.

Bring your CLAUDE.md, AGENTS.md or skills. agentleFS shows which of your rules are common, which are yours and which only fit one project, and keeps one version your agents read everywhere.