{ "name": "Telegram Assistant - Deck Integration", "nodes": [ { "parameters": { "httpMethod": "POST", "path": "telegram-deck", "responseMode": "responseNode", "options": {} }, "id": "webhook-deck-1", "name": "Webhook", "type": "n8n-nodes-base.webhook", "typeVersion": 1, "position": [240, 300], "webhookId": "telegram-deck" }, { "parameters": { "mode": "runOnceForEachItem", "jsCode": "const args = $input.item.json.args || '';\nconst chatId = $input.item.json.chatId;\nconst parts = args.trim().split(/\\s+/);\nconst subCommand = parts[0]?.toLowerCase() || 'help';\nconst taskText = parts.slice(1).join(' ');\nreturn {chatId, subCommand, taskText, originalArgs: args};" }, "id": "parse-deck-command-1", "name": "Parse Deck Command", "type": "n8n-nodes-base.code", "typeVersion": 2, "position": [460, 300] }, { "parameters": { "mode": "rules", "rules": { "rules": [ { "operation": "equal", "value1": "={{ $json.subCommand }}", "value2": "add" }, { "operation": "equal", "value1": "={{ $json.subCommand }}", "value2": "list" } ] }, "fallbackOutput": "extra" }, "id": "switch-deck-action-1", "name": "Route Deck Action", "type": "n8n-nodes-base.switch", "typeVersion": 1, "position": [680, 300] }, { "parameters": { "conditions": { "string": [{"value1": "={{ $json.taskText }}", "operation": "isNotEmpty"}] } }, "id": "check-task-text-1", "name": "Check Task Text", "type": "n8n-nodes-base.if", "typeVersion": 1, "position": [900, 200] }, { "parameters": { "url": "https://api.openai.com/v1/chat/completions", "authentication": "genericCredentialType", "genericAuthType": "httpHeaderAuth", "sendBody": true, "specifyBody": "json", "jsonBody": "={\"model\": \"gpt-4o-mini\", \"messages\": [{\"role\": \"system\", \"content\": \"Extract task information from user input. Return JSON with: title (required, concise task name), description (optional, details), duedate (optional, YYYY-MM-DD format). For German dates like 'morgen', 'รผbermorgen', calculate from today ({{ $now.toFormat('yyyy-MM-dd') }}). Be concise.\"}, {\"role\": \"user\", \"content\": \"{{ $json.taskText }}\"}], \"temperature\": 0.3, \"max_tokens\": 150}", "options": {} }, "id": "ai-extract-task-1", "name": "AI Extract Task Details", "type": "n8n-nodes-base.httpRequest", "typeVersion": 3, "position": [1120, 100], "credentials": { "httpHeaderAuth": { "id": "openai_api_key", "name": "OpenAI API Key" } } }, { "parameters": { "mode": "runOnceForEachItem", "jsCode": "const aiResponse = $input.item.json.choices[0].message.content;\nlet taskData;\ntry {taskData = JSON.parse(aiResponse);} catch (e) {taskData = {title: $input.item.json.taskText.substring(0, 100), description: $input.item.json.taskText, duedate: null};}\nreturn {chatId: $input.item.json.chatId, title: taskData.title || 'Untitled Task', description: taskData.description || '', duedate: taskData.duedate || null};" }, "id": "format-task-data-1", "name": "Format Task Data", "type": "n8n-nodes-base.code", "typeVersion": 2, "position": [1340, 100] }, { "parameters": { "command": "=/home/node/create_card_from_ai.sh \"{{ $json.title }}\" \"{{ $json.description }}\" \"{{ $json.duedate || '' }}\"" }, "id": "create-deck-card-1", "name": "Create Deck Card", "type": "n8n-nodes-base.executeCommand", "typeVersion": 1, "position": [1560, 100] }, { "parameters": { "mode": "runOnceForEachItem", "jsCode": "const output = $input.item.json.stdout || '';\nconst error = $input.item.json.stderr || '';\nlet success = !error || output.includes('Card created');\nconst urlMatch = output.match(/https?:\\/\\/[^\\s]+/);\nconst cardUrl = urlMatch ? urlMatch[0] : '';\nconst responseText = success ? `โœ… Task added to Nextcloud Deck!\\n\\n๐Ÿ“‹ *${$input.item.json.title}*${$input.item.json.duedate ? '\\n๐Ÿ“… Due: ' + $input.item.json.duedate : ''}${cardUrl ? '\\n๐Ÿ”— ' + cardUrl : ''}` : `โŒ Failed to create task.\\n\\nError: ${error}`;\nreturn {chatId: $input.item.json.chatId, text: responseText, parseMode: 'Markdown'};" }, "id": "format-success-response-1", "name": "Format Success Response", "type": "n8n-nodes-base.code", "typeVersion": 2, "position": [1780, 100] }, { "parameters": { "respondWith": "json", "responseBody": "={{ JSON.stringify($json) }}" }, "id": "respond-result-1", "name": "Respond Result", "type": "n8n-nodes-base.respondToWebhook", "typeVersion": 1, "position": [2000, 300] }, { "parameters": { "respondWith": "json", "responseBody": "={{ JSON.stringify({chatId: $json.chatId, text: \"โŒ Please specify a task to add.\\n\\nExample: /deck add Review Q4 reports by Friday\"}) }}" }, "id": "respond-no-task-1", "name": "Respond No Task", "type": "n8n-nodes-base.respondToWebhook", "typeVersion": 1, "position": [1120, 300] }, { "parameters": { "respondWith": "json", "responseBody": "={{ JSON.stringify({chatId: $json.chatId, text: \"๐Ÿ“‹ *Deck Commands*\\n\\n/deck add \\nOr: 'add a deck called cleaning'\\n\\nExample:\\n/deck add Review project proposal by tomorrow\", parseMode: 'Markdown'}) }}" }, "id": "respond-deck-help-1", "name": "Respond Deck Help", "type": "n8n-nodes-base.respondToWebhook", "typeVersion": 1, "position": [900, 500] }, { "parameters": { "respondWith": "json", "responseBody": "={{ JSON.stringify({chatId: $json.chatId, text: \"๐Ÿ“‹ List functionality coming soon!\\n\\nFor now, check your Nextcloud Deck at:\\nhttps://nextcloud.egonetix.de/apps/deck\"}) }}" }, "id": "respond-list-placeholder-1", "name": "Respond List", "type": "n8n-nodes-base.respondToWebhook", "typeVersion": 1, "position": [900, 400] } ], "connections": { "Webhook": {"main": [[{"node": "Parse Deck Command", "type": "main", "index": 0}]]}, "Parse Deck Command": {"main": [[{"node": "Route Deck Action", "type": "main", "index": 0}]]}, "Route Deck Action": {"main": [[{"node": "Check Task Text", "type": "main", "index": 0}], [{"node": "Respond List", "type": "main", "index": 0}], [{"node": "Respond Deck Help", "type": "main", "index": 0}]]}, "Check Task Text": {"main": [[{"node": "AI Extract Task Details", "type": "main", "index": 0}], [{"node": "Respond No Task", "type": "main", "index": 0}]]}, "AI Extract Task Details": {"main": [[{"node": "Format Task Data", "type": "main", "index": 0}]]}, "Format Task Data": {"main": [[{"node": "Create Deck Card", "type": "main", "index": 0}]]}, "Create Deck Card": {"main": [[{"node": "Format Success Response", "type": "main", "index": 0}]]}, "Format Success Response": {"main": [[{"node": "Respond Result", "type": "main", "index": 0}]]}, "Respond No Task": {"main": [[{"node": "Respond Result", "type": "main", "index": 0}]]}, "Respond Deck Help": {"main": [[{"node": "Respond Result", "type": "main", "index": 0}]]}, "Respond List": {"main": [[{"node": "Respond Result", "type": "main", "index": 0}]]} }, "settings": {} }