Your n8n Blueprint is Ready

    Here are the exact nodes and scripts you need to build the "Perfect Audit" workflow.

    CONGRATULATIONS

    You've been selected for a free trial of Outreach Magic.

    Don't want to maintain your own n8n reporting server? Skip the DIY setup and use our fully managed "Plug & Play" reporting platform.

    1. The Complete Workflow

    This section includes everything you need: the n8n node structure and the Identity Resolution logic.

    Part A: The Workflow JSON

    Copy and paste this directly into your n8n canvas. It includes a Webhook, a Switch to handle different platforms (Smartlead, Instantly, HeyReach), and the Google Sheets connector.

    n8n Workflow JSON
    {
      "nodes": [
        {
          "parameters": {
            "httpMethod": "POST",
            "path": "reporting",
            "options": {}
          },
          "name": "Webhook",
          "type": "n8n-nodes-base.webhook",
          "typeVersion": 1,
          "position": [460, 300]
        },
        {
          "parameters": {
            "jsCode": "// Identity Logic Placeholder"
          },
          "name": "Identity & Dedupe Logic",
          "type": "n8n-nodes-base.code",
          "typeVersion": 1,
          "position": [680, 300]
        },
        {
          "parameters": {
            "operation": "append",
            "sheetId": {
              "__rl": true,
              "mode": "list",
              "value": ""
            },
            "range": "Raw Events!A:Z",
            "options": {
              "useKeys": true
            }
          },
          "name": "Google Sheets",
          "type": "n8n-nodes-base.googleSheets",
          "typeVersion": 3,
          "position": [900, 300]
        }
      ],
      "connections": {
        "Webhook": {
          "main": [
            [
              {
                "node": "Identity & Dedupe Logic",
                "type": "main",
                "index": 0
              }
            ]
          ]
        },
        "Identity & Dedupe Logic": {
          "main": [
            [
              {
                "node": "Google Sheets",
                "type": "main",
                "index": 0
              }
            ]
          ]
        }
      }
    }

    Part B: The "Universal" Script

    Double-click the "Identity & Dedupe Logic" node and paste this Javascript. It automatically detects if the data is from Smartlead, Instantly, or HeyReach and normalizes it.

    Javascript for Code Node
    // Run for each item
    const item = $input.item.json;
    // Handle n8n webhook nesting (sometimes data is in item.body)
    // This fixes the issue where payload might be nested under 'body'
    const json = item.body || item;
    
    let platform = 'manual';
    let email = '';
    let linkedin = '';
    let messageId = '';
    let eventType = 'unknown';
    let campaignId = '';
    
    // --- DETECT PLATFORM & NORMALIZE ---
    
    // 1. SMARTLEAD
    if (json.sl_email_lead_id || (json.app_url && json.app_url.includes('smartlead'))) {
      platform = 'smartlead';
      email = (json.to_email || '').toLowerCase().trim();
      eventType = (json.event_type || '').toLowerCase(); 
      campaignId = json.campaign_id;
      
      if (json.sent_message && json.sent_message.message_id) {
        messageId = json.sent_message.message_id;
      } else {
        messageId = json.sl_email_lead_id + '_' + json.stats_id; 
      }
    }
    
    // 2. HEYREACH
    else if (json.lead && json.sender && json.event_type) {
      platform = 'heyreach';
      email = (json.lead.email_address || '').toLowerCase().trim();
      linkedin = (json.lead.profile_url || '').split('?')[0];
      eventType = json.event_type.toLowerCase(); 
      campaignId = json.campaign ? json.campaign.id : '';
      messageId = json.correlation_id || (json.lead.id + '_' + json.timestamp);
    }
    
    // 3. INSTANTLY
    else if (json.workspace && json.campaign_id) {
      platform = 'instantly';
      email = (json.lead_email || json.email || '').toLowerCase().trim();
      eventType = (json.event_type || '').toLowerCase();
      campaignId = json.campaign_id;
      messageId = email + '_' + campaignId + '_' + json.timestamp;
    }
    
    // --- CLEANUP ---
    
    if (linkedin.endsWith('/')) linkedin = linkedin.slice(0, -1);
    
    // Generate Unified ID
    const unifiedId = email || linkedin || 'unknown_' + Math.random().toString(36).substr(2, 9);
    
    // Generate Dedupe Key
    const dedupeKey = `${platform}_${messageId}_${eventType}`;
    
    return {
      json: {
        dedupe_key: dedupeKey,
        timestamp_iso: json.timestamp || json.event_timestamp || new Date().toISOString(),
        event_type: eventType,
        platform: platform,
        unified_lead_id: unifiedId,
        campaign_id: campaignId ? campaignId.toString() : ''
      }
    };

    2. Get the Dashboard Template

    Google Sheets Dashboard

    We've created a pre-formatted sheet with the correct columns and a "Raw Events" tab ready for your n8n data.

    Open Template(File > Make a copy)

    Advanced: Generate Custom Charts with AI

    Want to build custom trends? Copy this prompt into ChatGPT or Claude to generate formulas for your new sheet.

    Prompt for ChatGPT / Claude
    I need to build a Cold Email Reporting Dashboard in Google Sheets to connect with my n8n workflow. Please give me the exact setup instructions and formulas.
    
    1. **Tab "Raw Data"**: 
       - Headers in Row 1: [dedupe_key, timestamp_iso, event_type, platform, unified_lead_id, campaign_id]
       - This is where n8n will append new rows.
    
    2. **Tab "Analysis"**:
       - Column A (Date): Write an ARRAYFORMULA to extract unique dates from 'Raw Data'!B:B (timestamp_iso), sorted descending.
       - Column B (Sent Volume): Count rows where event_type="sent" for that date.
       - Column C (Replies): Count rows where event_type="reply" for that date.
       - Column D (Unique Leads Contacted): Count unique "unified_lead_id" where event_type="sent" for that date (Use COUNTUNIQUEIFS if available, or a QUERY).
       - Column E (Reply Rate): Column C / Column B (Formatted as %).
    
    Please provide the specific Google Sheets formulas (using ARRAYFORMULA or QUERY where possible) so I can paste them into Row 2 of the Analysis tab.

    Stuck on your setup?

    If you need help with a specific n8n node, database schema, or custom integration, you can schedule a 15-min call with our team at no cost.

    Schedule a free help call