Quire PDFGuides

Let Claude generate PDFs with the Quire MCP server

Add Quire's MCP server with claude mcp add quire --env QUIRE_API_KEY=qk_live_... -- npx -y quirepdf-mcp (or the equivalent mcpServers entry in Claude Desktop). Claude can then turn any data in the conversation into a PDF saved on your machine, using a gallery template when one fits and checking pages as PNG images.

An agent can’t write a PDF file directly, and generating HTML for a browser to print means running and maintaining a browser. With Quire, the agent only has to produce JSON. Quire validates it, picks a layout and renders the file, and the agent gets back a path, or an image of the page to check.

1. Get an API key

npx quirepdf-cli login you@example.com

Click the link in the email. The key (qk_live_…) is printed on the page and saved by the CLI. The free plan includes 20 renders a month, and test renders (watermarked, test: true) are unlimited.

2. Add the server

Claude Code:

claude mcp add quire --env QUIRE_API_KEY=qk_live_... -- npx -y quirepdf-mcp

Files are saved in the directory you run Claude Code from.

Claude Desktop: open Settings → Developer → Edit Config and add:

{
  "mcpServers": {
    "quire": {
      "command": "npx",
      "args": ["-y", "quirepdf-mcp"],
      "env": {
        "QUIRE_API_KEY": "qk_live_...",
        "QUIRE_OUTPUT_DIR": "/Users/you/Documents/Quire"
      }
    }
  }
}

Restart Claude Desktop. QUIRE_OUTPUT_DIR decides where files go; use an absolute path.

The server needs Node.js 18 or later. It gives Claude five tools: render_document, validate_document, list_templates, get_template and get_usage. The MCP reference describes each one.

3. Ask for a document

Here’s a typical exchange in Claude Code.

You: Make me a PDF invoice for 3 hours of consulting at $150/h for Acme Corp, 500 Oak Avenue, Austin, TX 78701. I’m Northwind Studio, 221 Market Street, San Francisco, CA 94105. Due in two weeks.

Claude calls get_template with {"name": "invoice"} to learn the fields, then render_document:

{
  "template": "invoice",
  "output_path": "acme-invoice",
  "data": {
    "number": "INV-2026-0031",
    "issued": "3 Oct 2026",
    "due": "17 Oct 2026",
    "currency": "$",
    "seller": { "name": "Northwind Studio", "address": ["221 Market Street", "San Francisco, CA 94105"] },
    "customer": { "name": "Acme Corp", "address": ["500 Oak Avenue", "Austin, TX 78701"] },
    "items": [{ "description": "Consulting", "detail": "3 hours at $150/h", "qty": 3, "unit_price": 150 }],
    "notes": "Payment due within 14 days."
  }
}

The tool returns:

{
  "saved_to": "/Users/you/projects/billing/acme-invoice.pdf",
  "template": "invoice",
  "template_source": "explicit",
  "pages": 1,
  "size_kb": 28,
  "render_ms": 7.9,
  "quota_remaining": 97
}

Claude: I’ve saved the invoice to acme-invoice.pdf: INV-2026-0031 from Northwind Studio to Acme Corp, 3 hours of consulting at $150, $450.00 due on 17 Oct 2026.

The invoice template computes the total itself, so Claude doesn’t do the arithmetic.

You: Show me what it looks like.

Claude calls render_document again with "format": "png". The tool returns the image along with the file path, so Claude can see the page, describe it and catch problems like a wrong name before you open anything.

Documents that don’t fit a template

Anything that isn’t an invoice, receipt, quote, credit note, statement or certificate uses the generic layout. You don’t need to explain it; the server tells Claude how it works.

You: Turn load-test-results.json into a PDF report titled “Load test, October”.

Claude reads the file, adds a title, and calls render_document without a template. Objects become key/value sections, arrays of objects become tables, and long text becomes paragraphs. If the data nearly matched a gallery template, the result includes a hint such as “Almost matched invoice (seller is required)”, and Claude can add the field and render again.

When data is wrong

If Claude names a template and leaves something out, the tool returns an error it can act on:

invalid_data: data has 2 problems
- seller is required
- items[0].qty must be a number
Tip: call get_template to see the expected fields, or omit `template` to use the generic layout.

Claude usually fixes the data and retries in the same turn. It can also call validate_document first, which is free. Failed renders don’t count against your quota.

Prompts to try

  • “Make a receipt for Maya Chen’s $240 payment by card today, transaction ID ch_3Q8x.”
  • “Create a certificate of completion for the 12 people in attendees.csv for the Advanced TypeScript workshop, one PDF each.”
  • “Write up these meeting notes as a PDF with action items as a table: owner, task, due date.”
  • “Quote Acme Corp for a website redesign: discovery $2,000, design $6,500, build $9,000, with 10% off.”
  • “How many renders do I have left this month?”

Good to know

  • Quire renders the data Claude sends and keeps nothing; the PDF exists only on your machine.
  • Each PDF, and each PNG preview, is one render. Validation is free.
  • Pages are A4. Quire renders data into its built-in layouts; it doesn’t convert HTML or web pages.
  • To check usage from the terminal instead, run npx quirepdf-cli usage.