{
  "markdown": "<div align=\"center\">\n\n# pdf-toolkit-mcp\n\n**18 PDF operations for Claude Code, Claude Desktop, and any MCP client — via iLoveAPI.**\n\n[![npm version](https://img.shields.io/npm/v/pdf-toolkit-mcp.svg?style=flat-square&logo=npm&color=cb3837)](https://www.npmjs.com/package/pdf-toolkit-mcp)\n[![npm downloads](https://img.shields.io/npm/dm/pdf-toolkit-mcp.svg?style=flat-square&color=blue)](https://www.npmjs.com/package/pdf-toolkit-mcp)\n[![License: MIT](https://img.shields.io/badge/license-MIT-yellow.svg?style=flat-square)](./LICENSE)\n[![Node.js](https://img.shields.io/badge/node-%E2%89%A518-43853d.svg?style=flat-square&logo=node.js&logoColor=white)](https://nodejs.org)\n[![TypeScript](https://img.shields.io/badge/typescript-strict-3178c6.svg?style=flat-square&logo=typescript&logoColor=white)](https://www.typescriptlang.org)\n[![MCP](https://img.shields.io/badge/MCP-1.x-000000.svg?style=flat-square)](https://modelcontextprotocol.io)\n[![Claude Code](https://img.shields.io/badge/Claude%20Code-plugin%20ready-7c3aed.svg?style=flat-square)](https://docs.claude.com/claude-code)\n[![CI](https://img.shields.io/github/actions/workflow/status/EigenCharlie/pdf-toolkit-mcp/ci.yml?style=flat-square&label=CI)](https://github.com/EigenCharlie/pdf-toolkit-mcp/actions)\n\n[Install](#-install) · [Tools](#-tool-catalog) · [Recipes](#-workflow-recipes) · [Architecture](#-architecture) · [Security](#-security-model) · [FAQ](#-faq)\n\n</div>\n\n---\n\n> **Disclaimer.** `pdf-toolkit-mcp` is an **independent, community-built** open-source client. It is **not affiliated with, endorsed, sponsored, or certified by iLovePDF SL**. The project talks to the public [iLoveAPI](https://www.iloveapi.com) REST service using *your* project credentials — nothing is proxied, resold, or relicensed. \"iLovePDF\" and \"iLoveAPI\" are trademarks of iLovePDF SL; this project does not claim ownership of those marks.\n\n---\n\n## 📖 Table of contents\n\n- [Why pdf-toolkit-mcp](#-why-pdf-toolkit-mcp)\n- [Quick tour](#-quick-tour)\n- [Install](#-install)\n- [Tool catalog](#-tool-catalog)\n- [Workflow recipes](#-workflow-recipes)\n- [Architecture](#-architecture)\n- [Configuration reference](#-configuration-reference)\n- [Security model](#-security-model)\n- [Development](#-development)\n- [Testing & CI](#-testing--ci)\n- [Releasing](#-releasing)\n- [Roadmap](#-roadmap)\n- [FAQ](#-faq)\n- [Contributing](#-contributing)\n- [License & trademarks](#-license--trademarks)\n- [Credits](#-credits)\n\n---\n\n## 🎯 Why pdf-toolkit-mcp\n\n| | Manual iLoveAPI | Raw `@ilovepdf/ilovepdf-nodejs` | **`pdf-toolkit-mcp`** |\n| --- | :---: | :---: | :---: |\n| Callable from Claude Code / Claude Desktop / any MCP client | ❌ | ❌ | ✅ |\n| JWT signing + 5-step lifecycle handled for you | ❌ | ✅ | ✅ |\n| Validated Zod schemas (no bad inputs reach the API) | ❌ | ❌ | ✅ |\n| Path sandboxing against traversal | ❌ | ❌ | ✅ |\n| Structured error codes (`RATE_LIMITED`, `PLAN_LIMIT`, …) | ❌ | partial | ✅ |\n| Progress notifications during long OCR tasks | ❌ | ❌ | ✅ |\n| Bundled Claude Code **skill** with multi-step pipelines | ❌ | ❌ | ✅ |\n| Zero-setup install via `npx -y` | ❌ | ❌ | ✅ |\n\n**Free for personal use.** iLoveAPI's free tier grants ~2,500 credits / month; this MCP itself is MIT-licensed and costs nothing.\n\n---\n\n## 🚀 Quick tour\n\nAfter installation, just *talk* to Claude. The model figures out which tools to call:\n\n```\nYou: Merge invoice-jan.pdf and invoice-feb.pdf into Q1.pdf, then compress it hard\n     and lock it with the password \"2026q1\".\n\nClaude (planning):\n  1. merge_pdf     → invoice-jan.pdf + invoice-feb.pdf  →  Q1.pdf\n  2. compress_pdf  → Q1.pdf                             →  Q1-compressed.pdf  (level: extreme)\n  3. protect_pdf   → Q1-compressed.pdf                  →  Q1-compressed-protected.pdf\n\nClaude (result):\n  ✅ Created ~/docs/Q1-compressed-protected.pdf (312 KB, password-protected).\n```\n\n---\n\n## 📦 Install\n\n### Prerequisites\n\n- **Node.js ≥ 18** (LTS recommended).\n- **iLoveAPI project keys** — free tier at [developer.ilovepdf.com](https://developer.ilovepdf.com). Takes ~2 minutes:\n  1. Sign up → create a project → copy `Project public key` and `Project secret key`.\n  2. Export them (or drop them into your client's MCP config — examples below).\n\n### Option A — Claude Code (CLI one-liner)\n\n```bash\nexport ILOVEAPI_PROJECT_PUBLIC_KEY=\"project_public_xxx\"\nexport ILOVEAPI_PROJECT_SECRET_KEY=\"secret_key_xxx\"\n\nclaude mcp add pdf-toolkit -- npx -y pdf-toolkit-mcp\n```\n\nRestart Claude Code and all 18 tools appear in the picker. Verify with `/mcp` → you should see `pdf-toolkit: connected (18 tools)`.\n\n### Option B — Claude Code Plugin (includes the `pdf-workflow` skill)\n\n```\n/plugin marketplace add EigenCharlie/pdf-toolkit-mcp\n/plugin install pdf-toolkit@EigenCharlie/pdf-toolkit-mcp\n```\n\nThe plugin auto-configures the MCP server *and* installs a skill that teaches Claude five canonical multi-step PDF pipelines (see [Workflow recipes](#-workflow-recipes)).\n\n### Option C — Claude Desktop (`claude_desktop_config.json`)\n\n<details>\n<summary>Click to expand</summary>\n\nEdit `claude_desktop_config.json` (`%APPDATA%\\Claude\\` on Windows, `~/Library/Application Support/Claude/` on macOS):\n\n```jsonc\n{\n  \"mcpServers\": {\n    \"pdf-toolkit\": {\n      \"command\": \"npx\",\n      \"args\": [\"-y\", \"pdf-toolkit-mcp\"],\n      \"env\": {\n        \"ILOVEAPI_PROJECT_PUBLIC_KEY\": \"project_public_xxx\",\n        \"ILOVEAPI_PROJECT_SECRET_KEY\": \"secret_key_xxx\"\n      }\n    }\n  }\n}\n```\n\nRestart Claude Desktop — the 🔌 icon should show `pdf-toolkit` connected.\n</details>\n\n### Option D — any MCP client via stdio\n\n```bash\nILOVEAPI_PROJECT_PUBLIC_KEY=… ILOVEAPI_PROJECT_SECRET_KEY=… npx -y pdf-toolkit-mcp\n```\n\nThe server speaks the standard MCP JSON-RPC 2.0 framing over stdio. Wire it into Cursor, Windsurf, `mcphub`, `mcp-inspector`, or anything else that speaks MCP.\n\n### Option E — Claude Desktop `.mcpb` bundle (drag-and-drop)\n\nGrab `pdf-toolkit-mcp-<version>.mcpb` from the [latest GitHub Release](https://github.com/EigenCharlie/pdf-toolkit-mcp/releases/latest) and drag it into Claude Desktop → **Settings → Extensions**. Claude will prompt for your iLoveAPI keys via the `user_config` section of the bundled manifest. No `npx`, no Node, no terminal.\n\n> Bundles ship unsigned (no publisher certificate yet). macOS Gatekeeper / Windows SmartScreen may warn on first install; verify the SHA-256 in the release notes before accepting.\n\n### Option F — MCP Registry (auto-discovered by compatible clients)\n\nThe server is indexed on the [official MCP Registry](https://registry.modelcontextprotocol.io) under `io.github.EigenCharlie/pdf-toolkit-mcp`. Clients that browse the registry (Claude Desktop extension pane, VS Code MCP picker, `mcphub`, etc.) can install it without any manual config — they'll point at the npm package and prompt for the two iLoveAPI env vars automatically.\n\n---\n\n## 🧰 Tool catalog\n\nAll 18 tools are exposed with strict Zod schemas, `additionalProperties: false`, and return both a `text` summary *and* a `file://` resource URI so the client can surface the output.\n\n### 📚 Organize\n\n| Tool | What it does | Key inputs |\n| --- | --- | --- |\n| `merge_pdf` | Combine ≥ 2 PDFs in order | `input_files[]`, `output_path?` |\n| `split_pdf` | Split by page ranges (`\"1-3,5-7\"`) or fixed chunk size | `input_file`, `ranges?`, `fixed_range?` |\n| `extract_pdf_pages` | Keep a specific subset of pages | `input_file`, `pages` (`\"1,3,5-9\"`) |\n\n### 🔄 Convert — from PDF\n\n| Tool | Output | Notes |\n| --- | --- | --- |\n| `pdf_to_word` | `.docx` | Scanned PDFs → run `ocr_pdf` first for best results |\n| `pdf_to_excel` | `.xlsx` | Works best on tabular source PDFs |\n| `pdf_to_powerpoint` | `.pptx` | One slide per PDF page |\n| `pdf_to_jpg` | `.zip` of `.jpg` | `mode: \"pages\"` renders pages; `\"extract\"` pulls embedded images |\n\n### 🔄 Convert — to PDF\n\n| Tool | Accepts | Notes |\n| --- | --- | --- |\n| `office_to_pdf` | `.doc`, `.docx`, `.xls`, `.xlsx`, `.ppt`, `.pptx` | Server-side rendering |\n| `html_to_pdf` | `.html`, `.htm` | Local HTML only; external assets may not resolve |\n| `image_to_pdf` | `.jpg`, `.jpeg`, `.png` | One image per page, preserves order |\n\n### ✏️ Edit\n\n| Tool | What it does | Key inputs |\n| --- | --- | --- |\n| `rotate_pdf` | Rotate pages 90 / 180 / 270° clockwise | `rotation`, `pages?` (default: all) |\n| `add_page_numbers` | Stamp numbered footer/header | `starting_number`, `vertical_position`, `horizontal_position` |\n| `add_watermark` | Text or image watermark | `mode: \"text\"` + `text`, OR `mode: \"image\"` + `image_file` |\n\n### 🔐 Security\n\n| Tool | What it does | Key inputs |\n| --- | --- | --- |\n| `unlock_pdf` | Remove known password | `input_file`, `password` |\n| `protect_pdf` | Add password | `input_file`, `password` |\n\n### 🩹 Repair / OCR\n\n| Tool | What it does | Notes |\n| --- | --- | --- |\n| `repair_pdf` | Attempt structural repair on damaged PDFs | Useful before further processing |\n| `ocr_pdf` | Run OCR to make scans searchable | `languages[]` (e.g. `[\"eng\"]`, `[\"spa\"]`, `[\"eng\",\"spa\"]`). ⏱ Can exceed 60s on image-heavy PDFs |\n\n> **All tools** accept absolute or CWD-relative paths for `input_file(s)` and an **optional** `output_path` (file or directory). Defaults place the result next to the first input with a timestamped name.\n\n---\n\n## 🍳 Workflow recipes\n\nThe bundled `pdf-workflow` skill ([skills/pdf-workflow/SKILL.md](skills/pdf-workflow/SKILL.md)) teaches Claude five canonical multi-step pipelines. You can also run these manually — just describe the end state and Claude chains the tools for you.\n\n<details>\n<summary><b>1. Assemble</b> — merge + compress + (optional) protect</summary>\n\n```\nmerge_pdf([a.pdf, b.pdf, c.pdf])\n   → compress_pdf(level=\"recommended\")\n   → protect_pdf(password=\"…\")\n```\n</details>\n\n<details>\n<summary><b>2. Convert & secure</b> — Office doc to locked PDF</summary>\n\n```\noffice_to_pdf(report.docx)\n   → add_watermark(mode=\"text\", text=\"CONFIDENTIAL\", opacity=30)\n   → protect_pdf(password=\"…\")\n```\n</details>\n\n<details>\n<summary><b>3. Extract & OCR</b> — pull pages out of a scan and make them editable</summary>\n\n```\nextract_pdf_pages(scan.pdf, pages=\"3-9\")\n   → ocr_pdf(languages=[\"eng\"])\n   → pdf_to_word\n```\n</details>\n\n<details>\n<summary><b>4. Prep for email</b> — shrink + lock</summary>\n\n```\ncompress_pdf(big.pdf, level=\"extreme\")\n   → protect_pdf(password=\"…\")\n```\n</details>\n\n<details>\n<summary><b>5. Scan cleanup</b> — repair + OCR + number</summary>\n\n```\nrepair_pdf(scan_broken.pdf)\n   → ocr_pdf(languages=[\"eng\"])\n   → add_page_numbers(position=\"bottom-center\")\n```\n</details>\n\n---\n\n## 🏛 Architecture\n\n```\n┌────────────────────────────┐    stdio    ┌──────────────────────────┐\n│     Claude Code / Desktop  │◀───────────▶│   pdf-toolkit-mcp server │\n│   (or any MCP client)      │  JSON-RPC   │   (this repo)            │\n└────────────────────────────┘             └────────────┬─────────────┘\n                                                        │\n                                                        ▼\n                                             ┌──────────────────────┐\n                                             │  @ilovepdf/          │\n                                             │  ilovepdf-nodejs     │\n                                             │  (JWT + HTTP)        │\n                                             └──────────┬───────────┘\n                                                        │\n                                                        ▼  HTTPS\n                                             ┌──────────────────────┐\n                                             │   iLoveAPI servers   │\n                                             │   api.ilovepdf.com   │\n                                             └──────────────────────┘\n```\n\n### iLoveAPI 5-phase lifecycle (orchestrated in [`src/api/tasks.ts`](src/api/tasks.ts))\n\n```\n  [ 10% ]   start     →  POST /v1/start/{tool}     (server assignment + task id)\n  [ 40% ]   upload    →  POST /v1/upload           (one call per file, progress scales)\n  [ 50% ]   process   →  POST /v1/process          (run the tool with params)\n  [ 90% ]   download  →  GET  /v1/download/{task}  (bytes → Buffer)\n  [100% ]   done      →  write to disk, emit file:// resource URI\n```\n\nThe server emits MCP `notifications/progress` at each boundary so your client can render a live progress bar for slow operations (OCR, large merges).\n\n### Project layout\n\n```\npdf-toolkit-mcp/\n├── .claude-plugin/\n│   ├── plugin.json           # Plugin manifest\n│   └── .mcp.json             # MCP server config (npx -y pdf-toolkit-mcp)\n├── skills/\n│   └── pdf-workflow/\n│       └── SKILL.md          # 5-recipe skill for multi-step pipelines\n├── src/\n│   ├── index.ts              # #!/usr/bin/env node shebang\n│   ├── server.ts             # MCP stdio bootstrap\n│   ├── api/\n│   │   ├── client.ts         # iLoveAPI client singleton (CJS interop via createRequire)\n│   │   ├── tasks.ts          # 5-phase lifecycle orchestrator\n│   │   ├── errors.ts         # HTTP → structured PdfToolkitError mapping\n│   │   └── types.ts          # Types + error class\n│   ├── tools/                # 18 tools, one file per concern\n│   │   ├── _shared.ts        # Zod fragments + writeOutputAndReport helper\n│   │   ├── merge.ts  split.ts  compress.ts\n│   │   ├── convertFromPdf.ts convertToPdf.ts\n│   │   ├── pageOps.ts  security.ts  watermark.ts\n│   │   ├── repair.ts  ocr.ts\n│   │   └── index.ts          # allTools[] barrel\n│   └── util/\n│       ├── paths.ts          # resolveInputs/resolveOutput + sandbox enforcement\n│       ├── progress.ts       # Progress adapter\n│       └── logger.ts         # stderr-only logger (stdio-safe)\n├── tests/\n│   ├── unit/                 # client, paths, errors, tools.merge (25 tests)\n│   └── integration/          # smoke.test.ts — gated on iLoveAPI creds\n├── scripts/\n│   └── inspector.sh          # npm run inspect → MCP Inspector UI\n└── .github/workflows/\n    ├── ci.yml                # ubuntu+windows × node 18/20/22\n    └── publish.yml           # Publishes to npm on v* tags with --provenance\n```\n\n---\n\n## ⚙️ Configuration reference\n\n### Environment variables\n\n| Variable | Required | Default | Description |\n| --- | :---: | --- | --- |\n| `ILOVEAPI_PROJECT_PUBLIC_KEY` | ✅ | — | Project public key from [developer.ilovepdf.com](https://developer.ilovepdf.com) |\n| `ILOVEAPI_PROJECT_SECRET_KEY` | ✅ | — | Project secret key. **Never logged.** Used for local JWT signing. |\n| `ILOVEAPI_SANDBOX_ROOT` | ❌ | — | Absolute path. When set, **all** input/output paths must resolve *inside* this directory — traversal attempts throw `PATH_TRAVERSAL`. |\n| `PDF_TOOLKIT_DEBUG` | ❌ | — | Set to `1` to emit verbose stderr logs (request shape, phase timings). Secrets never logged. |\n\n### Structured error codes\n\nEvery failure surfaces a `PdfToolkitError` with a stable machine-readable code:\n\n| Code | Trigger | What to tell the user |\n| --- | --- | --- |\n| `MISSING_CREDENTIALS` | Env vars not set | Point them at developer.ilovepdf.com |\n| `INVALID_INPUT` | HTTP 400 / Zod parse failure | Fix the arguments |\n| `AUTH_FAILED` | HTTP 401 | Regenerate the project keys |\n| `PLAN_LIMIT` | HTTP 402 | Free tier exhausted or tool not in plan |\n| `NOT_FOUND` | HTTP 404 | Input file or task missing |\n| `RATE_LIMITED` | HTTP 429 | Back off and retry |\n| `TASK_LIMIT` | SDK `TaskLimit` error | Too many concurrent tasks |\n| `PATH_TRAVERSAL` | Path escapes `ILOVEAPI_SANDBOX_ROOT` | Reject the request |\n| `API_ERROR` | Unmapped iLoveAPI error | Check `data.http_status` + `data.iloveapi_code` |\n\n---\n\n## 🔒 Security model\n\n`pdf-toolkit-mcp` is designed to be safe to install on a developer machine:\n\n- **Stdio only.** The server never opens a network socket; it only makes outbound HTTPS calls to `api.ilovepdf.com` via the official SDK.\n- **No `console.log`.** JSON-RPC over stdio would corrupt on any stray stdout write, so every log line goes through `process.stderr`.\n- **Secrets never persisted.** Credentials live in env vars for the lifetime of the process and are never written to disk, log files, or tool responses.\n- **JWT generated locally.** The `@ilovepdf/ilovepdf-nodejs` SDK self-signs JWTs with your secret key — no secret leaves the machine.\n- **Path sandbox (opt-in).** Set `ILOVEAPI_SANDBOX_ROOT` to constrain the server to a single directory tree; any path resolving outside throws before the API is ever called.\n- **Extension whitelists per tool.** `html_to_pdf` rejects `.exe`; `image_to_pdf` only accepts common raster formats, etc.\n- **MIT licensed, audit-friendly.** ~2k lines of TypeScript. No obfuscation, no minification, no postinstall scripts.\n\n---\n\n## 👩‍💻 Development\n\n```bash\ngit clone https://github.com/EigenCharlie/pdf-toolkit-mcp.git\ncd pdf-toolkit-mcp\nnpm install\n```\n\n### Common tasks\n\n| Command | What it does |\n| --- | --- |\n| `npm run build` | Compile TypeScript → `dist/` |\n| `npm run dev` | Watch-mode build |\n| `npm run typecheck` | `tsc --noEmit` — fast error surface |\n| `npm run lint` | ESLint on `src/` + `tests/` |\n| `npm test` | Vitest unit suite (no network) |\n| `npm run test:integration` | Real iLoveAPI calls (requires creds) |\n| `npm run inspect` | Launch [MCP Inspector](https://github.com/modelcontextprotocol/inspector) against the local build |\n\n### Debugging inside Claude Code\n\n1. Build locally: `npm run build`.\n2. Register the *local* dist instead of npm:\n   ```bash\n   claude mcp remove pdf-toolkit    # if previously registered\n   claude mcp add pdf-toolkit -- node \"$(pwd)/dist/index.js\"\n   ```\n3. Set `PDF_TOOLKIT_DEBUG=1` in your shell before launching Claude Code for verbose stderr.\n4. Stderr is visible with `claude mcp logs pdf-toolkit`.\n\n---\n\n## ✅ Testing & CI\n\n- **Unit tests** — 25 tests across `client`, `paths`, `errors`, and `tools.merge`. Fully mocked, no network. Run with `npm test`.\n- **Integration smoke test** — `tests/integration/smoke.test.ts` spins up two minimal valid PDFs and exercises a real `merge_pdf` end-to-end. Gated on `ILOVEAPI_*_KEY` env vars; automatically skipped in PR CI for security.\n- **CI matrix** — [.github/workflows/ci.yml](.github/workflows/ci.yml) runs `lint → typecheck → build → test` on:\n  - OS: `ubuntu-latest`, `windows-latest`\n  - Node: `18`, `20`, `22`\n\n---\n\n## 🚢 Releasing\n\nPublishing is automated on tag push:\n\n```bash\nnpm version patch           # or minor / major\ngit push --follow-tags\n```\n\nThe [publish workflow](.github/workflows/publish.yml) then:\n1. Re-runs lint + typecheck + build + tests.\n2. Publishes to npm with `--access public --provenance` (supply-chain attestation).\n3. Creates a GitHub Release with auto-generated notes.\n\nRepo secret required: **`NPM_TOKEN`** (npm *automation* token).\n\n---\n\n## 🗺 Roadmap\n\n- [x] v0.1 — 18 PDF tools, stdio transport, plugin + skill, CI, npm publish\n- [x] v0.1.1 — MCPB bundle (`.mcpb`) for Claude Desktop, marketplace manifest, MCP Registry submission (`mcpName`)\n- [ ] v0.2 — Submit the Claude plugin to `anthropics/claude-plugins-official`, publish an image-tools companion pack\n- [ ] v0.3 — 8 image tools (resize, convert, compress, crop, rotate, watermark, upscale, remove background)\n- [ ] v0.4 — Signature tools (signing flows require paid tier — gated behind env flag)\n- [ ] v1.0 — Optional Streamable-HTTP transport for hosted/multi-user setups\n\nHave a feature request? [Open an issue](https://github.com/EigenCharlie/pdf-toolkit-mcp/issues/new).\n\n---\n\n## 🙋 FAQ\n\n**Is this legal / safe / allowed by iLovePDF?**\nYes. It's a thin open-source client that uses *your* credentials — nothing is resold, relicensed, or proxied. The iLoveAPI Terms of Service explicitly permit open-source libraries using user-provided keys (several community SDKs have existed for years). This project does not ship any keys, does not use \"iLovePDF\"/\"iLoveAPI\" in its package name, and carries the required disclaimer.\n\n**Does it cost money?**\niLoveAPI offers ~2,500 credits per month free (enough for thousands of small ops). Heavier workloads need a paid iLoveAPI plan. This MCP itself is MIT and free forever.\n\n**Does it work offline?**\nNo. iLoveAPI is cloud-only, so every tool call requires internet access.\n\n**Can I pin a specific version?**\nYes: `claude mcp add pdf-toolkit -- npx -y pdf-toolkit-mcp@0.1.0`.\n\n**Can I self-host?**\nYes. Clone the repo, `npm run build`, and point your client at `node ./dist/index.js`. The server is entirely stateless.\n\n**What happens if iLoveAPI is down?**\nThe tool returns a `PdfToolkitError` with `code: \"API_ERROR\"` and `data.http_status`. Claude can retry with exponential backoff on your behalf.\n\n**Can I use this without Claude?**\nYes — any MCP-compatible client works: Cursor, Windsurf, Zed, MCP Inspector, custom clients. The server is 100% spec-compliant.\n\n---\n\n## 🤝 Contributing\n\nContributions welcome! Small checklist before opening a PR:\n\n1. `npm run lint && npm run typecheck && npm test` → all green.\n2. New tools follow the pattern in [src/tools/merge.ts](src/tools/merge.ts) (Zod schema → `runTask` → `writeOutputAndReport`).\n3. Add at least one unit test.\n4. Update the [Tool catalog](#-tool-catalog) in this README if you add/rename a tool.\n\nBug reports are even more welcome — include the tool name, the arguments, and (if safe to share) the stderr output.\n\n---\n\n## 📜 License & trademarks\n\nReleased under the [MIT License](./LICENSE) © 2026 Carlos.\n\n\"iLovePDF\" and \"iLoveAPI\" are trademarks of **iLovePDF SL**. This project is an independent, community-built client and is **not affiliated with, endorsed by, sponsored by, or certified by iLovePDF SL**. The package name intentionally avoids both marks.\n\n---\n\n## 🙏 Credits\n\n- [iLovePDF](https://www.ilovepdf.com) / [iLoveAPI](https://www.iloveapi.com) — the cloud PDF processing API that powers every tool call.\n- [Anthropic](https://www.anthropic.com) — for [Claude](https://www.anthropic.com/claude), [Claude Code](https://docs.claude.com/claude-code), and the [Model Context Protocol](https://modelcontextprotocol.io) specification.\n- [`@modelcontextprotocol/sdk`](https://www.npmjs.com/package/@modelcontextprotocol/sdk), [Zod](https://zod.dev), [Vitest](https://vitest.dev), [ESLint](https://eslint.org) — the toolchain this project stands on.\n- Every contributor who reports issues, suggests tools, and sends pull requests. 🙌\n",
  "bytes": 22220,
  "sha": "98edab466ca080d5d607e1956893c36af8ed6b5ececca083dd1b1117b3fd7d23",
  "repo_slug": "eigencharlie/pdf-toolkit-mcp",
  "fonte": "repo",
  "truncated": false,
  "api": "https://agentalog.com/api/listings/mcp_io_github_eigencharlie_pdf_toolkit_mcp_9fb4705f/readme"
}