One Article Into a Week of Posts

Build an n8n pipeline that turns any blog URL into three platform-ready posts.

Introduction

30 Second Summary

You publish a great article, then forget to share it anywhere else. Most creators know they should repurpose content for LinkedIn, X, and email, but rewriting the same ideas three different ways eats hours every week.

In this project, you will build an automation pipeline that takes any blog post URL and generates three platform-tailored social posts from it. Each post lands in a review queue with a "Draft" status, ready for you to approve before publishing.

What You'll Build

Paste a blog post URL into your n8n workflow and watch three platform-tailored posts appear in your Airtable review queue within seconds, each written in the right tone for LinkedIn, X, or email.

By the end of this project, you'll have:

  • A working content-repurposing pipeline where you paste any blog post URL and get back three platform-ready posts in seconds.
  • AI-adapted content for each platform, with the right tone, length, and formatting for LinkedIn vs X vs email.
  • An Airtable review queue where every generated batch lands with a "Draft" status, ready for approval before publishing.
  • Secret Mission: Add an Instagram caption with hashtags as a fourth platform output.

Are there any prerequisites?

This project uses Docker to run n8n locally. Step 1 includes setup instructions for every tool you need, including Docker if you don't have it yet.

Before We Start

Before we dive in, let's get clear on what you're building and why it matters.

Set Up n8n, OpenRouter, and Airtable

Your content pipeline needs three tools working in concert: an orchestration platform to wire the steps together, an LLM API to generate the posts, and a database to collect the output for review.

In this step, you will get all three running. n8n handles the automation, OpenRouter gives you free access to AI models, and Airtable stores every generated batch in a review queue.

In this step, get ready to:
  • Start n8n locally with Docker and sign in to the workflow editor.
  • Create a free OpenRouter account and generate an API key.
  • Set up an Airtable content review queue with the right columns and a Personal Access Token.
Start n8n locally with Docker

n8n is an open-source workflow automation tool. You will run it locally using Docker, which keeps everything self-contained in a container.

  • Confirm Docker is running by opening your terminal and running this command:
docker --version

✔️ I see a version number

Docker is ready. Move on to the next instruction.

ⓧ Command not found

Docker is not installed. Install it from the official Docker website.

  • Open https://docs.docker.com/get-docker/ in your browser and follow the installation instructions for your operating system.
  • After installation, restart your terminal and run docker --version again to confirm it works.

n8n provides a one-line setup command that downloads everything you need and starts the server automatically.

  • Move to your Desktop by running this command:
cd ~/Desktop
  • Install and start n8n by running this command:
curl -fsSL https://get.n8n.io | sh -s -- --version 2.35.0

What does this command do?

This script downloads a Docker Compose configuration into an n8n folder on your Desktop, generates unique secrets in a .env file, and starts the n8n container.

It may take a minute while Docker pulls the container image for the first time.

  • Wait for the command to finish. You should see output confirming that n8n is running.
  • Open your browser and go to http://localhost:5678.

n8n displays a signup screen on first launch. This creates your local owner account.

  • Enter your name, email, and a password. Your password must be at least 8 characters and include at least one number and one capital letter.
  • Click Next.

n8n logs you in and shows the workflow editor welcome screen.

Don't see the n8n signup screen?

  • Make sure Docker Desktop (or the Docker daemon) is running before you execute the setup command.
  • Check your terminal output for errors. If the port is already in use, stop whatever is running on port 5678 and try again.
  • Try refreshing the browser page. The container may need a few extra seconds to finish starting.

Still stuck? Help me troubleshoot why n8n isn't loading at localhost:5678.

Get your LLM API key

Your pipeline needs an AI model to generate social posts. OpenRouter is a gateway that gives you access to 25+ free models at $0 per token, with 50 requests per day on a free account.

  • Open https://openrouter.ai in your browser.
  • Click Sign In and create a free account using Google or email.

Once you are signed in, you need to create an API key so n8n can call OpenRouter's models.

  • Go to https://openrouter.ai/settings/keys.
  • Click Create new secret key.
  • Give the key a name like n8n-content-pipeline and click Create.
  • Copy the key and paste it somewhere safe (a text file or password manager). You will not be able to see it again after closing the dialog.

Why OpenRouter?

OpenRouter acts as a single gateway to hundreds of models. n8n has a native OpenRouter Chat Model node, so you can switch between models by changing a dropdown. No credential reconfiguration needed.

The free tier includes models like Google Gemma 4, NVIDIA Nemotron, and OpenAI gpt-oss-20b. That is more than enough power for content generation.

Having trouble creating an OpenRouter account?

  • If the sign-in page does not load, try a different browser or disable your ad blocker.
  • If you already have an OpenRouter account, you can use your existing key. Just make sure it has not been revoked.

Need more help? Help me set up my OpenRouter account and generate an API key.

Create your Airtable content queue

Airtable is where every generated batch of posts will land as a row, ready for human review. You need a base with a table that has a column for each platform's output.

✔️ I already have an Airtable account

Sign in to Airtable and continue to the next instruction.

ⓧ I need to create an account

  • Open https://airtable.com in your browser.
  • Click Sign up for free and create your account with Google or email.

What about the Team trial?

Airtable automatically starts a 14-day Team plan trial when you create your first workspace. You do not need to enter a payment method. After 14 days, you can stay on the Free plan at no cost.

Do not add a payment method during the trial. Adding one automatically upgrades your workspace and starts billing.

Now create the base and table that will hold your generated content.

  • On the Airtable home screen, click + Create.
  • Select your workspace, then choose Build an app on your own.
  • Click the base name at the top (it defaults to "Untitled Base") and rename it to Content Multiplier.
  • Double-click the default table tab ("Table 1") and rename it to Content Queue.

The default table comes with placeholder columns. You need to replace them with columns for your pipeline.

  • Click the header of the first column ("Name" or "Names"). Click the dropdown arrow and select Customize field type.
  • Rename it to Source URL and change the field type to URL. Click Save.
  • Delete the remaining default columns (Notes, Attachments, Status) by clicking each column header, selecting the dropdown arrow, and clicking Delete field.

Now add the columns your pipeline will write to.

  • Click the + icon to the right of the field headers to add a new field.
  • Name it LinkedIn Post and set the field type to Long text. Click Create field.
  • Repeat this process to add three more Long text fields: X Thread, and Email Blurb.
  • Add a field named Status with the type Single line text.
  • Add a field named Generated At with the type Date.

Your Content Queue table should now have six columns: Source URL, LinkedIn Post, X Thread, Email Blurb, Status, and Generated At.

Missing a column or wrong field type?

  • Click any column header, then the dropdown arrow, and select Customize field type to rename it or change its type.
  • Make sure the column names match exactly, including capitalization. n8n will reference these names later.

Need help fixing your table? Help me set up my Airtable Content Queue table with the right columns.

The last piece is generating an Airtable Personal Access Token so n8n can write to your table.

  • Open https://airtable.com/create/tokens in a new browser tab.
  • Click + Create new token.
  • Give the token a name like n8n-content-pipeline.
  • Under Scopes, add these three scopes: data.records:read, data.records:write, and schema.bases:read.
  • Under Access, select your Content Multiplier base.
  • Click Create token.
  • Copy the token and save it alongside your OpenRouter API key. You will not be able to see it again.

What are these scopes for?

The data.records:read and data.records:write scopes let n8n read from and write to your table. The schema.bases:read scope lets n8n discover your table names and column structure so it can show them in dropdown menus.

Can't find the token creation page?

  • Make sure you are signed in to Airtable before visiting the token page.
  • The direct URL is https://airtable.com/create/tokens. You can also reach it from your Airtable account settings under Personal access tokens.

Still stuck? Help me create an Airtable Personal Access Token with the right scopes.

Your tooling is locked in. Next up, you will build the first part of the pipeline: scraping an article so the AI has raw material to work with.

Scrape an Article

Your tools are in place. n8n is running, your OpenRouter key is ready, and your Airtable review queue is waiting for content.

Every content pipeline starts with raw material. Before the AI can generate platform-tailored posts, it needs clean article text from a URL. Raw HTML is full of navigation menus, sidebars, and script tags. In this step, you will build the first half of the pipeline: fetching a blog post and stripping it down to just the words that matter.

In this step, get ready to:
  • Add a Manual Trigger and HTTP Request node to fetch a blog post URL.
  • Extract clean article text using the HTML node.
Add the trigger and HTTP Request node

Every n8n workflow starts with a trigger node that decides when the workflow runs. For testing, a Manual Trigger lets you run the workflow on demand with one click.

  • In the n8n workflow editor, click the + button in the top right corner of the canvas to create a new workflow.
  • n8n adds a Manual Trigger node to the canvas by default.

What is a trigger node?

A trigger node is the starting point of any n8n workflow. It defines what kicks off the automation. The Manual Trigger fires when you click Test workflow in the editor. In production, you could swap it for a webhook, a schedule, or an event from another app.

Now you need a node to fetch the blog post. The HTTP Request node can call any URL and return the response.

  • Click the + connector on the right edge of the Manual Trigger node.
  • Search for HTTP Request in the node panel and select it.
  • The HTTP Request node opens its configuration panel. Leave Method set to GET (the default).
  • In the URL field, paste a blog post URL you want to repurpose. Any article with a few paragraphs of text works. For example: https://blog.n8n.io/what-is-workflow-automation/.
  • Scroll down and click Add Option, then select Response.
  • Set Response Format to Text. This stores the raw HTML as a readable string instead of a binary file.

Why set the response format to Text?

By default, the HTTP Request node auto-detects the response type. When it receives HTML, it stores it as a binary object, which is hard to read and harder for the next node to parse. Setting it to Text keeps the HTML as a plain string in a field called data, which makes it easy to inspect and pass to the HTML node.

Before you run the workflow, what do you think you will see in the output panel? Raw article text, or something messier?

  • Click Test step at the bottom of the HTTP Request node's configuration panel.

The output panel fills with raw HTML. You can see the article text buried in there, but it is surrounded by <div> tags, <nav> menus, <script> blocks, and other markup. This is not clean enough to feed to an AI model.

Not seeing any output?

  • Make sure the URL you entered is a valid, publicly accessible blog post. Try opening it in a new browser tab to confirm it loads.
  • Check that Method is set to GET, not POST or another method.
  • If you see a timeout error, the site might be blocking automated requests. Try a different blog post URL.

Why is my HTTP Request node not returning any data?

Extract clean article text with the HTML node

The raw HTML has everything you need, but buried under layers of markup. The HTML node can target a specific part of the page using a CSS selector and return just the text content, with no tags.

  • Close the HTTP Request node's configuration panel by clicking the X or clicking the canvas background.
  • Click the + connector on the right edge of the HTTP Request node.
  • Search for HTML in the node panel and select it.

The HTML node opens. Now configure it to extract just the article text.

  • Set Operation to Extract HTML Content.
  • Set Source Data to JSON.
  • In the JSON Property field, enter data. This is the field where the HTTP Request node stored the HTML string.
  • Under Extraction Values, click Add Value.
  • Set Key to article_text. This is the name your extracted content will be saved under.
  • Set CSS Selector to article. This targets the <article> element that most blogs wrap their post content in.
  • Set Return Value to Text.

What is a CSS selector?

A CSS selector is a pattern that targets specific HTML elements on a page. The selector article targets any <article> tag, which is the standard semantic element most blogs use to wrap their main content.

If your blog does not use an <article> tag, try main or .post-content. You can find the right selector by right-clicking the article text in your browser and selecting Inspect.

One more setting to enable before you test.

  • Click Add Option at the bottom of the HTML node panel.
  • Turn on Clean Up Text. This strips leading and trailing whitespace, removes line breaks, and condenses multiple spaces into one.

Why enable Clean Up Text?

Raw HTML text extraction often leaves behind extra whitespace, blank lines, and inconsistent spacing. Clean Up Text condenses all of that into a single, readable block of text. This gives the AI model a much cleaner input to work with, which leads to better output.

Your workflow now has three connected nodes: Manual Trigger, HTTP Request, and HTML. Before you run it, what do you expect to see in the HTML node's output this time?

  • Click Test step at the bottom of the HTML node's configuration panel.

The output panel now shows a clean, readable block of article text under the article_text field. No HTML tags, no navigation menus, no script blocks.

Seeing empty output or missing text?

  • If the article_text field is empty, the CSS selector did not match any element on the page. Try changing article to main or body and test again.
  • Make sure JSON Property is set to data (all lowercase). This must match the field name from the HTTP Request node's output.
  • Confirm Source Data is set to JSON, not Binary.

Why is my HTML node returning empty text?

✔️ Awesome, I've got everything!

Great. Confirm you have three connected nodes on the canvas: Manual Trigger, HTTP Request, and HTML. The HTML node's output should show clean article text with no HTML tags.

ⓧ I'd like to double check the full setup

Scroll up and confirm each node is configured as follows:

  • Manual Trigger: default settings, no changes needed.
  • HTTP Request: Method is GET. URL contains your blog post link. Under Options, Response Format is set to Text.
  • HTML: Operation is Extract HTML Content. Source Data is JSON. JSON Property is data. Key is article_text. CSS Selector is article. Return Value is Text. Clean Up Text is turned on.

You have raw material. The pipeline can now pull clean text from any blog post URL in seconds. Next up, you will connect this text to an AI model that transforms it into three platform-tailored posts.

Generate Platform Posts with AI

Your workflow now pulls clean article text from any blog post URL. The next challenge is transforming that raw text into posts tailored for three different platforms.

Each platform has its own expectations. LinkedIn rewards professional hooks and paragraph breaks. X demands tweets under 280 characters. Email newsletters need a compelling subject line. In this step, you will connect an LLM to your workflow through OpenRouter and write a prompt that generates all three post types from a single article.

In this step, get ready to:
  • Add a Basic LLM Chain node with an OpenRouter Chat Model to your workflow.
  • Write a prompt that generates a LinkedIn post, an X thread, and an email newsletter blurb from the article text.
Add the Basic LLM Chain and OpenRouter Chat Model

The Basic LLM Chain node takes a prompt and sends it to whichever language model you connect. You will attach an OpenRouter Chat Model sub-node to it so your workflow can call a free LLM through the OpenRouter API.

  • In your workflow canvas, select the Add node connector on the HTML node. n8n opens the nodes panel.
  • Search for Basic LLM Chain and select it. n8n adds the node to the canvas and opens it.
  • Inside the Basic LLM Chain node, click the + Chat Model button at the bottom of the node panel. n8n opens a selection of available Chat Models.
  • Search for OpenRouter Chat Model and select it. n8n adds it as a sub-node and opens it for configuration.

What is the Basic LLM Chain?

In n8n, AI features are built with cluster nodes. A root node (the Basic LLM Chain) defines the main behavior, and one or more sub-nodes extend it. Here, the OpenRouter Chat Model sub-node tells the Basic LLM Chain which language model to call.

The Basic LLM Chain is the right choice for a single-prompt workflow like this one. It sends your prompt once and returns the result. No tool-calling or memory is needed.

Now connect your OpenRouter API key so the Chat Model can authenticate.

  • In the OpenRouter Chat Model sub-node, select the Credential to connect with dropdown.
  • Select Create new credential. n8n opens the credentials view.
  • Paste your OpenRouter API key from Step 1 into the API Key field.
  • Select Save. n8n returns to the node with your new credential selected.
  • In the Model dropdown, select any free model. Good options include Google Gemma 4 26B or NVIDIA Nemotron 3 Super. n8n dynamically loads models from your OpenRouter account, so you will only see models available to you.
  • Close the OpenRouter Chat Model sub-node to return to the Basic LLM Chain node.

Your Basic LLM Chain node should now show the OpenRouter Chat Model connected beneath it on the canvas.

Don't see any models in the dropdown?

Make sure you saved your credential before opening the Model dropdown. If the dropdown is empty, close the node, reopen it, and try again. Your OpenRouter account must have at least one model available.

Help me connect my OpenRouter Chat Model in n8n. The model dropdown is empty even after I saved my API key credential.

Write the content-repurposing prompt

The prompt is what tells the model exactly how to transform the article text. A well-structured prompt specifies the platform, word count, tone, and formatting for each post type.

  • In the Basic LLM Chain node, find the Prompt dropdown and set it to Define below.
  • In the Prompt (User Message) field that appears, paste the following prompt:
You are an expert content repurposer. Take the following article and create three platform-tailored posts from it.

1. LINKEDIN POST
Write a professional LinkedIn post (150-200 words). Start with a bold hook line. Use short paragraphs and line breaks for readability. End with a call-to-action question to drive engagement.

2. X THREAD
Write an X (Twitter) thread of 3-5 tweets. Each tweet must be under 280 characters. Start with a hook tweet that makes people stop scrolling. End with a CTA tweet. Separate each tweet with "---".

3. EMAIL NEWSLETTER BLURB
Write an email newsletter blurb (100-150 words). Include a compelling subject line on the first line prefixed with "Subject: ". Keep the tone conversational but informative.

Here is the article:
{{ $json.article_text }}

What does this prompt do?

The prompt gives the LLM three separate assignments in a single request. Each section specifies the platform, target length, tone, and formatting rules.

The expression {{ $json.article_text }} is n8n's way of referencing data from the previous node. It pulls the clean article text that the HTML node extracted in Step 2 and injects it into the prompt at runtime.

✔️ Awesome, I've got everything!

Great. Make sure you have saved the prompt in the Basic LLM Chain node before moving on.

ⓧ I'd like to double check the full prompt

Your prompt should match this text exactly. Pay close attention to the {{ $json.article_text }} expression at the bottom.

You are an expert content repurposer. Take the following article and create three platform-tailored posts from it.

1. LINKEDIN POST
Write a professional LinkedIn post (150-200 words). Start with a bold hook line. Use short paragraphs and line breaks for readability. End with a call-to-action question to drive engagement.

2. X THREAD
Write an X (Twitter) thread of 3-5 tweets. Each tweet must be under 280 characters. Start with a hook tweet that makes people stop scrolling. End with a CTA tweet. Separate each tweet with "---".

3. EMAIL NEWSLETTER BLURB
Write an email newsletter blurb (100-150 words). Include a compelling subject line on the first line prefixed with "Subject: ". Keep the tone conversational but informative.

Here is the article:
{{ $json.article_text }}

Time to test the full pipeline. Before you run it, think about what you expect the output to look like. Will the LLM return three cleanly separated fields, or something else?

  • Close the Basic LLM Chain node to return to the canvas.
  • Run the entire workflow by pressing Ctrl+Enter (Windows) or Cmd+Enter (macOS), or by selecting Execute Workflow.
  • Wait for all nodes to finish executing. This may take 10-20 seconds while the LLM generates its response.
  • Double-click the Basic LLM Chain node to open it and view its output panel.

You will see all three posts in the output. The LinkedIn post, X thread, and email blurb are all there. But look closely at the format.

The entire response is a single text string. All three posts are combined into one blob with no structured separation between them.

Why is the unstructured output a problem?

Your Airtable review queue has separate columns for LinkedIn Post, X Thread, and Email Blurb. To fill those columns, you need each post as its own distinct field.

Right now, all three posts live in one text string. There is no reliable way to split them apart programmatically. The model might change its formatting slightly between runs, so parsing by line breaks or headings would be fragile. This is the gap that the next step fixes with structured output.

Seeing an error instead of output?

If you see a "No prompt specified" error, make sure the Prompt dropdown is set to Define below and that you pasted the prompt text into the Prompt (User Message) field.

If you see a credential or authentication error, open the OpenRouter Chat Model sub-node and confirm your API key is saved correctly. You can re-paste it and click Save again.

Help me troubleshoot my Basic LLM Chain node in n8n. I'm getting an error when I try to run the workflow with OpenRouter.

Your workflow can now generate all three platform posts from a single article. The content is there, but it is stuck in one unstructured blob. Next up, you will use a Structured Output Parser to split the response into clean, separate fields that map directly to your Airtable columns.

Structure the AI Output

Your workflow generates all three platform posts from a single article. The problem is that the output comes back as one continuous text blob.

To send each post to its own Airtable column, the LLM needs to return structured data with a separate field for each platform. In this step, you'll add a Structured Output Parser that forces the model to return clean JSON with a dedicated field for LinkedIn, X, and email.

In this step, get ready to:
  • Enable structured output on the Basic LLM Chain and attach a Structured Output Parser with a JSON Schema.
  • Update the prompt to reference each schema field by name and verify the structured JSON output.
Enable structured output and add the parser

The Basic LLM Chain node currently returns whatever text the LLM generates. Turning on structured output tells n8n to enforce a specific shape on the response using a schema you define.

  • Click on the Basic LLM Chain node on the canvas to open its settings panel.
  • Scroll down to find the Require Specific Output Format toggle.
  • Turn the toggle on.

A new output parser attachment point appears below the node on the canvas.

  • Click the output parser attachment point.
  • Select Structured Output Parser from the list of available parsers.

What is a Structured Output Parser?

Instead of letting the LLM return free-form text, the Structured Output Parser tells the model to return data matching a JSON Schema you define. It then validates the response before passing it to the next node.

This means downstream nodes can reference individual fields like linkedin_post instead of trying to parse a wall of text.

The Structured Output Parser settings panel should now be open. Configure the schema that defines the three fields you need.

  • Set Schema Type to Define using JSON Schema.
  • Clear any placeholder text in the JSON Schema field, then paste this schema:
{
  "type": "object",
  "properties": {
    "linkedin_post": {
      "type": "string",
      "description": "A professional LinkedIn post, 150-200 words with a hook opening and CTA"
    },
    "x_thread": {
      "type": "string",
      "description": "An X thread of 3-5 tweets each under 280 characters, separated by ---"
    },
    "email_blurb": {
      "type": "string",
      "description": "An email newsletter blurb with Subject: line, 100-150 words"
    }
  },
  "required": ["linkedin_post", "x_thread", "email_blurb"]
}

What does this schema do?

  • Each property (linkedin_post, x_thread, email_blurb) tells the LLM to return a separate string field for that platform's post.
  • The description values give the model context about what each field should contain.
  • The required array ensures all three fields are always present in the response.
  • Close the Structured Output Parser settings panel by clicking Back or clicking outside the panel.
  • On the canvas, confirm that the Structured Output Parser sub-node appears connected below the Basic LLM Chain node.

Don't see the Structured Output Parser on the canvas?

  • Make sure the Require Specific Output Format toggle is turned on in the Basic LLM Chain settings. The output parser attachment point only appears when this setting is enabled.
  • If the parser node appears disconnected, drag a connection line from the output parser attachment point on the Basic LLM Chain to the parser node.

Ask NextWork AI: Why isn't my Structured Output Parser connecting to the Basic LLM Chain in n8n?

Update the prompt to reference the schema fields

The current prompt uses numbered headings like "1. LINKEDIN POST" to separate each platform's instructions. The Structured Output Parser needs the prompt to reference field names from the schema instead, so the model knows which JSON key to put each platform's content into.

  • Click on the Basic LLM Chain node to open its settings.
  • Click into the Prompt text field.
  • Select all the existing prompt text and delete it.
  • Paste this updated prompt:
You are an expert content repurposer. Take the following article and create three platform-tailored posts from it.

For the linkedin_post field: Write a professional LinkedIn post (150-200 words). Start with a bold hook line. Use short paragraphs and line breaks for readability. End with a call-to-action question to drive engagement.

For the x_thread field: Write an X (Twitter) thread of 3-5 tweets. Each tweet must be under 280 characters. Start with a hook tweet that makes people stop scrolling. End with a CTA tweet. Separate each tweet with "---".

For the email_blurb field: Write an email newsletter blurb (100-150 words). Include a compelling subject line on the first line prefixed with "Subject: ". Keep the tone conversational but informative.

Here is the article:
{{ $json.article_text }}

What changed in the prompt?

The numbered headings ("1. LINKEDIN POST") are replaced with field references ("For the linkedin_post field:"). This tells the model exactly which JSON key to put each platform's content into.

The writing instructions for each platform stay the same. Only the section headers changed to match the schema's field names.

  • Close the Basic LLM Chain settings panel.

Before you run the workflow, think about what you expect the output to look like. Will the LLM still return a single text blob, or something different?

  • Click the Test workflow button to run the full workflow from the Manual Trigger.
  • Once the run finishes, click on the Basic LLM Chain node and open its Output panel.

The output panel now shows a clean JSON object with three separate fields: linkedin_post, x_thread, and email_blurb. Each field contains the platform-specific post as its own string value.

Still seeing unstructured text or an error?

  • Check that the Require Specific Output Format toggle is turned on in the Basic LLM Chain settings.
  • Verify that the Structured Output Parser sub-node is connected on the canvas below the Basic LLM Chain.
  • If the LLM returns a parsing error, open the Structured Output Parser and check for syntax errors in the JSON Schema (mismatched brackets, missing commas, or extra trailing commas).
  • If the model returns empty fields, try running the workflow one more time. Free-tier models occasionally produce inconsistent results on the first attempt.

Ask NextWork AI: My Structured Output Parser is returning an error or empty fields when I run the workflow. How do I fix it?

✔️ Awesome, I've got everything!

Great. Double check that you've saved your workflow by pressing Cmd+S (macOS) or Ctrl+S (Windows).

ⓧ I'd like to double check the full code

Here are the two pieces you configured in this step. Confirm each one matches.

Your Structured Output Parser JSON Schema should be:

{
  "type": "object",
  "properties": {
    "linkedin_post": {
      "type": "string",
      "description": "A professional LinkedIn post, 150-200 words with a hook opening and CTA"
    },
    "x_thread": {
      "type": "string",
      "description": "An X thread of 3-5 tweets each under 280 characters, separated by ---"
    },
    "email_blurb": {
      "type": "string",
      "description": "An email newsletter blurb with Subject: line, 100-150 words"
    }
  },
  "required": ["linkedin_post", "x_thread", "email_blurb"]
}

Your Basic LLM Chain Prompt should be:

You are an expert content repurposer. Take the following article and create three platform-tailored posts from it.

For the linkedin_post field: Write a professional LinkedIn post (150-200 words). Start with a bold hook line. Use short paragraphs and line breaks for readability. End with a call-to-action question to drive engagement.

For the x_thread field: Write an X (Twitter) thread of 3-5 tweets. Each tweet must be under 280 characters. Start with a hook tweet that makes people stop scrolling. End with a CTA tweet. Separate each tweet with "---".

For the email_blurb field: Write an email newsletter blurb (100-150 words). Include a compelling subject line on the first line prefixed with "Subject: ". Keep the tone conversational but informative.

Here is the article:
{{ $json.article_text }}

Each platform post now lives in its own JSON field, ready to be routed individually. Next up, you'll push these structured outputs into your Airtable review queue so every batch lands as a row ready for human review.

Push to the Airtable Review Queue

Your Structured Output Parser now returns a clean JSON object with separate fields for each platform. That structured data is the key to everything that comes next.

Right now, those posts are trapped inside n8n. Nobody else can see them, review them, or approve them. In this step, you'll connect an Airtable node to your workflow so every generated batch lands as a row in your Content Queue, ready for human review.

In this step, get ready to:
  • Add an Airtable node and connect your credentials.
  • Map the AI-generated fields to your Airtable columns.
  • Run the full pipeline end-to-end and confirm a new row appears in your Content Queue.
Add the Airtable node and connect credentials

The Airtable node lets n8n write data directly into your Airtable base. You need to add it to the end of your workflow and authenticate it with your Personal Access Token.

  • In your n8n workflow editor, click the + button on the right edge of the Basic LLM Chain node.
  • Search for Airtable in the node panel and select it.
  • Set Operation to Append the data to a table.
  • Under Credential to connect with, click Create New Credential.
  • Paste your Airtable Personal Access Token into the Access Token field and click Save.
  • Select your Content Multiplier base from the Base dropdown.
  • Select Content Queue from the Table dropdown.

Once you select the table, n8n loads the column names from your Airtable base. You should see your columns listed in the node configuration panel.

Don't see your base or table in the dropdown?

This usually means your Personal Access Token is missing the schema.bases:read scope. Go back to your Airtable token settings at airtable.com/create/tokens, edit your token, add the schema.bases:read scope, and regenerate it. Then update the credential in n8n with the new token.

help me fix my Airtable credential in n8n

Map the output fields to Airtable columns

Each field from the Structured Output Parser needs to land in the right Airtable column. Since the field names from the parser (like linkedin_post) don't exactly match your Airtable column names (like LinkedIn Post), you need to map them manually.

  • In the Airtable node's column mapping section, set Mapping Column Mode to Map Each Column Manually.
  • Find the LinkedIn Post column. Click its value field and drag linkedin_post from the input panel on the left, or type the expression {{ $json.linkedin_post }}.
  • Find the X Thread column. Map it to x_thread using the same method.
  • Find the Email Blurb column. Map it to email_blurb.
  • Find the Status column. Instead of dragging from the input panel, type Draft directly as a fixed value.
  • Remove any other columns you do not need to populate (like Source URL or Generated At) by clicking the x next to each unused column.

What does each mapping do?

  • linkedin_post, x_thread, and email_blurb are the JSON fields the Structured Output Parser created in the previous step. Mapping them to the matching Airtable columns sends each platform's post into its own cell.
  • The Status column is set to a fixed string Draft so every new row starts in a reviewable state. You or a client can change it to "Approved" or "Published" later.

Before you run the full workflow, what do you think will appear in your Airtable table when it completes?

  • Click the Manual Trigger node at the start of your workflow.
  • Click Test Workflow to run the entire pipeline from scratch.
  • Wait for all five nodes to complete. You should see a green checkmark on each node.

Switch to your Airtable base in the browser. A brand-new row should now appear in your Content Queue table with three populated text columns and a Draft status.

No new row in Airtable?

  • Click the Airtable node in your workflow and check its output panel for error details. A "Forbidden" error means your token is missing the required scopes. Regenerate it with data.records:read, data.records:write, and schema.bases:read.
  • Double-check that each column mapping points to the correct Airtable column name. Column names are case-sensitive in the Airtable API.
  • If the LLM node shows an error, your OpenRouter free-tier daily limit of 50 requests may be exhausted. Wait until the next day or try a different free model from the dropdown.

help me debug why my Airtable node isn't creating a row

✔️ Awesome, I've got everything!

Great. Make sure you have saved your workflow in n8n by pressing Ctrl+S (Windows) or Cmd+S (macOS).

ⓧ I'd like to double check the full setup

Your workflow should now have five nodes connected in sequence. Confirm each one:

  • Manual Trigger (the starting node).
  • HTTP Request (fetches the blog post URL).
  • HTML (extracts clean article text into article_text).
  • Basic LLM Chain (generates three posts with the Structured Output Parser returning linkedin_post, x_thread, and email_blurb fields).
  • Airtable (appends a row to Content Queue with linkedin_post mapped to LinkedIn Post, x_thread mapped to X Thread, email_blurb mapped to Email Blurb, and Status set to Draft).

Your content-repurposing pipeline is complete. You can now paste any blog post URL into the HTTP Request node, hit Test Workflow, and watch three tailored posts land in your Airtable review queue. Next up, you'll tackle a Secret Mission to extend the pipeline even further.

Secret mission

Add Instagram as a Fourth Platform

Your pipeline covers LinkedIn, X, and email. But real content strategies span more platforms. Can you extend the workflow to generate an Instagram caption with hashtags as a fourth output?

Clean Up Your Resources

Clean Up Your Resources

This project runs entirely on free-tier services and local Docker containers, so there are no ongoing costs. Decide whether to keep your resources running, pause them to come back later, or delete them entirely.

Resources you used:

  • n8n Docker containers running locally (free, uses local compute).
  • OpenRouter API key (free tier, no charges incurred).
  • Airtable Content Multiplier base with Content Queue table and Personal Access Token (free tier).

Keep everything running

No action needed. Choose this if you are still actively repurposing articles or want to keep experimenting with your workflow.

  • n8n stays running at http://localhost:5678. Open it anytime to run your workflow on a new article URL.
  • Your OpenRouter API key remains active with 50 free requests per day.
  • Your Airtable Content Queue table keeps collecting new rows each time you run the workflow.

Pause - I'll come back to this later

Shut down n8n to free up local compute. Your workflows and data persist so you can pick up right where you left off.

  • Stop n8n by running:
docker compose -f ./n8n/compose.yml down
  • When you are ready to come back, restart n8n by running:
docker compose -f ./n8n/compose.yml up -d

Your OpenRouter key and Airtable base stay active in the background. No action needed for those.

Delete - I don't want to use this again

Remove all project resources and start fresh. This is permanent.

  • Remove n8n and all its stored data (workflows, credentials, settings) by running:
docker compose -f ./n8n/compose.yml down -v
  • Delete the n8n project folder by running:
rm -rf ./n8n
  • Delete your OpenRouter API key. Go to https://openrouter.ai/settings/keys, find the key you created for this project, and delete it.
  • Delete your Airtable base. Go to airtable.com, find the Content Multiplier base on your home page, open its context menu, and select the option to delete it.
  • Revoke your Airtable Personal Access Token. Go to https://airtable.com/create/tokens, find the token you created for this project, and revoke it.

Your OpenRouter and Airtable accounts remain active separately. These are free accounts with no charges.

Nice Work!

Nice Work!

You just built a production-ready content-repurposing pipeline that turns a single blog post into platform-tailored social posts, all sitting in a review queue ready for approval.

What you learned:

  • Built a complete n8n automation pipeline that scrapes any blog post URL with the HTTP Request and HTML nodes, then generates three platform-tailored posts using a Basic LLM Chain connected to OpenRouter's free models.
  • Used the Structured Output Parser with a JSON Schema to get clean, separated fields from the LLM instead of an unstructured text blob.
  • Wired Airtable as a content review queue with status tracking, giving any team or client a single dashboard to approve posts before publishing.
  • Secret Mission: Extended the pipeline to cover Instagram as a fourth platform by modifying the prompt, schema, and Airtable mapping in sync.

Ready to quiz yourself?