{
  "id": "53DDbnukF168jZrW",
  "meta": {
    "templateCredsSetupCompleted": true
  },
  "name": "Summarize Daily RSS Feeds with AI and Send to Slack with X Sharing",
  "tags": [],
  "nodes": [
    {
      "id": "37c908ec-2019-4c1a-a43f-095d425d343b",
      "name": "Send a message",
      "type": "n8n-nodes-base.slack",
      "position": [
        736,
        -160
      ],
      "parameters": {
        "select": "channel",
        "blocksUi": "={\n\t\"blocks\": [\n\t\t{\n\t\t\t\"type\": \"section\",\n\t\t\t\"text\": {\n\t\t\t\t\"type\": \"mrkdwn\",\n\t\t\t\t\"text\": {{ JSON.stringify($json.slackMessage) }}\n\t\t\t}\n\t\t},\n\t\t{\n\t\t\t\"type\": \"divider\"\n\t\t},\n\t\t{\n\t\t\t\"type\": \"actions\",\n\t\t\t\"elements\": [\n\t\t\t\t{\n\t\t\t\t\t\"type\": \"button\",\n\t\t\t\t\t\"text\": {\n\t\t\t\t\t\t\"type\": \"plain_text\",\n\t\t\t\t\t\t\"text\": \"Share on X\",\n\t\t\t\t\t\t\"emoji\": true\n\t\t\t\t\t},\n\t\t\t\t\t\"value\": \"click_contact\",\n\t\t\t\t\t\"url\": \"{{ $json.xShareUrl }}\"\n\t\t\t\t}\n\t\t\t]\n\t\t}\n\t]\n}",
        "channelId": {
          "__rl": true,
          "mode": "id",
          "value": "sample"
        },
        "messageType": "block",
        "otherOptions": {}
      },
      "credentials": {
        "slackApi": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 2.3
    },
    {
      "id": "a159abc3-d583-424d-b1a5-d724ae9d6aa7",
      "name": "Sticky Note",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        -1456,
        -272
      ],
      "parameters": {
        "width": 432,
        "height": 752,
        "content": "## How it works\n\nThis workflow fetches RSS feeds daily and sends a notification to Slack if new topics are found.\n\nSince standard RSS snippets are often insufficient, the AI visits the source links to summarize the full articles and sends the summaries to Slack.\nYou can then share interesting topics directly to X from Slack using the button.\n\n## How to use\n\n* Open the **Gemini Chat Model** node (attached to the AI Agent) and set up the Credential.\n  * You can obtain an API key from [Google AI Studio](https://aistudio.google.com/api-keys).\n* Open the `Slack` node and set up the Credential to allow sending messages.\n  * You can create a new Slack App [here](https://api.slack.com/apps).\n* Finally, open the `Config` node and update the `rssUrls` parameter with the RSS feed URLs you want to follow.\n\n## Customizing this workflow\n\n* You can adjust the number of topics fetched per RSS feed by modifying the `takeCount` parameter in the `Config` node."
      },
      "typeVersion": 1
    },
    {
      "id": "e99a3362-b0a2-4303-88b3-bc2d9e599f98",
      "name": "Schedule Trigger",
      "type": "n8n-nodes-base.scheduleTrigger",
      "position": [
        -976,
        -160
      ],
      "parameters": {
        "rule": {
          "interval": [
            {
              "triggerAtHour": 2
            }
          ]
        }
      },
      "typeVersion": 1.3
    },
    {
      "id": "65b6b42b-c196-43ed-bbcc-e11da04d57b4",
      "name": "RSS Read",
      "type": "n8n-nodes-base.rssFeedRead",
      "position": [
        -96,
        -144
      ],
      "parameters": {
        "url": "={{ $json.url }}",
        "options": {
          "customFields": ""
        }
      },
      "typeVersion": 1.2
    },
    {
      "id": "b4a77c6c-e243-4f53-b825-be598738a36f",
      "name": "Loop Over Items",
      "type": "n8n-nodes-base.splitInBatches",
      "position": [
        -304,
        -160
      ],
      "parameters": {
        "options": {}
      },
      "typeVersion": 3
    },
    {
      "id": "e1881000-5c7b-4fe6-9b21-7bfdbb4d21a3",
      "name": "Config",
      "type": "n8n-nodes-base.set",
      "position": [
        -752,
        -160
      ],
      "parameters": {
        "options": {},
        "assignments": {
          "assignments": [
            {
              "id": "b473b3e9-c2b3-426c-b1e4-aa8831bc86ff",
              "name": "targetDate",
              "type": "string",
              "value": "={{ $now.minus({ days: 1 }).toFormat('yyyy-MM-dd') }}"
            },
            {
              "id": "17d30704-8a03-4c44-ab1d-223f4985fbc3",
              "name": "rssUrls",
              "type": "array",
              "value": "=['https://news.google.com/rss/headlines/section/topic/TECHNOLOGY?hl=en-US&gl=US&ceid=US:en', 'https://search.cnbc.com/rs/search/combinedcms/view.xml?partnerId=wrss01&id=19854910']"
            },
            {
              "id": "361abce1-bcee-4ec7-a80c-39746dc4add7",
              "name": "takeCount",
              "type": "string",
              "value": "1"
            }
          ]
        }
      },
      "typeVersion": 3.4
    },
    {
      "id": "8e63bb10-d007-4866-9b4c-71b5384b4c51",
      "name": "Convert to loop items",
      "type": "n8n-nodes-base.code",
      "position": [
        -544,
        -160
      ],
      "parameters": {
        "jsCode": "return $json.rssUrls.map((item) => ({\n  json: {\n    url: item\n  }\n}))"
      },
      "typeVersion": 2
    },
    {
      "id": "f7ff79b5-07af-431f-927c-3d8385ae27a2",
      "name": "When Executed by Another Workflow",
      "type": "n8n-nodes-base.executeWorkflowTrigger",
      "position": [
        -976,
        176
      ],
      "parameters": {
        "workflowInputs": {
          "values": [
            {
              "name": "rssFeed",
              "type": "object"
            }
          ]
        }
      },
      "typeVersion": 1.1
    },
    {
      "id": "769f080f-89eb-46b8-a229-a7ccebbd3eef",
      "name": "Filter Rss Feeds",
      "type": "n8n-nodes-base.code",
      "position": [
        112,
        -144
      ],
      "parameters": {
        "jsCode": "const config = $('Config').first().json\nconst targetDate = new Date(config.targetDate)\nreturn $input.all().filter((item) => {\n  const rssFeed = item.json\n  const date = new Date(rssFeed.isoDate)\n  return date >= targetDate\n}).slice(0, config.takeCount)"
      },
      "typeVersion": 2,
      "alwaysOutputData": true
    },
    {
      "id": "364bc786-7952-4559-8039-53be5478ed31",
      "name": "HttpRequestTool",
      "type": "n8n-nodes-base.httpRequestTool",
      "position": [
        -400,
        336
      ],
      "parameters": {
        "url": "={{ /*n8n-auto-generated-fromAI-override*/ $fromAI('URL', `URL to Get HTML`, 'string') }}",
        "options": {
          "timeout": 60000,
          "redirect": {
            "redirect": {
              "maxRedirects": 10
            }
          },
          "response": {
            "response": {
              "neverError": true,
              "fullResponse": true
            }
          },
          "allowUnauthorizedCerts": true
        },
        "sendHeaders": true,
        "toolDescription": "Get Page Content. Retrieves the content from the specified URL.",
        "headerParameters": {
          "parameters": [
            {
              "name": "=User-Agent",
              "value": "=Mozilla/5.0 (Macintosh; Intel Mac OS X 14_5_0) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/129.0.6668.71 Safari/537.36"
            }
          ]
        }
      },
      "typeVersion": 4.2
    },
    {
      "id": "4ef2ff55-1e98-4862-9b04-c66e2ff8b633",
      "name": "AI Agent (Access URL)",
      "type": "@n8n/n8n-nodes-langchain.agent",
      "onError": "continueRegularOutput",
      "position": [
        -544,
        176
      ],
      "parameters": {
        "text": "=You are a professional Social Media Manager. Your task is to create engaging content for X (formerly Twitter) based on a news article.\n\nPlease follow these steps:\n1. Use the provided `HttpRequestTool` to fetch the content from the following URL:\n{{ $json.link }}\n\n2. Based on the fetched content, generate a `title` and a `description`.\n   - **title**: A concise and catchy headline for the article.\n   - **description**: An engaging summary or comment suitable for an X post (informative, under 200 characters).\n\n3. Output the result strictly in the JSON format shown below, enclosed in a code block. Do not include any other text.\n\n```json\n{\n  \"title\": \"Your Generated Title\",\n  \"description\": \"Your Generated Description for X\"\n}\n```",
        "options": {},
        "promptType": "define"
      },
      "retryOnFail": true,
      "typeVersion": 3,
      "alwaysOutputData": true,
      "waitBetweenTries": 5000
    },
    {
      "id": "fb07bb89-5413-4458-81b5-1b4b676b46d3",
      "name": "Google Gemini Chat Model",
      "type": "@n8n/n8n-nodes-langchain.lmChatGoogleGemini",
      "position": [
        -544,
        336
      ],
      "parameters": {
        "options": {}
      },
      "credentials": {
        "googlePalmApi": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 1
    },
    {
      "id": "8a3fb4ca-be94-407d-89e4-38ddde5b2622",
      "name": "Format Request",
      "type": "n8n-nodes-base.code",
      "position": [
        -752,
        176
      ],
      "parameters": {
        "mode": "runOnceForEachItem",
        "jsCode": "return {\n  json: {\n    requestParameters: $input.item.json,\n    link: $input.item.json.rssFeed.link,\n  }\n}"
      },
      "typeVersion": 2
    },
    {
      "id": "3053dbf1-0271-4d55-9b69-abc156dd8d75",
      "name": "Format Response",
      "type": "n8n-nodes-base.code",
      "position": [
        -208,
        176
      ],
      "parameters": {
        "jsCode": "const request = $('Format Request').first().json\nconst aiOutput = $input.first().json.output\n\nconst cleanJson = aiOutput.replace(/```json|```/g, '').trim()\nconst result = JSON.parse(cleanJson)\n\nconst articleUrl = request.requestParameters?.rssFeed?.link || request.link || \"\"\nconst tweetText = `${result.title}\\n${result.description}`\n\nconst xShareUrl = `https://x.com/intent/tweet?text=${encodeURIComponent(tweetText)}&url=${encodeURIComponent(articleUrl)}`\n\nconst slackMessage = `\ud83d\udce2 *New Article Draft Ready*\n\nI have generated a draft for X based on the RSS feed.\n\n*Title:* ${result.title}\n*Content:* ${result.description}\n\n<${articleUrl}|\ud83d\udcc4 Read Original Article>` \n\nreturn [{\n  json: {\n    ...request,\n    ...result,\n    xShareUrl,\n    slackMessage\n  }\n}]"
      },
      "typeVersion": 2
    },
    {
      "id": "a7124a3f-6edd-4e74-a15d-b0c193b924b9",
      "name": "Call Sub-workflow",
      "type": "n8n-nodes-base.executeWorkflow",
      "position": [
        528,
        -160
      ],
      "parameters": {
        "mode": "each",
        "options": {
          "waitForSubWorkflow": true
        },
        "workflowId": {
          "__rl": true,
          "mode": "list",
          "value": "53DDbnukF168jZrW",
          "cachedResultUrl": "/workflow/53DDbnukF168jZrW",
          "cachedResultName": "Summarize Daily RSS Feeds with AI and Send to Slack with X Sharing"
        },
        "workflowInputs": {
          "value": {
            "rssFeed": "={{ $json }}"
          },
          "schema": [
            {
              "id": "rssFeed",
              "type": "object",
              "display": true,
              "removed": false,
              "required": false,
              "displayName": "rssFeed",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            }
          ],
          "mappingMode": "defineBelow",
          "matchingColumns": [
            "rssFeed"
          ],
          "attemptToConvertTypes": false,
          "convertFieldsToString": true
        }
      },
      "typeVersion": 1.3
    },
    {
      "id": "fbc438ba-4638-4c27-b5db-19c25be5cecd",
      "name": "Sticky Note1",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        -1008,
        -272
      ],
      "parameters": {
        "color": 7,
        "width": 1888,
        "height": 320,
        "content": "## Fetch RSS and Notify Slack\nThis is the main workflow. It fetches RSS feeds and sends notifications to Slack, calling a sub-workflow to process content with Generative AI."
      },
      "typeVersion": 1
    },
    {
      "id": "c543bbdf-08a7-4959-a4c6-fc6b507b88bb",
      "name": "Sticky Note2",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        -1008,
        64
      ],
      "parameters": {
        "color": 7,
        "width": 976,
        "height": 416,
        "content": "## Summarize Articles with AI\nSummarizes article content based on RSS URLs and formats the response for posting to X."
      },
      "typeVersion": 1
    },
    {
      "id": "909f5c4f-7ed9-4029-ba76-68086b6c4f03",
      "name": "Is not empty",
      "type": "n8n-nodes-base.if",
      "position": [
        320,
        -144
      ],
      "parameters": {
        "options": {},
        "conditions": {
          "options": {
            "version": 2,
            "leftValue": "",
            "caseSensitive": true,
            "typeValidation": "strict"
          },
          "combinator": "and",
          "conditions": [
            {
              "id": "450e0fed-8f5f-42d6-a1c4-68dddaacec45",
              "operator": {
                "type": "object",
                "operation": "notEmpty",
                "singleValue": true
              },
              "leftValue": "={{ $json }}",
              "rightValue": ""
            }
          ]
        }
      },
      "typeVersion": 2.2
    }
  ],
  "active": false,
  "settings": {
    "executionOrder": "v1"
  },
  "versionId": "182c7e58-26c5-4e03-af53-5ecc7f295246",
  "connections": {
    "Config": {
      "main": [
        [
          {
            "node": "Convert to loop items",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "RSS Read": {
      "main": [
        [
          {
            "node": "Filter Rss Feeds",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Is not empty": {
      "main": [
        [
          {
            "node": "Call Sub-workflow",
            "type": "main",
            "index": 0
          }
        ],
        [
          {
            "node": "Loop Over Items",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Format Request": {
      "main": [
        [
          {
            "node": "AI Agent (Access URL)",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Send a message": {
      "main": [
        [
          {
            "node": "Loop Over Items",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Format Response": {
      "main": [
        []
      ]
    },
    "HttpRequestTool": {
      "ai_tool": [
        [
          {
            "node": "AI Agent (Access URL)",
            "type": "ai_tool",
            "index": 0
          }
        ]
      ]
    },
    "Loop Over Items": {
      "main": [
        [],
        [
          {
            "node": "RSS Read",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Filter Rss Feeds": {
      "main": [
        [
          {
            "node": "Is not empty",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Schedule Trigger": {
      "main": [
        [
          {
            "node": "Config",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Call Sub-workflow": {
      "main": [
        [
          {
            "node": "Send a message",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "AI Agent (Access URL)": {
      "main": [
        [
          {
            "node": "Format Response",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Convert to loop items": {
      "main": [
        [
          {
            "node": "Loop Over Items",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Google Gemini Chat Model": {
      "ai_languageModel": [
        [
          {
            "node": "AI Agent (Access URL)",
            "type": "ai_languageModel",
            "index": 0
          }
        ]
      ]
    },
    "When Executed by Another Workflow": {
      "main": [
        [
          {
            "node": "Format Request",
            "type": "main",
            "index": 0
          }
        ]
      ]
    }
  }
}