A step-by-step guide to using the Anthropic and readPDF nodes in n8n, with full importable workflow JSON.
Here's the quick version: to use Claude in an n8n workflow, add an n8n-nodes-base.anthropic node and set your Anthropic API key as a credential. To extract text from PDFs before sending to Claude, chain an n8n-nodes-base.readpdf node first. Its text output becomes the prompt input for Claude.
The two nodes together cover the most common n8n + Claude pattern: ingest a document, extract its text, then have Claude summarize, classify, or answer questions about it. All without writing code.
Why These Two Nodes Together?
n8n ships native integrations for both Anthropic and PDF reading, and they compose naturally. The readPDF node handles binary-to-text conversion. The Anthropic node handles the API call. You connect them with a single wire and the workflow does the rest.
This combination unlocks a large class of document-processing automations that previously required Python scripts or dedicated document-intelligence SaaS tools:
- Summarize incoming contracts or invoices the moment they land in a shared inbox
- Classify uploaded research papers by topic and route them to the right Notion database
- Extract structured data from PDF reports and write the results to a Google Sheet
- Answer questions about a PDF using Claude, then post the answer to Slack
Setting Up the Anthropic Node
The Anthropic node is bundled in n8n's standard node library. No extra install needed. It supports Text and Chat operations and maps directly to the Anthropic Messages API.
Step 1: Add credentials. Go to Settings, then Credentials, then New. Search for "Anthropic" and paste your API key. The credential type is simply "Anthropic API," one field.
Step 2: Configure the node. In the node editor, the key fields are:
resource / operation: Set resource to text and operation to complete for a single-turn call, or use chat / sendMessage for a conversational flow.
model: The model ID string, for example claude-sonnet-4-6 or claude-haiku-4-5-20251001. Use Haiku for high-volume document classification. Use Sonnet for extraction and reasoning tasks.
prompt (Text operation) or messages (Chat operation): Reference the upstream node output here using an expression, for example {{ $json.text }} when chaining after a readPDF node.
maxTokensToSample: Cap the response length. 1024 is a safe default for summaries. Bump to 4096 for structured extraction where you need complete JSON output.
Minimal workflow JSON (Anthropic node only)
Import this via Workflows, then Import from JSON:
{
"nodes": [
{
"parameters": {
"prompt": "Summarize the following text in three bullet points:\n\n{{ $json.body }}"
},
"type": "n8n-nodes-base.anthropic",
"typeVersion": 1,
"position": [460, 300],
"name": "Claude – Summarize",
"credentials": {
"anthropicApi": {
"name": "Anthropic API"
}
}
}
]
}
The "type": "n8n-nodes-base.anthropic" field is how n8n identifies the node internally. You'll see this string in exported workflow JSON whenever the Anthropic node appears.
Reading PDFs Before Sending to Claude
The n8n-nodes-base.readpdf node converts a binary PDF attachment into plain text. It has no configuration options. You pass it a binary item and it outputs a text field. That text field is what you reference in the Anthropic node's prompt expression.
Where the binary comes from. The most common upstream nodes that produce PDF binary data are:
- Gmail / Outlook: attachment extraction from incoming emails
- HTTP Request: fetching a PDF from a URL, with response format set to file
- Google Drive / Dropbox: downloading a file by ID
- Webhook: receiving a multipart/form-data upload
In all cases, the binary field is typically called data. The readPDF node picks this up automatically unless you override the binary property name.
The readPDF node in workflow JSON
{
"parameters": {
"options": {}
},
"type": "n8n-nodes-base.readpdf",
"typeVersion": 1,
"position": [240, 300],
"name": "Extract PDF Text"
}
No required parameter beyond the node type itself. The node reads whatever binary is in the input item's data property and writes the extracted text to $json.text on the output item.
Full Workflow: PDF to Claude to Slack
Here is a complete, importable n8n workflow JSON that watches a Gmail inbox for PDF attachments, extracts their text, sends the text to Claude for summarization, and posts the summary to Slack.
{
"name": "PDF Summarizer via Claude",
"nodes": [
{
"parameters": {
"pollTimes": { "item": [{ "mode": "everyMinute" }] },
"filters": { "readStatus": "unread" },
"downloadAttachments": true
},
"type": "n8n-nodes-base.gmailTrigger",
"typeVersion": 1,
"position": [0, 300],
"name": "Gmail – New Email with Attachment"
},
{
"parameters": {
"conditions": {
"string": [{
"value1": "={{ $binary.data.mimeType }}",
"operation": "contains",
"value2": "pdf"
}]
}
},
"type": "n8n-nodes-base.if",
"typeVersion": 1,
"position": [220, 300],
"name": "Is PDF?"
},
{
"parameters": { "options": {} },
"type": "n8n-nodes-base.readpdf",
"typeVersion": 1,
"position": [440, 240],
"name": "Extract PDF Text"
},
{
"parameters": {
"model": "claude-haiku-4-5-20251001",
"prompt": "Summarize the following document in 3-5 bullet points. Be concise and focus on the key facts.\n\n{{ $json.text }}",
"maxTokensToSample": 1024
},
"type": "n8n-nodes-base.anthropic",
"typeVersion": 1,
"position": [660, 240],
"name": "Claude – Summarize PDF",
"credentials": {
"anthropicApi": { "name": "Anthropic API" }
}
},
{
"parameters": {
"channel": "#document-summaries",
"text": "=*New PDF summary:*\n{{ $json.completion }}"
},
"type": "n8n-nodes-base.slack",
"typeVersion": 2,
"position": [880, 240],
"name": "Post to Slack"
}
],
"connections": {
"Gmail – New Email with Attachment": {
"main": [[{ "node": "Is PDF?", "type": "main", "index": 0 }]]
},
"Is PDF?": {
"main": [[{ "node": "Extract PDF Text", "type": "main", "index": 0 }]]
},
"Extract PDF Text": {
"main": [[{ "node": "Claude – Summarize PDF", "type": "main", "index": 0 }]]
},
"Claude – Summarize PDF": {
"main": [[{ "node": "Post to Slack", "type": "main", "index": 0 }]]
}
}
}
Key things to observe:
- The readPDF output is accessed via
{{ $json.text }}in the Anthropic node's prompt - Claude's response is in
{{ $json.completion }}for the Text operation (or{{ $json.content[0].text }}for the Chat operation) - Claude Haiku is used here for cost efficiency. Swap to Sonnet for complex extraction
Structured Extraction: Getting JSON Out of Claude
For workflows that need to write data to a spreadsheet or database, you want Claude to return structured JSON rather than prose. Here's the prompt pattern that works reliably:
Extract the following fields from the invoice text and return ONLY valid JSON.
Do not include markdown code fences. Do not include any explanation.
Fields to extract:
- invoice_number (string)
- vendor_name (string)
- total_amount (number)
- due_date (ISO 8601 date string)
- line_items (array of { description, quantity, unit_price, total })
Invoice text:
{{ $json.text }}
After the Anthropic node, add a Code node to parse the output:
// Code node — parse Claude's JSON response
const raw = $input.first().json.completion;
const parsed = JSON.parse(raw.trim());
return [{ json: parsed }];
The parsed object then flows downstream as normal n8n item data, ready to map into a Google Sheets row, an Airtable record, or a database insert.
Handling Long PDFs (Token Limits)
Claude Haiku and Sonnet both support up to 200k input tokens. Most PDFs fall well within that limit. However, n8n-nodes-base.readpdf extracts all text at once. For very long documents (500+ pages), you may want to truncate or chunk the text before passing it to Claude.
Add a Code node between readPDF and the Anthropic node to cap the input:
// Truncate to first ~100k characters (~75k tokens)
const MAX_CHARS = 100_000;
const text = $input.first().json.text ?? '';
return [{ json: { text: text.slice(0, MAX_CHARS) } }];
For genuine multi-part documents, consider a map/loop pattern: split the text into overlapping chunks, run Claude on each, then combine the results with a final merge-and-consolidate call.
Common Errors and Fixes
readPDF: "No binary data found in item." The upstream node didn't pass a binary field named data. Check the binary property name in the previous node (Gmail attachment might name it attachment_0). Open the node output panel, click the binary tab, and copy the exact field name, then set it in readPDF's "Binary Property" option.
Anthropic: "Authentication failed." Your Anthropic credential is missing or the API key is wrong. Go to Settings, then Credentials, find the Anthropic credential, and re-enter the key from console.anthropic.com.
Anthropic: Empty completion or content field. This usually means maxTokensToSample was too low, or the prompt expression resolved to an empty string. Check that {{ $json.text }} is non-empty in the previous node's output before the Anthropic node fires. Add an IF node to skip items where text.length === 0.
JSON.parse fails on Claude's structured extraction output. Claude occasionally wraps JSON in markdown code fences even when told not to. Add a cleanup step before parsing:
const raw = $input.first().json.completion
.replace(/^```
{% endraw %}
json\n?/i, '')
.replace(/
{% raw %}
```$/, '')
.trim();
const parsed = JSON.parse(raw);
Going Further
The readPDF to Anthropic chain is one pattern. The broader playbook for n8n + Claude automation covers webhook triggers, scheduled document processing, multi-step reasoning chains, and memory across workflow runs.
I publish detailed playbooks for n8n workflow building and API integration at claudecodehq.com. If you want to go further with Claude in agentic pipelines (tool use, multi-step reasoning, or building your own Claude-powered integrations beyond n8n), the MCP servers guide and AI agent walkthrough on the site cover those patterns in depth.
Originally published on claudecodehq.com
Top comments (0)