signal-prospector

signal-prospector

Enables B2B prospecting from natural language: detect buying signals, score leads against ICP, enrich decision-makers, and draft personalized outreach messages via Claude.

Category
访问服务器

README

Signal Prospector

A signal-based B2B prospecting engine that runs on free infrastructure. It finds companies that just entered "buying mode" — funding, new leadership, hiring, expansion, competitor/topic engagement — scores them against your Ideal Customer Profile, enriches the decision-maker with a free MX-validated email guess, and drafts a personalized, signal-aware outreach message. Inbound replies get a ready-to-send AI draft.

The whole thing is exposed three ways: a CLI, a self-serve Flask dashboard, and an MCP server so you can prospect from Claude in natural language.

Prospector dashboard: pipeline KPIs, a lead funnel, and the hottest scored leads with their triggering signals.

The Flask dashboard. Every score and the funnel above are computed by the engine — the companies, contacts and signals shown here are illustrative demo data, not real records.

The leads table makes the scoring transparent: each row carries its triggering signal, the enriched contact and email, a lifecycle status, and a plain-English "why" the lead scored where it did.

Leads table: score, company, signal, contact, email, status and an explainable 'why' column.


Why it's interesting

Most "prospecting tools" are either a static lead list or a black box. This one is the opposite: a transparent detect → score → enrich → draft → reply → optimize loop where every number is explainable and every external call is free by default.

  • Eight signal families behind one contract. Funding, job-change, leadership-change, hiring, expansion, competitor-engagement, topic-engagement and news are each a small detector returning a typed Signal, registered in a registry and fed injected free search_fn / fetch_fn functions — so adding a detector, or swapping the search backend, is a drop-in.
  • An explainable ICP scorer, not a ranking black box. The 0–100 score is a precise weighted blend of right buyer × right moment (formula below), and every lead ships a plain-English "why this lead" reason string.
  • A free email-enrichment waterfall. Decision-maker discovery parses public search snippets, strips RTL/zero-width Unicode, then infers the most likely corporate email from name+domain patterns and validates the domain over DNS — no paid enrichment vendor, and it never invents an address it can't form.
  • Free-first by construction. Discovery is self-hosted SearXNG; fetching is an httpx → headless-browser → PDF cascade with trafilatura extraction; generation is DeepSeek (any OpenAI-compatible endpoint). Paid fallbacks stay off unless you key them.
  • 561 tests across detectors, scorer, enrichment waterfall, reply classifier and the web layer. Unknown data always stays n/a rather than being fabricated.

The scoring, precisely

No hand-waving — this is exactly how a lead's score is computed (prospector/icp.py):

Quantity Definition Notes
Final score (0–100) 100 × (0.55 · signal_score + 0.45 · icp_match) "right moment" weighted slightly over "right buyer"
icp_match (0–1) 0.45 · company_fit + 0.55 · contact_fit the person matters more than firmographics
company_fit mean of the configured industry / geo / size / keyword checks missing evidence is neutral (0.5 baseline); only positive matches lift, and an exclude_keyword hit is a hard 0
signal_score (0–1) clamp(best + 0.35·second + 0.12·third, 0..1) where each term is strength × recency the strongest recent signal dominates; extra strong, fresh signals add a decayed bonus
strength per-kind base weight (funding 0.95, leadership 0.9, …) a detector may override per-signal
recency step decay: ≤7d → 1.0, ≤30d → 0.85, ≤90d → 0.55, ≤180d → 0.3, older/future → 0.15 a future dateline is treated as stale, never as "freshest"

Because missing evidence is neutral rather than punishing, a strong buying signal can still surface a lead whose firmographics are only partly known — which is the whole point of signal-based prospecting.

The email waterfall, precisely

Enrichment never fabricates an address (prospector/enrich.py):

  1. Resolve a mail-capable domain from the company site, rejecting aggregator/social hosts and website-builder domains (*.wixsite.com, *.github.io, …) that are never the company's own mail domain.
  2. Generate candidates from the person's name, most-likely-first: {first}.{last} · {first} · {f}{last} · {first}{l} · {first}_{last} · {last} — dropping al-/el- prefixes and rejecting RFC-implausible locals (a bare initial like bisrat.d.@ is never emitted).
  3. Classify the domain over DNS: verified (publishes MX), risky (resolves but no MX), invalid (NXDOMAIN or RFC 7505 null-MX). Outbound-25 SMTP probing is deliberately not done.

How it works

 ICP (a preset, or auto-drafted from a website URL)
        │
        ▼
  1. DETECT   eight signal detectors ──► Signal[]          prospector/signals/*
        │      (SearXNG discovery + free httpx→browser→PDF scrape cascade,
        │       trafilatura extraction, optional LLM entity refinement)
        ▼
  2. SCORE    fit × signal-strength × recency ──► 0..100   prospector/icp.py
        │      + explainable "why this lead" reason
        ▼
  3. ENRICH   decision-maker + email waterfall (MX-validated)   prospector/enrich.py
        │
        ▼
  4. DRAFT    DeepSeek signal-aware outreach (+ A/B variants)    prospector/outreach.py
        │      multilingual (en/ar/fr), draft-first (never auto-sent)
        ▼
  5. REPLY    classify inbound + draft a response      prospector/reply.py
        │
        ▼
  6. OPTIMIZE weekly "what converts" feeds back into step 4     prospector/campaign.py

  Surfaces:  CLI (cli.py) · Flask dashboard (prospector/web) · MCP server (prospector/mcp_server.py)
  Storage:   SQLite (prospector/db.py)  ·  Export: CSV / XLSX / HubSpot / Pipedrive
  • prospector/signals/ — one detector per signal family behind a shared Signal dataclass + persist_signals; a registry runs them all with injected free search/fetch functions, so detectors are unit-tested offline.
  • prospector/icp.py — the ICP model and the transparent composite scorer above.
  • prospector/enrich.py — contact discovery + the email-pattern waterfall + free MX validation.
  • prospector/outreach.py / reply.py / campaign.py — signal-aware draft generation, reply classification, and the weekly optimization loop.
  • prospector/web/ — the self-serve Flask dashboard (onboarding, run progress, draft review, replies, exports).
  • cli.py / prospector/mcp_server.py — the same engine over a CLI and an MCP stdio server.

Tech stack

Python · Flask + waitress · SQLite · httpx · BeautifulSoup / lxml / trafilatura · feedparser · rapidfuzz · dnspython · openpyxl · DeepSeek (any OpenAI-compatible endpoint) · self-hosted SearXNG · MCP · pytest

Running it locally

python3 -m venv .venv && source .venv/bin/activate
pip install -r requirements.txt
pip install -e .              # exposes the `prospector` command (same as `python cli.py`)

cp .env.example .env          # fill in DEEPSEEK_API_KEY etc. (all optional; it degrades)
prospector selfcheck          # verify config + external deps -> READY

# Fastest path: seed an ICP from a preset, run the pipeline, show leads
prospector quickstart

# ...or everything in the browser
prospector serve              # http://127.0.0.1:8101

# ...or drive it from Claude
prospector mcp                # stdio MCP server (find_leads / draft_outreach / query_analytics / ...)

Manual pipeline:

prospector init-icp "KSA RE developers" \
    --titles "CEO,Managing Director,Head of Development" \
    --industries "real estate,proptech" --geos "Saudi Arabia,Riyadh,GCC" \
    --keywords "off-plan,residential,giga-project" --competitors "ROSHN,Dar Al Arkan"

prospector run --icp "KSA RE developers" --limit 30    # detect -> score -> enrich -> draft
prospector leads --min-score 70
prospector export --xlsx data/leads.xlsx

Full command list: quickstart, presets, init-icp / list-icp, detect, score, enrich, draft, run, replies ingest|list, export, notify, report / leads, serve, mcp, selfcheck.

Safety defaults

  • Draft-first — nothing is sent automatically. Email sends only with EMAIL_AUTOSEND=1 and SMTP configured; LinkedIn is never auto-sent.
  • Free-first — paid fallbacks (Serper, Firecrawl, CRM) stay off unless keyed.
  • Never fabricates — unknown data stays n/a; detectors skip results they can't ground to a real company.

Data & privacy

This repository contains code only — no leads, no database, no scraped output. The data/ directory (SQLite DB, search caches, session key) and .env are gitignored and never published. The example ICP presets name public real-estate developers, and all test fixtures use synthetic people with reserved example.com domains.

Project layout

prospector/      the engine: signals/ · icp · enrich · outreach · reply · campaign · db · web/ · mcp_server
cli.py           the `prospector` command surface
tests/           561 tests (detectors, scorer, enrichment, replies, web)
deploy/          systemd unit + Caddy reverse-proxy snippet
scripts/         nightly cron pipeline

License

MIT — see LICENSE.

推荐服务器

Baidu Map

Baidu Map

百度地图核心API现已全面兼容MCP协议,是国内首家兼容MCP协议的地图服务商。

官方
精选
JavaScript
Playwright MCP Server

Playwright MCP Server

一个模型上下文协议服务器,它使大型语言模型能够通过结构化的可访问性快照与网页进行交互,而无需视觉模型或屏幕截图。

官方
精选
TypeScript
Magic Component Platform (MCP)

Magic Component Platform (MCP)

一个由人工智能驱动的工具,可以从自然语言描述生成现代化的用户界面组件,并与流行的集成开发环境(IDE)集成,从而简化用户界面开发流程。

官方
精选
本地
TypeScript
Audiense Insights MCP Server

Audiense Insights MCP Server

通过模型上下文协议启用与 Audiense Insights 账户的交互,从而促进营销洞察和受众数据的提取和分析,包括人口统计信息、行为和影响者互动。

官方
精选
本地
TypeScript
VeyraX

VeyraX

一个单一的 MCP 工具,连接你所有喜爱的工具:Gmail、日历以及其他 40 多个工具。

官方
精选
本地
graphlit-mcp-server

graphlit-mcp-server

模型上下文协议 (MCP) 服务器实现了 MCP 客户端与 Graphlit 服务之间的集成。 除了网络爬取之外,还可以将任何内容(从 Slack 到 Gmail 再到播客订阅源)导入到 Graphlit 项目中,然后从 MCP 客户端检索相关内容。

官方
精选
TypeScript
Kagi MCP Server

Kagi MCP Server

一个 MCP 服务器,集成了 Kagi 搜索功能和 Claude AI,使 Claude 能够在回答需要最新信息的问题时执行实时网络搜索。

官方
精选
Python
e2b-mcp-server

e2b-mcp-server

使用 MCP 通过 e2b 运行代码。

官方
精选
Neon MCP Server

Neon MCP Server

用于与 Neon 管理 API 和数据库交互的 MCP 服务器

官方
精选
Exa MCP Server

Exa MCP Server

模型上下文协议(MCP)服务器允许像 Claude 这样的 AI 助手使用 Exa AI 搜索 API 进行网络搜索。这种设置允许 AI 模型以安全和受控的方式获取实时的网络信息。

官方
精选