mcpField
C
cold-email-outreach

cold-email-outreach

github.com/nikiandr营销与增长1116 次安装31 周前更新
代码仓库

关于 cold-email-outreach

将 Supabase 中符合条件的潜在客户转化为冷邮件活动的技能,涵盖筛选受众、撰写邮件序列、设置活动和记录数据。它会根据所选工具调整流程:Smartlead 使用 MCP 自动化,其他列出的工具通过 CSV 导出并提供导入指引。

主要功能

  1. 01筛选 Supabase 潜在客户
  2. 02执行 84 天联系冷却期
  3. 03规划并审核邮件序列
  4. 04自动设置 Smartlead 活动
  5. 05导出适配工具的 CSV 文件
  6. 06将触达记录写入 Supabase

适用场景

  1. 01启动经过审核的 Smartlead 活动
  2. 02为 Instantly、Lemlist 或 Apollo 准备 CSV 导入
  3. 03跟踪活动触达记录与联系冷却期

MCP 相关

对于 Smartlead,该技能通过 MCP 工具列出邮件账户、创建活动、配置序列与设置、导入潜在客户,并在获得批准后启动活动。其他触达工具采用 CSV 导出。

安装

复制下面的命令,在终端中运行。

$npx skills add https://github.com/nikiandr/goose-skills --skill cold-email-outreach

安装后在 Claude Code 中输入/cold-email-outreach确认已加载。

附带文件skill.meta.json

详细介绍

冷邮件外联

外联流程的最后一公里。从 Supabase 获取符合条件的潜在客户,使用 email-drafting 技能构建邮件序列,将营销活动加载到用户选择的外联工具中,并将所有记录写回 Supabase。

**与工具无关:**询问用户使用哪种外联平台。如果已配置 MCP 工具,则默认使用 Smartlead。对于其他工具或手动工作流,则回退到 CSV 导出。

自动加载时机

在以下情况下加载此技能:

  • 用户说“启动营销活动”“发送外联邮件”“给这些潜在客户发邮件”或“设置冷邮件”
  • 上游技能使用“创建邮件营销活动”进行连接,或传递 supabase-eligible-leads
  • 用户完成 lead-qualification,并希望采取后续行动

支持的外联工具

此技能不会假设用户使用特定工具,而是先询问,再进行适配。

工具集成方式工作方式
Smartlead(默认)MCP 工具(mcp__smartlead__*)全自动化:创建营销活动、添加序列、导入潜在客户、配置日程并启动
InstantlyCSV 导入生成符合 Instantly 导入格式的 CSV,由用户手动上传
LemlistCSV 导入生成包含 Lemlist 兼容列的 CSV
ApolloCSV 导入生成符合 Apollo 序列导入格式的 CSV
手动 / 其他CSV + 说明将潜在客户和邮件导出为通用 CSV,并提供设置说明

工具选择逻辑:

  1. 在阶段 0 询问用户:“你使用哪种外联工具?”
  2. 如果是 Smartlead → 使用 MCP 工具实现全自动化
  3. 如果是 Instantly / Lemlist / Apollo → 生成对应工具的专用导入 CSV
  4. 如果是 其他或未知 → 生成通用 CSV(每次触达包含 email、first_name、last_name、company、title、subject、body),并询问用户该工具的导入要求

前置条件

Supabase

人员必须按照 tools/supabase/schema.sql 中的架构存储在 Supabase 中。people 和 outreach_log 表必须存在。如果是全新设置,请运行 python3 tools/supabase/setup_database.py。

.env 中的环境变量:

SUPABASE_URL=https://xxx.supabase.co
SUPABASE_SERVICE_ROLE_KEY=eyJ...
外联工具
  • **Smartlead:**可通过 mcp__smartlead__* 使用 MCP 工具。无需额外设置。
  • **其他所有工具:**只需导出 CSV,无需 API 密钥。

阶段 0:信息收集

一次性询问所有问题,并按类别整理。跳过上游技能已经回答的问题。

营销活动目标
  1. 目标是什么?(预约会议、推动演示申请、获得回复、培育潜在客户)
  2. 外联切入点或吸引点是什么?(招聘信号、替代竞争对手、基于活动、基于痛点、冷门数据库)
  3. 这次营销活动应该叫什么名字?
外联工具
  1. 你使用哪种外联工具?(Smartlead / Instantly / Lemlist / Apollo / 其他 / 直接给我 CSV)
潜在客户筛选
  1. 应该联系哪些潜在客户?选项:
    • 指定 client_name 的所有潜在客户
    • 特定的 icp_segment
    • 职位名称模式(例如,“运营副总裁”“销售总监”)
    • 行业或地区筛选条件
    • 高于某一阈值的 qualification_score
    • 特定的 source(crustdata、apollo、linkedin 等)
    • 自定义筛选条件(描述你的需求)
  2. 有哪些排除条件?(特定公司、近期联系过的潜在客户、某些职位)
  3. 营销活动规模上限是多少?(默认:200)
序列设计
  1. 需要多少次触达?(默认:3)
  2. 每次触达之间间隔多久?(默认:第 1 天 / 第 5 天 / 第 12 天)
  3. 个性化级别?(第 1 级:仅合并字段 / 第 2 级:按细分群体个性化 / 第 3 级:为每位潜在客户单独撰写)
发送配置(导出 CSV 时跳过)
  1. 应使用哪些电子邮件账户发送?(列出账户,或说“使用所有可用账户”)
  2. 发送日程?(默认:按收件人所在时区,周一至周五上午 8 点至下午 5 点)
  3. 每个账户的每日发送上限是多少?(默认:每天 30 封)
  4. 是否跟踪打开和点击?(默认:跟踪打开,不跟踪点击)

阶段 1:从 Supabase 中筛选潜在客户

连接

使用共享的 Supabase 客户端:

import sys, os
sys.path.insert(0, os.path.join("tools", "supabase"))
from supabase_client import SupabaseClient

client = SupabaseClient(os.environ["SUPABASE_URL"], os.environ["SUPABASE_SERVICE_ROLE_KEY"])
构建筛选条件

将用户条件映射为 people 表上的 PostgREST 查询参数:

用户表述PostgREST 筛选条件
“VP Operations”title=ilike.*VP Operations*
客户“happy-robot”client_name=eq.happy-robot
评分 > 7qualification_score=gte.7
有已验证的邮箱email_verified=eq.true
行业“logistics”industry=ilike.*logistics*
地点“San Francisco”location=ilike.*San Francisco*
来源“crustdata”source=eq.crustdata
84 天内未联系过or=(last_contacted.is.null,last_contacted.lt.{84_days_ago})
冷却期筛选(必需)

始终排除 84 天(12 周)内联系过的人。这不是可选项。

使用共享客户端的 check_cooldown() 方法:

in_cooldown = client.check_cooldown(client_name="happy-robot", cooldown_days=84)
# Returns set of person_id strings still in cooldown

或者直接查询:

  1. 查询 outreach_log,找出 sent_date 在过去 84 天内的 person_id:
    GET /rest/v1/outreach_log?select=person_id&sent_date=gte.{84_days_ago}&status=neq.bounced&client_name=eq.{client}
    
  2. 将这些 person_id 收集到排除集合中
  3. 在 people 查询中添加 id=not.in.({excluded_ids})
展示并确认

展示一个示例表格(10-15 条潜在客户),包含:

  • 姓名、职位、公司、行业、评分、邮箱、上次联系时间

告知用户:符合条件的潜在客户总数、因冷却期排除的数量、拥有已验证邮箱的数量。

请用户确认或调整筛选条件后再继续。

第 2 阶段:序列设计

在撰写任何文案之前,先以表格形式展示序列计划:

触达天数邮件类型框架CTA
11冷启动介绍Signal-Proof-Ask15 分钟通话
25新角度 / 资源PAS提供资源
312社会认同BAB愿意聊聊吗?

在第 3 阶段生成文案之前,先征得用户对结构的批准。

第 3 阶段:邮件生成

加载 email-drafting 技能,并向其传递:

  • 活动背景(目标、角度、产品、证明要点)
  • 第 2 阶段的序列结构
  • 所选列表中的 3-5 条示例潜在客户
  • 个性化级别
  • 语气偏好
按个性化级别

级别 1(通用): 每次触达生成一个带合并字段({first_name}、{company}、{title})的模板。所有潜在客户使用同一模板。

级别 2(细分): 每个细分群体的每次触达生成一个模板。根据角色、行业或信号类型定义细分群体。在不同细分群体之间替换痛点和证明要点。

级别 3(深度): 为每位潜在客户的每次触达生成唯一邮件。最多处理 50 位潜在客户;超过此数量时建议使用级别 2。

审核流程
  1. 先为 3-5 位潜在客户生成邮件样例
  2. 提交给用户审核
  3. 迭代直至获批(最多 3 轮)
  4. 获批后生成其余邮件

第 4 阶段:活动设置

使用 Smartlead(MCP 自动化)

通过 MCP 工具实现完整自动化。按以下顺序执行:

第 1 步:列出邮箱账户

mcp__smartlead__get_email_accounts

展示可用账户。由用户选择要使用的账户。

第 2 步:创建活动

mcp__smartlead__create_campaign
  name: {campaign_name}

保存返回的 campaign_id。

第 3 步:添加序列步骤

mcp__smartlead__save_campaign_sequences
  campaign_id: {campaign_id}
  sequences: [
    { seq_number: 1, subject: "...", email_body: "...", seq_delay_details: { delay_in_days: 0 } },
    { seq_number: 2, subject: "...", email_body: "...", seq_delay_details: { delay_in_days: 4 } },
    { seq_number: 3, subject: "...", email_body: "...", seq_delay_details: { delay_in_days: 7 } }
  ]

合并变量映射: 将 {first_name} → {{first_name}}、{company} → {{company}}(Smartlead 使用双大括号语法)。

第 4 步:导入潜在客户(每批 100 条)

mcp__smartlead__add_leads_to_campaign
  campaign_id: {campaign_id}
  lead_list: [{ email: "...", first_name: "...", last_name: "...", company_name: "...", ... }]

如果潜在客户超过 100 条,则按每组 100 条分批处理。

第 5 步:分配发送账户

mcp__smartlead__add_email_accounts_to_campaign
  campaign_id: {campaign_id}
  email_account_ids: [...]

第 6 步:设置计划

mcp__smartlead__update_campaign_schedule
  campaign_id: {campaign_id}
  schedule: { ... }

第 7 步:配置设置

mcp__smartlead__update_campaign_settings
  campaign_id: {campaign_id}
  settings: { track_opens: true, track_clicks: false, stop_on_reply: true }
如果使用基于 CSV 的工具(Instantly、Lemlist、Apollo 等)

步骤 1:生成 CSV

列取决于个性化等级:

等级 1(所有人使用相同模板):

  • CSV 列:email、first_name、last_name、company、title、custom_field_1(信号/切入点)
  • 另建一个文件,存放序列模板(包含合并字段的主题和正文)

等级 2/3(针对每个细分群体或潜在客户撰写邮件):

  • CSV 列:email、first_name、last_name、company、title、touch_1_subject、touch_1_body、touch_2_subject、touch_2_body、touch_3_subject、touch_3_body

步骤 2:保存文件

skills/cold-email-outreach/output/{campaign-name}-{YYYY-MM-DD}.csv

步骤 3:提供特定工具的导入说明

Instantly:

  • 上传 CSV → Sequences → Create new sequence
  • 映射列:Email → email、First Name → first_name 等
  • 将序列模板粘贴到各个步骤中
  • 设置步骤间的延迟时间

Lemlist:

  • People → Import → Upload CSV
  • 将自定义变量映射到各列
  • 创建营销活动 → 添加邮件步骤 → 插入变量

Apollo:

  • Sequences → Create Sequence → 添加邮件步骤
  • Contacts → Import → Upload CSV
  • 将导入的联系人添加到序列中

其他工具/手动操作:

  • 提供 CSV 路径并说明列结构
  • 询问用户的工具要求什么格式,如有需要则进行调整

阶段 5:审核并启动

展示营销活动摘要:

Campaign: {name}
Leads: {count}
Sequence: {touches} touches over {days} days
Sending: {accounts} accounts × {daily_limit}/day = {daily_volume} emails/day
Estimated completion: {date}
Tool: {smartlead/instantly/etc.}
必须获得明确批准

**未经用户明确确认,不要激活营销活动。**展示摘要,然后询问:“准备好启动了吗?输入 ‘yes’ 以激活。”

  • Smartlead: mcp__smartlead__update_campaign_status → 设为 active
  • **CSV 工具:**告知用户文件已准备好导入,并提供文件路径

阶段 6:跟踪与记录

数据库写入策略

**此阶段的所有数据库写入都必须事先获得用户在阶段 5 的启动批准。**阶段 5 的批准(“准备好启动了吗?”)同时涵盖营销活动激活和后续记录。但是,如果营销活动是导出为 CSV(而非通过 Smartlead 启动),则记录前要先向用户确认——他们可能还没有实际导入或发送。

记录到 Supabase

启动(或导出)后,将记录插入 outreach_log:

POST /rest/v1/outreach_log
Prefer: return=minimal

[
  {
    "person_id": "{person_uuid}",
    "campaign_name": "{campaign_name}",
    "external_campaign_id": "{smartlead_campaign_id or null}",
    "channel": "email",
    "tool": "{smartlead/instantly/lemlist/apollo/manual}",
    "sent_date": "{ISO timestamp}",
    "status": "sent",
    "client_name": "{client_name}"
  },
  ...
]

或者使用共享客户端:

client.log_outreach(entries)

**对于基于 CSV 的工具:**记录时将 status 设为 "exported"。用户确认已在工具中启动营销活动后,将其改为 "sent"。

更新人员记录

为此营销活动中的所有人员更新 people 表中的 last_contacted:

PATCH /rest/v1/people?id=in.({person_ids})
{ "last_contacted": "{ISO timestamp}" }
展示摘要
{count} people logged to outreach_log
last_contacted updated for {count} people
Campaign ID: {id}
Cooldown active until: {date + 84 days}
Next eligible re-contact: {date}

冷却期执行规则

本节说明此技能中使用的冷却期逻辑。

规则详情
默认冷却期从 sent_date 起算 84 天(12 周)
邮件退回的潜在客户不受冷却期限制——邮件从未送达。检查冷却期时使用筛选条件:status=neq.bounced
活跃营销活动中的潜在客户始终不符合条件——如果某位潜在客户处于活跃营销活动中(状态 = "sent",且未回复/退回),则不能将其添加到其他营销活动
用户覆盖规则用户可以明确要求对特定潜在客户覆盖冷却期——允许前先征求确认
last_contacted 为空从未联系过的潜在客户始终符合条件

输出目录

营销活动导出文件保存至:

skills/cold-email-outreach/output/

如果此目录不存在,请创建该目录。文件命名格式为 {campaign-name}-{YYYY-MM-DD}.csv。

评论

支持 Markdown