This workflow follows the Agent → HTTP Request 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 →
{
"name": "Strategy Radar \u2014 Analyze Publication",
"nodes": [
{
"parameters": {
"httpMethod": "POST",
"path": "strategy-radar-analyze",
"options": {}
},
"id": "f95de433-7905-41d4-b018-df46e28b1c2a",
"name": "Publication Webhook",
"type": "n8n-nodes-base.webhook",
"typeVersion": 2.1,
"position": [
0,
0
]
},
{
"parameters": {
"jsCode": "const crypto = require('crypto');\nconst N8N_WEBHOOK_SECRET = '3e724d3f5e8587982aa19768d1eb717de56ab6798e4713b28c6c372d7c89fc3b';\nconst body = $input.first().json.body;\nconst rawBody = typeof body === 'string' ? body : JSON.stringify(body);\nconst sigHeader = $input.first().json.headers['x-signature-256'] || '';\nif (!sigHeader.startsWith('sha256=')) throw new Error('Missing or malformed X-Signature-256 header');\nconst receivedSig = sigHeader.slice('sha256='.length);\nconst computedSig = crypto.createHmac('sha256', N8N_WEBHOOK_SECRET).update(rawBody, 'utf8').digest('hex');\nif (!crypto.timingSafeEqual(Buffer.from(receivedSig, 'hex'), Buffer.from(computedSig, 'hex'))) throw new Error('HMAC mismatch');\nconst payload = typeof body === 'string' ? JSON.parse(body) : body;\nreturn [{ json: payload }];"
},
"id": "7920870b-f2a3-4ec4-b4db-ef2fb76897ff",
"name": "Verify HMAC",
"type": "n8n-nodes-base.code",
"typeVersion": 2,
"position": [
224,
0
]
},
{
"parameters": {
"url": "={{ $json.publicationFileUrl }}",
"options": {
"response": {
"response": {
"responseFormat": "file"
}
},
"timeout": 30000
}
},
"id": "22b4bb5d-65e6-42a3-ac91-8e25815fd942",
"name": "Fetch Publication File",
"type": "n8n-nodes-base.httpRequest",
"typeVersion": 4.2,
"position": [
448,
0
]
},
{
"parameters": {
"jsCode": "const payload = $input.first().json;\nconst fileUrl = (payload.publicationFileUrl || '').toLowerCase().split('?')[0];\nlet ext = '';\nif (fileUrl.endsWith('.pdf')) ext = 'pdf';\nelse if (fileUrl.endsWith('.docx') || fileUrl.endsWith('.doc')) ext = 'docx';\nelse if (fileUrl.endsWith('.md')) ext = 'md';\nelse if (fileUrl.endsWith('.txt')) ext = 'txt';\nelse throw new Error('Unsupported file type: ' + fileUrl);\nlet buf;\ntry { buf = await this.helpers.getBinaryDataBuffer(0, 'data'); } catch (err) { throw new Error('Could not load binary: ' + (err.message || err)); }\nif (!buf || buf.length === 0) throw new Error('Empty binary buffer.');\nlet extractedText = '';\nif (ext === 'md' || ext === 'txt') { extractedText = buf.toString('utf8'); }\nelse if (ext === 'docx') {\n const raw = buf.toString('utf8', 0, Math.min(buf.length, 2_000_000));\n const runs = raw.match(/<w:t[^>]*>([^<]+)<\\/w:t>/g) || [];\n extractedText = runs.map(t => t.replace(/<[^>]+>/g, '')).filter(t => t.trim().length > 0).join(' ');\n} else {\n const raw = buf.toString('latin1');\n const streams = [];\n const re = /stream[\\r\\n]([\\s\\S]*?)[\\r\\n]endstream/g;\n let m;\n while ((m = re.exec(raw)) !== null) streams.push(m[1]);\n const parts = [];\n for (const s of streams) {\n const inP = s.match(/\\(([^)]{3,})\\)/g) || [];\n for (const t of inP) {\n const c = t.slice(1, -1).replace(/\\\\n/g, ' ').replace(/\\\\r/g, ' ').replace(/\\\\t/g, ' ').trim();\n if (c.length > 2) parts.push(c);\n }\n }\n extractedText = parts.join(' ');\n}\nif (extractedText.length > 8000) extractedText = extractedText.slice(0, 8000) + '\\n\\n[Zkraceno.]';\nif (!extractedText || extractedText.trim().length < 50) extractedText = '[Extrakce textu se nezdarila.]';\nreturn [{ json: { ...payload, extractedText, extractionMethod: ext } }];"
},
"id": "4e93c548-ff00-4377-92ca-468900b10324",
"name": "Extract Text",
"type": "n8n-nodes-base.code",
"typeVersion": 2,
"position": [
672,
0
]
},
{
"parameters": {
"promptType": "define",
"text": "={{ $json.extractedText }}",
"options": {
"systemMessage": "Jsi prekladatel sektorovych analyz pro ceskeho maleho a stredniho podnikatele. Vygeneruj kratky cesky uvod (200-400 slov, vykani, vecny ton, bez statistickych terminu, bez anglicismu). Cisla pouze s kontextem. Vrat pouze samotny cesky text, bez nadpisu.",
"maxIterations": 3
}
},
"id": "517016a3-d09c-46a0-9267-af046a443c08",
"name": "Layperson Opener",
"type": "@n8n/n8n-nodes-langchain.agent",
"typeVersion": 3.1,
"position": [
880,
0
]
},
{
"parameters": {
"model": {
"__rl": true,
"mode": "list",
"value": "claude-haiku-4-5",
"cachedResultName": "Claude Haiku 4.5"
},
"options": {
"maxTokensToSample": 2048,
"temperature": 0.3
}
},
"id": "d8ed4340-6d55-46e1-ad7f-6dc6cc649a65",
"name": "Claude Haiku",
"type": "@n8n/n8n-nodes-langchain.lmChatAnthropic",
"typeVersion": 1.3,
"position": [
880,
608
],
"credentials": {
"anthropicApi": {
"name": "<your credential>"
}
}
},
{
"parameters": {
"promptType": "define",
"text": "=Cesky uvod publikace (kontext):\n{{ $('Layperson Opener').first().json.output }}\n\nPlne telo publikace:\n{{ $('Extract Text').first().json.extractedText }}",
"hasOutputParser": true,
"options": {
"systemMessage": "Jsi sektorov\u00fd analytik \u010cesk\u00e9 spo\u0159itelny pro v\u00fdrobu n\u00e1bytku (NACE 31).\nTYPICK\u00dd KLIENT: mal\u00fd/st\u0159edn\u00ed v\u00fdrobce n\u00e1bytku, 10\u201350 zam\u011bstnanc\u016f, B2B (kancel\u00e1\u0159e, hotely) i B2C (kuchyn\u011b, lo\u017enice, sedac\u00ed n\u00e1bytek).\n\nRELEVANCE (bu\u010f liber\u00e1ln\u00ed):\n- P\u0159\u00edmo: n\u00e1bytek, d\u0159eva\u0159sk\u00fd pr\u016fmysl, design interi\u00e9ru, retail n\u00e1bytku (IKEA, JYSK, ASKO), bytov\u00e9 dopl\u0148ky, kuchyn\u011b, \u010daloun\u011bn\u00fd n\u00e1bytek.\n- Nep\u0159\u00edmo: trh s bydlen\u00edm a nemovitostmi, stavebnictv\u00ed, ceny d\u0159eva a kompozit\u016f, retail trendy v \u010cR, mzdy ve v\u00fdrob\u011b, energie, EU regulace n\u00e1bytku \u010di d\u0159eva, e-commerce s bytov\u00fdm vybaven\u00edm.\n\nPravidlo: pokud lze vyvodit alespo\u0148 jedno u\u017eite\u010dn\u00e9 pozorov\u00e1n\u00ed pro typick\u00e9ho v\u00fdrobce n\u00e1bytku, vra\u0165 relevant=true. Jen publikace zcela bez vazby (nap\u0159. zahrani\u010dn\u00ed politika bez ekonomick\u00e9ho dopadu) \u2192 relevant=false.\n\nV\u00ddSTUP:\n- relevantn\u00ed: { \"relevant\": true, \"reason\": null, \"insights\": [3 pozorov\u00e1n\u00ed] }\n- nerelevantn\u00ed: { \"relevant\": false, \"reason\": \"kr\u00e1tk\u00e9 vysv\u011btlen\u00ed\", \"insights\": [] }\n\nPOZOROV\u00c1N\u00cd: headline \u226460 znak\u016f; body 2 v\u011bty max 400 znak\u016f, vyk\u00e1n\u00ed, v\u011bcn\u00fd t\u00f3n; time_horizon \u2208 {\"Okam\u017eit\u011b\",\"Do 3 m\u011bs\u00edc\u016f\",\"Do 12 m\u011bs\u00edc\u016f\",\"V\u00edce ne\u017e rok\"}; is_email_teaser=true jen u prvn\u00edho.\n\nV\u00ddSTUPN\u00cd PRAVIDLA: pouze valid JSON, bez markdown blok\u016f, bez koment\u00e1\u0159\u016f. Za\u010dni { a skon\u010di }. Boolean = true/false. Arrays = pole, ne stringifikovan\u00e9.",
"maxIterations": 3
}
},
"id": "4b91c309-9c7b-426a-8fd7-22bbe9a4849e",
"name": "Insights 31",
"type": "@n8n/n8n-nodes-langchain.agent",
"typeVersion": 3.1,
"position": [
1104,
-544
]
},
{
"parameters": {
"jsonSchemaExample": "{\n \"relevant\": true,\n \"reason\": null,\n \"insights\": [\n { \"headline\": \"Kr\u00e1tk\u00fd n\u00e1zev\", \"body\": \"Dv\u011b v\u011bty popisu.\", \"time_horizon\": \"Do 3 m\u011bs\u00edc\u016f\", \"is_email_teaser\": true }\n ]\n}",
"autoFix": true
},
"id": "a5cfefeb-f216-46cf-8ec5-9c2121715d2f",
"name": "Insights Parser 31",
"type": "@n8n/n8n-nodes-langchain.outputParserStructured",
"typeVersion": 1.3,
"position": [
1328,
-544
]
},
{
"parameters": {
"conditions": {
"options": {
"caseSensitive": true,
"leftValue": "",
"typeValidation": "strict",
"version": 2
},
"conditions": [
{
"id": "rel-31",
"leftValue": "={{ $json.output.relevant }}",
"rightValue": true,
"operator": {
"type": "boolean",
"operation": "true"
}
}
],
"combinator": "and"
},
"options": {}
},
"id": "0defe161-6269-4081-a5ca-244ec1caf856",
"name": "IF Relevant 31",
"type": "n8n-nodes-base.if",
"typeVersion": 2.2,
"position": [
1328,
-448
]
},
{
"parameters": {
"promptType": "define",
"text": "=Pozorovani z predchoziho agenta:\n{{ JSON.stringify($('Insights 31').first().json.output.insights) }}\n\nPlne telo publikace:\n{{ $('Extract Text').first().json.extractedText }}",
"hasOutputParser": true,
"options": {
"systemMessage": "Jsi sektorovy analytik Ceske sporitelny pro NACE 31. Pro KAZDE z 3 pozorovani vygeneruj 1 doporuceny krok pro maleho/stredniho vyrobce nabytku.\n\nPRAVIDLA pro akce:\n- action_text (do 240 znaku, sloveso na zacatku, konkretni vystup)\n- time_horizon \u2208 {\"1m\", \"3m\", \"6-12m\", \"1y+\"}\n- paired_observation_index 0/1/2 = index parovaneho pozorovani\n\nTODO: doplnit konkretni NACE 31 pravidla pro akce.\n\nVYSTUPNI PRAVIDLA (KRITICKE):\n- Vrat POUZE valid JSON. Bez markdown bloku ```json ... ```. Bez komentaru pred nebo za. Zacni primo znakem { a skonci znakem }.\n- Vsechny pole z prikladu jsou POVINNE.\n- Boolean hodnoty jsou true / false (ne \"true\" / \"false\" jako string).\n- Arrays jsou pole [{...}, {...}], ne stringifikovane.",
"maxIterations": 3
}
},
"id": "06c022d7-ae74-499d-8a64-4383dff3a0e9",
"name": "Actions 31",
"type": "@n8n/n8n-nodes-langchain.agent",
"typeVersion": 3.1,
"position": [
1552,
-448
]
},
{
"parameters": {
"jsonSchemaExample": "{\n \"actions\": [\n { \"action_text\": \"Akce: konkr\u00e9tn\u00ed krok.\", \"time_horizon\": \"1m\", \"paired_observation_index\": 0 }\n ]\n}",
"autoFix": true
},
"id": "ce759d2b-0c39-4e2f-bd9d-e29fc92f62f2",
"name": "Actions Parser 31",
"type": "@n8n/n8n-nodes-langchain.outputParserStructured",
"typeVersion": 1.3,
"position": [
1760,
-352
]
},
{
"parameters": {
"jsCode": "const insightsOut = $('Insights 31').first().json.output || {};\nlet actionsOut = null;\ntry { actionsOut = $('Actions 31').first()?.json?.output || null; } catch (e) { actionsOut = null; }\nconst relevant = insightsOut.relevant === true;\nreturn [{ json: { nace: '31', relevant, insights: insightsOut.insights || [], actions: relevant && actionsOut ? (actionsOut.actions || []) : [], reason: insightsOut.reason || null } }];"
},
"id": "ebefefc9-e6cf-47f3-9b76-508239f0b811",
"name": "Tag 31",
"type": "n8n-nodes-base.code",
"typeVersion": 2,
"position": [
1984,
-448
]
},
{
"parameters": {
"numberInputs": 4
},
"id": "2d8f441e-a769-48fc-8597-cc0cd95a5790",
"name": "Merge NACE Results",
"type": "n8n-nodes-base.merge",
"typeVersion": 3.2,
"position": [
2208,
112
]
},
{
"parameters": {
"promptType": "define",
"text": "=Cesky uvod publikace (kontext):\n{{ $('Layperson Opener').first().json.output }}\n\nPlne telo publikace:\n{{ $('Extract Text').first().json.extractedText }}",
"hasOutputParser": true,
"options": {
"systemMessage": "Jsi sektorov\u00fd analytik \u010cesk\u00e9 spo\u0159itelny pro pozemn\u00ed n\u00e1kladn\u00ed dopravu (NACE 49 \u2014 silni\u010dn\u00ed, \u017eelezni\u010dn\u00ed, ostatn\u00ed).\nTYPICK\u00dd KLIENT: mal\u00fd/st\u0159edn\u00ed dopravce, 10\u201380 zam\u011bstnanc\u016f, kamionov\u00e1 \u010di kombinovan\u00e1 doprava, B2B kontrakty s v\u00fdrobou a retailem.\n\nRELEVANCE (bu\u010f liber\u00e1ln\u00ed):\n- P\u0159\u00edmo: silni\u010dn\u00ed doprava, kamionov\u00e1 doprava, \u017eelezni\u010dn\u00ed n\u00e1kladn\u00ed doprava (\u010cD Cargo), spedice, logistika, m\u00fdtn\u00e9, ceny paliv, \u0159idi\u010di, EU dopravn\u00ed regulace, kombinovan\u00e1 doprava.\n- Nep\u0159\u00edmo: z\u00e1sobovac\u00ed \u0159et\u011bzce, e-commerce logistika, ceny pohonn\u00fdch hmot a energie, infrastruktura, mzdy v doprav\u011b, v\u00fdroba a retail jako klientsk\u00e1 z\u00e1kladna, automobilov\u00fd pr\u016fmysl, EU emisn\u00ed pravidla.\n\nPravidlo: pokud lze vyvodit alespo\u0148 jedno u\u017eite\u010dn\u00e9 pozorov\u00e1n\u00ed pro typick\u00e9ho dopravce, vra\u0165 relevant=true. Jen publikace zcela bez vazby \u2192 relevant=false.\n\nV\u00ddSTUP:\n- relevantn\u00ed: { \"relevant\": true, \"reason\": null, \"insights\": [3 pozorov\u00e1n\u00ed] }\n- nerelevantn\u00ed: { \"relevant\": false, \"reason\": \"kr\u00e1tk\u00e9 vysv\u011btlen\u00ed\", \"insights\": [] }\n\nPOZOROV\u00c1N\u00cd: headline \u226460 znak\u016f; body 2 v\u011bty max 400 znak\u016f, vyk\u00e1n\u00ed, v\u011bcn\u00fd t\u00f3n; time_horizon \u2208 {\"Okam\u017eit\u011b\",\"Do 3 m\u011bs\u00edc\u016f\",\"Do 12 m\u011bs\u00edc\u016f\",\"V\u00edce ne\u017e rok\"}; is_email_teaser=true jen u prvn\u00edho.\n\nV\u00ddSTUPN\u00cd PRAVIDLA: pouze valid JSON, bez markdown blok\u016f, bez koment\u00e1\u0159\u016f. Za\u010dni { a skon\u010di }. Boolean = true/false. Arrays = pole, ne stringifikovan\u00e9.",
"maxIterations": 3
}
},
"id": "6652e3c7-c8b5-4b12-b44b-2c68af72c518",
"name": "Insights 49",
"type": "@n8n/n8n-nodes-langchain.agent",
"typeVersion": 3.1,
"position": [
1104,
-144
]
},
{
"parameters": {
"jsonSchemaExample": "{\n \"relevant\": true,\n \"reason\": null,\n \"insights\": [\n { \"headline\": \"Kr\u00e1tk\u00fd n\u00e1zev\", \"body\": \"Dv\u011b v\u011bty popisu.\", \"time_horizon\": \"Do 3 m\u011bs\u00edc\u016f\", \"is_email_teaser\": true }\n ]\n}",
"autoFix": true
},
"id": "2bcd3c1d-767a-452b-a48f-8a19a0318745",
"name": "Insights Parser 49",
"type": "@n8n/n8n-nodes-langchain.outputParserStructured",
"typeVersion": 1.3,
"position": [
1328,
-144
]
},
{
"parameters": {
"conditions": {
"options": {
"caseSensitive": true,
"leftValue": "",
"typeValidation": "strict",
"version": 1
},
"conditions": [
{
"id": "rel-49",
"leftValue": "={{ $json.output.relevant }}",
"rightValue": true,
"operator": {
"type": "boolean",
"operation": "true"
}
}
],
"combinator": "and"
},
"options": {}
},
"id": "7da08124-4d9e-40dc-9b7c-1ed9c28f9ca8",
"name": "IF Relevant 49",
"type": "n8n-nodes-base.if",
"typeVersion": 2.2,
"position": [
1328,
-48
]
},
{
"parameters": {
"promptType": "define",
"text": "=Pozorovani z predchoziho agenta:\n{{ JSON.stringify($('Insights 49').first().json.output.insights) }}\n\nPlne telo publikace:\n{{ $('Extract Text').first().json.extractedText }}",
"hasOutputParser": true,
"options": {
"systemMessage": "Jsi sektorovy analytik Ceske sporitelny pro NACE 49 (nakladni doprava). Pro KAZDE z 3 pozorovani vygeneruj 1 doporuceny krok.\n\nPRAVIDLA: action_text \u2264240 znaku se slovesem na zacatku, time_horizon \u2208 {1m, 3m, 6-12m, 1y+}, paired_observation_index 0/1/2.\n\nTODO: NACE 49 pravidla.\n\nVYSTUPNI PRAVIDLA (KRITICKE):\n- Vrat POUZE valid JSON. Bez markdown bloku ```json ... ```. Bez komentaru pred nebo za. Zacni primo znakem { a skonci znakem }.\n- Vsechny pole z prikladu jsou POVINNE.\n- Boolean hodnoty jsou true / false (ne \"true\" / \"false\" jako string).\n- Arrays jsou pole [{...}, {...}], ne stringifikovane.",
"maxIterations": 3
}
},
"id": "72faae18-a9a0-4337-be6a-80eca3dc75d9",
"name": "Actions 49",
"type": "@n8n/n8n-nodes-langchain.agent",
"typeVersion": 3.1,
"position": [
1552,
-48
]
},
{
"parameters": {
"jsonSchemaExample": "{\n \"actions\": [\n { \"action_text\": \"Akce: konkr\u00e9tn\u00ed krok.\", \"time_horizon\": \"1m\", \"paired_observation_index\": 0 }\n ]\n}",
"autoFix": true
},
"id": "57094a48-98da-4420-a2a4-9ffa2184a1b5",
"name": "Actions Parser 49",
"type": "@n8n/n8n-nodes-langchain.outputParserStructured",
"typeVersion": 1.3,
"position": [
1760,
64
]
},
{
"parameters": {
"jsCode": "const insightsOut = $('Insights 49').first().json.output || {};\nlet actionsOut = null;\ntry { actionsOut = $('Actions 49').first()?.json?.output || null; } catch (e) { actionsOut = null; }\nconst relevant = insightsOut.relevant === true;\nreturn [{ json: { nace: '49', relevant, insights: insightsOut.insights || [], actions: relevant && actionsOut ? (actionsOut.actions || []) : [], reason: insightsOut.reason || null } }];"
},
"id": "255771b4-3b76-4ca5-937b-400214c8b869",
"name": "Tag 49",
"type": "n8n-nodes-base.code",
"typeVersion": 2,
"position": [
1984,
-48
]
},
{
"parameters": {
"promptType": "define",
"text": "=Cesky uvod publikace (kontext):\n{{ $('Layperson Opener').first().json.output }}\n\nPlne telo publikace:\n{{ $('Extract Text').first().json.extractedText }}",
"hasOutputParser": true,
"options": {
"systemMessage": "Jsi sektorov\u00fd analytik \u010cesk\u00e9 spo\u0159itelny pro v\u00fdrobu potravin se zam\u011b\u0159en\u00edm na pek\u00e1rny (NACE 10).\nTYPICK\u00dd KLIENT: mal\u00e1/st\u0159edn\u00ed pek\u00e1rna, 5\u201330 zam\u011bstnanc\u016f, B2C maloobchod a B2B distribuce do regionu.\n\nRELEVANCE (bu\u010f liber\u00e1ln\u00ed):\n- P\u0159\u00edmo: pek\u00e1rny, cukr\u00e1\u0159stv\u00ed, ml\u00e9k\u00e1rny, masn\u00fd pr\u016fmysl, v\u00fdroba potravin, mouka, obil\u00ed, ml\u00e9ko, ceny vstupn\u00edch surovin, retail potravin (Albert, Kaufland, Tesco, Lidl), spot\u0159ebitelsk\u00e9 trendy v potravin\u00e1ch.\n- Nep\u0159\u00edmo: zem\u011bd\u011blsk\u00e9 ceny, ceny energie, mzdy ve v\u00fdrob\u011b, FMCG retail, kupn\u00ed s\u00edla dom\u00e1cnost\u00ed, sez\u00f3nnost spot\u0159eby, EU potravin\u00e1\u0159sk\u00e1 regulace, hygiena, balen\u00ed a obaly.\n\nPravidlo: pokud lze vyvodit alespo\u0148 jedno u\u017eite\u010dn\u00e9 pozorov\u00e1n\u00ed pro typickou pek\u00e1rnu, vra\u0165 relevant=true. Jen publikace zcela bez vazby \u2192 relevant=false.\n\nV\u00ddSTUP:\n- relevantn\u00ed: { \"relevant\": true, \"reason\": null, \"insights\": [3 pozorov\u00e1n\u00ed] }\n- nerelevantn\u00ed: { \"relevant\": false, \"reason\": \"kr\u00e1tk\u00e9 vysv\u011btlen\u00ed\", \"insights\": [] }\n\nPOZOROV\u00c1N\u00cd: headline \u226460 znak\u016f; body 2 v\u011bty max 400 znak\u016f, vyk\u00e1n\u00ed, v\u011bcn\u00fd t\u00f3n; time_horizon \u2208 {\"Okam\u017eit\u011b\",\"Do 3 m\u011bs\u00edc\u016f\",\"Do 12 m\u011bs\u00edc\u016f\",\"V\u00edce ne\u017e rok\"}; is_email_teaser=true jen u prvn\u00edho.\n\nV\u00ddSTUPN\u00cd PRAVIDLA: pouze valid JSON, bez markdown blok\u016f, bez koment\u00e1\u0159\u016f. Za\u010dni { a skon\u010di }. Boolean = true/false. Arrays = pole, ne stringifikovan\u00e9.",
"maxIterations": 3
}
},
"id": "d4c856e9-4157-442c-90d1-39c88267e9c3",
"name": "Insights 10",
"type": "@n8n/n8n-nodes-langchain.agent",
"typeVersion": 3.1,
"position": [
1104,
256
]
},
{
"parameters": {
"jsonSchemaExample": "{\n \"relevant\": true,\n \"reason\": null,\n \"insights\": [\n { \"headline\": \"Kr\u00e1tk\u00fd n\u00e1zev\", \"body\": \"Dv\u011b v\u011bty popisu.\", \"time_horizon\": \"Do 3 m\u011bs\u00edc\u016f\", \"is_email_teaser\": true }\n ]\n}",
"autoFix": true
},
"id": "d2bef172-66d6-4580-81ee-532c606ba541",
"name": "Insights Parser 10",
"type": "@n8n/n8n-nodes-langchain.outputParserStructured",
"typeVersion": 1.3,
"position": [
1328,
256
]
},
{
"parameters": {
"conditions": {
"options": {
"caseSensitive": true,
"leftValue": "",
"typeValidation": "strict",
"version": 1
},
"conditions": [
{
"id": "rel-10",
"leftValue": "={{ $json.output.relevant }}",
"rightValue": true,
"operator": {
"type": "boolean",
"operation": "true"
}
}
],
"combinator": "and"
},
"options": {}
},
"id": "9073f07c-743c-45c4-b85a-a86a0ad315a6",
"name": "IF Relevant 10",
"type": "n8n-nodes-base.if",
"typeVersion": 2.2,
"position": [
1328,
352
]
},
{
"parameters": {
"promptType": "define",
"text": "=Pozorovani z predchoziho agenta:\n{{ JSON.stringify($('Insights 10').first().json.output.insights) }}\n\nPlne telo publikace:\n{{ $('Extract Text').first().json.extractedText }}",
"hasOutputParser": true,
"options": {
"systemMessage": "Jsi sektorovy analytik Ceske sporitelny pro NACE 10 (pekarstvi). Pro KAZDE z 3 pozorovani vygeneruj 1 doporuceny krok pro malou pekarnu.\n\nPRAVIDLA: action_text \u2264240, time_horizon \u2208 {1m, 3m, 6-12m, 1y+}, paired_observation_index 0/1/2.\n\nTODO: NACE 10 pravidla.\n\nVYSTUPNI PRAVIDLA (KRITICKE):\n- Vrat POUZE valid JSON. Bez markdown bloku ```json ... ```. Bez komentaru pred nebo za. Zacni primo znakem { a skonci znakem }.\n- Vsechny pole z prikladu jsou POVINNE.\n- Boolean hodnoty jsou true / false (ne \"true\" / \"false\" jako string).\n- Arrays jsou pole [{...}, {...}], ne stringifikovane.",
"maxIterations": 3
}
},
"id": "993dd72c-bd3d-42f7-9208-3131c5c2a111",
"name": "Actions 10",
"type": "@n8n/n8n-nodes-langchain.agent",
"typeVersion": 3.1,
"position": [
1552,
352
]
},
{
"parameters": {
"jsonSchemaExample": "{\n \"actions\": [\n { \"action_text\": \"Akce: konkr\u00e9tn\u00ed krok.\", \"time_horizon\": \"1m\", \"paired_observation_index\": 0 }\n ]\n}",
"autoFix": true
},
"id": "2db1aefb-f81c-48c6-a4ec-0bbd3eee2dce",
"name": "Actions Parser 10",
"type": "@n8n/n8n-nodes-langchain.outputParserStructured",
"typeVersion": 1.3,
"position": [
1760,
464
]
},
{
"parameters": {
"jsCode": "const insightsOut = $('Insights 10').first().json.output || {};\nlet actionsOut = null;\ntry { actionsOut = $('Actions 10').first()?.json?.output || null; } catch (e) { actionsOut = null; }\nconst relevant = insightsOut.relevant === true;\nreturn [{ json: { nace: '10', relevant, insights: insightsOut.insights || [], actions: relevant && actionsOut ? (actionsOut.actions || []) : [], reason: insightsOut.reason || null } }];"
},
"id": "9d53bff7-b47c-4d4c-a5d8-01de672b5eab",
"name": "Tag 10",
"type": "n8n-nodes-base.code",
"typeVersion": 2,
"position": [
1984,
352
]
},
{
"parameters": {
"promptType": "define",
"text": "=Cesky uvod publikace (kontext):\n{{ $('Layperson Opener').first().json.output }}\n\nPlne telo publikace:\n{{ $('Extract Text').first().json.extractedText }}",
"hasOutputParser": true,
"options": {
"systemMessage": "Jsi sektorov\u00fd analytik \u010cesk\u00e9 spo\u0159itelny pro velkoobchod kovy a kovov\u00fdmi polotovary (NACE 46).\nTYPICK\u00dd KLIENT: mal\u00fd/st\u0159edn\u00ed distributor kov\u016f (ocel, hlin\u00edk, m\u011b\u010f, polotovary), 10\u201360 zam\u011bstnanc\u016f, B2B prodej do stroj\u00edrenstv\u00ed, stavebnictv\u00ed a automotive.\n\nRELEVANCE (bu\u010f liber\u00e1ln\u00ed):\n- P\u0159\u00edmo: velkoobchod kovy, ocel, hlin\u00edk, m\u011b\u010f, kovov\u00e9 polotovary, distribuce kov\u016f, ceny kov\u016f na sv\u011btov\u00fdch trz\u00edch (LME), B2B prodej, sklady a logistika kov\u016f.\n- Nep\u0159\u00edmo: stavebnictv\u00ed, automobilov\u00fd pr\u016fmysl, stroj\u00edrenstv\u00ed, energetika (popt\u00e1vka po kovech), EU obchodn\u00ed politika, cla, sankce, doprava n\u00e1kladu, ceny energi\u00ed ve v\u00fdrob\u011b, kursy CZK/USD/EUR.\n\nPravidlo: pokud lze vyvodit alespo\u0148 jedno u\u017eite\u010dn\u00e9 pozorov\u00e1n\u00ed pro typick\u00e9ho velkoobchodn\u00edka s kovy, vra\u0165 relevant=true. Jen publikace zcela bez vazby \u2192 relevant=false.\n\nV\u00ddSTUP:\n- relevantn\u00ed: { \"relevant\": true, \"reason\": null, \"insights\": [3 pozorov\u00e1n\u00ed] }\n- nerelevantn\u00ed: { \"relevant\": false, \"reason\": \"kr\u00e1tk\u00e9 vysv\u011btlen\u00ed\", \"insights\": [] }\n\nPOZOROV\u00c1N\u00cd: headline \u226460 znak\u016f; body 2 v\u011bty max 400 znak\u016f, vyk\u00e1n\u00ed, v\u011bcn\u00fd t\u00f3n; time_horizon \u2208 {\"Okam\u017eit\u011b\",\"Do 3 m\u011bs\u00edc\u016f\",\"Do 12 m\u011bs\u00edc\u016f\",\"V\u00edce ne\u017e rok\"}; is_email_teaser=true jen u prvn\u00edho.\n\nV\u00ddSTUPN\u00cd PRAVIDLA: pouze valid JSON, bez markdown blok\u016f, bez koment\u00e1\u0159\u016f. Za\u010dni { a skon\u010di }. Boolean = true/false. Arrays = pole, ne stringifikovan\u00e9.",
"maxIterations": 3
}
},
"id": "f93b96e6-1ebc-4b08-bbb0-5daa876fca22",
"name": "Insights 46",
"type": "@n8n/n8n-nodes-langchain.agent",
"typeVersion": 3.1,
"position": [
1104,
656
]
},
{
"parameters": {
"jsonSchemaExample": "{\n \"relevant\": true,\n \"reason\": null,\n \"insights\": [\n { \"headline\": \"Kr\u00e1tk\u00fd n\u00e1zev\", \"body\": \"Dv\u011b v\u011bty popisu.\", \"time_horizon\": \"Do 3 m\u011bs\u00edc\u016f\", \"is_email_teaser\": true }\n ]\n}",
"autoFix": true
},
"id": "432038b1-3b03-4e41-b652-bb3a351731f6",
"name": "Insights Parser 46",
"type": "@n8n/n8n-nodes-langchain.outputParserStructured",
"typeVersion": 1.3,
"position": [
1328,
656
]
},
{
"parameters": {
"conditions": {
"options": {
"caseSensitive": true,
"leftValue": "",
"typeValidation": "strict",
"version": 1
},
"conditions": [
{
"id": "rel-46",
"leftValue": "={{ $json.output.relevant }}",
"rightValue": true,
"operator": {
"type": "boolean",
"operation": "true"
}
}
],
"combinator": "and"
},
"options": {}
},
"id": "c6f81add-3cc0-4082-8893-c019cb87c77d",
"name": "IF Relevant 46",
"type": "n8n-nodes-base.if",
"typeVersion": 2.2,
"position": [
1328,
752
]
},
{
"parameters": {
"promptType": "define",
"text": "=Pozorovani z predchoziho agenta:\n{{ JSON.stringify($('Insights 46').first().json.output.insights) }}\n\nPlne telo publikace:\n{{ $('Extract Text').first().json.extractedText }}",
"hasOutputParser": true,
"options": {
"systemMessage": "Jsi sektorovy analytik Ceske sporitelny pro NACE 46. Pro KAZDE z 3 pozorovani vygeneruj 1 doporuceny krok.\n\nPRAVIDLA: action_text \u2264240, time_horizon \u2208 {1m, 3m, 6-12m, 1y+}, paired_observation_index 0/1/2.\n\nTODO: NACE 46 pravidla.\n\nVYSTUPNI PRAVIDLA (KRITICKE):\n- Vrat POUZE valid JSON. Bez markdown bloku ```json ... ```. Bez komentaru pred nebo za. Zacni primo znakem { a skonci znakem }.\n- Vsechny pole z prikladu jsou POVINNE.\n- Boolean hodnoty jsou true / false (ne \"true\" / \"false\" jako string).\n- Arrays jsou pole [{...}, {...}], ne stringifikovane.",
"maxIterations": 3
}
},
"id": "dc3edb08-4dca-4e15-b25d-79099528e6ed",
"name": "Actions 46",
"type": "@n8n/n8n-nodes-langchain.agent",
"typeVersion": 3.1,
"position": [
1552,
752
]
},
{
"parameters": {
"jsonSchemaExample": "{\n \"actions\": [\n { \"action_text\": \"Akce: konkr\u00e9tn\u00ed krok.\", \"time_horizon\": \"1m\", \"paired_observation_index\": 0 }\n ]\n}",
"autoFix": true
},
"id": "4c858e4c-5de1-4d0a-86d1-1870b3fd1953",
"name": "Actions Parser 46",
"type": "@n8n/n8n-nodes-langchain.outputParserStructured",
"typeVersion": 1.3,
"position": [
1760,
864
]
},
{
"parameters": {
"jsCode": "const insightsOut = $('Insights 46').first().json.output || {};\nlet actionsOut = null;\ntry { actionsOut = $('Actions 46').first()?.json?.output || null; } catch (e) { actionsOut = null; }\nconst relevant = insightsOut.relevant === true;\nreturn [{ json: { nace: '46', relevant, insights: insightsOut.insights || [], actions: relevant && actionsOut ? (actionsOut.actions || []) : [], reason: insightsOut.reason || null } }];"
},
"id": "ccb337dc-ef7b-4c58-a40c-8bad571bc936",
"name": "Tag 46",
"type": "n8n-nodes-base.code",
"typeVersion": 2,
"position": [
1984,
752
]
},
{
"parameters": {
"jsCode": "const items = $input.all().map(i => i.json);\nconst relevant = items.filter(it => it.relevant === true);\nconst webhookCtx = $('Verify HMAC').first().json;\nconst opener = $('Layperson Opener').first().json.output;\nconst extracted = $('Extract Text').first().json.extractedText;\nconst horizonMap = { '1m': 'Okam\u017eit\u011b', '3m': 'Do 3 m\u011bs\u00edc\u016f', '6-12m': 'Do 12 m\u011bs\u00edc\u016f', '1y+': 'V\u00edce ne\u017e rok', 'Okamzite': 'Okam\u017eit\u011b', 'Do 3 mesicu': 'Do 3 m\u011bs\u00edc\u016f', 'Do 12 mesicu': 'Do 12 m\u011bs\u00edc\u016f', 'Vice nez rok': 'V\u00edce ne\u017e rok' };\nconst tx = (h) => horizonMap[h] || (['Okam\u017eit\u011b','Do 3 m\u011bs\u00edc\u016f','Do 12 m\u011bs\u00edc\u016f','V\u00edce ne\u017e rok'].indexOf(h) !== -1 ? h : 'Do 3 m\u011bs\u00edc\u016f');\nconst perNaceContent = {};\nconst naceSectors = [];\nfor (const it of relevant) {\n if (!Array.isArray(it.insights) || !Array.isArray(it.actions)) continue;\n if (it.insights.length === 0 || it.actions.length === 0) continue;\n naceSectors.push(it.nace);\n perNaceContent[it.nace] = {\n observations: it.insights.slice(0, 4).map((o, i) => ({\n headline: String(o.headline || ('Pozorovani ' + (i+1))).slice(0, 80),\n body: String(o.body || ''),\n time_horizon: horizonMap[o.time_horizon] || (['Okam\u017eit\u011b','Do 3 m\u011bs\u00edc\u016f','Do 12 m\u011bs\u00edc\u016f','V\u00edce ne\u017e rok'].indexOf(o.time_horizon) !== -1 ? o.time_horizon : 'Do 3 m\u011bs\u00edc\u016f'),\n is_email_teaser: typeof o.is_email_teaser === 'boolean' ? o.is_email_teaser : (i === 0),\n })),\n closing_actions: it.actions.slice(0, 4).map((a, i) => ({\n action_text: String(a.action_text || ''),\n time_horizon: tx(a.time_horizon),\n paired_observation_index: typeof a.paired_observation_index === 'number' ? a.paired_observation_index : i,\n })),\n };\n}\nconst now = new Date();\nconst M = ['Leden','Unor','Brezen','Duben','Kveten','Cerven','Cervenec','Srpen','Zari','Rijen','Listopad','Prosinec'];\nconst publicationMonth = M[now.getMonth()] + ' ' + now.getFullYear();\nconst isoMonth = now.getFullYear() + '-' + String(now.getMonth() + 1).padStart(2, '0');\nconst dash = String.fromCharCode(8212);\nconst primaryNace = (typeof webhookCtx.primaryNace === 'string' && webhookCtx.primaryNace.length > 0) ? webhookCtx.primaryNace : (naceSectors[0] || null);\nconst callbackPayload = {\n jobId: webhookCtx.jobId,\n status: 'done',\n naceSectors,\n primaryNace,\n publicationMonth,\n publicationMonthIso: isoMonth,\n title: 'Sektorova analyza ' + dash + ' ' + publicationMonth,\n publication: { heading: 'Sektorova analyza', opener_markdown: String(opener || ''), full_text_markdown: String(extracted || ''), source: 'Ekonomicke a strategicke analyzy Ceske sporitelny ' + dash + ' ' + publicationMonth },\n perNaceContent,\n diagnostics: { total: items.length, relevant_count: naceSectors.length, dropped: items.filter(it => !it.relevant).map(it => ({ nace: it.nace, reason: it.reason })) },\n};\nconst passedGates = items.filter(it => it.relevant === true).length;\nif (passedGates > 0 && naceSectors.length < passedGates) {\n throw new Error(\n `Tag drop: ${passedGates} gates passed but only ${naceSectors.length} tagged. ` +\n `items=${JSON.stringify(items.map(i => ({nace: i.nace, relevant: i.relevant, hasInsights: Array.isArray(i.insights), hasActions: Array.isArray(i.actions)})))}`\n );\n}\nreturn [{ json: { callbackPayload, callbackUrl: webhookCtx.callbackUrl, jobId: webhookCtx.jobId } }];"
},
"id": "7711e360-7232-4091-8b96-04ae1d2e36fa",
"name": "Compose Bundle",
"type": "n8n-nodes-base.code",
"typeVersion": 2,
"position": [
2432,
112
]
},
{
"parameters": {
"jsCode": "const crypto = require('crypto');\nconst N8N_CALLBACK_SECRET = '3e724d3f5e8587982aa19768d1eb717de56ab6798e4713b28c6c372d7c89fc3b';\nconst data = $input.first().json;\nconst bodyStr = JSON.stringify(data.callbackPayload);\nconst sig = crypto.createHmac('sha256', N8N_CALLBACK_SECRET).update(bodyStr, 'utf8').digest('hex');\nreturn [{ json: { callbackUrl: data.callbackUrl, callbackBody: bodyStr, signatureHeader: 'sha256=' + sig, jobId: data.jobId, naceSectors: data.callbackPayload.naceSectors, diagnostics: data.callbackPayload.diagnostics } }];"
},
"id": "da40f415-06e7-41b5-8d30-2a05144b7042",
"name": "Sign Callback",
"type": "n8n-nodes-base.code",
"typeVersion": 2,
"position": [
2640,
112
]
},
{
"parameters": {
"method": "POST",
"url": "={{ $json.callbackUrl }}",
"sendHeaders": true,
"headerParameters": {
"parameters": [
{
"name": "Content-Type",
"value": "application/json"
},
{
"name": "X-Signature-256",
"value": "={{ $json.signatureHeader }}"
},
{
"name": "ngrok-skip-browser-warning",
"value": "true"
},
{
"name": "User-Agent",
"value": "StrategyRadar-n8n/1.0"
}
]
},
"sendBody": true,
"contentType": "raw",
"rawContentType": "application/json",
"body": "={{ $json.callbackBody }}",
"options": {
"response": {
"response": {
"neverError": true,
"responseFormat": "json"
}
},
"timeout": 30000
}
},
"id": "c311fa22-f0b5-470f-8b9b-dace14382129",
"name": "Send Callback",
"type": "n8n-nodes-base.httpRequest",
"typeVersion": 4.2,
"position": [
2864,
112
]
}
],
"connections": {
"Publication Webhook": {
"main": [
[
{
"node": "Verify HMAC",
"type": "main",
"index": 0
}
]
]
},
"Verify HMAC": {
"main": [
[
{
"node": "Fetch Publication File",
"type": "main",
"index": 0
}
]
]
},
"Fetch Publication File": {
"main": [
[
{
"node": "Extract Text",
"type": "main",
"index": 0
}
]
]
},
"Extract Text": {
"main": [
[
{
"node": "Layperson Opener",
"type": "main",
"index": 0
}
]
]
},
"Layperson Opener": {
"main": [
[
{
"node": "Insights 31",
"type": "main",
"index": 0
},
{
"node": "Insights 49",
"type": "main",
"index": 0
},
{
"node": "Insights 10",
"type": "main",
"index": 0
},
{
"node": "Insights 46",
"type": "main",
"index": 0
}
]
]
},
"Claude Haiku": {
"ai_languageModel": [
[
{
"node": "Layperson Opener",
"type": "ai_languageModel",
"index": 0
},
{
"node": "Insights 31",
"type": "ai_languageModel",
"index": 0
},
{
"node": "Insights Parser 31",
"type": "ai_languageModel",
"index": 0
},
{
"node": "Actions 31",
"type": "ai_languageModel",
"index": 0
},
{
"node": "Actions Parser 31",
"type": "ai_languageModel",
"index": 0
},
{
"node": "Insights 49",
"type": "ai_languageModel",
"index": 0
},
{
"node": "Insights Parser 49",
"type": "ai_languageModel",
"index": 0
},
{
"node": "Actions 49",
"type": "ai_languageModel",
"index": 0
},
{
"node": "Actions Parser 49",
"type": "ai_languageModel",
"index": 0
},
{
"node": "Insights 10",
"type": "ai_languageModel",
"index": 0
},
{
"node": "Insights Parser 10",
"type": "ai_languageModel",
"index": 0
},
{
"node": "Actions 10",
"type": "ai_languageModel",
"index": 0
},
{
"node": "Actions Parser 10",
"type": "ai_languageModel",
"index": 0
},
{
"node": "Insights 46",
"type": "ai_languageModel",
"index": 0
},
{
"node": "Insights Parser 46",
"type": "ai_languageModel",
"index": 0
},
{
"node": "Actions 46",
"type": "ai_languageModel",
"index": 0
},
{
"node": "Actions Parser 46",
"type": "ai_languageModel",
"index": 0
}
]
]
},
"Insights 31": {
"main": [
[
{
"node": "IF Relevant 31",
"type": "main",
"index": 0
}
]
]
},
"Insights Parser 31": {
"ai_outputParser": [
[
{
"node": "Insights 31",
"type": "ai_outputParser",
"index": 0
}
]
]
},
"IF Relevant 31": {
"main": [
[
{
"node": "Actions 31",
"type": "main",
"index": 0
}
],
[
{
"node": "Tag 31",
"type": "main",
"index": 0
}
]
]
},
"Actions 31": {
"main": [
[
{
"node": "Tag 31",
"type": "main",
"index": 0
}
]
]
},
"Actions Parser 31": {
"ai_outputParser": [
[
{
"node": "Actions 31",
"type": "ai_outputParser",
"index": 0
}
]
]
},
"Tag 31": {
"main": [
[
{
"node": "Merge NACE Results",
"type": "main",
"index": 0
}
]
]
},
"Merge NACE Results": {
"main": [
[
{
"node": "Compose Bundle",
"type": "main",
"index": 0
}
]
]
},
"Insights 49": {
"main": [
[
{
"node": "IF Relevant 49",
"type": "main",
"index": 0
}
]
]
},
"Insights Parser 49": {
"ai_outputParser": [
[
{
"node": "Insights 49",
"type": "ai_outputParser",
"index": 0
}
]
]
},
"IF Relevant 49": {
"main": [
[
{
"node": "Actions 49",
"type": "main",
"index": 0
}
],
[
{
"node": "Tag 49",
"type": "main",
"index": 0
}
]
]
},
"Actions 49": {
"main": [
[
{
"node": "Tag 49",
"type": "main",
"index": 0
}
]
]
},
"Actions Parser 49": {
"ai_outputParser": [
[
{
"node": "Actions 49",
"type": "ai_outputParser",
"index": 0
}
]
]
},
"Tag 49": {
"main": [
[
{
"node": "Merge NACE Results",
"type": "main",
"index": 1
}
]
]
},
"Insights 10": {
"main": [
[
{
"node": "IF Relevant 10",
"type": "main",
"index": 0
}
]
]
},
"Insights Parser 10": {
"ai_outputParser": [
[
{
"node": "Insights 10",
"type": "ai_outputParser",
"index": 0
}
]
]
},
"IF Relevant 10": {
"main": [
[
{
"node": "Actions 10",
"type": "main",
"index": 0
}
],
[
{
"node": "Tag 10",
"type": "main",
"index": 0
}
]
]
},
"Actions 10": {
"main": [
[
{
"node": "Tag 10",
"type": "main",
"index": 0
}
]
]
},
"Actions Parser 10": {
"ai_outputParser": [
[
{
"node": "Actions 10",
"type": "ai_outputParser",
"index": 0
}
]
]
},
"Tag 10": {
"main": [
[
{
"node": "Merge NACE Results",
"type": "main",
"index": 2
}
]
]
},
"Insights 46": {
"main": [
[
{
"node": "IF Relevant 46",
"type": "main",
"index": 0
}
]
]
},
"Insights Parser 46": {
"ai_outputParser": [
[
{
"node": "Insights 46",
"type": "ai_outputParser",
"index": 0
}
]
]
},
"IF Relevant 46": {
"main": [
[
{
"node": "Actions 46",
"type": "main",
"index": 0
}
],
[
{
"node": "Tag 46",
"type": "main",
"index": 0
}
]
]
},
"Actions 46": {
"main": [
[
{
"node": "Tag 46",
"type": "main",
"index": 0
}
]
]
},
"Actions Parser 46": {
"ai_outputParser": [
[
{
"node": "Actions 46",
"type": "ai_outputParser",
"index": 0
}
]
]
},
"Tag 46": {
"main": [
[
{
"node": "Merge NACE Results",
"type": "main",
"index": 3
}
]
]
},
"Compose Bundle": {
"main": [
[
{
"node": "Sign Callback",
"type": "main",
"index": 0
}
]
]
},
"Sign Callback": {
"main": [
[
{
"node": "Send Callback",
"type": "main",
"index": 0
}
]
]
}
},
"active": true,
"settings": {
"executionOrder": "v1",
"binaryMode": "separate",
"availableInMCP": true
},
"versionId": "aa2e4aee-b04a-4c08-a333-1896a285bbc0",
"meta": {
"aiBuilderAssisted": true
},
"id": "Fnbbz2mT4k3HrBXd",
"tags": []
}
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.
anthropicApi
For the full experience including quality scoring and batch install features for each workflow upgrade to Pro
About this workflow
Strategy Radar — Analyze Publication. Uses httpRequest, agent, lmChatAnthropic, outputParserStructured. Webhook trigger; 34 nodes.
Source: https://github.com/pdeaibootcamp-netizen/saap/blob/e77ec1fef11bfc08421a84b49e5ac73812a903c4/n8n-workflows/analyze-publication.json — 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.
⏺ 🚀 How it works
Fully automates your service order pipeline from incoming booking to supplier confirmation — with built-in SLA enforcement and automatic escalation if a supplier goes silent. 📥 Receives orders via web
Tired of grinding out YouTube content? This n8n workflow turns AI into your personal video factory—creating engaging, faceless shorts on autopilot. Perfect for creators, marketers, or side-hustlers lo
Faceless YouTube Generator. Uses httpRequest, limit, googleDrive, googleSheets. Webhook trigger; 49 nodes.
This workflow automates end-to-end marketing campaign management for digital marketing teams and agencies executing multi-channel strategies. It solves the complex challenge of coordinating personaliz