Automatisation LinkedIn
Ceci est unContent Creation, Multimodal AIworkflow d'automatisation du domainecontenant 54 nœuds.Utilise principalement des nœuds comme If, Set, Code, Merge, Switch. Utiliser l'IA Gemini et un processus d'approbation pour convertir les messages Telegram en publications LinkedIn professionnelles
- •Informations d'identification LinkedIn API
- •Token Bot Telegram
- •Informations d'identification Google Sheets API
- •Clé API Google Gemini
Nœuds utilisés (54)
Catégorie
{
"id": "LWCrr5lorPtQRUfI",
"meta": {
"instanceId": "0b7fd9057c9a7248304e42ff851cb8ac210753ac550dbd39aab9acb302a34165",
"templateCredsSetupCompleted": true
},
"name": "Linkedin Automation",
"tags": [
{
"id": "HmvMKAccqyXZIUSY",
"name": "LinkedIn Automation",
"createdAt": "2025-08-14T08:42:36.216Z",
"updatedAt": "2025-08-14T08:42:36.216Z"
},
{
"id": "R0SHjnqB9YfJKAVu",
"name": "Gemini",
"createdAt": "2025-08-14T10:26:53.631Z",
"updatedAt": "2025-08-14T10:26:53.631Z"
},
{
"id": "l1eZzX8QnqsKk2gm",
"name": "Automation",
"createdAt": "2025-08-14T10:26:53.610Z",
"updatedAt": "2025-08-14T10:26:53.610Z"
},
{
"id": "n3OO3hKjfreBd7Hk",
"name": "LinkedIn",
"createdAt": "2025-08-14T10:26:53.668Z",
"updatedAt": "2025-08-14T10:26:53.668Z"
}
],
"nodes": [
{
"id": "96c77c8e-fc61-4d53-9bd6-568317aee08c",
"name": "Telegram Trigger",
"type": "n8n-nodes-base.telegramTrigger",
"position": [
-2544,
336
],
"webhookId": "c5b3b922-1355-41d4-8f9f-10d8fc803218",
"parameters": {
"updates": [
"message",
"callback_query"
],
"additionalFields": {
"download": true,
"imageSize": "extraLarge"
}
},
"credentials": {
"telegramApi": {
"id": "M9h9AMg2S3J0VkNB",
"name": "Telegram account"
}
},
"typeVersion": 1
},
{
"id": "a34caf37-c9b3-47e8-894a-5259323f70cc",
"name": "Validation Utilisateur",
"type": "n8n-nodes-base.code",
"position": [
-1872,
80
],
"parameters": {
"mode": "runOnceForEachItem",
"jsCode": "// Fetch authorized users configuration\nconst authorizedUsers = {\n telegram_ids: $json.telegram_ids,\n usernames: $json.usernames\n};\n\nconst userId = $('Switch').item.json.message.from.id.toString();\nconst username = $('Switch').item.json.message.from.username;\n\n// Check if user is authorized (by id or username)\nconst isAuthorized =\n authorizedUsers.telegram_ids.includes(userId) ||\n authorizedUsers.usernames.includes(username);\n\n// Return user info and original message\nreturn {\n json: {\n user_id: userId,\n username: username,\n message_text: $('Switch').item.json.message.text,\n chat_id: $('Switch').item.json.message.chat.id,\n message_id: $('Switch').item.json.message.message_id,\n timestamp: new Date().toISOString(),\n authorized: isAuthorized\n }\n};\n"
},
"typeVersion": 2
},
{
"id": "a7a0856a-344f-48c8-9308-5fb9dc06eea4",
"name": "Générer un ID de Publication",
"type": "n8n-nodes-base.code",
"position": [
-1424,
-32
],
"parameters": {
"mode": "runOnceForEachItem",
"jsCode": "// Generate unique post ID\nconst now = new Date();\nconst dateStr = now.toISOString().replace(/[-:T]/g, '').slice(0, 14);\nconst random = Math.floor(Math.random() * 1000).toString().padStart(3, '0');\nconst postId = `${dateStr}_${random}`;\n\nreturn {\n json: {\n ...$input.item.json,\n post_id: postId,\n created_at: now.toISOString()\n }\n};"
},
"typeVersion": 2
},
{
"id": "03be5ca8-54bb-4597-af45-0d13b66be14c",
"name": "Journaliser la Requête Initiale",
"type": "n8n-nodes-base.googleSheets",
"position": [
-1136,
-32
],
"parameters": {
"columns": {
"value": {
"post_id": "={{ $json.post_id }}",
"user_id": "={{ $json.user_id }}",
"timestamp": "={{ $json.timestamp }}",
"user_name": "={{ $json.username }}",
"original_message": "={{ $json.message_text }}"
},
"schema": [
{
"id": "post_id",
"type": "string",
"display": true,
"removed": false,
"required": false,
"displayName": "post_id",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "timestamp",
"type": "string",
"display": true,
"required": false,
"displayName": "timestamp",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "user_id",
"type": "string",
"display": true,
"required": false,
"displayName": "user_id",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "user_name",
"type": "string",
"display": true,
"required": false,
"displayName": "user_name",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "input_type",
"type": "string",
"display": true,
"required": false,
"displayName": "input_type",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "original_message",
"type": "string",
"display": true,
"required": false,
"displayName": "original_message",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "extracted_urls",
"type": "string",
"display": true,
"required": false,
"displayName": "extracted_urls",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "identified_topics",
"type": "string",
"display": true,
"required": false,
"displayName": "identified_topics",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "search_queries",
"type": "string",
"display": true,
"required": false,
"displayName": "search_queries",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "search_results_summary",
"type": "string",
"display": true,
"required": false,
"displayName": "search_results_summary",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "scraped_content_summary",
"type": "string",
"display": true,
"required": false,
"displayName": "scraped_content_summary",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "content_sources",
"type": "string",
"display": true,
"required": false,
"displayName": "content_sources",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "initial_generated_post",
"type": "string",
"display": true,
"required": false,
"displayName": "initial_generated_post",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "final_approved_post",
"type": "string",
"display": true,
"required": false,
"displayName": "final_approved_post",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "hashtags_used",
"type": "string",
"display": true,
"required": false,
"displayName": "hashtags_used",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "character_count",
"type": "string",
"display": true,
"required": false,
"displayName": "character_count",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "has_media",
"type": "string",
"display": true,
"required": false,
"displayName": "has_media",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "media_urls",
"type": "string",
"display": true,
"required": false,
"displayName": "media_urls",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "approval_status",
"type": "string",
"display": true,
"required": false,
"displayName": "approval_status",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "rejection_reason",
"type": "string",
"display": true,
"required": false,
"displayName": "rejection_reason",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "edit_iterations",
"type": "string",
"display": true,
"required": false,
"displayName": "edit_iterations",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "time_to_approval",
"type": "string",
"display": true,
"required": false,
"displayName": "time_to_approval",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "posted_datetime",
"type": "string",
"display": true,
"required": false,
"displayName": "posted_datetime",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "scheduled_time",
"type": "string",
"display": true,
"required": false,
"displayName": "scheduled_time",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "linkedin_post_url",
"type": "string",
"display": true,
"required": false,
"displayName": "linkedin_post_url",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "post_type",
"type": "string",
"display": true,
"required": false,
"displayName": "post_type",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "impressions_1h",
"type": "string",
"display": true,
"required": false,
"displayName": "impressions_1h",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "impressions_24h",
"type": "string",
"display": true,
"required": false,
"displayName": "impressions_24h",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "impressions_7d",
"type": "string",
"display": true,
"required": false,
"displayName": "impressions_7d",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "impressions_30d",
"type": "string",
"display": true,
"required": false,
"displayName": "impressions_30d",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "reactions_total",
"type": "string",
"display": true,
"required": false,
"displayName": "reactions_total",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "likes",
"type": "string",
"display": true,
"required": false,
"displayName": "likes",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "celebrates",
"type": "string",
"display": true,
"required": false,
"displayName": "celebrates",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "loves",
"type": "string",
"display": true,
"required": false,
"displayName": "loves",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "comments_total",
"type": "string",
"display": true,
"required": false,
"displayName": "comments_total",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "shares_total",
"type": "string",
"display": true,
"required": false,
"displayName": "shares_total",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "clicks_total",
"type": "string",
"display": true,
"required": false,
"displayName": "clicks_total",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "engagement_rate",
"type": "string",
"display": true,
"required": false,
"displayName": "engagement_rate",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "viral_score",
"type": "string",
"display": true,
"required": false,
"displayName": "viral_score",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "follower_growth",
"type": "string",
"display": true,
"required": false,
"displayName": "follower_growth",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "performance_tier",
"type": "string",
"display": true,
"required": false,
"displayName": "performance_tier",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "last_metrics_update",
"type": "string",
"display": true,
"required": false,
"displayName": "last_metrics_update",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "engagement_rate",
"type": "string",
"display": true,
"required": false,
"displayName": "engagement_rate",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "approval_status",
"type": "string",
"display": true,
"required": false,
"displayName": "approval_status",
"defaultMatch": false,
"canBeUsedToMatch": true
}
],
"mappingMode": "defineBelow",
"matchingColumns": [
"post_id"
],
"attemptToConvertTypes": false,
"convertFieldsToString": false
},
"options": {},
"operation": "appendOrUpdate",
"sheetName": {
"__rl": true,
"mode": "list",
"value": "gid=0",
"cachedResultUrl": "https://docs.google.com/spreadsheets/d/1RvHyWEvEZR5etmq1KfzTOkSIXY5tUT5TLVgDSUfAr5c/edit#gid=0",
"cachedResultName": "Posts_Master"
},
"documentId": {
"__rl": true,
"mode": "list",
"value": "1RvHyWEvEZR5etmq1KfzTOkSIXY5tUT5TLVgDSUfAr5c",
"cachedResultUrl": "https://docs.google.com/spreadsheets/d/1RvHyWEvEZR5etmq1KfzTOkSIXY5tUT5TLVgDSUfAr5c/edit?usp=drivesdk",
"cachedResultName": "LinekedIn Posts"
}
},
"credentials": {
"googleSheetsOAuth2Api": {
"id": "ExnZpB5bwFQ3gQ5N",
"name": "Google Sheets account 2"
}
},
"executeOnce": false,
"notesInFlow": false,
"typeVersion": 4,
"alwaysOutputData": true
},
{
"id": "2dbe1200-b0fb-4cf4-9ea5-214e76c48f7f",
"name": "Analyser la Classification",
"type": "n8n-nodes-base.code",
"position": [
-400,
-32
],
"parameters": {
"mode": "runOnceForEachItem",
"jsCode": "// Enhanced Parse Classification for better integration\nconst inputJson = $input.item.json;\n\n// Extract classification results\nconst classificationResult = {\n input_type: $json.output.input_type || 'Topic',\n urls: $json.output.urls || [],\n topics: $json.output.topics || [],\n content: $json.output.content || '',\n processing_instructions: $json.output.processing_instructions || ''\n};\n\n// Preserve original request data for tracking\nconst originalRequestData = {\n post_id: $('Log Initial Request').item.json.post_id,\n chat_id:$('Generate Post ID').item.json.chat_id,\n message_id:$('Generate Post ID').item.json.message_id,\n timestamp: inputJson.timestamp || new Date().toISOString(),\n user_id: $('Log Initial Request').item.json.user_id || '',\n username: $('Log Initial Request').item.json.user_name || '',\n original_message: $('Log Initial Request').item.json.original_message || inputJson.message_text || ''\n};\n\n// Add processing metadata\nconst processingMetadata = {\n classification_timestamp: new Date().toISOString(),\n has_urls: classificationResult.urls.length > 0,\n has_topics: classificationResult.topics.length > 0,\n has_content: classificationResult.content.length > 0,\n url_count: classificationResult.urls.length,\n topic_count: classificationResult.topics.length,\n content_length: classificationResult.content.length,\n requires_scraping: classificationResult.urls.length > 0,\n requires_search: classificationResult.topics.length > 0,\n processing_complexity: determineComplexity(classificationResult)\n};\n\n// Determine processing complexity\nfunction determineComplexity(result) {\n const factors = [\n result.urls.length > 0,\n result.topics.length > 0,\n result.content.length > 0\n ].filter(Boolean).length;\n \n if (factors === 0) return 'simple';\n if (factors === 1) return 'moderate';\n if (factors >= 2) return 'complex';\n}\n\n// Return comprehensive data for downstream processing\nreturn {\n json: {\n ...originalRequestData,\n ...classificationResult,\n ...processingMetadata,\n \n // Add routing hints for Content Router\n route_to_scraper: classificationResult.urls.length > 0,\n route_to_search: classificationResult.topics.length > 0,\n route_to_direct: classificationResult.urls.length === 0 && \n classificationResult.topics.length === 0,\n \n // Prepare data for Google Sheets tracking\n extracted_urls: classificationResult.urls.join(', '),\n identified_topics: classificationResult.topics.join(', '),\n input_classification: classificationResult.input_type,\n processing_stage: 'classified'\n }\n};"
},
"typeVersion": 2
},
{
"id": "d45ddc23-679a-4cd6-82e3-fe5bbe35107f",
"name": "Routeur de Contenu",
"type": "n8n-nodes-base.if",
"position": [
-176,
-224
],
"parameters": {
"options": {},
"conditions": {
"options": {
"version": 1,
"leftValue": "",
"caseSensitive": true,
"typeValidation": "strict"
},
"combinator": "or",
"conditions": [
{
"id": "url-only",
"operator": {
"type": "string",
"operation": "equals"
},
"leftValue": "={{ $json.input_type }}",
"rightValue": "URL"
},
{
"id": "topic-only",
"operator": {
"type": "string",
"operation": "equals"
},
"leftValue": "={{ $json.input_type }}",
"rightValue": "Topic"
},
{
"id": "mixed",
"operator": {
"type": "string",
"operation": "contains"
},
"leftValue": "={{ $json.input_type }}",
"rightValue": "URL+Topic"
}
]
}
},
"typeVersion": 2
},
{
"id": "70b4a682-8827-4e2b-8f01-af887ab7ec41",
"name": "Extraire les URLs pour Traitement",
"type": "n8n-nodes-base.code",
"position": [
272,
-464
],
"parameters": {
"jsCode": "const urls = $input.item.json.output?.urls || $input.item.json.urls || [];\n\nif (urls.length === 0) {\n // No URLs to process, pass through original data\n return {\n json: {\n ...$input.item.json,\n urls_to_process: [],\n total_urls: 0,\n processing_stage: 'no_urls'\n }\n };\n}\n\n// Create individual items for each URL to be processed\nconst urlItems = urls.map((url, index) => ({\n json: {\n ...$input.item.json,\n ...$input.item.json.output,\n current_url: url,\n url_index: index,\n total_urls: urls.length,\n processing_stage: 'url_extraction'\n }\n}));\n// Return array of items for processing\nreturn urlItems;"
},
"notesInFlow": false,
"typeVersion": 2,
"alwaysOutputData": false
},
{
"id": "2c8c8e1c-fb44-47a8-921f-2676f773df7a",
"name": "Boucle sur les URLs",
"type": "n8n-nodes-base.splitInBatches",
"position": [
496,
-464
],
"parameters": {
"options": {},
"batchSize": "={{ $json.total_urls }}"
},
"typeVersion": 3,
"alwaysOutputData": false
},
{
"id": "d8ef03dd-2db3-4adf-993f-de30fcb090ab",
"name": "Traiter le Contenu Extraité",
"type": "n8n-nodes-base.code",
"position": [
720,
-336
],
"parameters": {
"jsCode": "// Get all inputs from the loop\nconst allInputs = $input.all();\nconsole.log(\"Processing all loop outputs:\", allInputs.length, \"items\");\n\nlet mergedContent = '';\nlet allSourceUrls = [];\nlet allMetadataUrls = [];\nlet overallSuccess = true;\n\n// Process each input from the loop\nfor (const inputItem of allInputs) {\n const scrapedData = inputItem.json;\n let processedContent = '';\n let scrapingSuccess = false;\n let metadataUrl = '';\n \n try {\n // Handle Firecrawl response structure\n if (scrapedData.data && scrapedData.data.markdown) {\n processedContent = scrapedData.data.markdown;\n \n // Extract URL from metadata if available\n if (scrapedData.data.metadata && scrapedData.data.metadata.ogUrl) {\n metadataUrl = scrapedData.data.metadata.ogUrl;\n allMetadataUrls.push(metadataUrl);\n }\n \n scrapingSuccess = true;\n }\n // Handle alternative response structure\n else if (scrapedData.markdown) {\n processedContent = scrapedData.markdown;\n \n // Extract URL from metadata if available\n if (scrapedData.metadata && scrapedData.metadata.ogUrl) {\n metadataUrl = scrapedData.metadata.ogUrl;\n allMetadataUrls.push(metadataUrl);\n }\n \n scrapingSuccess = true;\n }\n // Handle plain text content\n else if (scrapedData.content) {\n processedContent = scrapedData.content;\n \n // Extract URL from metadata if available\n if (scrapedData.metadata && scrapedData.metadata.ogUrl) {\n metadataUrl = scrapedData.metadata.ogUrl;\n allMetadataUrls.push(metadataUrl);\n }\n \n scrapingSuccess = true;\n }\n else {\n throw new Error('No content found in Firecrawl response');\n }\n } catch (error) {\n processedContent = `Error scraping ${scrapedData.current_url}: ${error.message}`;\n scrapingSuccess = false;\n }\n \n // Use metadata URL if available, otherwise fall back to current_url\n const sourceUrl = metadataUrl || scrapedData.current_url;\n \n // Add to merged content with source separator\n if (sourceUrl) {\n mergedContent += `\\n\\n--- Source: ${sourceUrl} ---\\n\\n`;\n allSourceUrls.push(sourceUrl);\n }\n mergedContent += processedContent;\n \n // Update overall success (false if any scraping failed)\n if (!scrapingSuccess) {\n overallSuccess = false;\n }\n}\n\n// Remove duplicate URLs and create final source URL list\nconst uniqueSourceUrls = [...new Set(allSourceUrls)];\nconst uniqueMetadataUrls = [...new Set(allMetadataUrls)];\n\nconsole.log(\"Extracted metadata URLs:\", uniqueMetadataUrls);\nconsole.log(\"All source URLs:\", uniqueSourceUrls);\n\n// Return only the required fields\nreturn {\n json: {\n merged_content: mergedContent.trim(),\n scraping_success: overallSuccess,\n source_url: uniqueSourceUrls.join(', '),\n metadata_urls: uniqueMetadataUrls.join(', '), // Additional field with metadata URLs\n processing_stage: 'content_merged'\n }\n};"
},
"typeVersion": 2
},
{
"id": "8d16150a-502b-4c6c-a16c-b36efd85e7ed",
"name": "Fusionner les Sources de Contenu",
"type": "n8n-nodes-base.code",
"position": [
1168,
-96
],
"parameters": {
"jsCode": "// Optimized for direct JSON access without looping\nconst allInputs = $input.all();\n\nconsole.log(\"Total inputs received:\", allInputs.length);\n\n// Initialize the complete output structure\nlet processedData = {\n // Original input data\n post_id: '',\n user_id: '',\n username: '',\n chat_id: '',\n message_id:'',\n message_text: '',\n input_type: '',\n urls: [],\n topics: [],\n content: '',\n processing_instructions: '',\n \n // Scraped content from URLs\n scraped_content: '',\n scraped_urls: [],\n scraped_summary: '',\n \n // Brave search results\n brave_search_results: '',\n brave_search_performed: false,\n brave_search_query: '',\n \n // Processing metadata\n content_sources: [],\n total_scraped_urls: 0,\n successful_scrapes: 0,\n failed_scrapes: 0,\n processing_timestamp: new Date().toISOString(),\n routes_taken: [],\n \n // Final merged content for LLM\n merged_content_for_llm: ''\n};\n\n// Direct access to specific inputs based on expected structure\nconsole.log(\"Processing inputs with direct JSON access...\");\nconsole.log(\"Input structures:\", allInputs.map((input, index) => ({\n index,\n keys: Object.keys(input.json || {}).slice(0, 10),\n hasArray: Array.isArray(input.json),\n jsonType: typeof input.json\n})));\n\n// Look for Parse Classification data in any input\nconst parseInput = allInputs.find(input => {\n if (!input.json) return false;\n \n // Handle array structure\n if (Array.isArray(input.json)) {\n return input.json.some(item => \n item.post_id !== undefined || \n item.input_type !== undefined || \n item.processing_stage === 'classified'\n );\n }\n \n // Handle direct object\n return input.json.post_id !== undefined || \n input.json.input_type !== undefined || \n input.json.processing_stage === 'classified';\n});\n\nif (parseInput) {\n console.log(\"Found Parse Classification data\");\n \n let parseData;\n if (Array.isArray(parseInput.json)) {\n // Find the classification data in the array\n parseData = parseInput.json.find(item => \n item.post_id !== undefined || \n item.input_type !== undefined || \n item.processing_stage === 'classified'\n );\n } else {\n parseData = parseInput.json;\n }\n \n if (parseData) {\n console.log(\"Processing Parse Classification data:\", Object.keys(parseData));\n \n processedData.post_id = parseData.post_id || '';\n processedData.chat_id = parseData.chat_id || '';\n processedData.message_id = parseData.message_id || '';\n processedData.user_id = parseData.user_id || '';\n processedData.username = parseData.username || '';\n processedData.chat_id = parseData.chat_id || '';\n processedData.message_text = parseData.original_message || parseData.message_text || '';\n processedData.input_type = parseData.input_type || '';\n \n // Handle URLs - could be array or string\n if (parseData.urls && Array.isArray(parseData.urls)) {\n processedData.urls = parseData.urls;\n } else if (parseData.extracted_urls) {\n processedData.urls = Array.isArray(parseData.extracted_urls) ? \n parseData.extracted_urls : [parseData.extracted_urls];\n } else {\n processedData.urls = [];\n }\n \n // Handle topics - could be array or string \n if (parseData.topics && Array.isArray(parseData.topics)) {\n processedData.topics = parseData.topics;\n } else if (parseData.identified_topics) {\n processedData.topics = Array.isArray(parseData.identified_topics) ? \n parseData.identified_topics : [parseData.identified_topics];\n } else {\n processedData.topics = [];\n }\n \n processedData.content = parseData.content || '';\n processedData.processing_instructions = parseData.processing_instructions || '';\n processedData.routes_taken.push('Parse Classification');\n }\n}\n\n// Input 2: Scraped Content (look for merged_content or scraped_content)\nconst scrapedInput = allInputs.find(input => {\n if (!input.json) return false;\n \n // Handle array structure\n if (Array.isArray(input.json)) {\n return input.json.some(item => \n item.merged_content || \n item.scraped_content || \n item.processing_stage === 'content_merged'\n );\n }\n \n // Handle direct object\n return input.json.merged_content || \n input.json.scraped_content || \n input.json.processing_stage === 'content_merged';\n});\n\nif (scrapedInput) {\n console.log(\"Found Scraped Content\");\n \n let scrapedData;\n if (Array.isArray(scrapedInput.json)) {\n // Find the scraped data in the array\n scrapedData = scrapedInput.json.find(item => \n item.merged_content || item.scraped_content || item.processing_stage === 'content_merged'\n ) || scrapedInput.json[0]; // fallback to first item if structure is different\n } else {\n scrapedData = scrapedInput.json;\n }\n \n if (scrapedData) {\n console.log(\"Processing Scraped Content:\", Object.keys(scrapedData).slice(0, 10));\n \n // Use either scraped_content or merged_content\n processedData.scraped_content = scrapedData.scraped_content || scrapedData.merged_content || '';\n \n // Handle URLs from various sources\n if (scrapedData.scraped_urls && Array.isArray(scrapedData.scraped_urls)) {\n processedData.scraped_urls = scrapedData.scraped_urls;\n } else if (scrapedData.source_url) {\n processedData.scraped_urls = scrapedData.source_url.split(', ').filter(url => url.trim());\n } else if (scrapedData.metadata_urls) {\n processedData.scraped_urls = Array.isArray(scrapedData.metadata_urls) ? \n scrapedData.metadata_urls : [scrapedData.metadata_urls];\n } else {\n processedData.scraped_urls = [];\n }\n \n processedData.successful_scrapes = scrapedData.scraping_success !== false ? processedData.scraped_urls.length : 0;\n processedData.total_scraped_urls = processedData.scraped_urls.length;\n processedData.scraped_summary = `Successfully scraped ${processedData.successful_scrapes} URLs`;\n \n if (scrapedData.scraping_success !== false && processedData.scraped_urls.length > 0) {\n processedData.content_sources.push(`Web Scraping (${processedData.scraped_urls.length} URLs)`);\n } else {\n processedData.content_sources.push('Web Scraping (Failed)');\n }\n processedData.routes_taken.push('URL Processing');\n }\n}\n\n// Input 3: Brave Search Results (look for web.results)\nconst searchInput = allInputs.find(input => {\n if (!input.json) return false;\n \n // Handle array structure\n if (Array.isArray(input.json)) {\n return input.json.some(item => item.web && item.web.results);\n }\n \n // Handle direct object\n return input.json.web && input.json.web.results;\n});\n\nif (searchInput) {\n console.log(\"Found Brave Search Results\");\n \n let searchData;\n if (Array.isArray(searchInput.json)) {\n searchData = searchInput.json.find(item => item.web && item.web.results);\n } else {\n searchData = searchInput.json;\n }\n \n if (searchData) {\n console.log(\"Processing Brave Search Results\");\n \n processedData.brave_search_performed = true;\n processedData.brave_search_query = searchData.query || processedData.topics.join(' ');\n \n if (searchData.web.results && searchData.web.results.length > 0) {\n const formattedResults = searchData.web.results.slice(0, 5).map((result, index) => {\n return [\n `**Result ${index + 1}:**`,\n `Title: ${result.title}`,\n `URL: ${result.url}`,\n `Description: ${result.description || 'No description available'}`,\n result.age ? `Published: ${result.age}` : ''\n ].filter(line => line).join('\\n');\n }).join('\\n\\n');\n \n processedData.brave_search_results = formattedResults;\n processedData.content_sources.push(`Brave Search (${searchData.web.results.length} results)`);\n }\n processedData.routes_taken.push('Topic Search');\n }\n}\n\n// Input 4: Content Router False route (look for bypass_reason or similar markers)\nconst routerInput = allInputs.find(input => {\n if (!input.json) return false;\n \n // Handle array structure\n if (Array.isArray(input.json)) {\n return input.json.some(item => \n item.bypass_reason || \n item.route_taken === 'false' || \n item.processing_stage === 'bypassed'\n );\n }\n \n // Handle direct object\n return input.json.bypass_reason || \n input.json.route_taken === 'false' ||\n input.json.processing_stage === 'bypassed';\n});\n\nif (routerInput) {\n console.log(\"Found Content Router False route\");\n \n let routerData;\n if (Array.isArray(routerInput.json)) {\n routerData = routerInput.json.find(item => \n item.bypass_reason || item.route_taken === 'false' || item.processing_stage === 'bypassed'\n );\n } else {\n routerData = routerInput.json;\n }\n \n if (routerData) {\n processedData.routes_taken.push('Content Router (False)');\n if (routerData.bypass_reason) {\n processedData.bypass_reason = routerData.bypass_reason;\n }\n }\n}\n\n// Build the final merged content for LLM\nlet llmContent = [];\nlet sectionCount = 0;\n\n// Add processing instructions if available\nif (processedData.processing_instructions) {\n llmContent.push(`## PROCESSING INSTRUCTIONS\\n${processedData.processing_instructions}`);\n sectionCount++;\n}\n\n// Add original content if provided\nif (processedData.content) {\n llmContent.push(`## ORIGINAL CONTENT TO ENHANCE\\n${processedData.content}`);\n sectionCount++;\n}\n\n// Add topics if provided\nif (processedData.topics && processedData.topics.length > 0) {\n const topicsText = Array.isArray(processedData.topics) ? \n processedData.topics.filter(topic => topic).join('\\n- ') : \n processedData.topics;\n llmContent.push(`## TOPICS TO COVER\\n- ${topicsText}`);\n sectionCount++;\n}\n\n// Add scraped content with source attribution\nif (processedData.scraped_content) {\n llmContent.push(`## WEB CONTENT (Scraped from URLs)\\n${processedData.scraped_content}`);\n sectionCount++;\n}\n\n// Add Brave search results\nif (processedData.brave_search_results) {\n llmContent.push(`## SEARCH RESULTS (Latest Information)\\n${processedData.brave_search_results}`);\n sectionCount++;\n}\n\n// Create context summary for LLM\nconst contextSummary = [\n `Input Type: ${processedData.input_type || 'Not specified'}`,\n `Routes Processed: ${processedData.routes_taken.join(', ')}`,\n `Content Sources: ${processedData.content_sources.join(', ') || 'None'}`,\n `Sections Available: ${sectionCount}`\n].join('\\n');\n\n// Add context summary at the beginning\nif (sectionCount > 0) {\n processedData.merged_content_for_llm = [\n `## CONTEXT SUMMARY\\n${contextSummary}`,\n ...llmContent\n ].join('\\n\\n---\\n\\n');\n} else {\n // Fallback content if no data was gathered\n if (processedData.topics && processedData.topics.length > 0) {\n const topicsText = Array.isArray(processedData.topics) ? \n processedData.topics.filter(topic => topic).join('\\n- ') : \n processedData.topics;\n processedData.merged_content_for_llm = `Please generate content about the following topics:\\n- ${topicsText}`;\n processedData.content_sources.push('Topic-based Generation Request');\n } else if (processedData.content) {\n processedData.merged_content_for_llm = `Please enhance and format the following content:\\n\\n${processedData.content}`;\n processedData.content_sources.push('Content Enhancement Request');\n } else {\n processedData.merged_content_for_llm = 'Please generate relevant LinkedIn content based on current trends.';\n processedData.content_sources.push('General Generation Request');\n }\n}\n\n// Add processing statistics\nprocessedData.scraping_success_rate = processedData.total_scraped_urls > 0 ? \n `${((processedData.successful_scrapes / processedData.total_scraped_urls) * 100).toFixed(1)}%` : 'N/A';\n\n// Log final summary\nconsole.log(\"=== PROCESSING COMPLETE ===\");\nconsole.log(\"Routes taken:\", processedData.routes_taken);\nconsole.log(\"Content sources used:\", processedData.content_sources);\nconsole.log(\"Total content length:\", processedData.merged_content_for_llm.length, \"characters\");\nconsole.log(\"Sections included:\", sectionCount);\nconsole.log(\"Processing summary:\", {\n totalInputs: allInputs.length,\n routesTaken: processedData.routes_taken.length,\n contentSources: processedData.content_sources.length,\n hasScrapedContent: !!processedData.scraped_content,\n hasSearchResults: !!processedData.brave_search_results,\n finalContentLength: processedData.merged_content_for_llm.length\n});\n\nreturn { json: processedData };"
},
"executeOnce": false,
"typeVersion": 2,
"alwaysOutputData": false
},
{
"id": "79324d69-6cc4-4f3f-a398-c5a8e7478d93",
"name": "Prévisualisation du Formatage",
"type": "n8n-nodes-base.code",
"position": [
1744,
-96
],
"parameters": {
"mode": "runOnceForEachItem",
"jsCode": "// Parse Gemini response and format preview\nlet generatedPost;\ntry {\n const responseText = $input.item.json.text;\n const jsonMatch = responseText.match(/\\{[\\s\\S]*\\}/); // Find JSON in response\n \n if (jsonMatch) {\n generatedPost = JSON.parse(jsonMatch[0]);\n } else {\n // Fallback if JSON parsing fails\n generatedPost = {\n post_content: responseText,\n hashtags: ['#LinkedIn', '#Professional'],\n character_count: responseText.length,\n hook: responseText.substring(0, 50),\n cta: 'What do you think?',\n key_points: ['Generated content']\n };\n }\n} catch (error) {\n // Ultimate fallback\n generatedPost = {\n post_content: $input.item.json.text || 'Content generation failed',\n hashtags: ['#LinkedIn'],\n character_count: ($input.item.json.text || '').length,\n hook: 'Content preview',\n cta: 'Please try again',\n key_points: ['Error in generation']\n };\n}\n\n// Create preview text\nconst preview = `📝 **LinkedIn Post Preview**\n━━━━━━━━━━━━━━━━━━━━\n\n${generatedPost.post_content}\n\n━━━━━━━━━━━━━━━━━━━━\n📊 **Post Analytics:**\n• Characters: ${generatedPost.character_count}/2800\n• Hashtags: ${generatedPost.hashtags.join(', ')}\n• Hook: \"${generatedPost.hook.substring(0, 50)}...\"\n\n🎯 **Key Points:**\n${generatedPost.key_points.map(p => '• ' + p).join('\\n')}\n\n━━━━━━━━━━━━━━━━━━━━\n**Choose an action:**`;\n\nreturn {\n json: {\n ...$input.item.json,\n ...generatedPost,\n preview_text: preview,\n approval_pending: true,\n generation_timestamp: new Date().toISOString()\n }\n};"
},
"typeVersion": 2
},
{
"id": "7642abfa-80a4-4254-808d-8eafd3aa3d75",
"name": "Envoyer l'Aperçu à Telegram",
"type": "n8n-nodes-base.telegram",
"position": [
1968,
-96
],
"webhookId": "db5637e5-c376-4926-8416-dbaa1be9f796",
"parameters": {
"text": "={{ $json.preview_text }}",
"chatId": "={{ $('Merge Content Sources').item.json.chat_id }}",
"replyMarkup": "inlineKeyboard",
"inlineKeyboard": {
"rows": [
{
"row": {
"buttons": [
{
"text": "Approve",
"additionalFields": {
"callback_data": "=approve_{{ $('Merge Content Sources').item.json.post_id || $json.post_id || 'default' }}"
}
},
{
"text": "Edit",
"additionalFields": {
"callback_data": "=edit_{{ $('Merge Content Sources').item.json.post_id || $json.post_id || 'default' }}"
}
}
]
}
},
{
"row": {
"buttons": [
{
"text": "Reject",
"additionalFields": {
"callback_data": "=reject_{{ $('Merge Content Sources').item.json.post_id || $json.post_id || 'default' }}"
}
}
]
}
}
]
},
"additionalFields": {
"parse_mode": "HTML",
"reply_to_message_id": "={{ $('Merge Content Sources').item.json.message_id }}"
}
},
"credentials": {
"telegramApi": {
"id": "M9h9AMg2S3J0VkNB",
"name": "Telegram account"
}
},
"typeVersion": 1.2,
"alwaysOutputData": true
},
{
"id": "04db5e51-3a5f-4817-80d9-135a1164db3e",
"name": "Condition Si",
"type": "n8n-nodes-base.if",
"position": [
496,
-144
],
"parameters": {
"options": {},
"conditions": {
"options": {
"version": 2,
"leftValue": "",
"caseSensitive": true,
"typeValidation": "strict"
},
"combinator": "and",
"conditions": [
{
"id": "de6e0737-7f17-4336-92d2-a71c5bca8131",
"operator": {
"type": "array",
"operation": "notEmpty",
"singleValue": true
},
"leftValue": "={{ $json.output.topics }}",
"rightValue": ""
}
]
}
},
"typeVersion": 2.2
},
{
"id": "6f882b2f-c990-451f-ba17-015d992c4636",
"name": "Publication LinkedIn Initiale",
"type": "@n8n/n8n-nodes-langchain.chainLlm",
"position": [
1392,
-96
],
"parameters": {
"text": "=",
"batching": {},
"messages": {
"messageValues": [
{
"message": "=You are an expert LinkedIn content creator specializing in professional development and technology trends. Generate engaging, informative LinkedIn posts that provide genuine value to a professional audience.\n\nCONTENT REQUIREMENTS:\n\n-Start with a compelling, attention-grabbing hook related to the actual content\n-Provide specific, actionable insights directly from the source material\n-Include relevant statistics, data points, or key findings when available\n-Use short paragraphs (2-3 lines max) with line breaks for mobile readability\n-Write in third person perspective unless specified to use first person\n-Include 3-5 highly relevant hashtags aligned with the content topic\n-End with a meaningful call-to-action that encourages engagement\n-Keep content within 2800 characters maximum\n-Use 1-3 emojis strategically for emphasis, not decoration\n\nSOURCE ATTRIBUTION RULES:\n\n-If input_type contains \"URL\": Include \"Source: [URL]\" at the end before hashtags\n-If multiple URLs: List as \"Sources: [URL1], [URL2]\"\n-If content comes from web scraping: Extract and reference the actual article title and publication\n-Make it clear that insights are \"based on\" or \"according to\" the source\n\nCONTENT TONE:\n\n-Professional yet conversational and approachable\n-Authoritative but not preachy\n-Enthusiastic and focused on providing valuable insights\n-Credible while maintaining relatability\n\nTARGET AUDIENCE:\n\n-Industry professionals\n-Thought leaders\n-Individuals focused on career growth and staying current with industry trends\n\nCONTENT STRUCTURE:\n\n-Hook: 1-2 sentences that grab attention\n-Key insights or main content: 3-4 short paragraphs\n-Application or takeaway: 1-2 sentences\n-Call-to-action question to drive engagement\n-Source attribution (if applicable)\n-Hashtags\n\nEXAMPLES OF STRONG HOOKS:\n\n-The [industry/topic] landscape is shifting faster than ever…\n-Just discovered a comprehensive guide that could change how professionals approach [topic]…\n-The numbers don’t lie: [specific statistic] shows that [insight]…\n-[Surprising fact or trend] is reshaping [industry/field]…\n\nOUTPUT FORMAT: Return ONLY a JSON object with the following structure:\n{\n\"post_content\": \"the complete post including source attribution and hashtags\",\n\"hashtags\": [\"hashtag1\", \"hashtag2\", \"hashtag3\"],\n\"character_count\": 1234,\n\"hook\": \"the opening line that grabs attention\",\n\"cta\": \"the call-to-action question\",\n\"key_points\": [\"specific insight 1\", \"specific insight 2\", \"specific insight 3\"],\n\"source_urls\": [\"url1\", \"url2\"] // if applicable\n}\n\nBased on the following information, create a LinkedIn post that transforms the source content into engaging, valuable insights for your professional network:"
},
{
"type": "HumanMessagePromptTemplate",
"message": "=Input Type: {{ $json.input_type }}\nURLS: {{ $json.scraped_urls }}\nTopics: {{ $json.topics }} \nProcessing Instructions: {{ $json.processing_instructions }} \nScraped Content: {{ $json.scraped_content }}\nSearch Results: {{ $json.brave_search_results }}"
}
]
},
"promptType": "define"
},
"executeOnce": true,
"typeVersion": 1.7
},
{
"id": "ab0a005e-b926-49f7-93bc-4de5e3d5c011",
"name": "Extraire le contenu d'une URL",
"type": "@mendable/n8n-nodes-firecrawl.firecrawl",
"position": [
720,
-528
],
"parameters": {
"url": "={{ $json.current_url }}",
"operation": "scrape",
"scrapeOptions": {
"options": {
"headers": {}
}
},
"requestOptions": {}
},
"credentials": {
"firecrawlApi": {
"id": "dYaNt7iSC4jgmuK5",
"name": "Firecrawl account"
}
},
"typeVersion": 1
},
{
"id": "e5f7a21a-1dbc-4e2e-8f84-de06d87adaf3",
"name": "Condition Si1",
"type": "n8n-nodes-base.if",
"position": [
48,
-464
],
"parameters": {
"options": {},
"conditions": {
"options": {
"version": 2,
"leftValue": "",
"caseSensitive": true,
"typeValidation": "strict"
},
"combinator": "and",
"conditions": [
{
"id": "6cc58f5a-cc9b-4698-8bfe-3a8a08394cb5",
"operator": {
"type": "string",
"operation": "contains"
},
"leftValue": "={{ $json.input_type }}",
"rightValue": "URL"
}
]
}
},
"typeVersion": 2.2
},
{
"id": "784ae37f-d98c-46be-9cc0-f7abab2d7aaf",
"name": "Fusionner",
"type": "n8n-nodes-base.merge",
"position": [
944,
-128
],
"parameters": {
"numberInputs": 4
},
"typeVersion": 3.2
},
{
"id": "a7b81e78-6e44-4e2c-a96c-f4be302f8667",
"name": "Mettre à jour une ligne dans la feuille",
"type": "n8n-nodes-base.googleSheets",
"position": [
2192,
-96
],
"parameters": {
"columns": {
"value": {
"post_id": "={{ $('Merge Content Sources').item.json.post_id }}",
"timestamp": "={{ $('Merge Content Sources').item.json.processing_timestamp }}",
"hashtags_used": "={{ $('Format Preview').item.json.hashtags }}",
"extracted_urls": "={{ $('Merge Content Sources').item.json.urls }}",
"search_queries": "={{ $('Merge Content Sources').item.json.brave_search_query }}",
"character_count": "={{ $('Format Preview').item.json.character_count }}",
"content_sources": "={{ $('Merge Content Sources').item.json.content_sources }}",
"identified_topics": "={{ $('Merge Content Sources').item.json.topics }}",
"final_approved_post": "={{ $('Format Preview').item.json.post_content }}",
"initial_generated_post": "={{ $('Format Preview').item.json.post_content }}",
"search_results_summary": "={{ $('Merge Content Sources').item.json.brave_search_results }}",
"scraped_content_summary": "={{ $('Merge Content Sources').item.json.scraped_summary }}"
},
"schema": [
{
"id": "post_id",
"type": "string",
"display": true,
"removed": false,
"required": false,
"displayName": "post_id",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "timestamp",
"type": "string",
"display": true,
"required": false,
"displayName": "timestamp",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "user_id",
"type": "string",
"display": true,
"required": false,
"displayName": "user_id",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "user_name",
"type": "string",
"display": true,
"required": false,
"displayName": "user_name",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "input_type",
"type": "string",
"display": true,
"required": false,
"displayName": "input_type",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "original_message",
"type": "string",
"display": true,
"required": false,
"displayName": "original_message",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "extracted_urls",
"type": "string",
"display": true,
"required": false,
"displayName": "extracted_urls",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "identified_topics",
"type": "string",
"display": true,
"required": false,
"displayName": "identified_topics",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "search_queries",
"type": "string",
"display": true,
"required": false,
"displayName": "search_queries",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "search_results_summary",
"type": "string",
"display": true,
"required": false,
"displayName": "search_results_summary",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "scraped_content_summary",
"type": "string",
"display": true,
"required": false,
"displayName": "scraped_content_summary",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "content_sources",
"type": "string",
"display": true,
"required": false,
"displayName": "content_sources",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "initial_generated_post",
"type": "string",
"display": true,
"required": false,
"displayName": "initial_generated_post",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "final_approved_post",
"type": "string",
"display": true,
"required": false,
"displayName": "final_approved_post",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "hashtags_used",
"type": "string",
"display": true,
"required": false,
"displayName": "hashtags_used",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "character_count",
"type": "string",
"display": true,
"required": false,
"displayName": "character_count",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "has_media",
"type": "string",
"display": true,
"required": false,
"displayName": "has_media",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "media_urls",
"type": "string",
"display": true,
"required": false,
"displayName": "media_urls",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "approval_status",
"type": "string",
"display": true,
"removed": true,
"required": false,
"displayName": "approval_status",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "rejection_reason",
"type": "string",
"display": true,
"required": false,
"displayName": "rejection_reason",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "edit_iterations",
"type": "string",
"display": true,
"required": false,
"displayName": "edit_iterations",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "time_to_approval",
"type": "string",
"display": true,
"required": false,
"displayName": "time_to_approval",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "posted_datetime",
"type": "string",
"display": true,
"required": false,
"displayName": "posted_datetime",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "scheduled_time",
"type": "string",
"display": true,
"required": false,
"displayName": "scheduled_time",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "linkedin_post_url",
"type": "string",
"display": true,
"required": false,
"displayName": "linkedin_post_url",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "post_type",
"type": "string",
"display": true,
"required": false,
"displayName": "post_type",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "impressions_1h",
"type": "string",
"display": true,
"required": false,
"displayName": "impressions_1h",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "impressions_24h",
"type": "string",
"display": true,
"required": false,
"displayName": "impressions_24h",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "impressions_7d",
"type": "string",
"display": true,
"required": false,
"displayName": "impressions_7d",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "impressions_30d",
"type": "string",
"display": true,
"required": false,
"displayName": "impressions_30d",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "reactions_total",
"type": "string",
"display": true,
"required": false,
"displayName": "reactions_total",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "likes",
"type": "string",
"display": true,
"required": false,
"displayName": "likes",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "celebrates",
"type": "string",
"display": true,
"required": false,
"displayName": "celebrates",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "loves",
"type": "string",
"display": true,
"required": false,
"displayName": "loves",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "comments_total",
"type": "string",
"display": true,
"required": false,
"displayName": "comments_total",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "shares_total",
"type": "string",
"display": true,
"required": false,
"displayName": "shares_total",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "clicks_total",
"type": "string",
"display": true,
"required": false,
"displayName": "clicks_total",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "engagement_rate",
"type": "string",
"display": true,
"required": false,
"displayName": "engagement_rate",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "viral_score",
"type": "string",
"display": true,
"required": false,
"displayName": "viral_score",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "follower_growth",
"type": "string",
"display": true,
"required": false,
"displayName": "follower_growth",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "performance_tier",
"type": "string",
"display": true,
"required": false,
"displayName": "performance_tier",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "last_metrics_update",
"type": "string",
"display": true,
"required": false,
"displayName": "last_metrics_update",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "engagement_rate",
"type": "string",
"display": true,
"required": false,
"displayName": "engagement_rate",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "approval_status",
"type": "string",
"display": true,
"required": false,
"displayName": "approval_status",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "row_number",
"type": "number",
"display": true,
"removed": true,
"readOnly": true,
"required": false,
"displayName": "row_number",
"defaultMatch": false,
"canBeUsedToMatch": true
}
],
"mappingMode": "defineBelow",
"matchingColumns": [
"post_id"
],
"attemptToConvertTypes": false,
"convertFieldsToString": false
},
"options": {},
"operation": "update",
"sheetName": {
"__rl": true,
"mode": "list",
"value": "gid=0",
"cachedResultUrl": "https://docs.google.com/spreadsheets/d/1RvHyWEvEZR5etmq1KfzTOkSIXY5tUT5TLVgDSUfAr5c/edit#gid=0",
"cachedResultName": "Posts_Master"
},
"documentId": {
"__rl": true,
"mode": "list",
"value": "1RvHyWEvEZR5etmq1KfzTOkSIXY5tUT5TLVgDSUfAr5c",
"cachedResultUrl": "https://docs.google.com/spreadsheets/d/1RvHyWEvEZR5etmq1KfzTOkSIXY5tUT5TLVgDSUfAr5c/edit?usp=drivesdk",
"cachedResultName": "LinekedIn Posts"
}
},
"credentials": {
"googleSheetsOAuth2Api": {
"id": "ExnZpB5bwFQ3gQ5N",
"name": "Google Sheets account 2"
}
},
"typeVersion": 4.7
},
{
"id": "5c8b4551-ba7e-4cf1-8a97-479e3727d728",
"name": "Traiter le Callback",
"type": "n8n-nodes-base.code",
"position": [
-2096,
672
],
"parameters": {
"jsCode": "// Process callback query and determine action\nconst rawCallbackData = $input.item.json.callback_query.data;\nconsole.log('Raw callback data:', rawCallbackData);\n\n// Remove surrounding quotes and clean the callback data\nlet callbackData = rawCallbackData;\nif (typeof callbackData === 'string') {\n // Remove surrounding quotes (both single and double)\n callbackData = callbackData.replace(/^[\"']+|[\"']+$/g, '');\n // Remove any remaining quotes inside\n callbackData = callbackData.replace(/[\"']/g, '');\n}\n\nconsole.log('Cleaned callback data:', callbackData);\nconst [action, postId_1,postId_2] = callbackData.split('_');\nconst postId = postId_1 + '_' + postId_2\nconst queryId = $input.item.json.callback_query.id;\nconst userId = $input.item.json.callback_query.from.id;\nconst messageId = $input.item.json.callback_query.message.message_id;\nconst chatId = $input.item.json.callback_query.message.chat.id;\nconst userName = $input.item.json.callback_query.from.first_name || 'User';\n\n// Get original post content from message text\nconst originalText = $input.item.json.callback_query.message.text;\n\n// Extract just the post content (remove any previous instructions)\nconst contentLines = originalText.split('\\n');\nlet postContent = '';\nfor (let line of contentLines) {\n if (line.includes('📋') || line.includes('Actions:') || line.includes('👆')) {\n break;\n }\n postContent += line + '\\n';\n}\npostContent = postContent.trim();\n\nlet response = {\n post_id: postId || 'default',\n action: action,\n queryId:queryId,\n user_id: userId,\n chat_id: chatId,\n message_id: messageId,\n user_name: userName,\n original_content: postContent,\n timestamp: new Date().toISOString()\n};\n\nswitch(action) {\n case 'approve':\n response.status = 'approved';\n response.next_step = 'publish';\n response.linkedin_content = postContent;\n response.message = `✅ Post approved by ${userName}! Publishing to LinkedIn...`;\n break;\n \n case 'edit':\n response.status = 'editing';\n response.next_step = 'rewrite';\n response.edit_instruction = 'Please improve this post by making it more engaging, professional, and LinkedIn-appropriate. Keep the core message but enhance the tone and structure.';\n response.message = `✏️ ${userName} requested edits. Rewriting with Gemini...`;\n break;\n \n case 'reject':\n response.status = 'rejected';\n response.next_step = 'complete';\n response.message = `❌ Post rejected by ${userName}.`;\n break;\n \n case 'regenerate':\n response.status = 'regenerating';\n response.next_step = 'regenerate';\n response.regenerate_prompt = 'Create a completely new LinkedIn post on the same topic with a fresh perspective and different approach.';\n response.message = `🔄 ${userName} requested regeneration. Creating new version...`;\n break;\n \n case 'schedule':\n response.status = 'scheduling';\n response.next_step = 'request_schedule_time';\n response.linkedin_content = postContent;\n response.message = `⏰ ${userName} wants to schedule this post. When would you like it published?\\n\\nExamples:\\n• \"tomorrow 9am\"\\n• \"2024-12-25 14:30\"\\n• \"next monday 10:00\"`;\n break;\n \n default:\n response.status = 'error';\n response.message = '❓ Unknown action.';\n}\n\nreturn { json: response };"
},
"typeVersion": 2
},
{
"id": "e97c3e0d-218c-4e7b-befb-ff68e8a7edf6",
"name": "Router les Actions",
"type": "n8n-nodes-base.switch",
"position": [
-1648,
656
],
"parameters": {
"rules": {
"values": [
{
"conditions": {
"options": {
"version": 1,
"leftValue": "",
"caseSensitive": false,
"typeValidation": "strict"
},
"combinator": "and",
"conditions": [
{
"id": "45e826e8-9f56-4ab9-a373-451c8175849d",
"operator": {
"type": "string",
"operation": "equals"
},
"leftValue": "={{ $('Process Callback').item.json.action }}",
"rightValue": "approve"
}
]
}
},
{
"conditions": {
"options": {
"version": 1,
"leftValue": "",
"caseSensitive": false,
"typeValidation": "strict"
},
"combinator": "and",
"conditions": [
{
"id": "69c0bb23-fbec-4659-ae7b-c6a31499c946",
"operator": {
"type": "string",
"operation": "equals"
},
"leftValue": "={{ $('Process Callback').item.json.action }}",
"rightValue": "edit"
}
]
}
},
{
"conditions": {
"options": {
"version": 1,
"leftValue": "",
"caseSensitive": false,
"typeValidation": "strict"
},
"combinator": "and",
"conditions": [
{
"id": "4268d714-1ad7-41e3-9003-6261ffb5e61f",
"operator": {
"name": "filter.operator.equals",
"type": "string",
"operation": "equals"
},
"leftValue": "={{ $('Process Callback').item.json.action }}",
"rightValue": "reject"
}
]
}
}
]
},
"options": {
"ignoreCase": true
}
},
"typeVersion": 3,
"alwaysOutputData": false
},
{
"id": "211f2430-b7fc-47d7-8fb3-6353a1e9779a",
"name": "Envoyer le Statut (Approuver)",
"type": "n8n-nodes-base.telegram",
"position": [
-1120,
480
],
"webhookId": "a4e1e719-2120-4877-b087-a900797b2b7d",
"parameters": {
"text": "Approved the post and ready to post to linkedIn",
"chatId": "={{ $('Process Callback').item.json.chat_id }}",
"forceReply": {},
"replyMarkup": "forceReply",
"additionalFields": {
"parse_mode": "HTML"
}
},
"credentials": {
"telegramApi": {
"id": "M9h9AMg2S3J0VkNB",
"name": "Telegram account"
}
},
"typeVersion": 1.2
},
{
"id": "95a591bc-7533-445f-abc0-1cb60e76ec48",
"name": "Confirmer la Publication",
"type": "n8n-nodes-base.telegram",
"position": [
-96,
480
],
"webhookId": "89ab4048-4f71-4431-b9dd-0da3b05aa318",
"parameters": {
"text": "=🎉 Post Published Successfully!\n✅ Your LinkedIn post is now live\n{{ $json.urn }}\n📊 Engagement tracking enabled",
"chatId": "={{ $('Process Callback').item.json.chat_id }}",
"additionalFields": {
"parse_mode": "HTML"
}
},
"credentials": {
"telegramApi": {
"id": "M9h9AMg2S3J0VkNB",
"name": "Telegram account"
}
},
"typeVersion": 1.2
},
{
"id": "5c10dc1d-2964-4089-8222-25dc69b09f9d",
"name": "Traiter la Réécriture",
"type": "n8n-nodes-base.code",
"position": [
-528,
1280
],
"parameters": {
"jsCode": "// Process the rewritten content and prepare for approval\nconst rewrittenContent = $input.item.json.text || $input.item.json.response;\nconst originalData = $('Process Callback').item.json;\n\nreturn {\n json: {\n ...originalData,\n rewritten_content: rewrittenContent,\n status: 'rewritten',\n message: `✏️ <b>Post Rewritten!</b>\\n\\n<i>Here's the improved version:</i>\\n\\n${rewrittenContent}\\n\\n<b>📋 Actions:</b>`,\n linkedin_content: rewrittenContent\n }\n};"
},
"typeVersion": 2
},
{
"id": "3970d4b0-8d13-4854-9eb5-62db19484b81",
"name": "Envoyer la Réécriture pour Validation",
"type": "n8n-nodes-base.telegram",
"position": [
32,
1280
],
"webhookId": "033e2a7d-8f5a-44a4-bf61-e5d5b278775a",
"parameters": {
"text": "={{ $json.final_approved_post }}",
"chatId": "={{ $('Process Callback').item.json.chat_id }}",
"replyMarkup": "inlineKeyboard",
"inlineKeyboard": {
"rows": [
{
"row": {
"buttons": [
{
"text": "✅ Approve Rewrite",
"additionalFields": {
"callback_data": "=approve_{{ $json.post_id }}"
}
},
{
"text": "✏️ Edit Again",
"additionalFields": {
"callback_data": "=edit_{{ $json.post_id }}"
}
}
]
}
},
{
"row": {
"buttons": [
{
"text": "❌ Reject",
"additionalFields": {
"callback_data": "=reject_{{ $json.post_id }}"
}
}
]
}
}
]
},
"additionalFields": {
"parse_mode": "HTML"
}
},
"credentials": {
"telegramApi": {
"id": "M9h9AMg2S3J0VkNB",
"name": "Telegram account"
}
},
"typeVersion": 1.2
},
{
"id": "cfb82bd5-01a6-48dd-b6ea-293909b44d84",
"name": "Envoyer le Rejet",
"type": "n8n-nodes-base.telegram",
"position": [
-1216,
1584
],
"webhookId": "5d999c74-deb2-47d3-aa36-bf994e17d9f1",
"parameters": {
"text": "LinkedIn post has been rejected.",
"chatId": "={{ $('Switch').item.json.callback_query.message.chat.id }}",
"additionalFields": {
"parse_mode": "HTML"
}
},
"credentials": {
"telegramApi": {
"id": "M9h9AMg2S3J0VkNB",
"name": "Telegram account"
}
},
"typeVersion": 1.2
},
{
"id": "d21a09c5-dbf8-488e-9197-d32baa9e43df",
"name": "Répondre à une requête callback",
"type": "n8n-nodes-base.telegram",
"onError": "continueRegularOutput",
"position": [
-1872,
672
],
"webhookId": "56d17f3a-fa25-4615-bfe8-4e802f1ef3d2",
"parameters": {
"queryId": "={{ $json.queryId }}",
"resource": "callback",
"additionalFields": {
"text": "Processing your action..",
"show_alert": true
}
},
"credentials": {
"telegramApi": {
"id": "M9h9AMg2S3J0VkNB",
"name": "Telegram account"
}
},
"notesInFlow": false,
"typeVersion": 1.2
},
{
"id": "5808faa3-e584-4014-b476-4da1750bcdc9",
"name": "Envoyer un message et attendre la réponse",
"type": "n8n-nodes-base.telegram",
"position": [
-1216,
1280
],
"webhookId": "524bdf9a-82a3-4186-8a39-52f66f678b84",
"parameters": {
"chatId": "={{ $('Switch').item.json.callback_query.message.chat.id }}",
"message": "=Please add the instructions",
"options": {
"responseFormTitle": "Edit Instructions",
"messageButtonLabel": "Submit"
},
"operation": "sendAndWait",
"responseType": "freeText"
},
"credentials": {
"telegramApi": {
"id": "M9h9AMg2S3J0VkNB",
"name": "Telegram account"
}
},
"typeVersion": 1.2,
"alwaysOutputData": false
},
{
"id": "50cb382e-6d1f-458a-8cc4-57ee8d29fbca",
"name": "Créer une publication",
"type": "n8n-nodes-base.linkedIn",
"position": [
-432,
480
],
"parameters": {
"text": "={{ $json.final_approved_post }}",
"person": "2pXvRPsqOC",
"additionalFields": {
"visibility": "PUBLIC"
}
},
"credentials": {
"linkedInOAuth2Api": {
"id": "DPSxvNjFSB0jGoB0",
"name": "LinkedIn account"
}
},
"typeVersion": 1
},
{
"id": "f83aa078-06c1-4b19-82d2-eb7385609b9e",
"name": "Chaîne de Réédition",
"type": "@n8n/n8n-nodes-langchain.chainLlm",
"position": [
-992,
1184
],
"parameters": {
"text": "=Instructions: \n{{ $json.data.text }}",
"batching": {},
"messages": {
"messageValues": [
{
"message": "=You are a professional LinkedIn content writer. Rewrite the following post to make it more engaging, professional, and suitable for LinkedIn as per the user's instructions.\n\nCONTENT REQUIREMENTS:\n\nDeliver only the rewritten LinkedIn post content, without additional commentary or formatting.\n\nOutput should be in plain text, not markdown.\n\nStructure content for mobile readability with short paragraphs (2-3 lines).\n\nUse a compelling opening line that grabs attention.\n\nMake the content conversational yet professional, authoritative but approachable.\n\nInclude clear, actionable insights or takeaways.\n\nEnsure flow with smooth transitions between ideas.\n\nEnd with a meaningful call-to-action that encourages engagement.\n\nUse emojis sparingly (1-3 maximum) only for emphasis.\n\nIncorporate relevant hashtags (3-5) to increase reach.\n\nDo not exceed 2800 characters.\n\nINSTRUCTIONS:\n\nRewrite only the LinkedIn post section provided.\n\nDo not include explanations, notes, or additional commentary.\n\nMaintain third person perspective unless first person is explicitly requested."
},
{
"type": "HumanMessagePromptTemplate",
"message": "=Original Post: \n{{ $('Switch').item.json.callback_query.message.text }}\n"
}
]
},
"promptType": "define"
},
"typeVersion": 1.7
},
{
"id": "29cc76e7-c8eb-4931-91fa-1adafcbbea71",
"name": "Obtenir une/des ligne(s) dans feuille1",
"type": "n8n-nodes-base.googleSheets",
"position": [
-832,
480
],
"parameters": {
"options": {
"returnFirstMatch": true
},
"filtersUI": {
"values": [
{
"lookupValue": "={{ $('Process Callback').item.json.post_id }}",
"lookupColumn": "post_id"
}
]
},
"sheetName": {
"__rl": true,
"mode": "list",
"value": "gid=0",
"cachedResultUrl": "https://docs.google.com/spreadsheets/d/1RvHyWEvEZR5etmq1KfzTOkSIXY5tUT5TLVgDSUfAr5c/edit#gid=0",
"cachedResultName": "Posts_Master"
},
"documentId": {
"__rl": true,
"mode": "list",
"value": "1RvHyWEvEZR5etmq1KfzTOkSIXY5tUT5TLVgDSUfAr5c",
"cachedResultUrl": "https://docs.google.com/spreadsheets/d/1RvHyWEvEZR5etmq1KfzTOkSIXY5tUT5TLVgDSUfAr5c/edit?usp=drivesdk",
"cachedResultName": "LinekedIn Posts"
}
},
"credentials": {
"googleSheetsOAuth2Api": {
"id": "ExnZpB5bwFQ3gQ5N",
"name": "Google Sheets account 2"
}
},
"typeVersion": 4.7,
"alwaysOutputData": true
},
{
"id": "c6eed7a0-7e0b-49b6-8c5f-9fa27ea9b064",
"name": "Mettre à jour une ligne dans feuille1",
"type": "n8n-nodes-base.googleSheets",
"position": [
-192,
1280
],
"parameters": {
"columns": {
"value": {
"post_id": "={{ $json.post_id }}",
"final_approved_post": "={{ $json.rewritten_content }}"
},
"schema": [
{
"id": "post_id",
"type": "string",
"display": true,
"removed": false,
"required": false,
"displayName": "post_id",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "timestamp",
"type": "string",
"display": true,
"required": false,
"displayName": "timestamp",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "user_id",
"type": "string",
"display": true,
"required": false,
"displayName": "user_id",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "user_name",
"type": "string",
"display": true,
"required": false,
"displayName": "user_name",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "input_type",
"type": "string",
"display": true,
"required": false,
"displayName": "input_type",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "original_message",
"type": "string",
"display": true,
"required": false,
"displayName": "original_message",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "extracted_urls",
"type": "string",
"display": true,
"required": false,
"displayName": "extracted_urls",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "identified_topics",
"type": "string",
"display": true,
"required": false,
"displayName": "identified_topics",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "search_queries",
"type": "string",
"display": true,
"required": false,
"displayName": "search_queries",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "search_results_summary",
"type": "string",
"display": true,
"required": false,
"displayName": "search_results_summary",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "scraped_content_summary",
"type": "string",
"display": true,
"required": false,
"displayName": "scraped_content_summary",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "content_sources",
"type": "string",
"display": true,
"required": false,
"displayName": "content_sources",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "initial_generated_post",
"type": "string",
"display": true,
"required": false,
"displayName": "initial_generated_post",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "final_approved_post",
"type": "string",
"display": true,
"required": false,
"displayName": "final_approved_post",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "hashtags_used",
"type": "string",
"display": true,
"required": false,
"displayName": "hashtags_used",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "character_count",
"type": "string",
"display": true,
"required": false,
"displayName": "character_count",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "has_media",
"type": "string",
"display": true,
"required": false,
"displayName": "has_media",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "media_urls",
"type": "string",
"display": true,
"required": false,
"displayName": "media_urls",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "approval_status",
"type": "string",
"display": true,
"required": false,
"displayName": "approval_status",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "rejection_reason",
"type": "string",
"display": true,
"required": false,
"displayName": "rejection_reason",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "edit_iterations",
"type": "string",
"display": true,
"required": false,
"displayName": "edit_iterations",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "time_to_approval",
"type": "string",
"display": true,
"required": false,
"displayName": "time_to_approval",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "posted_datetime",
"type": "string",
"display": true,
"required": false,
"displayName": "posted_datetime",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "scheduled_time",
"type": "string",
"display": true,
"required": false,
"displayName": "scheduled_time",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "linkedin_post_url",
"type": "string",
"display": true,
"required": false,
"displayName": "linkedin_post_url",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "post_type",
"type": "string",
"display": true,
"required": false,
"displayName": "post_type",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "impressions_1h",
"type": "string",
"display": true,
"required": false,
"displayName": "impressions_1h",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "impressions_24h",
"type": "string",
"display": true,
"required": false,
"displayName": "impressions_24h",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "impressions_7d",
"type": "string",
"display": true,
"required": false,
"displayName": "impressions_7d",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "impressions_30d",
"type": "string",
"display": true,
"required": false,
"displayName": "impressions_30d",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "reactions_total",
"type": "string",
"display": true,
"required": false,
"displayName": "reactions_total",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "likes",
"type": "string",
"display": true,
"required": false,
"displayName": "likes",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "celebrates",
"type": "string",
"display": true,
"required": false,
"displayName": "celebrates",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "loves",
"type": "string",
"display": true,
"required": false,
"displayName": "loves",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "comments_total",
"type": "string",
"display": true,
"required": false,
"displayName": "comments_total",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "shares_total",
"type": "string",
"display": true,
"required": false,
"displayName": "shares_total",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "clicks_total",
"type": "string",
"display": true,
"required": false,
"displayName": "clicks_total",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "engagement_rate",
"type": "string",
"display": true,
"required": false,
"displayName": "engagement_rate",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "viral_score",
"type": "string",
"display": true,
"required": false,
"displayName": "viral_score",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "follower_growth",
"type": "string",
"display": true,
"required": false,
"displayName": "follower_growth",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "performance_tier",
"type": "string",
"display": true,
"required": false,
"displayName": "performance_tier",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "last_metrics_update",
"type": "string",
"display": true,
"required": false,
"displayName": "last_metrics_update",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "engagement_rate",
"type": "string",
"display": true,
"required": false,
"displayName": "engagement_rate",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "approval_status",
"type": "string",
"display": true,
"required": false,
"displayName": "approval_status",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "row_number",
"type": "number",
"display": true,
"removed": true,
"readOnly": true,
"required": false,
"displayName": "row_number",
"defaultMatch": false,
"canBeUsedToMatch": true
}
],
"mappingMode": "defineBelow",
"matchingColumns": [
"post_id"
],
"attemptToConvertTypes": false,
"convertFieldsToString": false
},
"options": {},
"operation": "update",
"sheetName": {
"__rl": true,
"mode": "list",
"value": "gid=0",
"cachedResultUrl": "https://docs.google.com/spreadsheets/d/1RvHyWEvEZR5etmq1KfzTOkSIXY5tUT5TLVgDSUfAr5c/edit#gid=0",
"cachedResultName": "Posts_Master"
},
"documentId": {
"__rl": true,
"mode": "list",
"value": "1RvHyWEvEZR5etmq1KfzTOkSIXY5tUT5TLVgDSUfAr5c",
"cachedResultUrl": "https://docs.google.com/spreadsheets/d/1RvHyWEvEZR5etmq1KfzTOkSIXY5tUT5TLVgDSUfAr5c/edit?usp=drivesdk",
"cachedResultName": "LinekedIn Posts"
}
},
"credentials": {
"googleSheetsOAuth2Api": {
"id": "ExnZpB5bwFQ3gQ5N",
"name": "Google Sheets account 2"
}
},
"typeVersion": 4.7
},
{
"id": "75e4fd6d-d628-4a5d-8f81-086239fe714e",
"name": "Mettre à jour une ligne dans feuille2",
"type": "n8n-nodes-base.googleSheets",
"position": [
-928,
1584
],
"parameters": {
"columns": {
"value": {
"post_id": "={{ $('Process Callback').item.json.post_id }}",
"approval_status": "Rejected",
"final_approved_post": "={{ $json.rewritten_content }}"
},
"schema": [
{
"id": "post_id",
"type": "string",
"display": true,
"removed": false,
"required": false,
"displayName": "post_id",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "timestamp",
"type": "string",
"display": true,
"required": false,
"displayName": "timestamp",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "user_id",
"type": "string",
"display": true,
"required": false,
"displayName": "user_id",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "user_name",
"type": "string",
"display": true,
"required": false,
"displayName": "user_name",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "input_type",
"type": "string",
"display": true,
"required": false,
"displayName": "input_type",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "original_message",
"type": "string",
"display": true,
"required": false,
"displayName": "original_message",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "extracted_urls",
"type": "string",
"display": true,
"required": false,
"displayName": "extracted_urls",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "identified_topics",
"type": "string",
"display": true,
"required": false,
"displayName": "identified_topics",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "search_queries",
"type": "string",
"display": true,
"required": false,
"displayName": "search_queries",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "search_results_summary",
"type": "string",
"display": true,
"required": false,
"displayName": "search_results_summary",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "scraped_content_summary",
"type": "string",
"display": true,
"required": false,
"displayName": "scraped_content_summary",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "content_sources",
"type": "string",
"display": true,
"required": false,
"displayName": "content_sources",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "initial_generated_post",
"type": "string",
"display": true,
"required": false,
"displayName": "initial_generated_post",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "final_approved_post",
"type": "string",
"display": true,
"required": false,
"displayName": "final_approved_post",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "hashtags_used",
"type": "string",
"display": true,
"required": false,
"displayName": "hashtags_used",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "character_count",
"type": "string",
"display": true,
"required": false,
"displayName": "character_count",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "has_media",
"type": "string",
"display": true,
"required": false,
"displayName": "has_media",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "media_urls",
"type": "string",
"display": true,
"required": false,
"displayName": "media_urls",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "approval_status",
"type": "string",
"display": true,
"required": false,
"displayName": "approval_status",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "rejection_reason",
"type": "string",
"display": true,
"required": false,
"displayName": "rejection_reason",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "edit_iterations",
"type": "string",
"display": true,
"required": false,
"displayName": "edit_iterations",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "time_to_approval",
"type": "string",
"display": true,
"required": false,
"displayName": "time_to_approval",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "posted_datetime",
"type": "string",
"display": true,
"required": false,
"displayName": "posted_datetime",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "scheduled_time",
"type": "string",
"display": true,
"required": false,
"displayName": "scheduled_time",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "linkedin_post_url",
"type": "string",
"display": true,
"required": false,
"displayName": "linkedin_post_url",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "post_type",
"type": "string",
"display": true,
"required": false,
"displayName": "post_type",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "impressions_1h",
"type": "string",
"display": true,
"required": false,
"displayName": "impressions_1h",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "impressions_24h",
"type": "string",
"display": true,
"required": false,
"displayName": "impressions_24h",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "impressions_7d",
"type": "string",
"display": true,
"required": false,
"displayName": "impressions_7d",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "impressions_30d",
"type": "string",
"display": true,
"required": false,
"displayName": "impressions_30d",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "reactions_total",
"type": "string",
"display": true,
"required": false,
"displayName": "reactions_total",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "likes",
"type": "string",
"display": true,
"required": false,
"displayName": "likes",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "celebrates",
"type": "string",
"display": true,
"required": false,
"displayName": "celebrates",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "loves",
"type": "string",
"display": true,
"required": false,
"displayName": "loves",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "comments_total",
"type": "string",
"display": true,
"required": false,
"displayName": "comments_total",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "shares_total",
"type": "string",
"display": true,
"required": false,
"displayName": "shares_total",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "clicks_total",
"type": "string",
"display": true,
"required": false,
"displayName": "clicks_total",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "engagement_rate",
"type": "string",
"display": true,
"required": false,
"displayName": "engagement_rate",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "viral_score",
"type": "string",
"display": true,
"required": false,
"displayName": "viral_score",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "follower_growth",
"type": "string",
"display": true,
"required": false,
"displayName": "follower_growth",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "performance_tier",
"type": "string",
"display": true,
"required": false,
"displayName": "performance_tier",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "last_metrics_update",
"type": "string",
"display": true,
"required": false,
"displayName": "last_metrics_update",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "engagement_rate",
"type": "string",
"display": true,
"required": false,
"displayName": "engagement_rate",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "approval_status",
"type": "string",
"display": true,
"required": false,
"displayName": "approval_status",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "row_number",
"type": "number",
"display": true,
"removed": true,
"readOnly": true,
"required": false,
"displayName": "row_number",
"defaultMatch": false,
"canBeUsedToMatch": true
}
],
"mappingMode": "defineBelow",
"matchingColumns": [
"post_id"
],
"attemptToConvertTypes": false,
"convertFieldsToString": false
},
"options": {},
"operation": "update",
"sheetName": {
"__rl": true,
"mode": "list",
"value": "gid=0",
"cachedResultUrl": "https://docs.google.com/spreadsheets/d/1RvHyWEvEZR5etmq1KfzTOkSIXY5tUT5TLVgDSUfAr5c/edit#gid=0",
"cachedResultName": "Posts_Master"
},
"documentId": {
"__rl": true,
"mode": "list",
"value": "1RvHyWEvEZR5etmq1KfzTOkSIXY5tUT5TLVgDSUfAr5c",
"cachedResultUrl": "https://docs.google.com/spreadsheets/d/1RvHyWEvEZR5etmq1KfzTOkSIXY5tUT5TLVgDSUfAr5c/edit?usp=drivesdk",
"cachedResultName": "LinekedIn Posts"
}
},
"credentials": {
"googleSheetsOAuth2Api": {
"id": "ExnZpB5bwFQ3gQ5N",
"name": "Google Sheets account 2"
}
},
"typeVersion": 4.7
},
{
"id": "d1d2ee44-33fb-4c42-b72e-d6c485b6f3ac",
"name": "Mettre à jour une ligne dans feuille3",
"type": "n8n-nodes-base.googleSheets",
"position": [
128,
480
],
"parameters": {
"columns": {
"value": {
"post_id": "={{ $('Process Callback').item.json.post_id }}",
"timestamp": "=",
"approval_status": "Approved",
"final_approved_post": "={{ $json.rewritten_content }}"
},
"schema": [
{
"id": "post_id",
"type": "string",
"display": true,
"removed": false,
"required": false,
"displayName": "post_id",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "timestamp",
"type": "string",
"display": true,
"required": false,
"displayName": "timestamp",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "user_id",
"type": "string",
"display": true,
"required": false,
"displayName": "user_id",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "user_name",
"type": "string",
"display": true,
"required": false,
"displayName": "user_name",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "input_type",
"type": "string",
"display": true,
"required": false,
"displayName": "input_type",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "original_message",
"type": "string",
"display": true,
"required": false,
"displayName": "original_message",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "extracted_urls",
"type": "string",
"display": true,
"required": false,
"displayName": "extracted_urls",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "identified_topics",
"type": "string",
"display": true,
"required": false,
"displayName": "identified_topics",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "search_queries",
"type": "string",
"display": true,
"required": false,
"displayName": "search_queries",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "search_results_summary",
"type": "string",
"display": true,
"required": false,
"displayName": "search_results_summary",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "scraped_content_summary",
"type": "string",
"display": true,
"required": false,
"displayName": "scraped_content_summary",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "content_sources",
"type": "string",
"display": true,
"required": false,
"displayName": "content_sources",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "initial_generated_post",
"type": "string",
"display": true,
"required": false,
"displayName": "initial_generated_post",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "final_approved_post",
"type": "string",
"display": true,
"required": false,
"displayName": "final_approved_post",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "hashtags_used",
"type": "string",
"display": true,
"required": false,
"displayName": "hashtags_used",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "character_count",
"type": "string",
"display": true,
"required": false,
"displayName": "character_count",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "has_media",
"type": "string",
"display": true,
"required": false,
"displayName": "has_media",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "media_urls",
"type": "string",
"display": true,
"required": false,
"displayName": "media_urls",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "approval_status",
"type": "string",
"display": true,
"required": false,
"displayName": "approval_status",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "rejection_reason",
"type": "string",
"display": true,
"required": false,
"displayName": "rejection_reason",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "edit_iterations",
"type": "string",
"display": true,
"required": false,
"displayName": "edit_iterations",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "time_to_approval",
"type": "string",
"display": true,
"required": false,
"displayName": "time_to_approval",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "posted_datetime",
"type": "string",
"display": true,
"required": false,
"displayName": "posted_datetime",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "scheduled_time",
"type": "string",
"display": true,
"required": false,
"displayName": "scheduled_time",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "linkedin_post_url",
"type": "string",
"display": true,
"required": false,
"displayName": "linkedin_post_url",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "post_type",
"type": "string",
"display": true,
"required": false,
"displayName": "post_type",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "impressions_1h",
"type": "string",
"display": true,
"required": false,
"displayName": "impressions_1h",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "impressions_24h",
"type": "string",
"display": true,
"required": false,
"displayName": "impressions_24h",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "impressions_7d",
"type": "string",
"display": true,
"required": false,
"displayName": "impressions_7d",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "impressions_30d",
"type": "string",
"display": true,
"required": false,
"displayName": "impressions_30d",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "reactions_total",
"type": "string",
"display": true,
"required": false,
"displayName": "reactions_total",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "likes",
"type": "string",
"display": true,
"required": false,
"displayName": "likes",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "celebrates",
"type": "string",
"display": true,
"required": false,
"displayName": "celebrates",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "loves",
"type": "string",
"display": true,
"required": false,
"displayName": "loves",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "comments_total",
"type": "string",
"display": true,
"required": false,
"displayName": "comments_total",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "shares_total",
"type": "string",
"display": true,
"required": false,
"displayName": "shares_total",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "clicks_total",
"type": "string",
"display": true,
"required": false,
"displayName": "clicks_total",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "engagement_rate",
"type": "string",
"display": true,
"required": false,
"displayName": "engagement_rate",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "viral_score",
"type": "string",
"display": true,
"required": false,
"displayName": "viral_score",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "follower_growth",
"type": "string",
"display": true,
"required": false,
"displayName": "follower_growth",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "performance_tier",
"type": "string",
"display": true,
"required": false,
"displayName": "performance_tier",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "last_metrics_update",
"type": "string",
"display": true,
"required": false,
"displayName": "last_metrics_update",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "engagement_rate",
"type": "string",
"display": true,
"required": false,
"displayName": "engagement_rate",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "approval_status",
"type": "string",
"display": true,
"required": false,
"displayName": "approval_status",
"defaultMatch": false,
"canBeUsedToMatch": true
},
{
"id": "row_number",
"type": "number",
"display": true,
"removed": true,
"readOnly": true,
"required": false,
"displayName": "row_number",
"defaultMatch": false,
"canBeUsedToMatch": true
}
],
"mappingMode": "defineBelow",
"matchingColumns": [
"post_id"
],
"attemptToConvertTypes": false,
"convertFieldsToString": false
},
"options": {},
"operation": "update",
"sheetName": {
"__rl": true,
"mode": "list",
"value": "gid=0",
"cachedResultUrl": "https://docs.google.com/spreadsheets/d/1RvHyWEvEZR5etmq1KfzTOkSIXY5tUT5TLVgDSUfAr5c/edit#gid=0",
"cachedResultName": "Posts_Master"
},
"documentId": {
"__rl": true,
"mode": "list",
"value": "1RvHyWEvEZR5etmq1KfzTOkSIXY5tUT5TLVgDSUfAr5c",
"cachedResultUrl": "https://docs.google.com/spreadsheets/d/1RvHyWEvEZR5etmq1KfzTOkSIXY5tUT5TLVgDSUfAr5c/edit?usp=drivesdk",
"cachedResultName": "LinekedIn Posts"
}
},
"credentials": {
"googleSheetsOAuth2Api": {
"id": "ExnZpB5bwFQ3gQ5N",
"name": "Google Sheets account 2"
}
},
"typeVersion": 4.7
},
{
"id": "c5099bdb-84f1-4f4c-bf87-789a7dafdd8b",
"name": "Commutateur",
"type": "n8n-nodes-base.switch",
"position": [
-2320,
336
],
"parameters": {
"rules": {
"values": [
{
"conditions": {
"options": {
"version": 2,
"leftValue": "",
"caseSensitive": true,
"typeValidation": "strict"
},
"combinator": "and",
"conditions": [
{
"id": "d188e181-85e5-4bfb-bf3e-246fa29fbc0f",
"operator": {
"type": "boolean",
"operation": "true",
"singleValue": true
},
"leftValue": "={{$json[\"message\"] ? true : false}}",
"rightValue": "true"
}
]
}
},
{
"conditions": {
"options": {
"version": 2,
"leftValue": "",
"caseSensitive": true,
"typeValidation": "strict"
},
"combinator": "and",
"conditions": [
{
"id": "daf43db7-93b4-47de-a666-22ba7cf90243",
"operator": {
"type": "boolean",
"operation": "true",
"singleValue": true
},
"leftValue": "={{$json[\"callback_query\"] ? true : false}}",
"rightValue": ""
}
]
}
}
]
},
"options": {}
},
"typeVersion": 3.2
},
{
"id": "d79f7123-a20b-4d0d-8d39-793d714b528f",
"name": "Vérification d'Autorisation",
"type": "n8n-nodes-base.if",
"position": [
-1648,
80
],
"parameters": {
"options": {},
"conditions": {
"options": {
"version": 2,
"leftValue": "",
"caseSensitive": true,
"typeValidation": "strict"
},
"combinator": "and",
"conditions": [
{
"id": "e1622adb-df46-4c6a-bc95-dd5ff2ef2951",
"operator": {
"type": "boolean",
"operation": "true",
"singleValue": true
},
"leftValue": "={{ $json.authorized }}",
"rightValue": ""
}
]
}
},
"typeVersion": 2.2
},
{
"id": "c4d4ed74-bf08-4a45-bdfd-9f5539fc025a",
"name": "Envoyer un message texte",
"type": "n8n-nodes-base.telegram",
"position": [
-1424,
176
],
"webhookId": "64c87731-9baa-425f-aa91-9e1a4df18af8",
"parameters": {
"text": "=⚠️ <b>Access Denied</b>\n\nHey {{ $json.username }},\nYou are not authorized to use this service, Reach out to your admin to know more.",
"chatId": "={{ $json.chat_id }}",
"forceReply": {},
"replyMarkup": "=none",
"additionalFields": {
"parse_mode": "HTML",
"reply_to_message_id": "={{ $json.message_id }}"
},
"replyKeyboardRemove": {},
"replyKeyboardOptions": {}
},
"credentials": {
"telegramApi": {
"id": "M9h9AMg2S3J0VkNB",
"name": "Telegram account"
}
},
"typeVersion": 1.2
},
{
"id": "48a35617-298e-40b1-bed2-4e0903a21e1b",
"name": "Catégorisation d'Intention",
"type": "@n8n/n8n-nodes-langchain.chainLlm",
"position": [
-848,
-240
],
"parameters": {
"text": "={{ $json.original_message }}",
"batching": {},
"messages": {
"messageValues": [
{
"message": "=You are a content classifier for LinkedIn automation.\n\nAnalyze the input message and classify it into one of these categories:\n\n1. URL - Contains only URLs to scrape\n2. Topic - Contains only topics to search\n3. Content - Contains ready-to-post content\n4. URL+Topic - Contains both URLs and topic\n5. URL+Content - Contains URLs with additional content\n6. Topic+Content - Contains topics with content\n\nAlso extract:\n- All URLs found\n- Topics/keywords identified\n- Any direct content provided\n\nReturn a JSON object with this structure:\n{\n\"input_type\": \"category\",\n\"urls\": [\"url1\", \"url2\"],\n\"topics\": [\"topic1\", \"topic2\"],\n\"content\": \"any direct content\",\n\"processing_instructions\": \"specific instructions for processing\"\n}\n\nAnalyze this message: {{$json.message_text}}"
}
]
},
"promptType": "define",
"hasOutputParser": true
},
"typeVersion": 1.7
},
{
"id": "4a124b14-56b6-4621-8b53-8124b953fb8e",
"name": "Recherche Web pour le contenu associé",
"type": "@brave/n8n-nodes-brave-search.braveSearch",
"position": [
720,
-144
],
"parameters": {
"query": "={{ $json.topics.join(' ') }} latest news 2024"
},
"credentials": {
"braveSearchApi": {
"id": "pIUa3jvWSpNXcddu",
"name": "Brave Search account"
}
},
"typeVersion": 1
},
{
"id": "c46d2b79-e477-45f3-b313-8d3c71803965",
"name": "Extraire la sortie au format JSON",
"type": "@n8n/n8n-nodes-langchain.outputParserStructured",
"position": [
-768,
-16
],
"parameters": {
"autoFix": true,
"jsonSchemaExample": "{\n\"input_type\": \"category\",\n\"urls\": [\"url1\", \"url2\"],\n\"topics\": [\"topic1\", \"topic2\"],\n\"content\": \"any direct content\",\n\"processing_instructions\": \"specific instructions for processing\"\n}"
},
"typeVersion": 1.3
},
{
"id": "4ac05525-2223-4ab8-8847-291d7c4ea264",
"name": "Google Gemini Model With Parser",
"type": "@n8n/n8n-nodes-langchain.lmChatGoogleGemini",
"position": [
-784,
208
],
"parameters": {
"options": {}
},
"credentials": {
"googlePalmApi": {
"id": "X60IqkX6jjUSqUzT",
"name": "Google Gemini(PaLM) Api account"
}
},
"typeVersion": 1
},
{
"id": "2de58572-8f5f-40a4-b678-7b271abf0103",
"name": "Gemini Model pour Générer la Publication",
"type": "@n8n/n8n-nodes-langchain.lmChatGoogleGemini",
"position": [
1472,
128
],
"parameters": {
"options": {}
},
"credentials": {
"googlePalmApi": {
"id": "X60IqkX6jjUSqUzT",
"name": "Google Gemini(PaLM) Api account"
}
},
"typeVersion": 1
},
{
"id": "5d64983c-a9fb-4805-9c28-6c80bfc4ebc0",
"name": "Gemini Model pour Régénérer la Publication",
"type": "@n8n/n8n-nodes-langchain.lmChatGoogleGemini",
"position": [
-928,
1408
],
"parameters": {
"options": {}
},
"credentials": {
"googlePalmApi": {
"id": "X60IqkX6jjUSqUzT",
"name": "Google Gemini(PaLM) Api account"
}
},
"typeVersion": 1
},
{
"id": "a509944c-8b08-441e-9112-21d0933bc017",
"name": "Utilisateurs Telegram Autorisés",
"type": "n8n-nodes-base.set",
"position": [
-2096,
80
],
"parameters": {
"mode": "raw",
"options": {},
"jsonOutput": "{\n \"telegram_ids\": [\"593214004\", \"987654321\", \"555666777\"],\n \"usernames\": [\"varun_k\", \"Sateesh_Yavarna\", \"john_doe\"]\n}"
},
"typeVersion": 3.4
},
{
"id": "11d89e4f-353c-4398-b762-faf68ddbc059",
"name": "Note Adhésive",
"type": "n8n-nodes-base.stickyNote",
"position": [
-960,
-512
],
"parameters": {
"width": 384,
"height": 240,
"content": "🔍 SMART CONTENT ANALYSIS\n\nUses AI to classify input message:\n- URL: Links to scrape content from\n- Topic: Keywords to search for\n- Content: Ready-to-post text\n- Mixed: Combination of above\n\nExtracts URLs, topics, and processing instructions\nNext: Dynamic routing based on content type"
},
"typeVersion": 1
},
{
"id": "31a9e79d-3003-40f3-994d-be810da49cc5",
"name": "Note Adhésive1",
"type": "n8n-nodes-base.stickyNote",
"position": [
-2480,
-176
],
"parameters": {
"width": 432,
"height": 272,
"content": "🎯 TELEGRAM INPUT & VALIDATION\n\n- Receives messages from authorized Telegram users\n- Validates user permissions against whitelist\n- Generates unique post ID for tracking\n- Routes messages vs callback queries to appropriate paths\n\nNext: Content analysis and classification"
},
"typeVersion": 1
},
{
"id": "a38b8c55-b379-44f1-9aa0-d96dfa5f8a0f",
"name": "Note Adhésive2",
"type": "n8n-nodes-base.stickyNote",
"position": [
16,
-800
],
"parameters": {
"width": 400,
"height": 256,
"content": "⚡ INTELLIGENT CONTENT ROUTING\n\nRoutes content based on classification:\n- URL Path → Web scraping pipeline\n- Topic Path → Search engine pipeline \n- Direct Path → Immediate processing\n- Mixed → Multiple pipelines\n\nSmart branching ensures optimal content gathering\nNext: Content collection from various sources"
},
"typeVersion": 1
},
{
"id": "7ff7438e-da97-45ea-9884-c234b73d0250",
"name": "Note Adhésive3",
"type": "n8n-nodes-base.stickyNote",
"position": [
704,
-784
],
"parameters": {
"width": 400,
"height": 224,
"content": "📄 CONTENT EXTRACTION\n\n- Processes each URL individually\n- Uses Firecrawl to extract article content\n- Handles multiple URLs with batch processing\n- Merges all scraped content with source attribution\n\nExtracts: Article text, metadata, source URLs\nNext: Content synthesis with other sources\n"
},
"typeVersion": 1
},
{
"id": "75f0c80c-5bc1-4f33-b473-3a05baf66b88",
"name": "Note Adhésive4",
"type": "n8n-nodes-base.stickyNote",
"position": [
560,
64
],
"parameters": {
"width": 336,
"height": 272,
"content": "📰 REAL-TIME INFORMATION GATHERING\n\n- Uses Brave Search for latest industry trends\n- Queries based on identified topics\n- Fetches current news and relevant information\n- Formats results for AI processing\n\nProvides: Recent articles, trending topics, fresh insights\nNext: Content synthesis with scraped data"
},
"typeVersion": 1
},
{
"id": "c5917579-5792-4a30-8a00-8f9e36287ca0",
"name": "Note Adhésive5",
"type": "n8n-nodes-base.stickyNote",
"position": [
960,
-400
],
"parameters": {
"width": 336,
"height": 256,
"content": "⚙️ MULTI-SOURCE DATA MERGER\n\nCombines all gathered information:\n- Original user message and instructions\n- Scraped web content with sources\n- Search results and trending data\n- Processing metadata and context\n\nCreates comprehensive content brief for AI generation\nNext: LinkedIn post creation"
},
"typeVersion": 1
},
{
"id": "ad320576-2de5-4f2a-892a-04aa42022b03",
"name": "Note Adhésive6",
"type": "n8n-nodes-base.stickyNote",
"position": [
1376,
-400
],
"parameters": {
"width": 336,
"height": 288,
"content": "✍️ PROFESSIONAL POST CREATION\n\nGoogle Gemini generates LinkedIn-optimized content:\n- Professional tone and structure\n- Mobile-friendly formatting\n- Strategic hashtags and CTAs\n- Source attribution when applicable\n- Character limit compliance (2800 max)\n\nOutput: Complete LinkedIn post with metadata\nNext: User preview and approval"
},
"typeVersion": 1
},
{
"id": "5fb895db-d346-41ad-8e9c-9f14c401aa1f",
"name": "Note Adhésive7",
"type": "n8n-nodes-base.stickyNote",
"position": [
1952,
-416
],
"parameters": {
"width": 384,
"height": 256,
"content": "👀 INTERACTIVE PREVIEW & APPROVAL\n\nSends formatted preview to Telegram with:\n- Complete post content preview\n- Character count and hashtag analysis\n- Interactive buttons: Approve/Edit/Reject\n- Post analytics and key points summary\n\nUser controls final content before publishing\nNext: Action processing based on user choice"
},
"typeVersion": 1
},
{
"id": "6db26f00-0f6f-4104-9ab1-781629851982",
"name": "Note Adhésive8",
"type": "n8n-nodes-base.stickyNote",
"position": [
-1712,
432
],
"parameters": {
"width": 368,
"height": 192,
"content": "⚡ USER ACTION HANDLER\n\nProcesses user decisions:\n- APPROVE → Direct LinkedIn publishing\n- EDIT → AI rewriting with user instructions\n- REJECT → Workflow termination with logging\n\nHandles approval workflow and edit iterations\nNext: Final action execution"
},
"typeVersion": 1
},
{
"id": "d251c735-f1db-4b41-99c3-33f5f581054e",
"name": "Note Adhésive9",
"type": "n8n-nodes-base.stickyNote",
"position": [
-1120,
704
],
"parameters": {
"width": 368,
"height": 224,
"content": "🔧 AI-POWERED CONTENT REFINEMENT\n\nWhen user requests edits:\n- Prompts for specific edit instructions\n- Uses AI to rewrite based on feedback\n- Maintains original intent and sources\n- Shows new version for re-approval\n\nIterative improvement until user satisfaction\nNext: Re-approval or publishing"
},
"typeVersion": 1
},
{
"id": "8d641fa1-5117-4554-bb3d-be2fd4bd725f",
"name": "Note Adhésive10",
"type": "n8n-nodes-base.stickyNote",
"position": [
-448,
720
],
"parameters": {
"width": 384,
"height": 224,
"content": "📤 LINKEDIN POST PUBLICATION\n\nFinal publishing process:\n- Retrieves approved content from tracking sheet\n- Posts directly to LinkedIn via API\n- Confirms successful publication\n- Updates tracking with post status\n\nOutput: Live LinkedIn post with confirmation"
},
"typeVersion": 1
}
],
"active": true,
"pinData": {},
"settings": {
"executionOrder": "v1"
},
"versionId": "ba025382-0d47-4264-9f3f-0c9d463b6cdd",
"connections": {
"04db5e51-3a5f-4817-80d9-135a1164db3e": {
"main": [
[
{
"node": "4a124b14-56b6-4621-8b53-8124b953fb8e",
"type": "main",
"index": 0
}
],
[]
]
},
"e5f7a21a-1dbc-4e2e-8f84-de06d87adaf3": {
"main": [
[
{
"node": "70b4a682-8827-4e2b-8f01-af887ab7ec41",
"type": "main",
"index": 0
}
],
[]
]
},
"784ae37f-d98c-46be-9cc0-f7abab2d7aaf": {
"main": [
[
{
"node": "8d16150a-502b-4c6c-a16c-b36efd85e7ed",
"type": "main",
"index": 0
}
]
]
},
"c5099bdb-84f1-4f4c-bf87-789a7dafdd8b": {
"main": [
[
{
"node": "a509944c-8b08-441e-9112-21d0933bc017",
"type": "main",
"index": 0
}
],
[
{
"node": "5c8b4551-ba7e-4cf1-8a97-479e3727d728",
"type": "main",
"index": 0
}
]
]
},
"50cb382e-6d1f-458a-8cc4-57ee8d29fbca": {
"main": [
[
{
"node": "95a591bc-7533-445f-abc0-1cb60e76ec48",
"type": "main",
"index": 0
}
]
]
},
"e97c3e0d-218c-4e7b-befb-ff68e8a7edf6": {
"main": [
[
{
"node": "211f2430-b7fc-47d7-8fb3-6353a1e9779a",
"type": "main",
"index": 0
}
],
[
{
"node": "5808faa3-e584-4014-b476-4da1750bcdc9",
"type": "main",
"index": 0
}
],
[
{
"node": "cfb82bd5-01a6-48dd-b6ea-293909b44d84",
"type": "main",
"index": 0
}
]
]
},
"d45ddc23-679a-4cd6-82e3-fe5bbe35107f": {
"main": [
[
{
"node": "04db5e51-3a5f-4817-80d9-135a1164db3e",
"type": "main",
"index": 0
},
{
"node": "e5f7a21a-1dbc-4e2e-8f84-de06d87adaf3",
"type": "main",
"index": 0
}
],
[
{
"node": "784ae37f-d98c-46be-9cc0-f7abab2d7aaf",
"type": "main",
"index": 2
}
]
]
},
"79324d69-6cc4-4f3f-a398-c5a8e7478d93": {
"main": [
[
{
"node": "7642abfa-80a4-4254-808d-8eafd3aa3d75",
"type": "main",
"index": 0
}
]
]
},
"2c8c8e1c-fb44-47a8-921f-2676f773df7a": {
"main": [
[
{
"node": "d8ef03dd-2db3-4adf-993f-de30fcb090ab",
"type": "main",
"index": 0
}
],
[
{
"node": "ab0a005e-b926-49f7-93bc-4de5e3d5c011",
"type": "main",
"index": 0
}
]
]
},
"cfb82bd5-01a6-48dd-b6ea-293909b44d84": {
"main": [
[
{
"node": "75e4fd6d-d628-4a5d-8f81-086239fe714e",
"type": "main",
"index": 0
}
]
]
},
"d79f7123-a20b-4d0d-8d39-793d714b528f": {
"main": [
[
{
"node": "a7a0856a-344f-48c8-9308-5fb9dc06eea4",
"type": "main",
"index": 0
}
],
[
{
"node": "c4d4ed74-bf08-4a45-bdfd-9f5539fc025a",
"type": "main",
"index": 0
}
]
]
},
"95a591bc-7533-445f-abc0-1cb60e76ec48": {
"main": [
[
{
"node": "d1d2ee44-33fb-4c42-b72e-d6c485b6f3ac",
"type": "main",
"index": 0
}
]
]
},
"5c10dc1d-2964-4089-8222-25dc69b09f9d": {
"main": [
[
{
"node": "c6eed7a0-7e0b-49b6-8c5f-9fa27ea9b064",
"type": "main",
"index": 0
}
]
]
},
"a34caf37-c9b3-47e8-894a-5259323f70cc": {
"main": [
[
{
"node": "d79f7123-a20b-4d0d-8d39-793d714b528f",
"type": "main",
"index": 0
}
]
]
},
"a7a0856a-344f-48c8-9308-5fb9dc06eea4": {
"main": [
[
{
"node": "03be5ca8-54bb-4597-af45-0d13b66be14c",
"type": "main",
"index": 0
}
]
]
},
"5c8b4551-ba7e-4cf1-8a97-479e3727d728": {
"main": [
[
{
"node": "d21a09c5-dbf8-488e-9197-d32baa9e43df",
"type": "main",
"index": 0
}
]
]
},
"f83aa078-06c1-4b19-82d2-eb7385609b9e": {
"main": [
[
{
"node": "5c10dc1d-2964-4089-8222-25dc69b09f9d",
"type": "main",
"index": 0
}
]
]
},
"96c77c8e-fc61-4d53-9bd6-568317aee08c": {
"main": [
[
{
"node": "c5099bdb-84f1-4f4c-bf87-789a7dafdd8b",
"type": "main",
"index": 0
}
]
]
},
"03be5ca8-54bb-4597-af45-0d13b66be14c": {
"main": [
[
{
"node": "48a35617-298e-40b1-bed2-4e0903a21e1b",
"type": "main",
"index": 0
}
]
]
},
"29cc76e7-c8eb-4931-91fa-1adafcbbea71": {
"main": [
[
{
"node": "50cb382e-6d1f-458a-8cc4-57ee8d29fbca",
"type": "main",
"index": 0
}
]
]
},
"2dbe1200-b0fb-4cf4-9ea5-214e76c48f7f": {
"main": [
[
{
"node": "d45ddc23-679a-4cd6-82e3-fe5bbe35107f",
"type": "main",
"index": 0
},
{
"node": "784ae37f-d98c-46be-9cc0-f7abab2d7aaf",
"type": "main",
"index": 3
}
]
]
},
"c6eed7a0-7e0b-49b6-8c5f-9fa27ea9b064": {
"main": [
[
{
"node": "3970d4b0-8d13-4854-9eb5-62db19484b81",
"type": "main",
"index": 0
}
]
]
},
"6f882b2f-c990-451f-ba17-015d992c4636": {
"main": [
[
{
"node": "79324d69-6cc4-4f3f-a398-c5a8e7478d93",
"type": "main",
"index": 0
}
]
]
},
"48a35617-298e-40b1-bed2-4e0903a21e1b": {
"main": [
[
{
"node": "2dbe1200-b0fb-4cf4-9ea5-214e76c48f7f",
"type": "main",
"index": 0
}
]
]
},
"8d16150a-502b-4c6c-a16c-b36efd85e7ed": {
"main": [
[
{
"node": "6f882b2f-c990-451f-ba17-015d992c4636",
"type": "main",
"index": 0
}
]
]
},
"211f2430-b7fc-47d7-8fb3-6353a1e9779a": {
"main": [
[
{
"node": "29cc76e7-c8eb-4931-91fa-1adafcbbea71",
"type": "main",
"index": 0
}
]
]
},
"d21a09c5-dbf8-488e-9197-d32baa9e43df": {
"main": [
[
{
"node": "e97c3e0d-218c-4e7b-befb-ff68e8a7edf6",
"type": "main",
"index": 0
}
]
]
},
"d8ef03dd-2db3-4adf-993f-de30fcb090ab": {
"main": [
[
{
"node": "784ae37f-d98c-46be-9cc0-f7abab2d7aaf",
"type": "main",
"index": 0
}
]
]
},
"7642abfa-80a4-4254-808d-8eafd3aa3d75": {
"main": [
[
{
"node": "a7b81e78-6e44-4e2c-a96c-f4be302f8667",
"type": "main",
"index": 0
}
]
]
},
"a509944c-8b08-441e-9112-21d0933bc017": {
"main": [
[
{
"node": "a34caf37-c9b3-47e8-894a-5259323f70cc",
"type": "main",
"index": 0
}
]
]
},
"70b4a682-8827-4e2b-8f01-af887ab7ec41": {
"main": [
[
{
"node": "2c8c8e1c-fb44-47a8-921f-2676f773df7a",
"type": "main",
"index": 0
}
]
]
},
"2de58572-8f5f-40a4-b678-7b271abf0103": {
"ai_languageModel": [
[
{
"node": "6f882b2f-c990-451f-ba17-015d992c4636",
"type": "ai_languageModel",
"index": 0
}
]
]
},
"4ac05525-2223-4ab8-8847-291d7c4ea264": {
"ai_languageModel": [
[
{
"node": "48a35617-298e-40b1-bed2-4e0903a21e1b",
"type": "ai_languageModel",
"index": 0
},
{
"node": "c46d2b79-e477-45f3-b313-8d3c71803965",
"type": "ai_languageModel",
"index": 0
}
]
]
},
"ab0a005e-b926-49f7-93bc-4de5e3d5c011": {
"main": [
[
{
"node": "2c8c8e1c-fb44-47a8-921f-2676f773df7a",
"type": "main",
"index": 0
}
]
]
},
"c46d2b79-e477-45f3-b313-8d3c71803965": {
"ai_outputParser": [
[
{
"node": "48a35617-298e-40b1-bed2-4e0903a21e1b",
"type": "ai_outputParser",
"index": 0
}
]
]
},
"5808faa3-e584-4014-b476-4da1750bcdc9": {
"main": [
[
{
"node": "f83aa078-06c1-4b19-82d2-eb7385609b9e",
"type": "main",
"index": 0
}
]
]
},
"4a124b14-56b6-4621-8b53-8124b953fb8e": {
"main": [
[
{
"node": "784ae37f-d98c-46be-9cc0-f7abab2d7aaf",
"type": "main",
"index": 1
}
]
]
},
"5d64983c-a9fb-4805-9c28-6c80bfc4ebc0": {
"ai_languageModel": [
[
{
"node": "f83aa078-06c1-4b19-82d2-eb7385609b9e",
"type": "ai_languageModel",
"index": 0
}
]
]
}
}
}Comment utiliser ce workflow ?
Copiez le code de configuration JSON ci-dessus, créez un nouveau workflow dans votre instance n8n et sélectionnez "Importer depuis le JSON", collez la configuration et modifiez les paramètres d'authentification selon vos besoins.
Dans quelles scénarios ce workflow est-il adapté ?
Avancé - Création de contenu, IA Multimodale
Est-ce payant ?
Ce workflow est entièrement gratuit et peut être utilisé directement. Veuillez noter que les services tiers utilisés dans le workflow (comme l'API OpenAI) peuvent nécessiter un paiement de votre part.
Workflows recommandés
Sateesh
@sateeshPartager ce workflow