Enriquecimiento de leads y contacto frío personalizado con IA para LinkedIn

Avanzado

Este es unContent Creation, Multimodal AIflujo de automatización del dominio deautomatización que contiene 18 nodos.Utiliza principalmente nodos como If, Set, Code, Wait, SplitOut. Enriquecimiento de información de prospectos y contacto frío personalizado en LinkedIn, integrando Hunter.io, GPT-4 y Sheets

Requisitos previos
  • Pueden requerirse credenciales de autenticación para la API de destino
  • Credenciales de API de Google Sheets
  • Clave de API de OpenAI
Vista previa del flujo de trabajo
Visualización de las conexiones entre nodos, con soporte para zoom y panorámica
Exportar flujo de trabajo
Copie la siguiente configuración JSON en n8n para importar y usar este flujo de trabajo
{
  "id": "",
  "meta": {
    "instanceId": "your-instance-id-here",
    "templateCredsSetupCompleted": false
  },
  "name": "LinkedIn Lead Enrichment with AI Personalization for Cold Outreach",
  "tags": [
    {
      "id": "1",
      "name": "Sales",
      "createdAt": "2025-01-01T00:00:00.000Z",
      "updatedAt": "2025-01-01T00:00:00.000Z"
    },
    {
      "id": "2",
      "name": "Lead Generation",
      "createdAt": "2025-01-01T00:00:00.000Z",
      "updatedAt": "2025-01-01T00:00:00.000Z"
    },
    {
      "id": "3",
      "name": "AI",
      "createdAt": "2025-01-01T00:00:00.000Z",
      "updatedAt": "2025-01-01T00:00:00.000Z"
    }
  ],
  "nodes": [
    {
      "id": "workflow-overview-note",
      "name": "📋 Descripción General y Guía de Configuración del Flujo de Trabajo",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        -420,
        240
      ],
      "parameters": {
        "color": 4,
        "width": 680,
        "height": 620,
        "content": "## 🎯 LinkedIn Lead Enrichment with AI Personalization\n\n### **Who's it for:**\nSales teams, growth marketers, and business development professionals who want to automate lead research and create personalized outreach at scale.\n\n### **What it does:**\n- Scrapes LinkedIn profiles to extract professional information\n- Enriches leads with email addresses using hunter.io\n- Generates personalized outreach messages using AI\n- Stores enriched data in Google Sheets for easy management\n\n### **How to set up:**\n1. **Configure Google Sheets:** Create a sheet with columns: Name, LinkedIn URL, Email, Company, Title, Personalized Message\n2. **Set up credentials:** Add your OpenAI API key and Hunter.io API key in n8n credentials\n3. **Customize the AI prompt:** Edit the OpenAI node to match your outreach style and value proposition\n4. **Test with sample data:** Start with 2-3 LinkedIn URLs before scaling\n\n### **Requirements:**\n- OpenAI API key (GPT-4 recommended for best personalization)\n- Hunter.io API key for email finding\n- Google Sheets access\n- LinkedIn profile URLs of your target leads\n\n### **How to customize:**\n- **Change AI tone:** Modify the system prompt in the OpenAI node\n- **Add more data sources:** Integrate company website scraping\n- **Filter leads:** Add conditional logic to qualify leads before enrichment\n- **Connect to CRM:** Replace Google Sheets with Salesforce, HubSpot, or Pipedrive\n\n💡 **Pro Tip:** Use the \"Set Fields\" node to easily update your target industry and value proposition without editing multiple nodes.\n\n📺 **Watch Setup Guide:** [Add your Loom video link here]\n\n⚠️ **Important:** This workflow uses community nodes for LinkedIn scraping. Self-hosted n8n instance required."
      },
      "typeVersion": 1
    },
    {
      "id": "step-1-note",
      "name": "Contexto del Paso 1",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        140,
        240
      ],
      "parameters": {
        "color": 7,
        "width": 380,
        "height": 180,
        "content": "## Step 1: Configure Your Campaign\n\nSet your target criteria and personalization variables here.\n\nThis makes it easy to update without touching other nodes."
      },
      "typeVersion": 1
    },
    {
      "id": "step-2-note",
      "name": "Contexto del Paso 2",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        660,
        240
      ],
      "parameters": {
        "color": 7,
        "width": 380,
        "height": 180,
        "content": "## Step 2: Extract LinkedIn Data\n\nScrape professional information from LinkedIn profiles.\n\n⚠️ Rate limit: Max 20 profiles per minute"
      },
      "typeVersion": 1
    },
    {
      "id": "step-3-note",
      "name": "Contexto del Paso 3",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        1180,
        240
      ],
      "parameters": {
        "color": 7,
        "width": 380,
        "height": 180,
        "content": "## Step 3: Find Email Addresses\n\nUse Hunter.io to find verified work emails.\n\nFallback to company domain + name patterns if not found."
      },
      "typeVersion": 1
    },
    {
      "id": "step-4-note",
      "name": "Contexto del Paso 4",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        1700,
        240
      ],
      "parameters": {
        "color": 7,
        "width": 380,
        "height": 180,
        "content": "## Step 4: AI Personalization\n\nGenerate custom outreach messages based on:\n- Job title\n- Company info\n- Recent activity\n- Your value proposition"
      },
      "typeVersion": 1
    },
    {
      "id": "step-5-note",
      "name": "Contexto del Paso 5",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        2220,
        240
      ],
      "parameters": {
        "color": 7,
        "width": 380,
        "height": 180,
        "content": "## Step 5: Store Enriched Leads\n\nSave all enriched data to Google Sheets for review and outreach."
      },
      "typeVersion": 1
    },
    {
      "id": "campaign-settings-node",
      "name": "Configurar Variables de la Campaña",
      "type": "n8n-nodes-base.set",
      "position": [
        180,
        480
      ],
      "parameters": {
        "mode": "raw",
        "options": {},
        "jsonOutput": "{\n  \"target_industry\": \"SaaS\",\n  \"target_role\": \"Head of Sales\",\n  \"company_name\": \"YourCompany\",\n  \"value_proposition\": \"We help sales teams book 30% more meetings using AI-powered personalization\",\n  \"linkedin_urls\": [\n    \"https://www.linkedin.com/in/sample-profile-1\",\n    \"https://www.linkedin.com/in/sample-profile-2\"\n  ]\n}"
      },
      "typeVersion": 3.4
    },
    {
      "id": "split-urls-node",
      "name": "Dividir URLs de LinkedIn",
      "type": "n8n-nodes-base.splitOut",
      "position": [
        380,
        480
      ],
      "parameters": {
        "options": {},
        "fieldToSplitOut": "linkedin_urls"
      },
      "typeVersion": 1
    },
    {
      "id": "scrape-linkedin-node",
      "name": "Extraer Datos del Perfil de LinkedIn",
      "type": "n8n-nodes-base.httpRequest",
      "position": [
        700,
        480
      ],
      "parameters": {
        "url": "={{ $json.linkedin_urls }}",
        "options": {
          "timeout": 10000
        },
        "sendHeaders": true,
        "authentication": "genericCredentialType",
        "genericAuthType": "httpHeaderAuth",
        "headerParameters": {
          "parameters": [
            {
              "name": "User-Agent",
              "value": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36"
            }
          ]
        }
      },
      "typeVersion": 4.2
    },
    {
      "id": "parse-linkedin-data-node",
      "name": "Analizar Datos de LinkedIn",
      "type": "n8n-nodes-base.code",
      "position": [
        900,
        480
      ],
      "parameters": {
        "jsCode": "// Extract key information from LinkedIn HTML\nconst html = $input.item.json.data || '';\n\n// Helper function to extract text between patterns\nfunction extractText(pattern, text) {\n  const match = text.match(pattern);\n  return match ? match[1].trim() : null;\n}\n\n// Extract name\nconst name = extractText(/<title>([^|]+)/, html) || 'Unknown';\n\n// Extract current position\nconst title = extractText(/aria-label=\"Current position[^>]*>([^<]+)/, html) || 'Not specified';\n\n// Extract company\nconst company = extractText(/aria-label=\"Current company[^>]*>([^<]+)/, html) || 'Unknown';\n\n// Extract location\nconst location = extractText(/aria-label=\"Location[^>]*>([^<]+)/, html) || 'Unknown';\n\n// Clean up name\nconst cleanName = name.replace(/[\\|\\-].*$/, '').trim();\nconst nameParts = cleanName.split(' ');\nconst firstName = nameParts[0] || '';\nconst lastName = nameParts.slice(1).join(' ') || '';\n\nreturn {\n  full_name: cleanName,\n  first_name: firstName,\n  last_name: lastName,\n  title: title,\n  company: company,\n  location: location,\n  linkedin_url: $json.linkedin_urls,\n  raw_html: html.substring(0, 1000) // Keep snippet for debugging\n};"
      },
      "typeVersion": 2
    },
    {
      "id": "find-email-node",
      "name": "Buscar Email con Hunter.io",
      "type": "n8n-nodes-base.httpRequest",
      "position": [
        1220,
        480
      ],
      "parameters": {
        "url": "=https://api.hunter.io/v2/email-finder",
        "method": "GET",
        "options": {
          "response": {
            "response": {
              "neverError": true
            }
          }
        },
        "sendQuery": true,
        "authentication": "genericCredentialType",
        "genericAuthType": "queryAuth",
        "queryParameters": {
          "parameters": [
            {
              "name": "domain",
              "value": "={{ $json.company.toLowerCase().replace(/[^a-z0-9]/g, '') }}.com"
            },
            {
              "name": "first_name",
              "value": "={{ $json.first_name }}"
            },
            {
              "name": "last_name",
              "value": "={{ $json.last_name }}"
            }
          ]
        }
      },
      "typeVersion": 4.2
    },
    {
      "id": "process-email-node",
      "name": "Procesar Resultado del Email",
      "type": "n8n-nodes-base.code",
      "position": [
        1420,
        480
      ],
      "parameters": {
        "jsCode": "// Extract email from Hunter.io response\nconst hunterData = $input.item.json.data || {};\nconst emailData = hunterData.email || null;\n\n// Get previous node data\nconst leadData = $('Parse LinkedIn Data').item.json;\n\nreturn {\n  ...leadData,\n  email: emailData,\n  email_confidence: hunterData.score || 0,\n  email_verified: emailData ? true : false\n};"
      },
      "typeVersion": 2
    },
    {
      "id": "check-email-exists-node",
      "name": "¿Email Encontrado?",
      "type": "n8n-nodes-base.if",
      "position": [
        1620,
        480
      ],
      "parameters": {
        "options": {},
        "conditions": {
          "options": {
            "leftValue": "",
            "caseSensitive": true,
            "typeValidation": "strict"
          },
          "combinator": "and",
          "conditions": [
            {
              "id": "email-exists-condition",
              "operator": {
                "type": "string",
                "operation": "isNotEmpty"
              },
              "leftValue": "={{ $json.email }}",
              "rightValue": ""
            }
          ]
        }
      },
      "typeVersion": 2.2
    },
    {
      "id": "generate-personalization-node",
      "name": "Generar Personalización con IA",
      "type": "@n8n/n8n-nodes-langchain.openAi",
      "position": [
        1900,
        400
      ],
      "parameters": {
        "modelId": {
          "__rl": true,
          "mode": "list",
          "value": "gpt-4-turbo-preview",
          "cachedResultName": "GPT-4 Turbo"
        },
        "options": {},
        "messages": {
          "values": [
            {
              "content": "=You are an expert sales copywriter. Generate a highly personalized cold outreach message based on the prospect's information.\n\n**Prospect Details:**\n- Name: {{ $json.first_name }} {{ $json.last_name }}\n- Title: {{ $json.title }}\n- Company: {{ $json.company }}\n- Location: {{ $json.location }}\n\n**Our Company:** {{ $('Set Campaign Variables').item.json.company_name }}\n**Value Proposition:** {{ $('Set Campaign Variables').item.json.value_proposition }}\n\n**Instructions:**\n1. Start with a personalized opener that references their role or company\n2. Clearly state the value proposition in one sentence\n3. Include a soft call-to-action\n4. Keep it under 100 words\n5. Professional but conversational tone\n6. No hype or pushy language\n\n**Output Format:**\nProvide ONLY the message body, no subject line or greetings. Return as JSON:\n{\n  \"message\": \"your personalized message here\"\n}"
            }
          ]
        },
        "jsonOutput": true
      },
      "typeVersion": 1.8
    },
    {
      "id": "save-to-sheets-node",
      "name": "Guardar en Google Sheets",
      "type": "n8n-nodes-base.googleSheets",
      "position": [
        2260,
        480
      ],
      "parameters": {
        "columns": {
          "value": {
            "Email": "={{ $json.email }}",
            "Title": "={{ $json.title }}",
            "Company": "={{ $json.company }}",
            "Location": "={{ $json.location }}",
            "Full Name": "={{ $json.full_name }}",
            "Last Name": "={{ $json.last_name }}",
            "First Name": "={{ $json.first_name }}",
            "LinkedIn URL": "={{ $json.linkedin_url }}",
            "Enriched Date": "={{ $now.toFormat('yyyy-MM-dd HH:mm:ss') }}",
            "Email Confidence": "={{ $json.email_confidence }}",
            "Personalized Message": "={{ $json.ai_message }}"
          },
          "schema": [],
          "mappingMode": "defineBelow",
          "matchingColumns": []
        },
        "options": {},
        "operation": "append",
        "sheetName": {
          "__rl": true,
          "mode": "list",
          "value": "gid=0",
          "cachedResultName": "Sheet1"
        },
        "documentId": {
          "__rl": true,
          "mode": "list",
          "value": "YOUR_GOOGLE_SHEET_ID",
          "cachedResultName": "Lead Enrichment Sheet"
        }
      },
      "typeVersion": 4.5
    },
    {
      "id": "merge-ai-data-node",
      "name": "Combinar Mensaje de IA",
      "type": "n8n-nodes-base.code",
      "position": [
        2100,
        400
      ],
      "parameters": {
        "jsCode": "// Merge AI-generated message with lead data\nconst leadData = $('Process Email Result').item.json;\nconst aiResponse = $input.item.json.message?.content || {};\nconst aiMessage = aiResponse.message || 'Personalization failed - manual review needed';\n\nreturn {\n  ...leadData,\n  ai_message: aiMessage,\n  processing_timestamp: new Date().toISOString()\n};"
      },
      "typeVersion": 2
    },
    {
      "id": "no-email-found-node",
      "name": "Sin Email - Omitir",
      "type": "n8n-nodes-base.noOp",
      "position": [
        1900,
        560
      ],
      "parameters": {},
      "typeVersion": 1
    },
    {
      "id": "rate-limit-wait-node",
      "name": "Retraso por Límite de Tasa",
      "type": "n8n-nodes-base.wait",
      "position": [
        560,
        480
      ],
      "webhookId": "rate-limit-webhook-id",
      "parameters": {
        "unit": "seconds",
        "amount": 2
      },
      "typeVersion": 1.1
    }
  ],
  "active": false,
  "pinData": {},
  "settings": {
    "callerPolicy": "workflowsFromSameOwner",
    "errorWorkflow": "",
    "executionOrder": "v1",
    "saveManualExecutions": true
  },
  "versionId": "",
  "connections": {
    "check-email-exists-node": {
      "main": [
        [
          {
            "node": "generate-personalization-node",
            "type": "main",
            "index": 0
          }
        ],
        [
          {
            "node": "no-email-found-node",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "merge-ai-data-node": {
      "main": [
        [
          {
            "node": "save-to-sheets-node",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "rate-limit-wait-node": {
      "main": [
        [
          {
            "node": "scrape-linkedin-node",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "parse-linkedin-data-node": {
      "main": [
        [
          {
            "node": "find-email-node",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "split-urls-node": {
      "main": [
        [
          {
            "node": "rate-limit-wait-node",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "process-email-node": {
      "main": [
        [
          {
            "node": "check-email-exists-node",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "campaign-settings-node": {
      "main": [
        [
          {
            "node": "split-urls-node",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "scrape-linkedin-node": {
      "main": [
        [
          {
            "node": "parse-linkedin-data-node",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "find-email-node": {
      "main": [
        [
          {
            "node": "process-email-node",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "generate-personalization-node": {
      "main": [
        [
          {
            "node": "merge-ai-data-node",
            "type": "main",
            "index": 0
          }
        ]
      ]
    }
  }
}
Preguntas frecuentes

¿Cómo usar este flujo de trabajo?

Copie el código de configuración JSON de arriba, cree un nuevo flujo de trabajo en su instancia de n8n y seleccione "Importar desde JSON", pegue la configuración y luego modifique la configuración de credenciales según sea necesario.

¿En qué escenarios es adecuado este flujo de trabajo?

Avanzado - Creación de contenido, IA Multimodal

¿Es de pago?

Este flujo de trabajo es completamente gratuito, puede importarlo y usarlo directamente. Sin embargo, tenga en cuenta que los servicios de terceros utilizados en el flujo de trabajo (como la API de OpenAI) pueden requerir un pago por su cuenta.

Flujos de trabajo relacionados recomendados

Información del flujo de trabajo
Nivel de dificultad
Avanzado
Número de nodos18
Categoría2
Tipos de nodos10
Descripción de la dificultad

Adecuado para usuarios avanzados, flujos de trabajo complejos con 16+ nodos

Autor
Amirul Hakimi

Amirul Hakimi

@amirulhaaakimi

CS Student Specializing in Artificial Intelligence @UNITEN | Certified in CRO & Copywriting for High-Impact Digital Growth

Enlaces externos
Ver en n8n.io

Compartir este flujo de trabajo

Categorías

Categorías: 34