This workflow follows the Chainllm → 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": "LineCalendar",
"nodes": [
{
"parameters": {
"httpMethod": "POST",
"path": "db2d962b-3f35-4278-be83-02f3e5c21588",
"options": {}
},
"type": "n8n-nodes-base.webhook",
"typeVersion": 2.1,
"position": [
-432,
304
],
"id": "e51ffb2d-65be-4c18-a092-4cef126deb09",
"name": "Webhook"
},
{
"parameters": {
"method": "POST",
"url": "https://api.line.me/v2/bot/message/push",
"authentication": "genericCredentialType",
"genericAuthType": "httpHeaderAuth",
"sendBody": true,
"specifyBody": "json",
"jsonBody": "{\n \"to\": \"U81025e615f2b5734e31d2715303acb5a\",\n \"messages\":[\n { \n \"type\":\"text\", \n \"text\":\"\u884c\u4e8b\u66c6\u5efa\u7acb\u6210\u529f\" \n }\n ]\n}",
"options": {}
},
"type": "n8n-nodes-base.httpRequest",
"typeVersion": 4.3,
"position": [
1040,
208
],
"id": "6308608d-406d-4089-83b0-271d9b864e02",
"name": "HTTP Request: Send Line Msg",
"credentials": {
"httpHeaderAuth": {
"name": "<your credential>"
}
}
},
{
"parameters": {
"promptType": "define",
"text": "={{ $json.body.events[0].message.text }}",
"hasOutputParser": true,
"messages": {
"messageValues": [
{
"message": "=\u4f60\u662f\u4e00\u500b\u5c08\u696d\u7684\u65e5\u7a0b\u7ba1\u7406\u52a9\u624b\u3002\u8acb\u5206\u6790\u7528\u6236\u7684\u8a0a\u606f\uff0c\u63d0\u53d6\u53ef\u80fd\u7684\u65e5\u7a0b\u4fe1\u606f\u3002\n\n\ud83c\udfaf **\u91cd\u8981\u539f\u5247\uff1a\u6bcf\u500b\u5206\u6790\u7d50\u679c\u53ea\u7522\u751f\u4e00\u500b\u4e3b\u8981\u4e8b\u4ef6\uff0c\u5c07\u6240\u6709\u76f8\u95dc\u6d3b\u52d5\u6574\u5408\u70ba\u5b8c\u6574\u7684\u6d3b\u52d5\u63cf\u8ff0**\n\n\ud83d\udd0d **\u5730\u9ede\u5075\u6e2c\u898f\u5247**\uff1a\n1. \u79fb\u52d5\u52d5\u8a5e\u5f8c\u7684\u5730\u9ede\uff1a\u300c\u53bbXX\u300d\u3001\u300c\u5230XX\u300d\u3001\u300c\u5f80XX\u300d\u3001\u300c\u8d74XX\u300d\u3001\u300c\u524d\u5f80XX\u300d\u3001\u300c\u51fa\u767c\u5230XX\u300d\u3001\u300c\u98db\u5f80XX\u300d\n2. \u4f4d\u7f6e\u4ecb\u8a5e\u5f8c\u7684\u5730\u9ede\uff1a\u300c\u5728XX\u300d\u3001\u300c\u65bcXX\u300d\u3001\u300c\u4f4d\u65bcXX\u300d\u3001\u300cXX\u8209\u884c\u300d\u3001\u300cXX\u9032\u884c\u300d\u3001\u300cXX\u53ec\u958b\u300d\n3. \u5e38\u898b\u5730\u9ede\u985e\u578b\uff1a\u57ce\u5e02/\u570b\u5bb6\u3001\u5730\u6a19/\u666f\u9ede\u3001\u5834\u6240\u3001\u7dda\u4e0a\u5834\u6240\u3001\u5efa\u7bc9\u7269\n4. \u5730\u9ede\u63d0\u53d6\u512a\u5148\u9806\u5e8f\uff1a\u5177\u9ad4\u5730\u5740 > \u5efa\u7bc9\u540d\u7a31 > \u57ce\u5e02\u540d\u7a31 > \u5340\u57df\u540d\u7a31\n5. \u591a\u5730\u9ede\u6d3b\u52d5\uff1a\u9078\u64c7\u4e3b\u8981\u96c6\u5408\u5730\u9ede\u6216\u6700\u91cd\u8981\u7684\u5730\u9ede\u4f5c\u70ba\u4e3b\u8981 location\n\n\ud83d\udcc5 **\u6d3b\u52d5\u985e\u578b\u8b58\u5225\uff08\u91cd\u8981\uff09**\uff1a\n- **\u5168\u5929\u6d3b\u52d5**\uff1a\n - \u65c5\u904a\u3001\u4e00\u65e5\u904a\u3001\u51fa\u5dee\u3001\u4f11\u5047\u3001\u7bc0\u65e5\u6176\u5178\n - \u7814\u7fd2\u71df\u3001\u5de5\u4f5c\u574a\u3001\u8a13\u7df4\u71df\n - \u591a\u5730\u9ede\u884c\u7a0b\u6d3b\u52d5\uff08\u5373\u4f7f\u6709\u96c6\u5408\u6642\u9593\u4e5f\u7b97\u5168\u5929\u6d3b\u52d5\uff09\n - \u53ea\u63d0\u5230\u65e5\u671f\u6c92\u6709\u5177\u9ad4\u6642\u9593\n- **\u5b9a\u6642\u6d3b\u52d5**\uff1a\n - \u55ae\u4e00\u5730\u9ede\u7684\u6703\u8b70\u3001\u7c21\u5831\n - \u6709\u660e\u78ba\u958b\u59cb\u548c\u7d50\u675f\u6642\u9593\u7684\u77ed\u6642\u9593\u6d3b\u52d5\n - \u975e\u65c5\u904a\u6027\u8cea\u7684\u5b9a\u6642\u805a\u6703\n\n\ud83d\udd50 **\u7576\u524d\u65e5\u671f\u6642\u9593\u57fa\u6e96**\uff1a{{ DateTime.now().setZone('Asia/Taipei').toFormat('yyyy\u5e74MM\u6708dd\u65e5 (cccc)', { locale: 'zh-TW' }) }}\uff08\u53f0\u5317\u6642\u9593\uff09\n - \u7576\u524d\u5e74\u4efd\uff1a{{ DateTime.now().setZone('Asia/Taipei').toFormat('yyyy') }}\n - \u7576\u524d\u6708\u4efd\uff1a{{ DateTime.now().setZone('Asia/Taipei').toFormat('MM') }}\u6708\n\n\u23f0 **\u6642\u9593\u683c\u5f0f\u898f\u5247**\uff1a\n- \u5168\u5929\u6d3b\u52d5\uff1astartDateTime \u548c endDateTime \u90fd\u8a2d\u70ba \"YYYY-MM-DD\"\uff08\u4e0d\u5305\u542b\u6642\u9593\u90e8\u5206\uff09\uff0cisAllDay: true\n- \u5b9a\u6642\u6d3b\u52d5\uff1a\u4f7f\u7528\u5b8c\u6574\u7684 ISO 8601 \u683c\u5f0f \"YYYY-MM-DDTHH:mm:ss+08:00\"\uff0cisAllDay: false\n- **\u5e74\u4efd\u63a8\u65b7\u898f\u5247\uff08\u91cd\u8981\uff09**\uff1a\n - \u5982\u679c\u8a0a\u606f\u4e2d\u660e\u78ba\u6307\u5b9a\u5e74\u4efd\uff0c\u4f7f\u7528\u8a72\u5e74\u4efd\n - \u5982\u679c\u53ea\u6709\u6708/\u65e5\u6c92\u6709\u5e74\u4efd\uff1a\n - 6\u6708\u30017\u6708\u30018\u6708\u30019\u6708\u300110\u6708\u300111\u6708\u300112\u6708 \u2192 \u4f7f\u7528 **2025\u5e74**\n - 1\u6708\u30012\u6708\u30013\u6708\u30014\u6708 \u2192 \u4f7f\u7528 **2026\u5e74**\n - 5\u6708 \u2192 \u6839\u64da\u5177\u9ad4\u65e5\u671f\u5224\u65b7\uff0c\u901a\u5e38\u4f7f\u7528 **2025\u5e74**\n - **\u7bc4\u4f8b**\uff1a\u300c6/14\u6d3b\u52d5\u300d\u2192 2025-06-14\uff08\u4e0d\u662f2024\u5e74\uff01\uff09\n - \u82e5\u5b8c\u5168\u7121\u6cd5\u63a8\u65b7\uff0c\u9810\u8a2d\u4f7f\u7528 2025 \u5e74\n- \u6642\u5340\uff1aAsia/Taipei (+08:00)\n\n\u26a0\ufe0f **\u91cd\u8981\u63d0\u9192**\uff1a\n- \u65c5\u904a\u3001\u4e00\u65e5\u904a\u3001\u591a\u5730\u9ede\u6d3b\u52d5\u5373\u4f7f\u6709\u96c6\u5408\u6642\u9593\uff0c\u4e5f\u61c9\u8a72\u8a2d\u70ba\u5168\u5929\u6d3b\u52d5\n- \u5168\u5929\u6d3b\u52d5\u7684\u958b\u59cb\u548c\u7d50\u675f\u6642\u9593\u61c9\u8a72\u76f8\u540c\uff0c\u683c\u5f0f\u70ba\u7d14\u65e5\u671f\n\n\ud83d\udccb **\u8a73\u7d30\u63cf\u8ff0\u5167\u5bb9\u5efa\u69cb**\uff1a\n\u5fc5\u9808\u5305\u542b\u4ee5\u4e0b\u8cc7\u8a0a\uff08\u5982\u679c\u8a0a\u606f\u4e2d\u6709\u63d0\u53ca\uff09\uff1a\n1. **\u96c6\u5408\u8cc7\u8a0a**\uff1a\u96c6\u5408\u6642\u9593\u3001\u96c6\u5408\u5730\u9ede\u3001\u505c\u8eca\u8cc7\u8a0a\n2. **\u5b8c\u6574\u884c\u7a0b**\uff1a\u6309\u6642\u9593\u9806\u5e8f\u5217\u51fa\u6240\u6709\u6d3b\u52d5\u5b89\u6392\n3. **\u8cbb\u7528\u660e\u7d30**\uff1a\u5404\u9805\u8cbb\u7528\uff08\u4ea4\u901a\u3001\u9910\u8cbb\u3001\u9580\u7968\u7b49\uff09\n4. **\u53c3\u8207\u8005\u8cc7\u8a0a**\uff1a\u8eca\u624b\u5b89\u6392\u3001\u53c3\u52a0\u4eba\u54e1\n5. **\u651c\u5e36\u7269\u54c1**\uff1a\u9700\u8981\u6e96\u5099\u7684\u7269\u54c1\u6216\u8863\u7269\n6. **\u6ce8\u610f\u4e8b\u9805**\uff1a\u5929\u6c23\u3001\u53d6\u6d88\u689d\u4ef6\u3001\u5176\u4ed6\u91cd\u8981\u63d0\u9192\n7. **\u806f\u7d61\u8cc7\u8a0a**\uff1a\u76f8\u95dc\u9023\u7d50\u3001\u53c3\u8003\u8cc7\u6599\uff08\u4fdd\u6301\u5b8c\u6574\u7db2\u5740\uff09\n\n\ud83d\udc65 **\u53c3\u8207\u8005\u63d0\u53d6\u898f\u5247**\uff1a\n- **\u91cd\u8981\uff1aattendees \u6b04\u4f4d\u8acb\u4fdd\u6301\u7a7a\u9663\u5217 []\uff0c\u907f\u514d\u767c\u9001 Google Calendar \u901a\u77e5**\n- \u6240\u6709\u53c3\u8207\u8005\u8cc7\u8a0a\uff08\u5305\u542b\u8eca\u624b\u548c\u4e58\u5ba2\uff09\u90fd\u5beb\u5728 description \u4e2d\n- \u9019\u6a23\u53ef\u4ee5\u907f\u514d Google Calendar \u81ea\u52d5\u767c\u9001\u9080\u8acb\u901a\u77e5\n\n\ud83d\udcb0 **\u8cbb\u7528\u8cc7\u8a0a\u63d0\u53d6**\uff1a\n- \u4ea4\u901a\u8cbb\u3001\u9910\u8cbb\u3001\u9580\u7968\u3001\u5176\u4ed6\u96dc\u8cbb\n- \u5728 description \u4e2d\u8a73\u7d30\u8aaa\u660e\u5404\u9805\u8cbb\u7528\n\n\ud83d\udd17 **\u9023\u7d50\u8655\u7406**\uff1a\n- \u4fdd\u6301\u7db2\u5740\u5b8c\u6574\uff0c\u4e0d\u8981\u622a\u65b7\n- \u5982\u679c\u9023\u7d50\u592a\u9577\uff0c\u78ba\u4fdd\u5305\u542b\u5b8c\u6574\u7684\u53ef\u9ede\u64ca\u7db2\u5740\n\n\ud83c\udfaf **\u4fe1\u5fc3\u5ea6\u8a55\u4f30**\uff1a\n- 0.9+\uff1a\u5b8c\u6574\u6642\u9593+\u5730\u9ede+\u8a73\u7d30\u884c\u7a0b+\u53c3\u8207\u8005\u8cc7\u8a0a\n- 0.7-0.9\uff1a\u660e\u78ba\u6642\u9593\u548c\u5730\u9ede\uff0c\u90e8\u5206\u8a73\u7d30\u8cc7\u8a0a\n- 0.5-0.7\uff1a\u57fa\u672c\u6642\u9593\u6216\u5730\u9ede\uff0c\u7f3a\u5c11\u8a73\u7d30\u8cc7\u8a0a\n- <0.5\uff1a\u7f3a\u4e4f\u95dc\u9375\u4fe1\u606f\n\n\u8acb\u6309\u7167\u4ee5\u4e0b JSON \u683c\u5f0f\u56de\u8986\uff0c\u4e0d\u8981\u6dfb\u52a0\u4efb\u4f55\u5176\u4ed6\u6587\u5b57\uff1a\n{\n \"hasEvent\": true,\n \"events\": [\n {\n \"title\": \"\u4e3b\u8981\u6d3b\u52d5\u6a19\u984c\",\n \"description\": \"\u8a73\u7d30\u7684\u6d3b\u52d5\u63cf\u8ff0\uff0c\u5305\u542b\u5b8c\u6574\u884c\u7a0b\u5b89\u6392\u3001\u96c6\u5408\u8cc7\u8a0a\u3001\u8cbb\u7528\u660e\u7d30\u3001\u53c3\u8207\u8005\u8cc7\u8a0a\u3001\u6ce8\u610f\u4e8b\u9805\u7b49\",\n \"startDateTime\": \"2025-06-29\",\n \"endDateTime\": \"2025-06-29\", \n \"isAllDay\": true,\n \"location\": \"\u4e3b\u8981\u96c6\u5408\u5730\u9ede\u6216\u6700\u91cd\u8981\u7684\u5730\u9ede\",\n \"attendees\": [],\n \"confidence\": 0.95\n }\n ],\n \"reasoning\": \"\u5206\u6790\u539f\u56e0\uff0c\u8aaa\u660e\u5982\u4f55\u6574\u5408\u591a\u500b\u6d3b\u52d5\u70ba\u55ae\u4e00\u4e8b\u4ef6\uff0c\u4ee5\u53ca\u4fe1\u5fc3\u5ea6\u8a55\u4f30\u4f9d\u64da\"\n}\n\n**\u6d3b\u52d5\u985e\u578b\u5224\u65b7\u7bc4\u4f8b**\uff1a\n- \u2705 \u5168\u5929\u6d3b\u52d5\uff1a\u300c\u4e09\u5cfd\u7011\u5e03\u4e00\u65e5\u904a\u300d\u2192 isAllDay: true, startDateTime: \"2025-06-29\"\n- \u2705 \u5168\u5929\u6d3b\u52d5\uff1a\u300c6/14\u70e4\u8089\u6d3b\u52d5\u300d\u2192 isAllDay: true, startDateTime: \"2025-06-14\"\n- \u2705 \u5168\u5929\u6d3b\u52d5\uff1a\u300c\u5de5\u4f5c\u574a\u300d\u2192 isAllDay: true, startDateTime: \"2025-06-15\" \n- \u2705 \u5b9a\u6642\u6d3b\u52d5\uff1a\u300c\u4e0b\u53482\u9ede\u958b\u6703\u300d\u2192 isAllDay: false, startDateTime: \"2025-06-01T14:00:00+08:00\"\n- \u2705 \u5b9a\u6642\u6d3b\u52d5\uff1a\u300c\u7c21\u58311\u5c0f\u6642\u300d\u2192 isAllDay: false, startDateTime: \"2025-06-01T14:00:00+08:00\"\n\n**\u5e74\u4efd\u5224\u65b7\u91cd\u8981\u63d0\u9192**\uff1a\n- \u274c \u932f\u8aa4\uff1a\u300c6/14\u6d3b\u52d5\u300d\u2192 2024-06-14\n- \u2705 \u6b63\u78ba\uff1a\u300c6/14\u6d3b\u52d5\u300d\u2192 2025-06-14\n\n**\u63cf\u8ff0\u683c\u5f0f\u5efa\u8b70**\uff1a\n\u4f7f\u7528\u6e05\u6670\u7684\u7d50\u69cb\u5316\u683c\u5f0f\uff0c\u5c07\u6240\u6709\u53c3\u8207\u8005\u8cc7\u8a0a\u5beb\u5728\u63cf\u8ff0\u4e2d\uff1a\n```\n\u96c6\u5408\u6642\u9593\uff1a9:30 a.m.\uff1b\u96c6\u5408\u5730\u9ede\uff1a\u4e09\u5cfd\u5340\u7af9\u5d19\u8def238\u865f\uff08\u79be\u7166\u718a\u7a7a\u8336\u5712\u5916\u78b0\u9762+\u505c\u8eca\uff09\u3002\n\n\u884c\u7a0b\u5b89\u6392\uff1a\n\u2022 \u4e0a\u5348\uff1a\u53c3\u8a2a\u79be\u7166\u718a\u7a7a\u8336\u5712\n\u2022 \u4e2d\u5348\uff1a\u4e09\u5cfd\u63d2\u89d2133\u73fe\u70e4\u80e1\u6912\u96de\u7528\u9910 \n\u2022 \u4e0b\u5348\uff1a\u96f2\u68ee\u7011\u5e03\u5065\u884c+\u73a9\u6c34\u6ce1\u8173\n\u2022 \u508d\u665a\uff1a\u4e09\u5cfd\u8001\u8857\u81ea\u7531\u6d3b\u52d5\n\n\u8cbb\u7528\uff1a\u8eca\u8cc7200\u5143\uff1b\u9910\u8cbb200-400\u5143\uff1b\u8336\u5712\u9580\u7968280\u5143\uff08\u53ef\u62b5\u9910\u9ede100\u5143\uff09\u3002\n\n\u8eca\u624b\u5b89\u6392\uff1a\n\u2022 @\u5c0f\u6cc9\uff1aVivian, Conni, Lucia\n\u2022 @bryan\uff1aTing, Vera, \u54f2\u744b\n\u2022 @\u97cb\u6210\uff1a\u5c0f\u5f35, \u8b1d\u5c0f\u73a5, \u738b\u7f8e\u60e0\n\u2022 @Money Yu\uff1a\u5176\u4ed6\u53c3\u8207\u8005\n\n\u6ce8\u610f\u4e8b\u9805\uff1a\u9047\u96e8\u53d6\u6d88/\u6539\u671f\uff0c\u8acb\u651c\u5e36\u63db\u6d17\u8863\u7269\u3002\n```\n\n\u73fe\u5728\u8acb\u5206\u6790\u4ee5\u4e0b Slack \u8a0a\u606f\uff1a\u300c={{ $json.body.events[0].message.text }}\u300d\n\n\u8acb\u5c07\u6574\u500b\u6d3b\u52d5\u8996\u70ba\u4e00\u500b\u5b8c\u6574\u4e8b\u4ef6\uff0c\u628a\u6240\u6709\u7d30\u7bc0\u3001\u884c\u7a0b\u5b89\u6392\u3001\u53c3\u8207\u8005\u8cc7\u8a0a\u90fd\u6574\u7406\u5728 description \u4e2d\uff0c\u76f4\u63a5\u56de\u8986 JSON \u683c\u5f0f\uff0c\u4e0d\u8981\u5305\u542b ```json \u6a19\u8a18\uff0c\u4e5f\u4e0d\u8981\u5305\u542b\u63db\u884c\u7b26\u865f\u3002"
}
]
},
"batching": {}
},
"type": "@n8n/n8n-nodes-langchain.chainLlm",
"typeVersion": 1.7,
"position": [
-208,
304
],
"id": "16f7e4ed-ded9-40af-b0c9-b335364f4fa4",
"name": "Basic LLM Chain"
},
{
"parameters": {
"model": "gpt-4o",
"options": {}
},
"type": "@n8n/n8n-nodes-langchain.lmChatAzureOpenAi",
"typeVersion": 1,
"position": [
-208,
528
],
"id": "54160076-28a8-46a6-b698-3b45995c1cfd",
"name": "Azure OpenAI Chat Model",
"credentials": {
"azureOpenAiApi": {
"name": "<your credential>"
}
}
},
{
"parameters": {
"jsonSchemaExample": "{\n \"hasEvent\": true,\n \"events\": [\n {\n \"title\": \"11/23 \u592a\u5e73\u5c71\u6ce1\u6e6f\u4e00\u65e5\u904a\",\n \"description\": \"\u96c6\u5408\u6642\u9593\uff1a03:00\uff1b\u96c6\u5408\u5730\u9ede\uff1a\u53f0\u5317\u8eca\u7ad9\u6771\u4e09\u9580\u3002\u4ea4\u901a\uff1a\u5305\u8eca\u5e73\u5206\uff088\u4eba\u8eca\uff09\uff0c\u5167\u5efa5\u4eba\uff0c\u6b63\u5728\u5fb53\u5973\u540c\u6b65\u52a0\u5165\u5718\u3002\uff08\u76ee\u524d\u5718\u51671\u59734\u7537\uff09\u884c\u7a0b\u5b89\u6392\uff1a03:00 \u53f0\u5317\u51fa\u767c05:00 \u62b5\u9054\u592a\u5e73\u5c71\u570b\u5bb6\u516c\u5712\u552e\u7968\u53e305:40 \u5230\u9054\u592a\u5e73\u5c71\u838a\u505c\u8eca\u583407:00 \u8cfc\u8cb7\u7b2c\u4e00\u73ed\u78b0\u78b0\u8eca\u7968\uff08\u53ea\u80fd\u73fe\u5834\u8cfc\u7968\uff09\u4e3b\u8981\u6d3b\u52d5\uff1a1. \u592a\u5e73\u5c71\u89c0\u666f\u5e73\u53f0\u770b\u65e5\u51fa\u96f2\u6d77\uff0c\u4e26\u5728\u9644\u8fd1\u6b65\u9053\u6b23\u8cde\u6953\u8449\u30022. \u8208\u61f7\u820a\u6b65\u9053\uff08\u6a9c\u6728\u68ee\u6797\u611f\uff09\u53ca\u6a9c\u6728\u6797\u6b65\u9053\u30023. \u592a\u5e73\u5c71\u5c71\u6bdb\u6af8\u6b65\u9053\u968e\u68af\u65c1\u89c0\u8cde\u6953\u8449\uff08\u6b64\u6b65\u9053\u6642\u9593\u8f03\u9577\uff0c\u907f\u514d\u8d85\u6642\u672a\u8a08\u756b\u6df1\u5165\uff09\u30024. \u898b\u6674\u61f7\u53e4\u6b65\u9053\uff1a\u6b65\u9053\u77ed\u3001\u666f\u9ede\u77e5\u540d\u4f46\u5fc5\u5230\u7684\u98a8\u666f\u9ede\u30025. \u9ce9\u4e4b\u6fa4\uff1a\u9ad4\u9a57\u6ce1\u6e6f\uff0c\u4e26\u53ef\u5617\u8a66\u5730\u71b1\u6c34\u716e\u7389\u7c73\u3001\u96de\u86cb\u7b49\u3002\u8a73\u7d30\u5730\u9ede\u8aaa\u660e\uff1a\u2022 \u592a\u5e73\u5c71\u838a\u5340\u57df\uff1a\u5efa\u8b70\u642d\u4e58\u78b0\u78b0\u8eca\u5230\u8302\u8208\uff0c\u63a2\u7d22\u8302\u8208\u61f7\u820a\u6b65\u9053\uff08\u6a9c\u6728\u68ee\u6797\u611f\uff09\u3001\u6a9c\u6728\u539f\u59cb\u6797\u6b65\u9053\uff08\u77ed\uff09\u3001\u9435\u6749\u6797\u6b65\u9053\u3002\u6b64\u5916\uff0c\u592a\u5e73\u5c71\u838a\u65c1\u908a\u968e\u68af\u7684\u6953\u8449\u6700\u8fd1\u975e\u5e38\u7d05\u8449\u6f02\u4eae\u3002\u2022 \u7fe0\u5cf0\u6e56\u5340\u57df\uff1a\u5c71\u6bdb\u6af8\u6b65\u9053\uff08\u5efa\u8b70\u6b65\u884c\u6642\u9593\u7d043\u5c0f\u6642\uff09\u53ca\u7fe0\u5cf0\u6e56\u74b0\u6e56\u6b65\u9053\uff08\u6b65\u884c\u74b0\u6e56\u53ea\u970010\u5206\u9418\uff0c\u4e3b\u8981\u7528\u65bc\u770b\u6e56\uff09\u3002\u7531\u65bc\u90e8\u5206\u8def\u6bb5\u5c01\u9589\uff0c\u76ee\u524d\u53ea\u80fd\u901a\u884c\u5230\u89c0\u6e56\u9ede\u3002\u2022 \u65e5\u51fa\u89c0\u8cde\u9ede\u63a8\u85a6\uff1a\u592a\u5e73\u5c71\u838a\u89c0\u666f\u5e73\u53f0\u3001\u8e66\u8e66\u8eca\u7ad9\u8d77\u9ede\u6708\u53f0\u3001\u7fe0\u5cf0\u666f\u89c0\u9053\u8def\uff0814\u516c\u91cc\uff09\u89c0\u65e5\u53f0\u3001\u7fe0\u5cf0\u6e56\u74b0\u5c71\u6b65\u9053\uff080.8\u516c\u91cc\uff09\u89c0\u6e56\u5e73\u53f0\u62163\u516c\u91cc\u8655\uff0c\u671b\u6d0b\u5c71\u6b65\u9053\u7d42\u9ede\uff081.2\u516c\u91cc\uff09\u89c0\u666f\u53f0\u3002\u8cbb\u7528\u660e\u7d30\uff1a\u2022 \u5305\u8eca\u8cbb\u7528\uff1a8\u4eba\u5e73\u5206\u2022 \u6ce1\u6e6f\u8cbb\u7528\uff1a\u4f9d\u500b\u4eba\u9078\u64c7\uff08\u73fe\u5834\u652f\u4ed8\uff09\u2022 \u90e8\u5206\u666f\u9ede\u70ba\u514d\u8cbb\uff0c\u53ef\u81ea\u8cbb\u9078\u8cfc\u5730\u71b1\u98df\u54c1\u6216\u9580\u7968\uff08\u82e5\u9069\u7528\uff09\u6ce8\u610f\u4e8b\u9805\uff1a\u2022 \u78b0\u78b0\u8eca\u7968\u50c5\u7576\u5929\u73fe\u5834\u8cfc\u8cb7\uff0c\u8acb\u6e96\u6642\u5230\u9054\u3002\u2022 \u56e0\u90e8\u5206\u6b65\u9053\u5c01\u9589\uff0c\u8acb\u6ce8\u610f\u516c\u544a\u4e26\u9075\u5b88\u898f\u7bc4\u3002\u2022 \u884c\u7a0b\u6d89\u53ca\u9ad8\u5c71\u6b65\u884c\uff0c\u8acb\u651c\u5e36\u8212\u9069\u7684\u670d\u88dd\u8207\u6b65\u884c\u978b\u3002\u2022 \u81ea\u5099\u6bdb\u5dfe\u548c\u8f15\u4fbf\u8863\u7269\u4ee5\u4fbf\u6ce1\u6e6f\u4f7f\u7528\u3002\u5929\u6c23\u53ca\u53d6\u6d88\u689d\u4ef6\uff1a\u9047\u91cd\u5927\u964d\u96e8\u5929\u6c23\u53ef\u80fd\u53d6\u6d88\u6216\u6539\u671f\uff0c\u5c07\u63d0\u524d\u901a\u77e5\u53c3\u52a0\u8005\u3002\",\n \"startDateTime\": \"2025-11-23\",\n \"endDateTime\": \"2025-11-23\",\n \"isAllDay\": true,\n \"location\": \"\u53f0\u5317\u8eca\u7ad9\u6771\u4e09\u9580\",\n \"attendees\": [],\n \"confidence\": 0.95\n }\n ],\n \"reasoning\": \"\u672c\u6d3b\u52d5\u4ee5\u300e11/23 \u592a\u5e73\u5c71\u6ce1\u6e6f\u26f0\ufe0f\u4e00\u65e5\u904a\u300f\u70ba\u4e3b\u984c\uff0c\u6a19\u660e\u4e86\u96c6\u5408\u6642\u9593\u548c\u5730\u9ede\uff0c\u4e26\u8a73\u7d30\u5217\u51fa\u4e86\u5b8c\u6574\u7684\u884c\u7a0b\u898f\u5283\uff08\u5305\u542b\u65e5\u51fa\u3001\u6b65\u9053\u53ca\u6ce1\u6e6f\u6d3b\u52d5\uff09\u3002\u6d3b\u52d5\u5730\u9ede\u4e3b\u8981\u5728\u53f0\u5317\u8eca\u7ad9\u8207\u592a\u5e73\u5c71\u5340\u3002\u7531\u65bc\u662f\u591a\u5730\u9ede\u884c\u7a0b\u4e14\u8de8\u6574\u5929\uff0c\u5224\u65b7\u70ba\u5168\u5929\u6d3b\u52d5\uff1b\u4fe1\u5fc3\u5ea6\u9ad8\u4e3b\u8981\u57fa\u65bc\u8a73\u7d30\u884c\u7a0b\u8207\u53c3\u8003\u8cc7\u8a0a\u7684\u5b8c\u6574\u6027\u3002\"\n}"
},
"type": "@n8n/n8n-nodes-langchain.outputParserStructured",
"typeVersion": 1.3,
"position": [
-80,
528
],
"id": "65feb9f3-465a-48ba-96a2-63ae14afd205",
"name": "Structured Output Parser"
},
{
"parameters": {
"jsCode": "// ===============================================\n// Process AI Response - \u4fee\u6b63\u7248 JavaScript \u4ee3\u78bc\n// ===============================================\n\nconsole.log('\ud83d\ude80 \u958b\u59cb\u8655\u7406 AI \u56de\u61c9...');\n\n// 1. \u6aa2\u67e5\u57fa\u672c\u8f38\u5165\nconst inputData = $input.first();\nif (!inputData || !inputData.json) {\n console.log('\u274c \u6c92\u6709\u8f38\u5165\u6578\u64da\uff0c\u505c\u6b62\u57f7\u884c');\n return [];\n}\n\nconsole.log('\ud83d\udce5 \u8f38\u5165\u6578\u64da:', JSON.stringify(inputData.json, null, 2));\n\n// 2. \ud83d\udd27 \u4fee\u6b63\uff1a\u76f4\u63a5\u53d6\u5f97 AI \u8f38\u51fa\u7269\u4ef6\uff08\u4e0d\u9700\u8981\u89e3\u6790 JSON\uff09\nlet aiOutput;\n\n// \u6aa2\u67e5 output \u662f\u5b57\u4e32\u9084\u662f\u7269\u4ef6\nif (typeof inputData.json.output === 'string') {\n // \u5982\u679c\u662f\u5b57\u4e32\uff0c\u9700\u8981\u89e3\u6790\n try {\n const cleanResponse = inputData.json.output.replace(/```json\\n?|```\\n?/g, '').trim();\n aiOutput = JSON.parse(cleanResponse);\n console.log('\u2705 \u5f9e\u5b57\u4e32\u89e3\u6790 AI \u8f38\u51fa');\n } catch (error) {\n console.log('\u274c JSON \u89e3\u6790\u5931\u6557:', error.message);\n return [{\n json: {\n status: 'error',\n error: `AI \u56de\u61c9\u89e3\u6790\u5931\u6557: ${error.message}`,\n rawResponse: inputData.json.output\n }\n }];\n }\n} else if (typeof inputData.json.output === 'object') {\n // \u5982\u679c\u5df2\u7d93\u662f\u7269\u4ef6\uff0c\u76f4\u63a5\u4f7f\u7528\n aiOutput = inputData.json.output;\n console.log('\u2705 AI \u8f38\u51fa\u5df2\u7d93\u662f\u7269\u4ef6\u683c\u5f0f');\n} else if (inputData.json.text) {\n // \u5099\u7528\uff1a\u6aa2\u67e5 text \u6b04\u4f4d\n try {\n const cleanResponse = inputData.json.text.replace(/```json\\n?|```\\n?/g, '').trim();\n aiOutput = JSON.parse(cleanResponse);\n console.log('\u2705 \u5f9e text \u6b04\u4f4d\u89e3\u6790 AI \u8f38\u51fa');\n } catch (error) {\n console.log('\u274c \u7121\u6cd5\u53d6\u5f97\u6709\u6548\u7684 AI \u8f38\u51fa');\n return [];\n }\n} else {\n console.log('\u274c \u627e\u4e0d\u5230 AI \u8f38\u51fa\u6578\u64da');\n return [];\n}\n\nconsole.log('\ud83e\udd16 AI \u8f38\u51fa\u5167\u5bb9:', JSON.stringify(aiOutput, null, 2));\n\n// 3. \u6aa2\u67e5 Slack \u539f\u59cb\u6578\u64da\uff08\u5f9e\u4e0a\u6e38\u7bc0\u9ede\uff09\nlet slackData = {};\ntry {\n // \ud83d\udd27 \u6539\u826f\uff1a\u66f4\u9748\u6d3b\u5730\u53d6\u5f97 Slack \u6578\u64da\n const allNodes = $input.all();\n \n // \u5148\u5617\u8a66\u5f9e\u7b2c\u4e00\u500b\u7bc0\u9ede\u53d6\u5f97\n if (allNodes.length > 0 && allNodes[0].json) {\n slackData = allNodes[0].json;\n }\n \n // \u5982\u679c\u6c92\u6709 Slack \u7279\u5fb5\uff0c\u5617\u8a66\u5176\u4ed6\u7bc0\u9ede\n if (!slackData.user && !slackData.channel) {\n for (const node of allNodes) {\n if (node.json && (node.json.user || node.json.channel || node.json.text)) {\n slackData = node.json;\n break;\n }\n }\n }\n \n // \u5982\u679c\u9084\u662f\u627e\u4e0d\u5230\uff0c\u4f7f\u7528\u9810\u8a2d\u503c\n if (!slackData.user && !slackData.channel) {\n slackData = {\n text: inputData.json.originalMessage || '\u7121\u6cd5\u53d6\u5f97\u539f\u59cb\u8a0a\u606f',\n user: 'unknown',\n channel: 'unknown',\n ts: Date.now().toString()\n };\n }\n \n console.log('\ud83d\udcf1 Slack \u6578\u64da:', JSON.stringify(slackData, null, 2));\n} catch (error) {\n console.log('\u26a0\ufe0f \u53d6\u5f97 Slack \u6578\u64da\u6642\u767c\u751f\u932f\u8aa4:', error.message);\n slackData = {\n text: '\u7121\u6cd5\u53d6\u5f97\u539f\u59cb\u8a0a\u606f',\n user: 'unknown',\n channel: 'unknown',\n ts: Date.now().toString()\n };\n}\n\n// 4. \u6aa2\u67e5 AI \u662f\u5426\u627e\u5230\u4e8b\u4ef6\nif (!aiOutput.hasEvent || !aiOutput.events || aiOutput.events.length === 0) {\n console.log('\u2139\ufe0f AI \u6c92\u6709\u627e\u5230\u4e8b\u4ef6');\n return [{\n json: {\n status: 'no_event',\n message: '\u672a\u627e\u5230\u6709\u6548\u7684\u65e5\u7a0b\u4fe1\u606f',\n originalMessage: slackData.text,\n slackUser: slackData.user,\n slackChannel: slackData.channel,\n slackTimestamp: slackData.ts,\n reasoning: aiOutput.reasoning || '\u7121\u6cd5\u8b58\u5225\u65e5\u7a0b\u76f8\u95dc\u5167\u5bb9'\n }\n }];\n}\n\n// 5. \u8655\u7406\u627e\u5230\u7684\u4e8b\u4ef6\nconsole.log(`\ud83d\udcc5 \u627e\u5230 ${aiOutput.events.length} \u500b\u4e8b\u4ef6\uff0c\u958b\u59cb\u8655\u7406`);\n\ntry {\n const processedEvents = aiOutput.events.map((event, index) => {\n console.log(`\ud83d\udd04 \u8655\u7406\u4e8b\u4ef6 ${index}:`, JSON.stringify(event, null, 2));\n \n // \u9a57\u8b49\u4e8b\u4ef6\u5fc5\u8981\u6b04\u4f4d\n if (!event.title || !event.startDateTime) {\n console.log(`\u26a0\ufe0f \u4e8b\u4ef6 ${index} \u7f3a\u5c11\u5fc5\u8981\u6b04\u4f4d\uff0c\u8df3\u904e`);\n return null;\n }\n\n // \u8655\u7406\u6642\u9593\n let startDateTime, endDateTime, isAllDay;\n let calendarStartDateTime, calendarEndDateTime;\n \n try {\n // \u6aa2\u67e5\u662f\u5426\u70ba\u5168\u5929\u6d3b\u52d5\n isAllDay = event.isAllDay === true || \n (!event.startDateTime.includes('T') && !event.endDateTime?.includes('T'));\n \n if (isAllDay) {\n // \u5168\u5929\u6d3b\u52d5\u8655\u7406\n console.log(`\ud83d\udcc5 \u4e8b\u4ef6 ${index} \u662f\u5168\u5929\u6d3b\u52d5`);\n \n startDateTime = event.startDateTime.includes('T') \n ? event.startDateTime.split('T')[0] \n : event.startDateTime;\n endDateTime = event.endDateTime \n ? (event.endDateTime.includes('T') ? event.endDateTime.split('T')[0] : event.endDateTime)\n : startDateTime;\n \n // \u9a57\u8b49\u65e5\u671f\u683c\u5f0f\n if (!startDateTime.match(/^\\d{4}-\\d{2}-\\d{2}$/)) {\n throw new Error('\u5168\u5929\u6d3b\u52d5\u65e5\u671f\u683c\u5f0f\u932f\u8aa4');\n }\n \n calendarStartDateTime = startDateTime;\n calendarEndDateTime = endDateTime;\n \n console.log(`\u2705 \u5168\u5929\u6d3b\u52d5\u6642\u9593: ${startDateTime} \u5230 ${endDateTime}`);\n \n } else {\n // \u90e8\u5206\u6642\u9593\u6d3b\u52d5\u8655\u7406\n console.log(`\u23f0 \u4e8b\u4ef6 ${index} \u662f\u90e8\u5206\u6642\u9593\u6d3b\u52d5`);\n \n const startDate = new Date(event.startDateTime);\n const endDate = new Date(event.endDateTime || event.startDateTime);\n \n if (isNaN(startDate.getTime())) {\n throw new Error('\u7121\u6548\u7684\u958b\u59cb\u6642\u9593\u683c\u5f0f');\n }\n \n // \u5982\u679c\u7d50\u675f\u6642\u9593\u7121\u6548\u6216\u65e9\u65bc\u958b\u59cb\u6642\u9593\uff0c\u9810\u8a2d\u70ba\u958b\u59cb\u5f8c1\u5c0f\u6642\n if (isNaN(endDate.getTime()) || endDate <= startDate) {\n endDate.setTime(startDate.getTime() + 60 * 60 * 1000);\n }\n \n calendarStartDateTime = startDate.toISOString();\n calendarEndDateTime = endDate.toISOString();\n \n console.log(`\u2705 \u90e8\u5206\u6642\u9593\u6d3b\u52d5: ${calendarStartDateTime} \u5230 ${calendarEndDateTime}`);\n }\n \n } catch (dateError) {\n console.log(`\u26a0\ufe0f \u4e8b\u4ef6 ${index} \u6642\u9593\u8655\u7406\u5931\u6557:`, dateError.message);\n \n // \u9810\u8a2d\u70ba\u660e\u5929\u7684\u5168\u5929\u6d3b\u52d5\n const tomorrow = new Date();\n tomorrow.setDate(tomorrow.getDate() + 1);\n const dateStr = tomorrow.toISOString().split('T')[0];\n \n startDateTime = dateStr;\n endDateTime = dateStr;\n calendarStartDateTime = dateStr;\n calendarEndDateTime = dateStr;\n isAllDay = true;\n \n console.log(`\ud83d\udd04 \u4f7f\u7528\u9810\u8a2d\u6642\u9593: ${dateStr}`);\n }\n \n // \u8655\u7406\u53c3\u8207\u8005\n const attendees = (event.attendees || []).filter(email => \n email && typeof email === 'string' && email.includes('@')\n );\n \n // \u8655\u7406\u4fe1\u5fc3\u5ea6\n const confidence = parseFloat(event.confidence) || 0.5;\n console.log(`\ud83d\udcca \u4e8b\u4ef6 ${index} \u4fe1\u5fc3\u5ea6: ${confidence} (${Math.round(confidence * 100)}%)`);\n \n // \u69cb\u5efa\u63cf\u8ff0\n const descriptionParts = [\n event.description || '',\n '',\n '\ud83d\udccb \u4f86\u6e90\u4fe1\u606f\uff1a',\n `\u2022 Slack \u8a0a\u606f: ${slackData.text || '\u7121'}`,\n `\u2022 \u767c\u9001\u8005: <@${slackData.user}>`,\n `\u2022 \u983b\u9053: <#${slackData.channel}>`,\n `\u2022 \u6d3b\u52d5\u985e\u578b: ${isAllDay ? '\ud83d\udcc5 \u5168\u5929\u6d3b\u52d5' : '\u23f0 \u90e8\u5206\u6642\u9593\u6d3b\u52d5'}`,\n `\u2022 AI \u5206\u6790\u4fe1\u5fc3\u5ea6: ${Math.round(confidence * 100)}%`\n ];\n \n if (aiOutput.reasoning) {\n descriptionParts.push(`\u2022 \u5206\u6790\u8aaa\u660e: ${aiOutput.reasoning}`);\n }\n \n const description = descriptionParts.filter(line => line !== '').join('\\n');\n \n // \u6c7a\u5b9a\u8655\u7406\u72c0\u614b\n const eventStatus = confidence >= 0.7 ? 'high_confidence' : 'low_confidence';\n console.log(`${confidence >= 0.7 ? '\u2705' : '\u26a0\ufe0f'} \u4e8b\u4ef6 ${index} ${eventStatus}`);\n \n // \u69cb\u5efa\u8f38\u51fa\n const processedEvent = {\n json: {\n eventIndex: index,\n title: event.title,\n description: description,\n \n // \u6642\u9593\u4fe1\u606f\n startDateTime: calendarStartDateTime,\n endDateTime: calendarEndDateTime,\n isAllDay: isAllDay,\n \n // \u5730\u9ede\u548c\u53c3\u8207\u8005\n location: event.location || '',\n attendees: attendees,\n \n // \u5206\u6790\u4fe1\u606f\n confidence: confidence,\n confidenceDisplay: `${Math.round(confidence * 100)}%`,\n reasoning: aiOutput.reasoning || '',\n \n // \u539f\u59cb\u4fe1\u606f\n originalMessage: slackData.text || '',\n slackUser: slackData.user,\n slackChannel: slackData.channel,\n slackTimestamp: slackData.ts,\n \n // \u8655\u7406\u72c0\u614b\n status: eventStatus\n }\n };\n \n console.log(`\u2705 \u4e8b\u4ef6 ${index} \u8655\u7406\u5b8c\u6210`);\n return processedEvent;\n \n }).filter(event => event !== null);\n\n // 6. \u6aa2\u67e5\u8655\u7406\u7d50\u679c\n if (processedEvents.length === 0) {\n console.log('\u274c \u6c92\u6709\u6709\u6548\u7684\u4e8b\u4ef6\u53ef\u8655\u7406');\n return [{\n json: {\n status: 'error',\n error: '\u6240\u6709\u4e8b\u4ef6\u90fd\u8655\u7406\u5931\u6557',\n originalMessage: slackData.text,\n slackUser: slackData.user,\n slackChannel: slackData.channel,\n slackTimestamp: slackData.ts\n }\n }];\n }\n\n console.log(`\ud83c\udf89 \u6210\u529f\u8655\u7406 ${processedEvents.length} \u500b\u4e8b\u4ef6`);\n return processedEvents;\n \n} catch (error) {\n console.log('\u274c \u8655\u7406\u4e8b\u4ef6\u6642\u767c\u751f\u932f\u8aa4:', error.message);\n console.log('\ud83d\udd0d \u932f\u8aa4\u5806\u758a:', error.stack);\n \n return [{\n json: {\n status: 'error',\n error: `\u8655\u7406\u5931\u6557: ${error.message}`,\n errorStack: error.stack,\n originalMessage: slackData.text,\n slackUser: slackData.user,\n slackChannel: slackData.channel,\n slackTimestamp: slackData.ts\n }\n }];\n}"
},
"type": "n8n-nodes-base.code",
"typeVersion": 2,
"position": [
144,
304
],
"id": "fdf4dab4-5de5-4205-aaf9-0592b7be28fd",
"name": "Code in JavaScript"
},
{
"parameters": {
"conditions": {
"options": {
"caseSensitive": true,
"leftValue": "",
"typeValidation": "strict",
"version": 2
},
"conditions": [
{
"id": "6b023445-90f7-4895-ba31-87be54e21664",
"leftValue": "={{ $json.confidence }}",
"rightValue": 0.7,
"operator": {
"type": "number",
"operation": "gt"
}
}
],
"combinator": "and"
},
"options": {}
},
"type": "n8n-nodes-base.if",
"typeVersion": 2.2,
"position": [
368,
304
],
"id": "08341eaa-6d95-4508-adf9-2f777da40420",
"name": "If"
},
{
"parameters": {
"method": "POST",
"url": "https://api.line.me/v2/bot/message/push",
"authentication": "genericCredentialType",
"genericAuthType": "httpHeaderAuth",
"sendBody": true,
"specifyBody": "json",
"jsonBody": "={\n \"to\": \"U81025e615f2b5734e31d2715303acb5a\",\n \"messages\":[\n { \n \"type\":\"text\", \n \"text\":\"\u884c\u4e8b\u66c6\u5efa\u7acb\u5931\u6557\uff0c\u4fe1\u5fc3\u7a0b\u5ea6\u904e\u4f4e\" \n }\n ]\n} ",
"options": {}
},
"type": "n8n-nodes-base.httpRequest",
"typeVersion": 4.3,
"position": [
816,
496
],
"id": "70423981-f4d1-418b-a62d-c16e2027147d",
"name": "HTTP Request: Send Line Msg1",
"credentials": {
"httpHeaderAuth": {
"name": "<your credential>"
}
}
},
{
"parameters": {
"assignments": {
"assignments": [
{
"id": "id-1",
"name": "failMsg",
"value": "=\u26a0\ufe0f *\u767c\u73fe\u53ef\u80fd\u7684\u65e5\u7a0b\uff0c\u4f46\u4fe1\u5fc3\u5ea6\u8f03\u4f4e*\n\n\ud83d\udcdd *{{ $json.rawResponse.events[0].title }}*\n\ud83d\udd50 \u6642\u9593: {{ $json.rawResponse.events[0].startDateTime }}\n\ud83d\udccd \u5730\u9ede: {{$json.location || '\u672a\u6307\u5b9a'}}\n\ud83d\udcca AI \u4fe1\u5fc3\u5ea6: {{ $json.rawResponse.events[0].confidence }} ({{$json.confidence >= 0.7 ? '\u9ad8' : '\u4f4e'}}\u4fe1\u5fc3\u5ea6)\n\n\ud83d\udcad *AI \u5206\u6790*: _{{ $json.rawResponse.reasoning }}_\n\n\ud83d\udca1 *\u5efa\u8b70*: \u5982\u9700\u5275\u5efa\u65e5\u66c6\u4e8b\u4ef6\uff0c\u8acb\u767c\u9001\u66f4\u8a73\u7d30\u7684\u8a0a\u606f\uff08\u5305\u542b\u78ba\u5207\u6642\u9593\u3001\u5730\u9ede\u7b49\u8cc7\u8a0a\uff09\n\n_\ud83e\udd16 \u6b64\u70ba AI \u52a9\u624b\u4f4e\u4fe1\u5fc3\u5ea6\u63d0\u9192\uff0c\u4e0d\u6703\u81ea\u52d5\u5275\u5efa\u4e8b\u4ef6_",
"type": "string"
}
]
},
"options": {}
},
"id": "24127335-2362-4f75-a751-be05b7e32ebd",
"name": "Set Variables",
"type": "n8n-nodes-base.set",
"typeVersion": 3.4,
"position": [
592,
496
]
},
{
"parameters": {
"conditions": {
"options": {
"caseSensitive": true,
"leftValue": "",
"typeValidation": "strict",
"version": 2
},
"conditions": [
{
"id": "ab31d2f3-999b-4ae1-8db0-88bc7bee7164",
"leftValue": "={{ $json.isAllDay }}",
"rightValue": "",
"operator": {
"type": "boolean",
"operation": "true",
"singleValue": true
}
}
],
"combinator": "and"
},
"options": {}
},
"type": "n8n-nodes-base.if",
"typeVersion": 2.2,
"position": [
592,
208
],
"id": "10f1688d-4b90-4ede-bd59-fc0f3ef0e529",
"name": "If All Day Event"
},
{
"parameters": {
"calendar": {
"__rl": true,
"value": "abc12207@gmail.com",
"mode": "list",
"cachedResultName": "abc12207@gmail.com"
},
"start": "={{ $json.startDateTime }}",
"end": "={{ $json.endDateTime }}",
"additionalFields": {
"allday": "yes",
"description": "={{ $json.description }}",
"location": "={{ $json.location }}",
"summary": "={{ $json.title }}"
}
},
"type": "n8n-nodes-base.googleCalendar",
"typeVersion": 1.3,
"position": [
816,
112
],
"id": "db62a5f3-66db-4592-9a3f-826d8fcf3ced",
"name": "Create an event",
"alwaysOutputData": false,
"credentials": {
"googleCalendarOAuth2Api": {
"name": "<your credential>"
}
}
},
{
"parameters": {
"calendar": {
"__rl": true,
"value": "abc12207@gmail.com",
"mode": "list",
"cachedResultName": "abc12207@gmail.com"
},
"start": "={{ $json.startDateTime }}",
"end": "={{ $json.endDateTime }}",
"additionalFields": {
"allday": "no",
"description": "={{ $json.description }}",
"location": "={{ $json.location }}",
"summary": "={{ $json.title }}"
}
},
"type": "n8n-nodes-base.googleCalendar",
"typeVersion": 1.3,
"position": [
816,
304
],
"id": "8156f471-f18a-4cb0-8166-872d0bef5670",
"name": "Create an event1",
"alwaysOutputData": false,
"credentials": {
"googleCalendarOAuth2Api": {
"name": "<your credential>"
}
}
}
],
"connections": {
"Webhook": {
"main": [
[
{
"node": "Basic LLM Chain",
"type": "main",
"index": 0
}
]
]
},
"Basic LLM Chain": {
"main": [
[
{
"node": "Code in JavaScript",
"type": "main",
"index": 0
}
]
]
},
"Azure OpenAI Chat Model": {
"ai_languageModel": [
[
{
"node": "Basic LLM Chain",
"type": "ai_languageModel",
"index": 0
}
]
]
},
"Structured Output Parser": {
"ai_outputParser": [
[
{
"node": "Basic LLM Chain",
"type": "ai_outputParser",
"index": 0
}
]
]
},
"Code in JavaScript": {
"main": [
[
{
"node": "If",
"type": "main",
"index": 0
}
]
]
},
"If": {
"main": [
[
{
"node": "If All Day Event",
"type": "main",
"index": 0
}
],
[
{
"node": "Set Variables",
"type": "main",
"index": 0
}
]
]
},
"HTTP Request: Send Line Msg1": {
"main": [
[]
]
},
"Set Variables": {
"main": [
[
{
"node": "HTTP Request: Send Line Msg1",
"type": "main",
"index": 0
}
]
]
},
"If All Day Event": {
"main": [
[
{
"node": "Create an event",
"type": "main",
"index": 0
}
],
[
{
"node": "Create an event1",
"type": "main",
"index": 0
}
]
]
},
"Create an event": {
"main": [
[
{
"node": "HTTP Request: Send Line Msg",
"type": "main",
"index": 0
}
]
]
},
"Create an event1": {
"main": [
[
{
"node": "HTTP Request: Send Line Msg",
"type": "main",
"index": 0
}
]
]
}
},
"active": true,
"settings": {
"executionOrder": "v1"
},
"versionId": "e21d8d6c-c83d-4d9c-87a6-284f7b5ab8dd",
"meta": {
"templateCredsSetupCompleted": true
},
"id": "uFwNKjs68ncMw7qh",
"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.
azureOpenAiApigoogleCalendarOAuth2ApihttpHeaderAuth
For the full experience including quality scoring and batch install features for each workflow upgrade to Pro
About this workflow
LineCalendar. Uses httpRequest, chainLlm, lmChatAzureOpenAi, outputParserStructured. Webhook trigger; 12 nodes.
Source: https://github.com/MoneyDemo/20251119.N8N/blob/efec3c86841a734b8c62aa13873734ebc25f3d9d/demo/workflows/LineCalendar.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.
Benchmark Dataset | Improve Dataset. Uses chainLlm, lmChatAzureOpenAi, outputParserStructured, httpRequest. Webhook trigger; 15 nodes.
My workflow 53. Uses formTrigger, httpRequest, lmChatOpenAi, form. Event-driven trigger; 74 nodes.
Episode 23: UGC with nanobanana. Uses lmChatOpenAi, lmChatOllama, lmChatDeepSeek, lmChatOpenRouter. Event-driven trigger; 74 nodes.
The "Short Content" automation is a powerful, all-in-one solution designed to streamline the creation of short videos for social media, marketing, or personal projects. Leveraging cutting-edge AI tool
🔥 LIMITED-TIME OFFER: AI Video Automation (Previously \$59) Previously Template