This workflow corresponds to n8n.io template #14124 — we link there as the canonical source.
This workflow follows the HTTP Request → Notion 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 →
{
"id": "06REJtR4u554I4dR",
"name": "Signal Router",
"tags": [],
"nodes": [
{
"id": "3006021a-6014-47d4-8fa1-1c22dbe79a52",
"name": "Sticky Note - How It Works",
"type": "n8n-nodes-base.stickyNote",
"position": [
-1408,
-48
],
"parameters": {
"width": 420,
"height": 440,
"content": "## How it works\n\nWhen you set a signal's Route Status to 'Routing' in Notion, this workflow picks it up and sends it to the right destination: Jira bug, Jira feature, RICE+ backlog, customer health, or sprint backlog."
},
"typeVersion": 1
},
{
"id": "f6aaa487-af0a-4a0e-a30a-d0db7dc630d7",
"name": "Sticky Note - Routing",
"type": "n8n-nodes-base.stickyNote",
"position": [
-944,
-64
],
"parameters": {
"color": 7,
"width": 1924,
"height": 1736,
"content": "## Routing Engine\n\nReads signal details from Notion, flattens properties, then routes via a 5-way switch based on the Route Destination field you selected."
},
"typeVersion": 1
},
{
"id": "331189d2-7230-43cb-a190-9be31d459c41",
"name": "Signal Route Trigger",
"type": "n8n-nodes-base.notion",
"polling": true,
"position": [
-800,
704
],
"parameters": {
"limit": 10,
"simple": false,
"options": {},
"resource": "databasePage",
"operation": "getAll",
"databaseId": "31e06bab-3ebe-811b-b204-c5f41b273303",
"filterType": "singleCondition"
},
"typeVersion": 2.2
},
{
"id": "9d7e2e06-8dda-49fd-ac66-9a6b747a52de",
"name": "Filter Routing Status",
"type": "n8n-nodes-base.if",
"position": [
-496,
704
],
"parameters": {
"options": {},
"conditions": {
"options": {
"leftValue": "",
"caseSensitive": true,
"typeValidation": "strict"
},
"combinator": "and",
"conditions": [
{
"id": "condition-routing-check",
"operator": {
"type": "string",
"operation": "equals"
},
"leftValue": "={{ $json.properties?.['Route Status']?.select?.name }}",
"rightValue": "Routing"
}
]
}
},
"typeVersion": 2
},
{
"id": "6a7f26bd-15e4-4693-a3f2-2944c78497a3",
"name": "Read Signal Details",
"type": "n8n-nodes-base.code",
"position": [
-208,
704
],
"parameters": {
"jsCode": "// Extract all useful properties from the Notion page into a flat object\nconst props = $json.properties;\n\nconst getValue = (prop) => {\n if (!prop) return '';\n if (prop.title) return prop.title.map(t => t.plain_text).join('');\n if (prop.rich_text) return prop.rich_text.map(t => t.plain_text).join('');\n if (prop.select) return prop.select?.name || '';\n if (prop.url) return prop.url || '';\n if (prop.date) return prop.date?.start || '';\n return '';\n};\n\nreturn [{\n json: {\n notionPageId: $json.id,\n signal: getValue(props['Signal']),\n dateCaptured: getValue(props['Date Captured']),\n sourceChannel: getValue(props['Source Channel']),\n originalMessage: getValue(props['Original Message']),\n author: getValue(props['Author']),\n signalType: getValue(props['Signal Type']),\n sentiment: getValue(props['Sentiment']),\n urgency: getValue(props['Urgency']),\n aiAnalysis: getValue(props['AI Analysis']),\n customerMentioned: getValue(props['Customer Mentioned']),\n routeDestination: getValue(props['Route Destination']),\n routeStatus: getValue(props['Route Status']),\n threadUrl: getValue(props['Thread URL']),\n slackMessageId: getValue(props['Slack Message ID'])\n }\n}];"
},
"typeVersion": 2
},
{
"id": "1a2e166a-b874-441b-af72-a517fbaf89e4",
"name": "Route Destination",
"type": "n8n-nodes-base.switch",
"position": [
112,
704
],
"parameters": {
"rules": {
"values": [
{
"conditions": {
"options": {
"leftValue": "",
"caseSensitive": true,
"typeValidation": "strict"
},
"conditions": [
{
"operator": {
"type": "string",
"operation": "equals"
},
"leftValue": "={{ $json.routeDestination }}",
"rightValue": "Jira Bug"
}
]
}
},
{
"conditions": {
"options": {
"leftValue": "",
"caseSensitive": true,
"typeValidation": "strict"
},
"conditions": [
{
"operator": {
"type": "string",
"operation": "equals"
},
"leftValue": "={{ $json.routeDestination }}",
"rightValue": "Jira Feature"
}
]
}
},
{
"conditions": {
"options": {
"leftValue": "",
"caseSensitive": true,
"typeValidation": "strict"
},
"conditions": [
{
"operator": {
"type": "string",
"operation": "equals"
},
"leftValue": "={{ $json.routeDestination }}",
"rightValue": "RICE+ Backlog"
}
]
}
},
{
"conditions": {
"options": {
"leftValue": "",
"caseSensitive": true,
"typeValidation": "strict"
},
"conditions": [
{
"operator": {
"type": "string",
"operation": "equals"
},
"leftValue": "={{ $json.routeDestination }}",
"rightValue": "Customer Health"
}
]
}
},
{
"conditions": {
"options": {
"leftValue": "",
"caseSensitive": true,
"typeValidation": "strict"
},
"conditions": [
{
"operator": {
"type": "string",
"operation": "equals"
},
"leftValue": "={{ $json.routeDestination }}",
"rightValue": "Sprint Backlog"
}
]
}
}
]
},
"options": {}
},
"typeVersion": 3.2
},
{
"id": "6bbe4bff-e55e-48d6-8f91-c97fd2f6c082",
"name": "Create Jira Bug",
"type": "n8n-nodes-base.httpRequest",
"position": [
400,
304
],
"parameters": {
"url": "https://company.atlassian.net/rest/api/3/issue",
"method": "POST",
"options": {},
"jsonBody": "={{ JSON.stringify({ fields: { project: { key: 'PROJ' }, issuetype: { name: 'Bug' }, summary: '[Signal] ' + $json.signal, description: { type: 'doc', version: 1, content: [{ type: 'heading', attrs: { level: 3 }, content: [{ type: 'text', text: 'Signal Captured from Slack' }] }, { type: 'paragraph', content: [{ type: 'text', text: 'Source: ', marks: [{ type: 'strong' }] }, { type: 'text', text: $json.sourceChannel + ' by ' + $json.author }] }, { type: 'heading', attrs: { level: 4 }, content: [{ type: 'text', text: 'Original Message' }] }, { type: 'blockquote', content: [{ type: 'paragraph', content: [{ type: 'text', text: $json.originalMessage || '' }] }] }, { type: 'heading', attrs: { level: 4 }, content: [{ type: 'text', text: 'AI Analysis' }] }, { type: 'paragraph', content: [{ type: 'text', text: $json.aiAnalysis || '' }] }, { type: 'paragraph', content: [{ type: 'text', text: 'Slack Thread: ' }, { type: 'text', text: 'View original', marks: [{ type: 'link', attrs: { href: $json.threadUrl || '#' } }] }] }] }, priority: { name: $json.urgency === 'Critical' ? 'Highest' : $json.urgency === 'High' ? 'High' : $json.urgency === 'Medium' ? 'Medium' : 'Low' }, labels: ['signal-catcher', 'slack-signal'] } }) }}",
"sendBody": true,
"sendHeaders": true,
"specifyBody": "json",
"authentication": "genericCredentialType",
"genericAuthType": "httpBasicAuth",
"headerParameters": {
"parameters": [
{
"name": "Content-Type",
"value": "application/json"
}
]
}
},
"typeVersion": 4.2
},
{
"id": "be4d49da-3b63-42b5-8c29-13f50e1afa24",
"name": "Parse Jira Bug Response",
"type": "n8n-nodes-base.code",
"position": [
704,
304
],
"parameters": {
"jsCode": "// Extract Jira bug ticket reference\nconst jiraKey = $json.key || 'PROJ-???';\nconst signalData = $('Read Signal Details').first().json;\n\nreturn [{\n json: {\n ...signalData,\n routedReference: jiraKey,\n routedUrl: `https://company.atlassian.net/browse/${jiraKey}`\n }\n}];"
},
"typeVersion": 2
},
{
"id": "a98d8368-06d9-4cff-9f9f-a527e64cf1c4",
"name": "Create Jira Feature",
"type": "n8n-nodes-base.httpRequest",
"position": [
400,
512
],
"parameters": {
"url": "https://company.atlassian.net/rest/api/3/issue",
"method": "POST",
"options": {},
"jsonBody": "={{ JSON.stringify({ fields: { project: { key: 'PROJ' }, issuetype: { name: 'Story' }, summary: '[Signal] ' + $json.signal, description: { type: 'doc', version: 1, content: [{ type: 'heading', attrs: { level: 3 }, content: [{ type: 'text', text: 'Feature Signal from Slack' }] }, { type: 'paragraph', content: [{ type: 'text', text: 'Source: ', marks: [{ type: 'strong' }] }, { type: 'text', text: $json.sourceChannel + ' by ' + $json.author }] }, { type: 'paragraph', content: [{ type: 'text', text: 'Customer: ', marks: [{ type: 'strong' }] }, { type: 'text', text: $json.customerMentioned || 'None mentioned' }] }, { type: 'heading', attrs: { level: 4 }, content: [{ type: 'text', text: 'Original Message' }] }, { type: 'blockquote', content: [{ type: 'paragraph', content: [{ type: 'text', text: $json.originalMessage || '' }] }] }, { type: 'heading', attrs: { level: 4 }, content: [{ type: 'text', text: 'AI Analysis' }] }, { type: 'paragraph', content: [{ type: 'text', text: $json.aiAnalysis || '' }] }, { type: 'paragraph', content: [{ type: 'text', text: 'Slack Thread: ' }, { type: 'text', text: 'View original', marks: [{ type: 'link', attrs: { href: $json.threadUrl || '#' } }] }] }] }, priority: { name: $json.urgency === 'Critical' ? 'Highest' : $json.urgency === 'High' ? 'High' : 'Medium' }, labels: ['signal-catcher', 'feature-signal', 'slack-signal'] } }) }}",
"sendBody": true,
"sendHeaders": true,
"specifyBody": "json",
"authentication": "genericCredentialType",
"genericAuthType": "httpBasicAuth",
"headerParameters": {
"parameters": [
{
"name": "Content-Type",
"value": "application/json"
}
]
}
},
"typeVersion": 4.2
},
{
"id": "b736cf5c-d89e-4496-953c-b1ad5a836e33",
"name": "Parse Jira Feature Response",
"type": "n8n-nodes-base.code",
"position": [
704,
512
],
"parameters": {
"jsCode": "// Extract Jira feature ticket reference\nconst jiraKey = $json.key || 'PROJ-???';\nconst signalData = $('Read Signal Details').first().json;\n\nreturn [{\n json: {\n ...signalData,\n routedReference: jiraKey,\n routedUrl: `https://company.atlassian.net/browse/${jiraKey}`\n }\n}];"
},
"typeVersion": 2
},
{
"id": "68977746-0f16-4571-8c10-2d698e1a8121",
"name": "Create RICE+ Entry",
"type": "n8n-nodes-base.notion",
"position": [
400,
704
],
"parameters": {
"title": "={{ '[Signal] ' + $json.signal }}",
"options": {},
"resource": "databasePage",
"databaseId": "31e06bab-3ebe-81fe-9d0c-e65a49a99ef3",
"propertiesUi": {
"propertyValues": [
{
"key": "Source|select",
"selectValue": "Signal Catcher"
},
{
"key": "Status|select",
"selectValue": "Proposed"
},
{
"key": "Customer Request|rich_text"
}
]
}
},
"typeVersion": 2.2
},
{
"id": "27c0937e-2eae-4087-98d0-3c37ea268b02",
"name": "Parse RICE Response",
"type": "n8n-nodes-base.code",
"position": [
704,
704
],
"parameters": {
"jsCode": "// Generate a readable reference for the RICE+ entry\nconst riceRef = 'RICE-' + String(Math.floor(Math.random() * 900) + 100).padStart(3, '0');\nconst signalData = $('Read Signal Details').first().json;\n\nreturn [{\n json: {\n ...signalData,\n routedReference: riceRef,\n routedUrl: $json.url || '#',\n notionRicePageId: $json.id || ''\n }\n}];"
},
"typeVersion": 2
},
{
"id": "d6e5ff17-b892-428e-bd15-43161c1ddbc0",
"name": "Create Customer Health Entry",
"type": "n8n-nodes-base.notion",
"position": [
400,
912
],
"parameters": {
"title": "={{ '[Signal] ' + $json.signal }}",
"options": {},
"resource": "databasePage",
"databaseId": "31e06bab-3ebe-811b-b204-c5f41b273303",
"propertiesUi": {
"propertyValues": [
{
"key": "Account|rich_text"
},
{
"key": "Type|select",
"selectValue": "={{ $json.signalType === 'Customer Escalation' ? 'Escalation' : $json.signalType === 'Bug Report' ? 'Support Issue' : 'Product Signal' }}"
},
{
"key": "Sentiment|select",
"selectValue": "={{ $json.sentiment }}"
},
{
"key": "Date|date"
},
{
"key": "Notes|rich_text"
}
]
}
},
"typeVersion": 2.2
},
{
"id": "7463e91e-dded-4608-b358-81e1ddd55578",
"name": "Parse Customer Health Response",
"type": "n8n-nodes-base.code",
"position": [
704,
912
],
"parameters": {
"jsCode": "// Generate a health reference\nconst signalData = $('Read Signal Details').first().json;\nconst healthRef = signalData.customerMentioned\n ? signalData.customerMentioned.replace(/\\s+/g, '').substring(0, 3).toUpperCase() + '-HEALTH-' + String(Math.floor(Math.random() * 900) + 100).padStart(3, '0')\n : 'UNK-HEALTH-' + String(Math.floor(Math.random() * 900) + 100).padStart(3, '0');\n\nreturn [{\n json: {\n ...signalData,\n routedReference: healthRef,\n routedUrl: $json.url || '#',\n notionHealthPageId: $json.id || ''\n }\n}];"
},
"typeVersion": 2
},
{
"id": "98a0e380-8810-4d66-aa8b-b36562949507",
"name": "Create Sprint Backlog Item",
"type": "n8n-nodes-base.notion",
"position": [
400,
1104
],
"parameters": {
"title": "={{ '[Signal] ' + $json.signal }}",
"options": {},
"resource": "databasePage",
"databaseId": "31e06bab-3ebe-81fe-9d0c-e65a49a99ef3",
"propertiesUi": {
"propertyValues": [
{
"key": "Status|select",
"selectValue": "To Do"
},
{
"key": "Priority|select",
"selectValue": "={{ $json.urgency }}"
},
{
"key": "Source|select",
"selectValue": "Signal Catcher"
},
{
"key": "Sprint|select",
"selectValue": "Sprint 24"
},
{
"key": "Description|rich_text"
}
]
}
},
"typeVersion": 2.2
},
{
"id": "769c9788-87a2-4ce2-8bdf-726fb23dd95d",
"name": "Parse Sprint Response",
"type": "n8n-nodes-base.code",
"position": [
704,
1104
],
"parameters": {
"jsCode": "// Generate a sprint reference\nconst signalData = $('Read Signal Details').first().json;\nconst sprintRef = 'SPRINT-' + String(Math.floor(Math.random() * 900) + 100).padStart(3, '0');\n\nreturn [{\n json: {\n ...signalData,\n routedReference: sprintRef,\n routedUrl: $json.url || '#',\n notionSprintPageId: $json.id || ''\n }\n}];"
},
"typeVersion": 2
},
{
"id": "02da030b-7d20-4ca4-aac7-a53cc9cf1ab0",
"name": "Update Signal Status",
"type": "n8n-nodes-base.notion",
"position": [
1040,
704
],
"parameters": {
"pageId": "={{ $json.notionPageId }}",
"options": {},
"resource": "databasePage",
"operation": "update",
"propertiesUi": {
"propertyValues": [
{
"key": "Route Status|select",
"selectValue": "Routed"
},
{
"key": "Routed Reference|rich_text"
}
]
}
},
"typeVersion": 2.2
},
{
"id": "11f1c990-b23d-4a34-8fea-ddee8dbc25bc",
"name": "Build Thread Reply",
"type": "n8n-nodes-base.code",
"position": [
1312,
704
],
"parameters": {
"jsCode": "// Build Slack Thread Reply\nconst signal = $json;\n\n// Determine the channel ID from the name\nconst channelMap = {\n '#product': 'C01PRODUCT',\n '#support': 'C02SUPPORT',\n '#sales': 'C03SALES',\n '#engineering': 'C04ENGINEERING',\n '#general': 'C05GENERAL'\n};\n\nconst channelId = channelMap[signal.sourceChannel] || signal.sourceChannel;\n\n// Build confirmation message\nconst destinationLabel = {\n 'Jira Bug': 'Jira Bug Ticket',\n 'Jira Feature': 'Jira Feature Story',\n 'RICE+ Backlog': 'RICE+ Feature Backlog',\n 'Customer Health': 'Customer Health Tracker',\n 'Sprint Backlog': 'Sprint 24 Backlog'\n}[signal.routeDestination] || signal.routeDestination;\n\nconst replyMessage = `Captured and routed to *${signal.routedReference}* (${destinationLabel})`;\n\nreturn [{\n json: {\n ...signal,\n slackChannelId: channelId,\n replyMessage: replyMessage\n }\n}];"
},
"typeVersion": 2
},
{
"id": "c802324b-f571-42de-911c-9373ded5060a",
"name": "Reply in Thread",
"type": "n8n-nodes-base.httpRequest",
"position": [
1600,
704
],
"parameters": {
"url": "https://slack.com/api/chat.postMessage",
"method": "POST",
"options": {},
"jsonBody": "={{ JSON.stringify({ channel: $json.slackChannelId, text: $json.replyMessage, thread_ts: $json.slackMessageId, unfurl_links: false }) }}",
"sendBody": true,
"sendHeaders": true,
"specifyBody": "json",
"authentication": "predefinedCredentialType",
"headerParameters": {
"parameters": [
{
"name": "Content-Type",
"value": "application/json"
}
]
},
"nodeCredentialType": "slackApi"
},
"typeVersion": 4.2,
"continueOnFail": true
},
{
"id": "d774ff2f-e48c-43dc-9102-1857e7c16929",
"name": "Sticky Note",
"type": "n8n-nodes-base.stickyNote",
"position": [
1008,
-64
],
"parameters": {
"color": 7,
"width": 800,
"height": 1744,
"content": "## Closed Loop\n\nAfter routing, updates the signal status to 'Routed' with a reference link, and replies in the original Slack thread to confirm where it went."
},
"typeVersion": 1
}
],
"active": false,
"settings": {
"binaryMode": "separate",
"availableInMCP": false,
"executionOrder": "v1"
},
"versionId": "fa198898-5fb4-4a4d-8f15-4de2d6435afe",
"connections": {
"Create Jira Bug": {
"main": [
[
{
"node": "Parse Jira Bug Response",
"type": "main",
"index": 0
}
]
]
},
"Route Destination": {
"main": [
[
{
"node": "Create Jira Bug",
"type": "main",
"index": 0
}
],
[
{
"node": "Create Jira Feature",
"type": "main",
"index": 0
}
],
[
{
"node": "Create RICE+ Entry",
"type": "main",
"index": 0
}
],
[
{
"node": "Create Customer Health Entry",
"type": "main",
"index": 0
}
],
[
{
"node": "Create Sprint Backlog Item",
"type": "main",
"index": 0
}
]
]
},
"Build Thread Reply": {
"main": [
[
{
"node": "Reply in Thread",
"type": "main",
"index": 0
}
]
]
},
"Create RICE+ Entry": {
"main": [
[
{
"node": "Parse RICE Response",
"type": "main",
"index": 0
}
]
]
},
"Create Jira Feature": {
"main": [
[
{
"node": "Parse Jira Feature Response",
"type": "main",
"index": 0
}
]
]
},
"Parse RICE Response": {
"main": [
[
{
"node": "Update Signal Status",
"type": "main",
"index": 0
}
]
]
},
"Read Signal Details": {
"main": [
[
{
"node": "Route Destination",
"type": "main",
"index": 0
}
]
]
},
"Signal Route Trigger": {
"main": [
[
{
"node": "Filter Routing Status",
"type": "main",
"index": 0
}
]
]
},
"Update Signal Status": {
"main": [
[
{
"node": "Build Thread Reply",
"type": "main",
"index": 0
}
]
]
},
"Filter Routing Status": {
"main": [
[
{
"node": "Read Signal Details",
"type": "main",
"index": 0
}
]
]
},
"Parse Sprint Response": {
"main": [
[
{
"node": "Update Signal Status",
"type": "main",
"index": 0
}
]
]
},
"Parse Jira Bug Response": {
"main": [
[
{
"node": "Update Signal Status",
"type": "main",
"index": 0
}
]
]
},
"Create Sprint Backlog Item": {
"main": [
[
{
"node": "Parse Sprint Response",
"type": "main",
"index": 0
}
]
]
},
"Parse Jira Feature Response": {
"main": [
[
{
"node": "Update Signal Status",
"type": "main",
"index": 0
}
]
]
},
"Create Customer Health Entry": {
"main": [
[
{
"node": "Parse Customer Health Response",
"type": "main",
"index": 0
}
]
]
},
"Parse Customer Health Response": {
"main": [
[
{
"node": "Update Signal Status",
"type": "main",
"index": 0
}
]
]
}
}
}
For the full experience including quality scoring and batch install features for each workflow upgrade to Pro
About this workflow
Route captured signals to the right destination with one click. Set a signal’s Route Destination in Notion, and this workflow automatically creates a Jira ticket, backlog item, or customer health entry, then confirms in the original Slack thread.
Source: https://n8n.io/workflows/14124/ — 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.
Are you tired of the repetitive dance between git push, creating a pull request in GitHub, updating the corresponding task in JIRA, and then manually notifying your team in Slack, or Notion?
This workflow is an AI-assisted clean plate and object removal pipeline built for modern VFX production environments. It transforms a single plate image and removal brief into multiple high-quality cl
This n8n template from Intuz provides a complete and automated solution for preparing and delivering context-rich briefings directly to attendees before every meeting.
This workflow is an AI-driven FX concept generation pipeline that transforms a single VFX brief into multiple high-quality simulation-ready video concepts. It automates ideation, rendering, storage, a
I wanted a journal but never had the discipline to write one. Most of my day happens in Discord anyway, so I built this to do it for me.