This workflow corresponds to n8n.io template #15242 — we link there as the canonical source.
This workflow follows the Chainllm → Documentdefaultdataloader recipe pattern — see all workflows that pair these two integrations.
The workflow JSON
Copy or download the full n8n JSON below. Paste it into a new n8n workflow, add your credentials, activate. Full import guide →
{
"meta": {
"templateCredsSetupCompleted": true
},
"nodes": [
{
"id": "d73049ab-1e97-4ad0-82e0-bb67c62f9c89",
"name": "Webhook",
"type": "n8n-nodes-base.webhook",
"position": [
-496,
96
],
"parameters": {
"path": "0c325586-4a79-46d2-a676-64bcf12621e9",
"options": {},
"httpMethod": "POST",
"responseMode": "responseNode"
},
"typeVersion": 2.1
},
{
"id": "f05ee177-c969-461e-9b70-fc4f3d7f56fe",
"name": "Respond to Webhook",
"type": "n8n-nodes-base.respondToWebhook",
"position": [
1232,
-624
],
"parameters": {
"options": {}
},
"typeVersion": 1.5
},
{
"id": "03057181-f80c-40d6-8d52-fc9f60e81c10",
"name": "Split Out",
"type": "n8n-nodes-base.splitOut",
"position": [
16,
-144
],
"parameters": {
"options": {},
"fieldToSplitOut": "body.posts"
},
"typeVersion": 1
},
{
"id": "148e18f0-a806-46c6-a0fd-8845c4885724",
"name": "Aggregate",
"type": "n8n-nodes-base.aggregate",
"position": [
656,
-624
],
"parameters": {
"options": {},
"aggregate": "aggregateAllItemData"
},
"typeVersion": 1
},
{
"id": "fc11ab73-1756-42d4-a6e8-457242772cbf",
"name": "Structured Output Parser",
"type": "@n8n/n8n-nodes-langchain.outputParserStructured",
"position": [
1040,
-400
],
"parameters": {
"schemaType": "manual",
"inputSchema": "{\n \"type\": \"array\",\n \"items\": {\n \"type\": \"object\",\n \"properties\": {\n \"id\": {\n \"type\": \"string\",\n \"description\": \"The 43-character componentkey post identifier, passed through from the input\"\n },\n \"status\": {\n \"type\": \"string\",\n \"enum\": [\"pass\", \"fail\"],\n \"description\": \"pass = quality content, fail = slop to be hidden\"\n }\n },\n \"required\": [\"id\", \"status\"],\n \"additionalProperties\": false\n }\n}"
},
"typeVersion": 1.3
},
{
"id": "95f3be15-895e-49b8-a365-c7694da3818d",
"name": "Embeddings OpenAI",
"type": "@n8n/n8n-nodes-langchain.embeddingsOpenAi",
"position": [
656,
608
],
"parameters": {
"options": {}
},
"credentials": {
"openAiApi": {
"name": "<your credential>"
}
},
"typeVersion": 1.2,
"alwaysOutputData": true
},
{
"id": "116382b4-291c-4bbc-be57-a826bca8f0cf",
"name": "Default Data Loader",
"type": "@n8n/n8n-nodes-langchain.documentDefaultDataLoader",
"position": [
64,
608
],
"parameters": {
"options": {
"metadata": {
"metadataValues": [
{
"name": "vote",
"value": "={{ $('Webhook').item.json.body.vote }}"
},
{
"name": "id",
"value": "={{ $('Webhook').item.json.body.id }}"
}
]
}
},
"jsonData": "={{ $('Webhook').item.json.body.text }}",
"jsonMode": "expressionData"
},
"typeVersion": 1.1
},
{
"id": "81032755-cee1-4576-a95b-a47d3d33d7aa",
"name": "Loop Over Items",
"type": "n8n-nodes-base.splitInBatches",
"position": [
432,
-144
],
"parameters": {
"options": {}
},
"typeVersion": 3
},
{
"id": "069f8153-84cf-4c8d-a00a-6f7bf88864ab",
"name": "Aggregate1",
"type": "n8n-nodes-base.aggregate",
"position": [
1904,
-144
],
"parameters": {
"options": {},
"aggregate": "aggregateAllItemData",
"destinationFieldName": "prior_ratings"
},
"typeVersion": 1
},
{
"id": "7ac4369b-5dab-4a5d-9625-d535db124070",
"name": "Respond to Webhook1",
"type": "n8n-nodes-base.respondToWebhook",
"position": [
368,
384
],
"parameters": {
"options": {},
"respondWith": "noData"
},
"typeVersion": 1.5
},
{
"id": "d50b55dd-d4b1-4e88-84f2-33d76dc983a4",
"name": "OpenAI Chat Model",
"type": "@n8n/n8n-nodes-langchain.lmChatOpenAi",
"position": [
864,
-400
],
"parameters": {
"model": {
"__rl": true,
"mode": "list",
"value": "gpt-5.1-chat-latest",
"cachedResultName": "gpt-5.1-chat-latest"
},
"options": {},
"builtInTools": {}
},
"credentials": {
"openAiApi": {
"name": "<your credential>"
}
},
"typeVersion": 1.3
},
{
"id": "e8297c25-14e8-431e-9edd-005912fb56cf",
"name": "Merge",
"type": "n8n-nodes-base.merge",
"position": [
1008,
-64
],
"parameters": {},
"typeVersion": 3.2
},
{
"id": "aa341fe8-7f38-4a3b-922c-0c8d3d629409",
"name": "Skip empty items",
"type": "n8n-nodes-base.filter",
"position": [
224,
-144
],
"parameters": {
"options": {},
"conditions": {
"options": {
"version": 3,
"leftValue": "",
"caseSensitive": true,
"typeValidation": "strict"
},
"combinator": "and",
"conditions": [
{
"id": "c3dc93ff-dffb-45c8-8020-d1f410d3471e",
"operator": {
"type": "string",
"operation": "notEmpty",
"singleValue": true
},
"leftValue": "={{ $json.text }}",
"rightValue": ""
}
]
}
},
"typeVersion": 2.3
},
{
"id": "61ae649c-b670-40e9-b4d2-eca63bbd51d1",
"name": "Sticky Note",
"type": "n8n-nodes-base.stickyNote",
"position": [
-1312,
-144
],
"parameters": {
"width": 640,
"height": 592,
"content": "## How it works\nA single webhook exposes two actions, selected by a `?action=` query parameter.\n_Every vote is stored as an embedding so future classifications can reference it, letting the filter adapt to your taste over time._\n1. A `Switch` routes requests based on the `action` parameter\n2. On `analyze`: each post is enriched with similar prior-rated posts from Qdrant (RAG) and sent to the LLM with a strict quality-gate prompt\n3. The LLM returns a JSON array of `pass` / `fail` results to the caller\n4. On `vote`: the post is embedded and stored in Qdrant with the \"good\" or \"slop\" rating as metadata\n\nFallback: empty posts are skipped automatically.\n\n## Setup\n- [ ] Add your OpenAI credentials to the `OpenAI Chat Model` and `Embeddings OpenAI` nodes\n- [ ] Add your Qdrant credentials to both `Qdrant Vector Store` nodes and create a collection named `stopslopin`\n- [ ] Activate the workflow, copy the webhook URL, and paste it into the StopSlopIn Chrome extension settings\n\n## Customization\n- Swap the `OpenAI Chat Model` for any LangChain-compatible chat model (Claude, Ollama, etc.)\n- Edit the system prompt inside the `Basic LLM Chain` node to match your taste\n- Change the similarity threshold in the `Filter` node (default `0.7`)\n"
},
"typeVersion": 1
},
{
"id": "852fa092-9c7f-4b9b-a880-7e5dc8260d0a",
"name": "Switch by action",
"type": "n8n-nodes-base.switch",
"position": [
-272,
96
],
"parameters": {
"rules": {
"values": [
{
"outputKey": "analyze",
"conditions": {
"options": {
"version": 3,
"leftValue": "",
"caseSensitive": true,
"typeValidation": "strict"
},
"combinator": "and",
"conditions": [
{
"id": "d05efb53-3d47-4b4e-b31c-e4c8ee81095c",
"operator": {
"type": "string",
"operation": "equals"
},
"leftValue": "={{ $json.query.action }}",
"rightValue": "analyze"
}
]
},
"renameOutput": true
},
{
"outputKey": "vote",
"conditions": {
"options": {
"version": 3,
"leftValue": "",
"caseSensitive": true,
"typeValidation": "strict"
},
"combinator": "and",
"conditions": [
{
"id": "21faab1f-0f4b-4de4-929b-db9ae1312f74",
"operator": {
"name": "filter.operator.equals",
"type": "string",
"operation": "equals"
},
"leftValue": "={{ $json.query.action }}",
"rightValue": "vote"
}
]
},
"renameOutput": true
}
]
},
"options": {}
},
"typeVersion": 3.4
},
{
"id": "c26b7242-44de-4c91-9aaf-aea7f967b1a0",
"name": "Retrieve similar posts",
"type": "@n8n/n8n-nodes-langchain.vectorStoreQdrant",
"position": [
656,
16
],
"parameters": {
"mode": "load",
"prompt": "={{ $json.text }}",
"options": {},
"qdrantCollection": {
"__rl": true,
"mode": "id",
"value": "stopslopin"
}
},
"credentials": {
"qdrantApi": {
"name": "<your credential>"
}
},
"typeVersion": 1.3
},
{
"id": "d92d7207-83a5-4904-af75-71b6fdab3e8a",
"name": "Store post",
"type": "@n8n/n8n-nodes-langchain.vectorStoreQdrant",
"position": [
16,
384
],
"parameters": {
"mode": "insert",
"options": {},
"qdrantCollection": {
"__rl": true,
"mode": "id",
"value": "stopslopin"
}
},
"credentials": {
"qdrantApi": {
"name": "<your credential>"
}
},
"typeVersion": 1.3
},
{
"id": "022da01f-37a7-461a-bcb2-362d5bd4ebb3",
"name": "Filter by similarity score",
"type": "n8n-nodes-base.filter",
"position": [
1232,
-64
],
"parameters": {
"options": {},
"conditions": {
"options": {
"version": 3,
"leftValue": "",
"caseSensitive": true,
"typeValidation": "strict"
},
"combinator": "and",
"conditions": [
{
"id": "8e479873-4f89-47b3-83a5-554775c8c1e6",
"operator": {
"type": "number",
"operation": "gte"
},
"leftValue": "={{ $json.score }}",
"rightValue": 0.7
}
]
}
},
"typeVersion": 2.3,
"alwaysOutputData": true
},
{
"id": "f4b9660e-0c68-4d78-a1cb-3eb2a86a26d1",
"name": "If similar posts found",
"type": "n8n-nodes-base.if",
"position": [
1456,
-64
],
"parameters": {
"options": {},
"conditions": {
"options": {
"version": 3,
"leftValue": "",
"caseSensitive": true,
"typeValidation": "strict"
},
"combinator": "and",
"conditions": [
{
"id": "1d40544d-e2c6-4a9c-98ee-f67a3da588b1",
"operator": {
"type": "object",
"operation": "notEmpty",
"singleValue": true
},
"leftValue": "={{ $json }}",
"rightValue": ""
}
]
}
},
"typeVersion": 2.3
},
{
"id": "3938d8ac-4bd3-4ae8-9bf5-86fb1f6438eb",
"name": "Prepare fields",
"type": "n8n-nodes-base.set",
"position": [
1680,
-144
],
"parameters": {
"options": {},
"assignments": {
"assignments": [
{
"id": "ecbfd40f-2f81-4419-9fae-a96e7faf9e9c",
"name": "text",
"type": "string",
"value": "={{ $json.document.pageContent }}"
},
{
"id": "7408b8ab-8b48-4f26-9f37-46c475cbb4a7",
"name": "vote",
"type": "string",
"value": "={{ $json.document.metadata.vote }}"
},
{
"id": "49e19c0e-2aac-40f2-9866-d4463bbe22bf",
"name": "similarity",
"type": "number",
"value": "={{ $json.score.round(2) }}"
}
]
}
},
"typeVersion": 3.4
},
{
"id": "eeaaa86b-1bfa-49e9-bd2b-c2941a5331e8",
"name": "Prepare output",
"type": "n8n-nodes-base.set",
"position": [
2128,
-144
],
"parameters": {
"options": {},
"assignments": {
"assignments": [
{
"id": "3f88e53f-d91c-48fe-adee-422e1b5732ae",
"name": "id",
"type": "string",
"value": "={{ $('Loop Over Items').item.json.id }}"
},
{
"id": "5846fb1b-1b3a-4557-8102-87f17c5c332b",
"name": "text",
"type": "string",
"value": "={{ $('Loop Over Items').item.json.text }}"
},
{
"id": "be141ab0-1990-4a11-90e8-a054b095f01c",
"name": "prior_ratings",
"type": "array",
"value": "={{ $json.prior_ratings }}"
}
]
}
},
"typeVersion": 3.4
},
{
"id": "512ebb5b-4ac3-4fc3-9b06-3431423b355a",
"name": "Prepare output1",
"type": "n8n-nodes-base.set",
"position": [
2128,
48
],
"parameters": {
"options": {},
"assignments": {
"assignments": [
{
"id": "3f88e53f-d91c-48fe-adee-422e1b5732ae",
"name": "id",
"type": "string",
"value": "={{ $('Loop Over Items').item.json.id }}"
},
{
"id": "5846fb1b-1b3a-4557-8102-87f17c5c332b",
"name": "text",
"type": "string",
"value": "={{ $('Loop Over Items').item.json.text }}"
}
]
}
},
"typeVersion": 3.4
},
{
"id": "9f73fa87-f227-42fe-9b99-5970e490b562",
"name": "No Operation",
"type": "n8n-nodes-base.noOp",
"position": [
2352,
48
],
"parameters": {},
"typeVersion": 1
},
{
"id": "c4705c09-928f-4845-9fe6-a156da2e9640",
"name": "Analyze posts",
"type": "@n8n/n8n-nodes-langchain.chainLlm",
"position": [
880,
-624
],
"parameters": {
"text": "={{ $json.data.toJsonString() }}",
"batching": {},
"messages": {
"messageValues": [
{
"message": "=You are a **strict quality gate** for a LinkedIn feed. You receive a JSON array of posts (`id` + `text`) and classify each as \"pass\" or \"fail\".\n\n**EXTREMELY IMPORTANT:** Only posts that clearly deliver real value to the reader may pass. Everything else is slop and must fail. This is not a fair/lenient filter \u2014 it is a hard gate. When in doubt, **fail**. The feed owner would rather lose a borderline post than see another piece of slop.\n\n## Primary test\n\nA post passes ONLY IF a reader would walk away having **learned something specific, seen something genuinely built, or gained a useful firsthand perspective**. If you cannot name what concrete value the post delivers in one sentence, fail it.\n\n### What qualifies as quality content\n\n- **Practical tips and tricks** \u2014 a concrete technique the reader can apply. Examples: \"use a Redis flag with TTL to prevent overlapping n8n executions\", \"share one Execute Workflow Trigger with a switch node for multi-action sub-workflows\", \"how to use hooks in Claude Code to run tests on save\".\n- **Tutorials and how-tos** \u2014 written guide, video walkthrough, or step-by-step on using a tool, library, API, framework, or technique.\n- **Builder showcase** \u2014 the author actually built something and demos what it does. Value stands even if every link were removed. An invitation to try it is fine; a pure pitch is not.\n- **SaaS / product demo with substance** \u2014 founder explains a real problem and shows the product solving it. Not \"limited spots, DM me\".\n- **Firsthand technical or industry commentary** \u2014 original analysis of tech, tools, workflows, or domain developments from someone who actually works in the space.\n- **Genuine craft / career / psychology insight** \u2014 thoughtful perspective on learning, work, or self-development grounded in personal experience, not motivational-poster platitudes.\n- **Short authentic milestones** \u2014 a brief, real update tied to something concrete the author did (e.g. \"just got certified as an n8n Expert Partner \ud83c\udf89\"). Authentic tone, not engagement-farming.\n\nAny post that does not clearly fit one of the above patterns is a fail candidate. A \"nice observation\" or \"beautiful symbolism\" does not qualify. Neither does a clickbait tease over mystery media.\n\n## Hard fails (single signal \u2192 immediate fail)\n\nAny ONE of these fails the post. Do not apply the 2+ rule here.\n\n1. **Political or geopolitical content.** Partisan takes, nation-vs-nation framing, policy hot takes, elections, ideological manifestos, \"country X is quietly doing Y\" dramatization, unsourced geopolitical hype stats. Narrow exception only when a practitioner discusses a specific technical/regulatory detail they personally work with (e.g. a concrete GDPR implementation note in their own product).\n2. **Forced-inspiration / motivational-poster content.** Mundane subject (supply chain, nature, sports, factory tour) + tacked-on \"beautiful symbolism of vision/journey/ideas becoming reality\" framing with no firsthand stake and no actionable takeaway. The banana-chip-factory-as-metaphor-for-entrepreneurship pattern.\n3. **Pure engagement or lead-magnet funnels.** \"Comment YES for the link\", \"drop 'X' and I'll DM you the RSVP\", \"repost to unlock part 2\", \"like for the template\", \"join the waitlist\". The post's primary purpose is capturing comments/DMs/signups, not delivering value.\n4. **Fabricated feel-good stories** with unrealistic neat outcomes (\"helped a stranger \u2192 she was the CEO \u2192 got hired\"). Performative-vulnerability-to-CTA pipelines.\n5. **Hustle porn / thought-leader cosplay.** \"I wake up at 4am\", \"That's what makes you a 50x builder\", \"Most people are thinking about X the wrong way\" followed by generic common knowledge framed as proprietary insight.\n6. **Humble brags framed as gratitude.** \"I'm humbled/honored/thrilled to announce\u2026\" opener when the post is promotional or empty of substance. A short authentic milestone without the formula is fine.\n7. **Off-topic hashtag farming.** 10+ hashtags at the bottom that are mostly unrelated to the post's actual topic (e.g. `#healthcare #education #leadership #inspiration #whatinspiresme` on a banana-chip factory post). This is reach-bait. Topical, relevant hashtag clusters are fine.\n\n## Soft fails (2+ signals AND fails to clear the quality bar \u2192 fail)\n\nIf a post does not clearly deliver value AND hits two or more of the following, fail it.\n\n**Structure**\n- Broetry: one sentence per line, blank lines between, dramatic pacing for manufactured impact\n- Fake dialogue: \"Me: \u2026 Boss: \u2026 Me: \u2026\" scripts with tidy outcomes\n- Generic numbered listicle: \"10 things nobody tells you about X\" where X is interchangeable\n- Bolded inline headers with colon descriptions mimicking AI formatting (`**Key:** text`)\n- Clickbait opener emoji + tease: \"Did you know\ud83e\udd2f\", \"Wait till you see this\ud83d\udc40\", \"You won't believe\ud83d\ude31\"\n\n**AI language**\n- Clusters (3+) of buzzwords: delve, leverage, utilize, harness, foster, facilitate, empower, elevate, navigate, streamline, underscore, unleash, unlock, bolster, cultivate | pivotal, robust, seamless, groundbreaking, transformative, holistic, nuanced, multifaceted, cutting-edge, invaluable, paramount | landscape, realm, tapestry, synergy, testament, beacon, paradigm, ecosystem, cornerstone, catalyst, blueprint\n- Em-dash abuse as universal punctuation (the \"ChatGPT dash\")\n- Uniform sentence length with no natural short/long variation\n- Zero typos or imperfections in a long, personal-sounding post\n- Formal, emotionally detached tone reading like corporate documentation\n- \"It's not about X, it's about Y\" parallelism, especially repeated\n- Hedging overload: typically, might be, generally speaking, can also, to some extent\n- Filler phrases: \"it's important to note\", \"in today's rapidly evolving\", \"at the end of the day\", \"in the realm of\", \"that being said\", \"furthermore\", \"moreover\"\n\n**Content**\n- Generic advice that applies to anyone \u2014 swap one noun and it fits any industry\n- Motivational poster tone with no concrete data, names, dates, or verifiable detail\n- Hot-take theater: \"Unpopular opinion:\" followed by an extremely popular opinion\n- News repackaging as civilizational turning point with no firsthand analysis\n- Unsourced big-number hype stats. Numbers only count toward quality when sourced, firsthand, or verifiable. Unsourced big-number claims count **against** the post, not for it.\n\n**Promotional**\n- Discount codes, \"limited spots\", \"grab it now\", \"spots filling up\" urgency\n- Affiliate-style ad copy without genuine experience\n- \"Free PDF / template / checklist\" when the post has no standalone value without it\n- Entire structure is setup-to-CTA with no value before the CTA\n\n**Formatting**\n- **Decorative** emoji padding \u2014 sparkles, fire, rockets, flexed biceps sprinkled for vibes with no semantic role. Emoji that carry meaning (\ud83d\udccc note, \u2705 solution, \ud83d\udea9 warning, \ud83d\udca1 idea, \u26a0\ufe0f caution, \ud83d\udc49 link pointer, \u23f1\ufe0f timing) are fine and must NOT count against the post. Test: if removing the emoji loses information (category, sentiment, emphasis), it is meaningful.\n- ALL CAPS lines used for artificial emphasis\n- Hashtag stuffing **inline in prose**: country/topic hashtags used as nouns in sentences (\"this week #Germany moving away from #USA\"). A hashtag cluster at the bottom of the post is not the same thing and is fine when topical.\n- Formatting inconsistency paired with grandiose claims: mixed bullet styles (`+`/`-`), typos alongside sweeping statements \u2014 signals careless LLM-assisted drafting\n\n## Video and image posts\n\nMany posts are a short caption over a video, image, or carousel you cannot see. Infer what the media likely contains from the caption:\n\n- If the caption credibly signals substantive value \u2014 a demo of a tool the author built, a tutorial, a specific technique, a firsthand story \u2014 pass it.\n- If the caption is just vibes, hashtags, and a clickbait hook (\"A thing of beauty\u2026\", \"Did you know\ud83e\udd2f\", \"Pure inspiration \ud83d\udcaa\") with no indication the media teaches or shows anything specific, fail it. A mysterious video behind an empty caption is almost certainly not quality content.\n- Never pass a post on the hope that \"maybe the video is good\". The caption must carry enough signal on its own.\n\n## Prior ratings\n\nPosts may include a `prior_ratings` array of similar human-voted examples, each with `text`, `vote` (\"good\" or \"slop\"), and `similarity` (0.0\u20131.0). Use as reference, not rules:\n\n- High similarity (0.85+) with consistent votes (e.g. 3\u00d7 slop) = strong signal.\n- Low similarity (<0.75) or mixed votes = weak hint.\n- Empty or missing = judge by the rules above alone.\n\nNever override an obviously quality post because a vaguely similar one was voted slop, or vice versa. Prior ratings inform judgment; they do not replace it.\n\n## Doubt \u2192 fail\n\nIf you cannot clearly name the concrete value a post provides in one sentence, fail it. A strict gate is the point. The feed owner will gain far more signal from rejecting borderline posts than from letting them through.\n\n## Input\n\nEach post has `id`, `text`, and optionally `prior_ratings`:\n\n{posts_json}\n\n## Output\n\nReturn ONLY a raw JSON array. No markdown fences, no explanation, no wrapping:\n\n[{\"id\":\"<post_id>\",\"status\":\"pass\"},{\"id\":\"<post_id>\",\"status\":\"fail\"}]\n\nOne entry per input post. Exact same `id` from input. `status` is \"pass\" or \"fail\" only."
}
]
},
"promptType": "define",
"hasOutputParser": true
},
"typeVersion": 1.9
},
{
"id": "4f8f9295-4422-4b5d-a9d9-e76a86c2e210",
"name": "Sticky Note1",
"type": "n8n-nodes-base.stickyNote",
"position": [
-64,
-240
],
"parameters": {
"color": 7,
"width": 2592,
"height": 496,
"content": "## 1. Compare posts one by one with previous ones\nRetrieve similar posts (with a certain relevance score) from the vector store and add them to the following LLM Analysis including the belonging rating done by you in the past."
},
"typeVersion": 1
},
{
"id": "54caae76-99b4-440c-8391-b509466ed7e4",
"name": "Sticky Note2",
"type": "n8n-nodes-base.stickyNote",
"position": [
544,
-752
],
"parameters": {
"color": 7,
"width": 944,
"height": 496,
"content": "## 2. Analyze posts and return rating\nTake all posts (including additional rating context if available) and analyze them for quality. Return a JSON object containing the post ID and the final rating."
},
"typeVersion": 1
},
{
"id": "58ac2d3e-47ee-4531-acfd-bd1eadb3051c",
"name": "Sticky Note3",
"type": "n8n-nodes-base.stickyNote",
"position": [
-64,
272
],
"parameters": {
"color": 7,
"width": 944,
"height": 496,
"content": "## Optional: Store manual rating for post\nSave the manually voted post with it's contend and vote in a vector store."
},
"typeVersion": 1
}
],
"connections": {
"Merge": {
"main": [
[
{
"node": "Filter by similarity score",
"type": "main",
"index": 0
}
]
]
},
"Webhook": {
"main": [
[
{
"node": "Switch by action",
"type": "main",
"index": 0
}
]
]
},
"Aggregate": {
"main": [
[
{
"node": "Analyze posts",
"type": "main",
"index": 0
}
]
]
},
"Split Out": {
"main": [
[
{
"node": "Skip empty items",
"type": "main",
"index": 0
}
]
]
},
"Aggregate1": {
"main": [
[
{
"node": "Prepare output",
"type": "main",
"index": 0
}
]
]
},
"Store post": {
"main": [
[
{
"node": "Respond to Webhook1",
"type": "main",
"index": 0
}
]
]
},
"No Operation": {
"main": [
[
{
"node": "Loop Over Items",
"type": "main",
"index": 0
}
]
]
},
"Analyze posts": {
"main": [
[
{
"node": "Respond to Webhook",
"type": "main",
"index": 0
}
]
]
},
"Prepare fields": {
"main": [
[
{
"node": "Aggregate1",
"type": "main",
"index": 0
}
]
]
},
"Prepare output": {
"main": [
[
{
"node": "No Operation",
"type": "main",
"index": 0
}
]
]
},
"Loop Over Items": {
"main": [
[
{
"node": "Aggregate",
"type": "main",
"index": 0
}
],
[
{
"node": "Retrieve similar posts",
"type": "main",
"index": 0
},
{
"node": "Merge",
"type": "main",
"index": 0
}
]
]
},
"Prepare output1": {
"main": [
[
{
"node": "No Operation",
"type": "main",
"index": 0
}
]
]
},
"Skip empty items": {
"main": [
[
{
"node": "Loop Over Items",
"type": "main",
"index": 0
}
]
]
},
"Switch by action": {
"main": [
[
{
"node": "Split Out",
"type": "main",
"index": 0
}
],
[
{
"node": "Store post",
"type": "main",
"index": 0
}
]
]
},
"Embeddings OpenAI": {
"ai_embedding": [
[
{
"node": "Store post",
"type": "ai_embedding",
"index": 0
},
{
"node": "Retrieve similar posts",
"type": "ai_embedding",
"index": 0
}
]
]
},
"OpenAI Chat Model": {
"ai_languageModel": [
[
{
"node": "Analyze posts",
"type": "ai_languageModel",
"index": 0
}
]
]
},
"Default Data Loader": {
"ai_document": [
[
{
"node": "Store post",
"type": "ai_document",
"index": 0
}
]
]
},
"If similar posts found": {
"main": [
[
{
"node": "Prepare fields",
"type": "main",
"index": 0
}
],
[
{
"node": "Prepare output1",
"type": "main",
"index": 0
}
]
]
},
"Retrieve similar posts": {
"main": [
[
{
"node": "Merge",
"type": "main",
"index": 1
}
]
]
},
"Structured Output Parser": {
"ai_outputParser": [
[
{
"node": "Analyze posts",
"type": "ai_outputParser",
"index": 0
}
]
]
},
"Filter by similarity score": {
"main": [
[
{
"node": "If similar posts found",
"type": "main",
"index": 0
}
]
]
}
}
}
Credentials you'll need
Each integration node will prompt for credentials when you import. We strip credential IDs before publishing — you'll add your own.
openAiApiqdrantApi
For the full experience including quality scoring and batch install features for each workflow upgrade to Pro
About this workflow
This workflow is the official backend for the StopSlopIn Chrome extension – it classifies LinkedIn posts as quality or slop using a strict LLM quality gate and learns from user votes over time via a Qdrant vector store.
Source: https://n8n.io/workflows/15242/ — original creator credit. Request a take-down →
Related workflows
Workflows that share integrations, category, or trigger type with this one. All free to copy and import.
This Workflow simulates an AI-powered phone agent with RetellAI with two main functions: 📅 Appointment Booking – It can schedule appointments directly into Google Calendar. 🧠 RAG-based Information Ret
AI Phone Agent with RetellAI. Uses lmChatOpenAi, outputParserStructured, vectorStoreQdrant, embeddingsOpenAi. Webhook trigger; 36 nodes.
Build a Chatbot, Voice Agent and Phone Agent with Voiceflow, Google Calendar and RAG. Uses googleCalendar, lmChatOpenAi, chainLlm, vectorStoreQdrant. Webhook trigger; 34 nodes.
Voiceflow is a no-code platform that allows you to design, prototype, and deploy conversational assistants across multiple channels—such as chat, voice, and phone—with advanced logic and natural langu
Automate AI-Powered RAG System with Contextual Q&A, Google Sheets Integration, and Glide Frontend—Powered by n8n, OpenAI, Supabase, and Google Apps Script.