mcpField
A
apify-link-prospecting-outreach

apify-link-prospecting-outreach

github.com/apify营销与增长283213 次安装5 周前更新
代码仓库

关于 apify-link-prospecting-outreach

用于 SEO 外链推广的营销技能,可从搜索结果中筛选潜在合作网站,并生成分层名单、切入理由和邮件草稿。适合需要推广指定页面的营销团队;结合 Ahrefs 指标评估潜在对象。

主要功能

  1. 01按关键词发现搜索结果潜客
  2. 02使用 Ahrefs 指标评分并分层
  3. 03筛除不合适或已联系域名
  4. 04为潜客匹配切入理由和邮件
  5. 05生成可复制的链接 размещ置内容

适用场景

  1. 01为品牌提及未加链接的页面拟定联系名单
  2. 02寻找替换竞争对手链接的机会
  3. 03为指定页面规划主题相关外链
  4. 04按域名筛选并整理外联邮件

MCP 相关

技能通过 Ahrefs MCP 工具获取潜客评分所需的指标。

安装

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

$npx skills add https://github.com/apify/awesome-skills --skill apify-link-prospecting-outreach

安装后在 Claude Code 中输入/apify-link-prospecting-outreach确认已加载。

包含的文件

除 SKILL.md 外,安装时一起下载的参考资料和脚本。

campaign.json.example
examples/
example-email-abc.md
example-email-resource-page.md
example-input.md
reference/
apify-actor-usage.md
email-templates.md
output-formats.md
troubleshooting.md
scripts/
build_prospects.py
enrich_prospects.py
fetch_run_artifacts.js
fetch_subactors_from_log.js
merge_subagent_outputs.py
package.json
run_actor.js
write_xlsx.py

详细介绍

链接开发外联

将目标 + 目标关键词 + 用户想推广的网址,转化为分级且可直接发送的外联名单:在 SERP 中排名的潜在对象及其 Ahrefs 评分的权威度、针对每个潜在对象的最佳推介角度、与外联类型匹配的邮件草稿,以及可直接复制粘贴的链接植入内容。

前提条件

(无需预先检查)

  • .env 文件中包含 APIFY_TOKEN
  • 可使用 Ahrefs MCP(此技能会调用 mcp__claude_ai_Ahrefs__* 工具为潜在对象评分)
  • Node.js 20.6+(支持原生 --env-file)
  • 在技能的 scripts/ 文件夹中进行一次性设置:npm install

辅助脚本(一个配置,四个步骤)

收集完步骤 1–2 的输入后,将其写入单个 campaign.json(架构见 campaign.json.example)。之后的每个脚本都会读取 --config campaign.json,因此 Agent 无需为每个营销活动创建单独副本。执行顺序:

# 1. Run the Actor (writes {base}.json + sub-Actor sidecars when --fetch-sub-datasets)
node --env-file=.env scripts/run_actor.js --actor "apify/link-prospecting-tool" --input '<json>' --timeout 1800 --fetch-sub-datasets --output {base}.json --format json

# 2. Build unified prospect table from the sidecars
python3 scripts/build_prospects.py --config campaign.json

# 3. (After Step 5 Ahrefs MCP calls → save to {base}_ahrefs_domain.json + {base}_ahrefs_page.json)
python3 scripts/enrich_prospects.py --config campaign.json

# 4. (After Step 8 sub-agents write outputs to /tmp/placement_outputs/row_*.json)
python3 scripts/merge_subagent_outputs.py --config campaign.json --outputs-dir /tmp/placement_outputs

# 5. Write the final xlsx + metadata sidecar
python3 scripts/write_xlsx.py --config campaign.json

如果运行器的客户端等待时间已到,但 Actor 仍在 Apify 上运行,请使用 scripts/fetch_run_artifacts.js --run-id <id> --output {base}.json,而不是重新启动。如果父级运行缺少 SUB_ACTOR_RESULTS(2026-05-20 之后的 Actor 架构),scripts/fetch_subactors_from_log.js 会从父级日志中解析子 Actor 的 runId。

工作流

复制此清单并跟踪进度:

Task Progress:
- [ ] Step 1: Collect required anchor inputs incl. goal (block on these)
- [ ] Step 2: Collect brand voice, partnership type, output format
- [ ] Step 3: Run apify/link-prospecting-tool
- [ ] Step 4: Pull leads, mentions, authors, and sub-Actor datasets
- [ ] Step 5: Enrich every domain with Ahrefs metrics, assign Prospect Tier
- [ ] Step 6: Run skip pass — flag rows to drop before drafting
- [ ] Step 7: Compute "Why This Prospect" tag per surviving row
- [ ] Step 8: Compose per-row 3-artifact placement + outreach-type-aware email
- [ ] Step 9: Render output in chosen format
步骤 1:必需的锚文本输入(首先询问,先于其他所有内容)

在每项必需输入都得到回答前,不要继续步骤 2。首次交互时就提出这些问题。去重输入(#7)为可选项,但仍必须明确询问。

  1. 本次营销活动的具体目标 — 选择一个预设,或提供自定义文本。目标决定跳过筛选、外联类型模板选择以及潜在对象等级阈值。必填。

    预设下游影响
    Recover unlinked brand mentions跳过筛选会删除所有 brand_mentioned_in_source 为 false 的行。默认外联类型 = unlinked-mention-claim。
    Replace competitor links跳过筛选会删除所有未标记为 Links to competitor 的行。默认外联类型 = competitor-link-replacement。
    Topical authority links to specific URL不筛选。等级阈值收紧(A 级 DR ≥ 50)。默认外联类型按行从 Why This Prospect 中选择。
    Maximum link volume from any relevant site不筛选。等级阈值放宽(A 级 DR ≥ 30)。默认外联类型按行选择。
    Custom用户提供的段落;会影响邮件语气和等级权重。不进行自动跳过筛选。
  2. 目标关键词 — 用户希望其链接出现在相邻位置的一个或多个关键词。该技能会针对每个关键词检索 SERP。至少需要一个。

  3. 品牌名称 — 用户的品牌或产品名称。没有此项,Actor 将无法运行(它是 brand 输入字段)。

  4. 产品/类别描述 — 用一到两个句子描述用户销售的产品、目标客户,以及产品所属类别。示例:“Apify — 可作为 API 运行无服务器爬虫的网页抓取平台。我们的客户是需要抓取数据、但不想管理基础设施的开发者和数据团队。” 必填。在步骤 6(主题契合度门槛)和步骤 7(对抗性提及检测)中使用,以识别与用户属于同一产品类别的潜在合作对象——无论推介内容如何,这些对象都不会添加链接。如果没有此项,该技能就无法区分真正的编辑合作机会和竞争对手的博客。

  5. 要添加链接的内容 URL — 将插入合作伙伴文章中的目标 URL。必填。

  6. 竞争对手 — 用户产品类别中可能会在自己的网站上发布“我们 vs 他们”对比页面的任何公司。请明确这样提出问题:“列出所有会撰写‘X vs YourBrand’对比页面的公司。无论如何,这些公司都不会为你添加链接——小型竞争对手也算。” 鼓励用户列出 10 家以上;大多数用户通常只列出 3–5 家显而易见的公司,因此会漏掉长尾竞争对手。映射到 Actor 中的 competitorDomains,并在步骤 6(跳过对抗性提及)和步骤 7(Links to competitor 原因标签)中重复使用。

    用户回答后,询问是否要从 Ahrefs 自动提取自然搜索竞争对手(不要强行推荐):“要我从 Ahrefs 提取你排名最高的自然搜索竞争对手并添加到此列表中吗?这会增加约 50 个 API 单位的用量,并找出你可能遗漏的小型竞争对手。” 如果用户同意且 Ahrefs MCP 可用,则对用户的域名(从输入 #5 中提取)调用 mcp__claude_ai_Ahrefs__site-explorer-organic-competitors,并将结果合并到 competitorDomains。如果 Ahrefs 不可用或用户拒绝,则仅使用用户提供的列表继续。

  7. 已推介过的域名(可选) — 用户在以往活动中联系过的域名。接受逗号分隔的列表、CSV/Sheet 路径,或“无”。该技能会在跳过阶段过滤这些域名,避免用户重复推介。非必填。

  8. 每个关键词的自然搜索结果数量 — 针对每个关键词检索多少条 Google 自然搜索 SERP 结果。若用户不确定,默认值为 10,但要提出此问题,让用户知道可以调整此项。映射到 organicResult。

  9. 要跟踪的大模型来源 — 多选。每个启用的引擎都会查询一个额外的 AI 搜索/聊天界面,并增加每条抓取结果对应的 Google Search Scraper 子 Actor 费用。默认值:全部启用。映射到 Actor 输入标志:

    选项Actor 标志费用影响
    ChatGPT SearchenableChatGpt按结果计收 Google Search Scraper 费用
    GeminienableGemini按结果计收 Google Search Scraper 费用
    Copilot(Microsoft / Bing)enableCopilot按结果计收 Google Search Scraper 费用
    PerplexityenablePerplexity按结果计收 Google Search Scraper 费用
    Google AI ModeenableAiMode按结果计收 Google Search Scraper 费用
    Google AI OverviewsenableAiOverviews免费 — 从已抓取的 SERP 中解析。无论预算如何,都应保持启用。
    向用户展示多选项,默认勾选全部六项。禁用单个引擎是除放弃 organicResult 之外主要的节省成本手段——建议至少保留 ChatGPT + Gemini(它们在 2026 年占据了由大模型驱动的发现流量中的最大份额)。
  10. 运行邮箱验证?——布尔值。默认值:yes。映射到 Actor 上的 enableEmailVerification。启用后,Actor 会验证 Contact Details Scraper 子 Actor 返回的每个邮箱,并为每条潜在客户记录添加验证状态标签(verified / catch-all / risky / invalid / unknown)。该技能会在步骤 6 中使用此状态(无效邮箱会自动跳过),并在输出中将其显示为 Email Verification 列。仅在用户的验证配额受到速率限制,或运行成本紧张的冒烟测试时才禁用。

完成 1–6 和 8–10 项的收集后(第 7 项可选),继续下一步。

步骤 2:次要输入项

接下来询问:

  1. 品牌信息和语气——简短介绍产品/品牌,并说明外联沟通的语气(例如“轻松友好”“正式的 B2B 风格”“创始人主导”)。每封生成的邮件都会原样使用这些信息。

  2. 合作类型——用户愿意提供的方案。决定每行邮件中替换的方案段落。外联类型模板会在步骤 8 中单独按行选择。

    选项提供内容
    ABC 链接互换三方链接互换:合作方链接到用户,用户链接到第三方,第三方链接到合作方。
    直接 A B 链接互换双方链接互换:合作方链接到用户,用户链接到合作方。
    纳入资源页面 / 列表请求将用户添加到现有的精选列表或汇总中。不提供互惠链接。
    单方面请求(不提供互惠)用户请求获得链接,但不提供任何回报——适用于未链接提及认领和失效链接替换。
    其他用户自行输入方案(付费展示、免费产品、联合创作内容等)。
  3. 输出格式:

    格式行为
    xlsxrun_actor.js 将带样式的电子表格写入磁盘。
    markdownAgent 在聊天中直接呈现表格,并在每行下方附上邮件草稿。
步骤 3:运行 Actor

Actor ID 为 apify/link-prospecting-tool。完整的输入架构位于 reference/apify-actor-usage.md。

此技能推荐的调用载荷(默认设置适用于优先拓展客户的工作流):

{
  "queries": "<keyword 1>\n<keyword 2>",
  "brand": "<user's brand name>",
  "ownDomains": ["<user-domain.com>"],
  "competitorDomains": [],
  "ignoreDomains": [
    "wikipedia.org", "github.com", "stackoverflow.com", "stackexchange.com",
    "reddit.com", "quora.com", "youtube.com", "twitter.com", "x.com",
    "linkedin.com", "facebook.com", "medium.com", "archive.org",
    "chromewebstore.google.com", "addons.mozilla.org", "apps.apple.com",
    "play.google.com", "microsoftedge.microsoft.com", "marketplace.visualstudio.com"
  ],
  "organicResult": 10,
  "maxContactsPerDomain": 3,
  "department": ["marketing"],
  "searchAuthorName": true,
  "includeMention": true,
  "enableChatGpt": true,
  "enableGemini": true,
  "enableCopilot": true,
  "enablePerplexity": true,
  "enableAiMode": true,
  "enableAiOverviews": true,
  "enableEmailVerification": true
}

六个 enable* LLM 来源标志与用户在步骤 1 输入项 #9 中的多选项一一对应。对于用户取消选择的引擎,传入 false。enableEmailVerification 对应步骤 1 输入项 #10。

ignoreDomains 默认值包含两组网站:

  • 大型网站和 UGC(wikipedia、github、stackoverflow、reddit 等)——范围太广,不适合作为内容合作伙伴来推介。
  • 应用 / 扩展程序市场(Chrome Web Store、Firefox Add-ons、Apple/Google Play、VS Code Marketplace 等)——这些是产品目录列表,没有内容编辑决策者。

不要自动将以下网站添加到 ignoreDomains(由用户决定):

  • kaggle.com、dev.to、substack.com、producthunt.com、g2.com、capterra.com、trustpilot.com 等 UGC/社区网站——有些用户向这些网站推介确实能获得实际价值。
  • rapidapi.com、programmableweb.com、publicapis.dev 等 API 目录——对某些产品(尤其是开发者工具品牌)很相关,对另一些则无关。仅当用户希望添加时,才将这些网站列为候选项。

步骤 6 中的 URL 模式跳过规则可过滤逐行噪声(子域名前缀、路径模式),这是 ignoreDomains 无法做到的。

department 默认仅为 ["marketing"]。在组合行数据时,此技能会优先选择返回的 marketing 部门中偏向内容编辑的联系人(见步骤 8)。只有当用户明确希望推介类似业务拓展的合作方案时,才添加 sales。只有当潜在客户的域名对应非常小的团队(1–5 人),且创始人可能同时担任编辑时,才添加 c_suite。

调用运行脚本:

node --env-file=.env ${CLAUDE_PLUGIN_ROOT}/scripts/run_actor.js \
  --actor "apify/link-prospecting-tool" \
  --input 'JSON_INPUT' \
  --timeout 1800 \
  --fetch-sub-datasets \
  --output YYYY-MM-DD_outreach.json \
  --format json

注意:

  • 建议将 --timeout 1800 设为客户端等待时长。Actor 本身会运行 15–50 多分钟,具体取决于关键词数量、LLM 引擎的并行扇出以及 enableEmailVerification。以往的校准运行耗时为 20–55 分钟。调高默认值可避免运行器提前放弃、但 Actor 仍在继续运行而导致结果不完整。
  • 如果客户端等待时间仍然耗尽,而 Actor 仍在 Apify 上运行(运行器退出时状态为 RUNNING 或 READY),不要重新启动 Actor。使用 scripts/fetch_run_artifacts.js --run-id <id> --output <file> 轮询现有运行并下载所有产物——输出格式与 run_actor.js --fetch-sub-datasets 相同。
  • --fetch-sub-datasets 会将同级文件与主输出一并下载:*_mentions.json、*_authors.json、*_serp.json、*_wcc.json。要填充所有输出列,需要这些文件。
第 4 步:访问所有数据集

Actor 的输出架构于 2026-05-20 或之前发生了变化。build_prospects 脚本必须处理新的结构;使用单独的 MENTIONS 数据集进行关联的旧版 skill 已无法正常运行。

当前架构(已于 2026-05-20 验证):

runner / fetcher 写入的文件来源填充字段
*_output.json(主文件)“All leads” 数据集Contact Full Name、Contact Job Title、Department、Seniority、Contact Email、Email Verification(当 enableEmailVerification: true 时)、Contact LinkedIn、Company、Domain。每个 lead 的 source_url[] 数组包含产生该联系人的文章 URL,每个 URL 都带有一个 brand_mentioned_in_source 布尔值——这是单个(URL、联系人)提及数据的新存储位置。
*_serp.jsonGoogle Search Results Scraper 子 Actor(每个 (query × engine) 组合对应一项)SERP Position、Article Title、Publish Date(通过 organicResults[]),以及每个 URL 的引擎归属(Google Organic、ChatGPT、Gemini、Copilot、Perplexity、Google AI Mode),通过关联 aiModeResult.sources[]、perplexitySearchResult.sources[]、chatGptSearchResult.sources[]、geminiSearchResult.sources[]、copilotSearchResult.sources[] 获取。ChatGPT 返回的 URL 带有 ?utm_source=chatgpt.com 查询后缀——关联之前请规范化 URL(去除跟踪参数)。
*_wcc.jsonWebsite Content Crawler 子 ActorPlacement Source Sentence、Placement With Link、Placement New Insertion、用于交叉核对的 Article Author、出站链接检查(用于添加 Links to competitor 和 Resource / roundup page 标签)。用于构建行的规范 URL 列表——每个经过正文抓取的 URL 都会出现在此处,包括未产生 lead 的 URL。
*_authors.jsonAI Web Scraper 子 Actor(当 searchAuthorName: true 时)Article Author、Author Source(设为 searchAuthorName)。注意:此子 Actor 经常在默认的 300s 时限内超时——仍会保存部分结果。

变化内容(与 2026-05-20 之前的运行相比):

  1. 不再有名为 MENTIONS / AUTHORS / DOMAINS_WITH_LEADS 的独立数据集——提及信息已并入 main_leads[i].source_url[]。
  2. 父运行的键值存储中不再有 SUB_ACTOR_RESULTS 记录。现在只能通过父运行日志中的正则表达式 \[apify\.<slug> runId:([A-Za-z0-9]+)\] 查找子 Actor 的 runId。如果缺少 KV 索引,runner 脚本的 --fetch-sub-datasets 标志现在会改为解析日志;独立脚本 scripts/fetch_subactors_from_log.js 对于 runner 已退出的运行也会执行相同操作。
  3. 提及数据架构已精简:source_url[i] 仅包含 {domain, brand_mentioned_in_source, url}——不再包含旧版 ChatGPT_mention / Perplexity_mention 等按引擎划分的标志。必须根据 SERP 子数据集的 LLM 结果子字段重建引擎归属(见上方 SERP 行)。

如果某列缺少来源,请填写 "Not found",并在 Notes 中添加手动查询提示。切勿捏造信息。

第 5 步:Ahrefs 数据补充与潜在对象分级

对于每个通过 Actor 筛选的唯一域名,通过 Ahrefs MCP 获取权威度和流量指标。针对每个域名并行调用全部三个工具(也要跨域名批量并行处理,以确保典型的 20–50 个潜在对象列表能在一分钟内完成此步骤):

Ahrefs 工具用途填充的列
mcp__claude_ai_Ahrefs__site-explorer-domain-rating(target = domain)域名评分Domain DR
mcp__claude_ai_Ahrefs__site-explorer-metrics(target = article URL,mode = exact)页面级自然流量(过去 30 天)Page Traffic
mcp__claude_ai_Ahrefs__site-explorer-backlinks-stats(target = domain)引用域名数量Referring Domains

如果 Ahrefs 没有返回数据(域名尚未被索引,或页面发布时间太短),将该列设为 "-",并在 Notes 中添加提示 "Ahrefs has no data — verify manually before pitching"。不要编造数值。

根据用户的目标和对应的阈值设置 Prospect Tier:

目标A 级B 级C 级
指向特定 URL 的主题权威链接DR ≥ 50 且 Page Traffic ≥ 300/月DR 30–49 或 Page Traffic 50–299低于以上阈值
从任何相关网站获取尽可能多的链接DR ≥ 30 且 Page Traffic ≥ 100/月DR 15–29 或 Page Traffic 20–99低于以上阈值
找回未加链接的品牌提及不适用——每次提及都值得争取;仅按 DR 分级(≥ 40 = A,20–39 = B,< 20 = C)
替换竞争对手链接按 DR 分级(≥ 50 = A,30–49 = B,< 30 = C)
自定义使用 主题权威 阈值

在第 8 步之前向用户展示各级别的数量分布,并让他们确认是为所有级别还是仅 A/B 级起草邮件。

第 6 步:跳过检查

起草任何邮件之前,逐行检查并应用跳过规则。被跳过的行应将 Outreach Status = "Skip",在 Notes 中写明一行原因,且不生成邮件或链接位置(节省 token 和用户审核时间)。

跳过规则(按顺序):

  1. 目标不匹配。 如果目标是 Recover unlinked brand mentions,且该行的 Mentions 数据显示 brand_mentioned_in_source: false,则跳过。如果目标是 Replace competitor links,且该行的 WCC 正文没有指向任何 competitorDomains 条目的出站链接,则跳过。

  2. 已联系过。 如果该行的域名与 Step 1 输入 #7 中可选的已联系名单里的某个条目匹配,则跳过。

  3. 自有域名/竞争对手域名泄漏。 Actor 应已过滤这些内容,但请再次检查——如果该行的域名与 ownDomains 或 competitorDomains 匹配,则跳过。

  4. 内容过时。 如果 Publish Date 距今超过 5 年,则跳过(编辑更新帖子的可能性较低)。

  5. 按 URL 模式跳过。 跳过 URL 匹配以下任一模式的行:

    • 子域名前缀:developers.*、docs.*、support.*、helpcenter.*、legacy.*、dsarequests.*、connectivity.*、community.*、dev.*(用作文档子域名时,例如 dev.example.com/api/)、api.* 仅当后面跟着明显属于文档的路径时(/reference/、/docs/、/spec/)。不要仅凭此规则跳过 rapidapi.com 或其他 API 目录域名——api.* 是子域名检查,而非子字符串检查。
    • 路径模式:/api-docs/、/reference/、/marketplace/、/extensions/、/profile/、/users/、/free-tools/、/spec/、/content/privacy、/content/terms、/content/dma、/content/how_we_work、/legal/、/_redirects、/sitemap。
    • 供应商产品页面模式:URL 以 -scraper.php 结尾、包含 -scraping.php、包含 -data-scraper.、包含 -data-scraping.、包含 /bots/、/extension/、/detail/(扩展详情页)。
  6. 非编辑类页面。 检查 WCC 页面正文。跳过供应商产品页、定价页、登录墙、注册页、条款/法律页面,以及正文少于 400 词的页面。少于 400 词即达到跳过阈值——大多数编辑类文章都在 800 词以上。

  7. 漏网的 UGC。 如果页面 URL 包含 /forum/、/thread/、/comments/、/answers/、/q/、/topic/、/discussion/,或 WCC 正文采用讨论回复的结构,则跳过。

  8. 类别匹配门槛(宽松)。 从用户的产品描述(Step 1 输入 #4)中提取 4–6 个类别关键词——这些词描述的是产品类别,而非用户 URL 的具体主题。网页抓取产品的关键词示例:scrape、scraping、scraper、crawl、extract、data extraction。CMS 产品的关键词示例:cms、headless、content、editorial。该行的 WCC 正文必须包含这些类别关键词中的至少 1 个。否则,以原因 Article isn't in user's product category (no '<kw>' match) 跳过——这会筛掉经 SERP 过滤后仍漏网的食谱博客、金融文章等类别不符的内容。

    对于非英语营销活动,类别词集需包含源语言和英语关键词——许多捷克语/德语/法语文章会在文中引用英文品牌名称和产品类别。捷克水过滤品牌的关键词示例:{filtr, filtrace, vod, voda, filter, filtration, water}。纯捷克语关键词集会漏掉由捷克作者撰写、混合使用捷克语和英语的文章。 此规则无法识别的已知漏判(第 8 步的逐行子 Agent 必须识别这些情况):

    • 销售完全相同产品类别的本地电商竞争对手。 过去的活动中,有多家区域性网店通过了机械筛选——通常是基于平台搭建的商店(例如 Shoptet、Shopify),文章正文中嵌有“加入购物车”按钮。子 Agent 正确地跳过了它们,但浪费计算资源是个隐患。此规则的未来版本应检测平台特征(平台资源包 URL、本地化的“加入购物车”字符串、/eshop/、正文中嵌有价格的产品卡片),并提前跳过。
    • 类别名称同形异义。 捷克语中的“filtr”也有摄影或咖啡领域中“滤镜/过滤器”的意思——咖啡滤纸或相机滤镜博客会通过此关,但并不真正匹配。子 Agent 会通过阅读正文上下文识别这些情况。

    类别关卡有意设置得较宽松。 这是类别检查,而非主题检查——更细致地判断“这篇具体文章是否适合我的这个具体 URL”由第 8 步的逐行子 Agent 负责。例如:如果用户的 URL 专门介绍如何爬取某个旅游网站,那么一篇从未提及该旅游网站的通用“python 网页爬取”指南会通过此关,因为它属于用户的类别。接下来,第 8 步的子 Agent 会决定是起草一条推荐植入内容(例如,添加一句点名该旅游网站的话),还是建议因内容不符而跳过。

    在第 6 步开始时向用户展示提取出的类别关键词列表,并让用户在筛选运行前添加或删除关键词。

  9. 检测对抗性提及。 当 brand_mentioned_in_source: true 时,扫描 WCC 正文中品牌提及前后 ±100 个字符的范围,查找负面语境词:vs、versus、alternative to、alternatives to、compared to、compared with、instead of、better than、worse than、pros and cons、comparison、review of。如果范围内出现任何一个词,则跳过,原因设为 Adversarial mention (likely competitor comparison page) — won't link。这可以识别“ScrapeHero vs Apify”页脚提及、“YourBrand 的替代品”榜单文章,以及类似的非链接语境。至关重要——没有此规则,unlinked-mention-claim 外联类型会触发数十个误报。

  10. 既无联系人,也无编辑联系途径。 如果 Contact Email = "Not found",且没有 Article Author,WCC 外链中也没有找到域名级别的联系页面,则跳过——没有可联系的人。

  11. 无效电子邮件(来自验证结果)。 如果运行了 enableEmailVerification: true,请检查每行的 Email Verification 状态。如果主要联系人的状态为 invalid,则在跳过该行前,先尝试备用联系人——过去的运行曾因主要联系人的电子邮件无效、但同一域名下存在已验证的备用联系人而漏掉 A 级候选对象。只有在没有任何备用联系人拥有已验证或未经检查的电子邮件时,才以原因 Email failed verification (invalid address) 跳过。catch-all、risky、unknown 状态仅供参考(不会自动跳过)——在 Email Verification 列中显示。verified 状态照常保留。如果本次活动未运行验证,则该列显示 -,且此规则不生效。

绝不要在 Notes 中建议使用外部查询服务或替代工具——例如 hunter.io、LinkedIn search、第三方验证服务。此技能的职责是如实展示我们找到的信息。信息缺失时(没有电子邮件、没有作者等),说明缺失之处并停止。用户知道该去哪里查;把他们自己的工具推荐回去既居高临下,也会让输出变得臃肿。

以上任一规则不通过的行都会在第 7 步之前跳过。跳过的行仍会出现在最终输出中(以便用户查看筛除了哪些内容),但植入内容和电子邮件单元格为空,且 Outreach Status = "Skip",并在 Notes 中注明原因。

第 7 步:“为什么选择这位潜在客户”标签

为每个保留的行计算一个或两个 Why This Prospect 标签,并按最有说服力的角度优先排序。这些标签用于驱动第 8 步中的外联类型模板选择。

标签触发条件权威来源
提及品牌,但没有反向链接Mentions 数据集中的 brand_mentioned_in_source: true 且 backlink_in_source: falseMentions 数据集
链接到竞争对手 [domain]WCC 页面正文包含出站链接,且其主机名与任意 competitorDomains 条目匹配WCC 数据集
[keyword] 的 SERP 前 3 名任意关键词的 SERP Position 为 1、2 或 3Google Search Scraper 子数据集
资源/汇总页面WCC 页面正文包含 10 个或更多出站链接,且页面标题或 H1 匹配 /(best|top|list|roundup|tools|resources|guide to)/iWCC 数据集
内容过时Publish Date 早于 24 个月但晚于 5 年(5 年及以上的内容已跳过)Google Search Scraper/WCC

每行最多可带两个标签。按说服力从强到弱排序,优先级如下:提及品牌,但没有反向链接 > 链接到竞争对手 > 资源/汇总页面 > SERP 前 3 名 > 内容过时。如果没有匹配的标签,将该列留为 "-" — 该行仍会纳入外联,只是没有特别切入角度。

第 8 步:为每行撰写植入方案和邮件

每个保留的行都需要生成三项植入材料和一份邮件草稿。务必遵守以下质量规则:

  1. 不得捏造信息。 如果文章作者或联系邮箱未知,将字段设为 "Not found",并留下一条简短的事实说明(例如,"未找到此联系人的邮箱" 或 "未检测到作者")。不要在 Notes 中建议使用外部查找工具或变通方法 — 原因见第 6 步规则 11。只陈述事实即可。

  2. 优先选择偏编辑类联系人。 如果 All leads 数据集为同一域名返回了多个联系人,优先选择 jobTitle 匹配 /editor|content|writer|managing|editorial|blog|copy/i 的联系人;除非公司只有 1–5 人,否则将 jobTitle 匹配 /ceo|cfo|cto|founder|chief|vp\b|president/i 的联系人列为次选。在该行中显示选定的联系人;在 Notes 中保留其他联系人,格式为 "备用联系人:<name1>(<title>)、<name2>(<title>)"。

  3. 三种植入方式 — 按以下优先级顺序尝试。 使用 WCC 子数据集中的页面文本。按顺序尝试策略 1 → 2 → 3;遇到第一个能自然契合的策略时即停止。将所用策略写在 Notes 字段开头:Placement: drop-in/Placement: additive/Placement: new insertion。

    策略 1 — 直接植入(优先)。 在文章中找到一个句子,使用户的 URL 能添加到现有词语上,且无需更改周围的任何文字。链接需添加到作者已写好的现有词语或短语上。输出:

    • Placement Source Sentence = 文章中的原句,逐字照录。
    • Placement With Link = 在现有词语/短语上添加链接后的同一句子。不添加新文字、不改写、不删减。 示例:原句 = "Tools like Octoparse and BeautifulSoup work well for hotel data." → 添加链接后 = "Tools like Octoparse and **[BeautifulSoup](URL)** work well for hotel data."(将链接添加到现有词语上)。编辑无需审核任何新文字 — 只需添加超链接。
    • Placement New Insertion = "-"。

    当文章中已经提到与用户 URL 适配的品牌、工具或技术时,适合采用直接植入。这是所有外联方式中阻力最小的请求:“能否给您已经写好的词语添加一个超链接?” 策略 2 — 添加式(次选)。 如果没有可直接替换的目标,但文章中有一句话适合自然地承接用户的 URL,则保留原句不变,并在其后添加一句新句子。新句子应引出文章尚未涵盖、且用户的 URL 能满足的相关读者需求。输出:

    • Placement Source Sentence = 原文中的完整句子。
    • Placement With Link = 原句保持不变,后接 → 和一句包含链接的补充句。例如:source = "By integrating with Acme Travel's APIs, developers can enrich their platforms with hotel data." → with-link = "By integrating with Acme Travel's APIs, developers can enrich their platforms with hotel data. → ...with hotel data. In need of competitor pricing data the API doesn't expose? Then you need a [hotel-data scraper](URL)." 保持原句不变;补充句是唯一新增的文案。
    • Placement New Insertion = "-"。

    补充句必须:(a) 提出原句未涉及的读者需求;(b) 将该需求与用户的 URL 联系起来;(c) 只有一句,不超过 25 个单词,并采用文章的语气。

    策略 3 — 新增插入(最后手段)。 只有在直接替换和添加式方案都不可行时(例如,文章正文中没有相关句子),才起草一段全新的 1–2 句内容,并精确说明插入位置:

    • Placement Source Sentence = "-"。
    • Placement With Link = "-"。
    • Placement New Insertion = 起草的段落 + 精确位置说明("在 H2 'Y' 下的章节中,紧接以 '…X.' 结尾的句子后,作为新段落插入。")。

    如果连新增插入也无法起草(文章主题与用户的 URL 不匹配),则设定 Outreach Status = "Skip",并添加 Notes: "No natural placement — article topic mismatch"。但是,第 6 步规则 8 中的主题匹配门槛本应已筛出这种情况;如果某行进入第 8 步后仍无法安排插入位置,这说明门槛需要补充更多关键词。

    每一条未筛除的记录都必须交由子 Agent 处理,而不只是 Tier A/B/仅提及的记录。机械式跳过筛查(第 6 步)会剔除明显不合格的潜在对象(竞争对手域名、文档子域名、政策页面、联系人失效的记录、类别不符的文章)。所有通过筛查的对象都值得认真考虑,子 Agent 会做出最终匹配判断:阅读文章,尝试安排插入(直接替换 → 添加式 → 新增插入),然后起草邮件,或返回 placement_strategy = "skip" 并附上与内容相关的原因。最终草稿不得使用 Python 模板、正则表达式或关键词评分——这些方法会生成生硬的机械式拼接内容,放在上下文中读起来不自然(我们在真实推广活动中已见过这种失败案例)。

    并行启动子 Agent:每条未筛除的记录对应一个子 Agent,并向其提供 WCC 文本、用户 URL 上下文、联系人信息、品牌语气和合作邀约。输出架构(插入策略、三个插入列的值、邮件主题 + 正文、跳过建议、备注)将合并回电子表格对应行。

    如果子 Agent 在审阅内容后决定跳过某条记录,则设定 Outreach Status = "Skip",并在 Notes 中填写 Agent 给出的原因——格式与第 6 步机械式跳过相同,只是理由更加细致。

  4. 根据 Why This Prospect 标签和用户目标,逐行确定 Outreach Type:

    触发条件Outreach Type
    存在标签 Mentions brand, no backlinkunlinked-mention-claim
    存在标签 Links to competitorcompetitor-link-replacement
    存在标签 Resource / roundup pageresource-page-inclusion
    存在标签 Outdated contentoutdated-content-replacement
    以上均不符合,或仅有 Top-3 SERP 标签topical-niche-edit
    从 reference/email-templates.md 中提取匹配的模板。用户在步骤 2 中给出的 Partnership type 答案会代入模板中的 {{offer_paragraph}} 占位符——外联类型决定结构和开场切入点,合作类型决定提议内容。
  5. Suggested Email Copy 必须使用用户的品牌语气。 根据 reference/email-templates.md 中的语气替换规则,逐字应用语气段落。如果用户跳过了语气输入,则使用通用专业语气作为默认值,并在 Notes 中注明。

5a. 邮件必须包含确切的放置文案——逐字呈现。 收件人不应需要追问“您建议使用什么措辞?”或点击另一个单元格来查看提议文案。请直接在邮件中嵌入提议内容:

  • 对于 drop-in:内嵌引用来源句子和添加链接后的版本。示例:"在您的句子 'Tools like X and Y work well for Z' 中,您愿意将 'Y' 改成指向 <URL> 的超链接吗?"
  • 对于 additive:逐字引用锚点句子,并附上您建议添加的确切后续句子。示例:"紧接在您的句子 'X happens because Y.' 后面,您愿意添加:'For the Z case specifically, see <URL>.'吗?"
  • 对于 new insertion:引用新段落应接在其后的锚点句子,然后内嵌完整的拟议段落。示例:"在 'Honorable mentions' 部分中,紧接在 'each platform has its own trade-offs.' 后面,您愿意添加这段内容吗:'<full paragraph with link>'?"

邮件本身就是提议。如果措辞没有出现在邮件中,提议就不完整。像“很乐意帮您起草”/“很乐意提供确切措辞”/“添加一个包含链接的后续句子”等模糊表达,都是内容技能缺陷——务必改写为包含逐字呈现的提议文案。

  1. 字数上限:邮件不超过 150 个单词(主题 + 正文)。

  2. 必须进行个性化。 每封邮件都必须以对特定文章的具体引用开头(标题 + 一句话概述文章内容)。不要使用“我很喜欢您的文章”这类通用开场白。

步骤 9:呈现输出

Markdown 格式——Agent 在聊天中直接呈现:

  1. 一行标题,包含 Apify 运行 ID 和分级统计(A: 8, B: 15, C: 7, Skipped: 12)。
  2. 每位潜在客户一行 Markdown 表格,包含最具行动价值的列(分级、原因、联系人、放置摘要)。已跳过的行在底部单独的折叠区域中呈现。
  3. 表格下方,每条未跳过的记录对应一个围栏代码块,包含邮件草稿(主题 + 正文),并标注行索引、分级和外联类型。

xlsx 格式——步骤 5–8 完成后,scripts/write_xlsx.py --config campaign.json 会生成一个包含 2 个工作表的工作簿。

xlsx 文件包含两个工作表:

  • Outreach——仅包含有效记录,包含全部 30 列。这是可直接用于发送的交付文件。按 Prospect Tier 升序排列(A 优先),然后按 Domain DR 降序排列,再按 SERP Position 升序排列。
  • Skipped——已跳过的记录,包含精简列:Domain、Article URL、Article Title、Skip Reason(从 Notes 中提取)、Source Engines、Why This Prospect。此工作表便于审查被筛除的记录,同时避免主视图杂乱。这里不会显示缺失的 Ahrefs 列,因此不会再让人困惑为何数据为空。

用户打开文件后,默认进入 Outreach——只显示可采取行动的潜在客户。用户可以切换到 Skipped 进行审查。此模式取代了旧版将跳过记录标红、全部放在单个工作表中的做法。

两种格式都会另外生成一个 run_metadata.json 文件:{ runId, actorId, startedAt, finishedAt, inputs, datasetIds, tierCounts, skipCounts }。将其放在主输出文件旁边。

输出行架构(30 列)

SERP Position、Source Engines、Keyword、Article Title、Article URL、Domain、Domain DR、Page Traffic、Referring Domains、Prospect Tier、Why This Prospect、Article Author、Author Source、Publish Date、Contact Full Name、Contact Job Title、Department、Seniority、Contact Email、Email Verification(取值为 verified / catch-all / risky / invalid / unknown / -)、Contact LinkedIn、Company、Outreach Type、Partnership Offer、Placement Source Sentence、Placement With Link、Placement New Insertion、Suggested Email Copy、Outreach Status(默认值为 "Not started",跳过的行使用 "Skip")、Notes(自动标记 + 跳过原因 + 手动提示 + 其他联系人)。

包含各列类型和来源数据集的完整架构见 reference/output-formats.md。

错误处理

错误 / 症状处理方法
APIFY_TOKEN not found请用户创建包含 APIFY_TOKEN=your_token 的 .env 文件。在 console.apify.com/account/integrations 获取令牌。
Ahrefs MCP 不可用跳过步骤 5。将 Domain DR、Page Traffic、Referring Domains、Prospect Tier 设为 "-",并在输出标题中添加一行说明,解释未计算层级。继续执行工作流的其余部分。
Cannot find module 'xlsx'在技能的 scripts/ 文件夹内运行 npm install。
Error: 'brand' is required用户跳过了步骤 1 的锚点 #3。重新询问品牌名称。
Actor 运行 TIMED-OUT(客户端超时,Actor 仍在 Apify 上运行)不要重新启动。使用 node --env-file=.env scripts/fetch_run_artifacts.js --run-id <runId> --output YYYY-MM-DD_outreach.json --timeout 1800 轮询现有运行,并在其终止时下载所有数据集。输出结构与运行器相同。
Actor 运行 TIMED-OUT(Actor 自身运行时间超过其 timeoutSecs)参阅 reference/troubleshooting.md。降低 organicResult、减少关键词,或停用部分 LLM 引擎。这几乎不是超时原因——通常是客户端等待超时。
Author = Not found对于约 30% 没有署名信息的页面,这是预期情况。技能会写入 "Not found",并在 Notes 中添加手动查找提示。不得捏造信息。AI Web Scraper 子 Actor 经常会在默认的 300s 时限内爬取过程中超时(以往的活动中,曾因此一次丢失约 7 个高 DR 网站的作者数据);发生这种情况时,_authors.json 数据集仍包含超时前已完成的部分结果。写入 "Not found" 前,Agent 应尝试使用 WCC metadata.author / openGraph article:author / JSON-LD Person.name 作为备用来源。
缺少子 Actor 数据集(运行 --fetch-sub-datasets 后没有 _mentions.json / _authors.json / _serp.json / _wcc.json)Actor 的输出架构在 2026-05-20 当日或之前已更改:SUB_ACTOR_RESULTS 不再存储于 KV store 中,名为 MENTIONS / AUTHORS / DOMAINS_WITH_LEADS 的数据集也已移除。运行器脚本现在会自动回退到解析日志;但如果未能回退,请运行 node --env-file=.env scripts/fetch_subactors_from_log.js --run-id <id> --base <prefix>,从父级日志中可见的子 Actor runIds 生成 _serp.json、_wcc.json、_authors.json。提及数据现在嵌入在 main_leads[i].source_url[] 中,而非单独的文件。
Contact Email = Not foundContact Details Scraper 子 Actor 未能从网站找到邮箱。将该字段设为 "Not found",并在 Notes 中留下一行事实说明("No email found for this contact")。不得捏造信息,也不要建议使用外部工具。如果联系人和作者信息都缺失,跳过处理步骤(步骤 6,规则 7)会移除该行。
目标筛选器跳过了所有行用户的目标相对于 SERP 结果而言过于狭窄。建议放宽目标(例如,使用 Topical authority 代替 Recover unlinked brand mentions),或扩展关键词。
0 leads returned关键词过于狭窄,或 ownDomains / competitorDomains 筛掉了所有 SERP 结果。扩大关键词范围、缩小排除范围,或提高 organicResult。
成本高于预期子 Actor 扇出(Google Search Scraper、WCC、Contact Details Scraper、AI Web Scraper)会叠加成本。参阅 reference/apify-actor-usage.md 中的成本部分。要降低成本:移除 searchAuthorName,停用 AI 平台(enableChatGpt: false 等),将 maxContactsPerDomain 降至 1,将 organicResult 降至 5。

评论

支持 Markdown