Cross-Stage RevOps RevOpsDemand GenMarketingSales Leadership

Lead Enrichment and Routing with a Claude Agent

Lead enrichment is the other half of speed-to-lead, and most teams lose it in a queue. Fire every form fill into a Claude agent that enriches the lead with web research, scores it against your ICP, writes the record to HubSpot over MCP, and pings the right rep in Slack, in seconds. No n8n workflow, no Zapier, no human triaging a queue.

StageCross-Stage
Time to buildAn afternoon
DifficultyIntermediate
Best forRevOps, Demand Gen, Marketing, Sales Leadership
THE CHECKLIST

The lead enrichment checklist

Lead enrichment is only useful if it feeds a decision. These are the fields worth pulling on an inbound lead and the inputs that turn them into an ICP score the router can act on. The agent fills them from web research in seconds; you set the thresholds once.

What to enrich, and what to score on
Company (firmographic)
  • industry, size, revenue band
  • funding stage and recency
  • tech-stack signals
  • region
Person
  • title and seniority
  • function / department
  • decision-maker vs end-user
Signals (why now)
  • hiring for roles you serve
  • recent launch, funding, or news
  • repeat visits or high-intent pages
The fit score
  • ICP match against your rules
  • score band -> route (AE / SDR / nurture / disqualify)
  • the one reason for the score, so a human can sanity-check it

Enrich for the decision, not for the dossier. Every field here maps to either the routing call or the rep's first line. If a field does neither, it's cost with no payoff, cut it.

The stack

The stack

How the tools connect
What a run costs
Per inbound
web research + one scoring call, cents on a mid-tier model
CRM + Slack
free over MCP, no orchestration plan to pay for
Heavy enrichment
optional Clay credits only if you need waterfall depth
Watch at volume
cache known domains so a traffic spike doesn't surprise the bill
The problem

The problem

Speed-to-lead is the single biggest predictor of inbound conversion, and most teams are quietly terrible at it. A demo request lands with a name and a personal-looking email, sits in a queue, gets researched whenever someone has a minute, and is assigned a day later. By then the buyer already talked to the competitor who called them back in five. Intent was highest the second they hit submit, and you let it cool in a queue.

A raw form fill has almost nothing to route on. 'Jamie, jamie@gmail.com, message: interested' tells you nothing about company, size, role, or fit. Someone has to work all of that out before they can route well, and by hand that research is the exact bottleneck that kills speed-to-lead. So teams pick a bad trade: route fast on no information and misroute, or route well and slow. Either way, low-fit fills eat the same rep attention as the high-fit ones.

I have built this the messy way, and I have watched it fail in the most avoidable way there is. A routing flow in Zapier, airtight in the diagram, no fallback owner. A lead that matched no rule dropped into a gap and sat there for eleven days. It was a 4,000-person, dead-center-ICP account. Nobody cold-pitched them. Nobody pitched them at all. The clever rules worked fine. What broke was everything the diagram did not bother to draw.

A Claude agent collapses the pile. The instant a lead submits, one agent enriches it with web research (company, size, role, and a HubSpot check for an existing account), scores it against your ICP, writes the record and owner to HubSpot over MCP, and pings the right rep in Slack with the context, all in seconds. No Clay-plus-n8n-plus-Zapier stack to keep alive. But before you build anything clever, build two boring things: the existing-customer check, so you never cold-pitch a current account, and a fallback owner, so no lead ever vanishes. Those two failures erode more trust than slow routing ever could.

How it works

How it works

The workflow, end to end
  1. 01 Catch the form Webhookfires the instant they submit
  2. 02 Enrich the lead Claude web researchcompany, role, size from the domain
  3. 03 Check + score Claude CodeHubSpot match over MCP, then hot/warm/nurture
  4. 04 Route by rule Claude Codeexisting-customer branch first, then tier
  5. 05 Write the record HubSpot (MCP)owner set, all fields written
  6. 06 Alert the rep Slack (MCP)context plus links, in seconds
  • A thin webhook catches the form the instant someone submits and hands it to the Claude agent
  • The agent enriches the lead with web research: company from the domain, size, industry, and role
  • It checks HubSpot over MCP for an existing account or open deal before anything else
  • It scores the lead hot / warm / nurture against your ICP, with a one-line reason the rep can read
  • It writes the record, owner, score, and reason to HubSpot, routing existing customers to their owner
  • It pings the assigned rep in Slack with full context, and drops anything unroutable on a fallback owner
The playbook

The playbook

Catch the submission and hand it to the agent instantly

Wire your form, whatever it is, a HubSpot form, a website form, Typeform, to fire a webhook on submission that hands the payload to your Claude agent. Instant is the whole idea: the agent starts working the moment someone hits submit, not on an overnight batch, because the intent you are racing decays in minutes. This thin webhook is the only glue left; everything after it is Claude.

Pass whatever the form has plus the email. Even a bare email is enough to proceed, because the agent fills in the rest from the domain. Do not gate the pipeline on a long form; long forms suppress conversion, and the enrichment makes them unnecessary anyway.

Grab the page they submitted from and any UTM or campaign parameters too. A demo request off the pricing page from a high-intent campaign is a different animal than a blog download, and the rep wants that in the alert. It is free to capture at submission and impossible to reconstruct later.

💡

TipGrab the source page and UTM data at submission. A demo request from the pricing page off a high-intent campaign is a different lead than a content download, and the rep wants that context in the alert, but you can only capture it at the moment of submission.

Enrich the lead with web research

The agent resolves the company from the email domain, then researches it: size, industry, the person's role and seniority, and the buying signals that matter to fit. For a work email, Claude's web research covers this in one pass, which is what makes second-level speed-to-lead real instead of aspirational. No separate enrichment platform sits in the middle for the everyday case.

Before it scores anything, have the agent check HubSpot over the MCP connector for an existing account or open deal. This is the single most important field in the whole flow, and it is a read the agent does itself, not a separate tool you wire in. Flag personal-email domains (gmail, outlook) in their own lane too, because there is no company domain to resolve and they usually carry lower B2B intent.

For very high volume, or for the deep firmographic and waterfall coverage a bulk cold list needs, you can still hand enrichment to Clay via its API and let the agent read the result. For everyday inbound, one work email and web research is plenty, and a lead that genuinely cannot be enriched should go to a human fallback, never get auto-filed as nurture on thin data.

  • Company resolved from the email domain
  • Company size and industry
  • Person role and seniority
  • Existing HubSpot record / open-deal check (read over MCP, the most important field)
  • Buying signal: source page, message, campaign
  • Personal-vs-corporate email-domain flag

Score the lead against your ICP

The same agent scores the enriched lead against your ICP and assigns a routing tier. Reuse the rubric from your account-scoring workflow so a sourced account and an inbound lead are judged by the same standard; that is what keeps the whole funnel coherent. The output is a simple, machine-actionable tier plus a one-line reason, because the agent branches on the tier and the rep reads the reason.

Keep it fast and decisive: hot, warm, or nurture, a clear reason, and an explicit existing-customer flag. This is a routing call made in seconds, not a deep account teardown, so the instruction should be lean.

Handle the existing-customer case right here in the score. If the HubSpot check shows a current customer or an open deal, the score says so and sends the lead to the account owner, never to a new-business rep. Cold-pitching your own customer is the most embarrassing routing failure there is, and it belongs handled before anything else can fire.

The agent's ICP scoring step
Score this inbound lead for routing. Use ONLY the enriched data.

Lead: {{FULL_NAME}}, {{TITLE}} at {{COMPANY}}
Company size: {{EMPLOYEES}}, Industry: {{INDUSTRY}}
Email type: {{EMAIL_TYPE}} (work/personal)
Existing HubSpot record: {{CRM_MATCH}}
Source page / message: {{SOURCE_PAGE}}, {{MESSAGE}}

Return JSON only:
{"tier": "hot|warm|nurture", "reason": "<one sentence>", "is_existing": true|false}

Rules:
- If the HubSpot match shows an existing customer or open deal: set is_existing true, and reason must say to route to the account owner (NOT new business).
- tier 'hot' if: ICP fit (industry in {{ICP}}, size in {{RANGE}}, decision-maker title) AND a work email AND a buying-intent signal (demo request, pricing page, 'pricing'/'demo' in message).
- tier 'nurture' if: clearly non-ICP, a student or job seeker, or a competitor.
- otherwise: tier 'warm'.
- Treat missing data as neutral. Do not penalize a blank field; a lead that failed to enrich goes to a human, not to nurture.
💡

TipMake 'hot' genuinely demanding: ICP fit AND work email AND an intent signal. If everything scores hot, reps stop trusting the tier and triage the queue themselves, which puts you right back where you started. A tier reps trust is one that is right when it says hot.

Write the record and route by rule

The agent writes the lead to HubSpot over MCP with all the enriched fields, the score, the tier, and the reason, then sets the owner per your rules: round-robin within a territory, by company-size segment, or to the existing account owner when it is a current customer. Your routing policy stops being a wiki page nobody reads and becomes something the agent runs identically every single time.

Handle the existing-customer case as the first branch, always. If is_existing is true, route to the account owner or CS and stop, never falling through to a new-business assignment. This one rule prevents the most damaging error there is, so it goes at the top where it cannot be skipped.

Give the agent a fallback owner for anything that fails the rules: the personal-email leads it could not enrich, the edge cases, the weird ones. A real human owns that bucket and works it, so a lead that matches no rule lands on a desk instead of disappearing into a gap in the logic. Build this before the clever rules, not after.

💡

TipBuild the fallback owner before the clever rules. The leads that match no rule are exactly the ones most likely to be unusual and high-value (ask me about the eleven-day account). A lead that silently vanishes is worse than one routed imperfectly. Nothing should ever have no owner.

Alert the rep in Slack with context

The moment the record is written, the agent posts to the assigned rep in Slack, over the same MCP connector, no separate Slack app to wire up. The whole chain from submission to alert should finish in well under a minute; that speed is the entire value proposition, so measure it and protect it.

Make the alert genuinely actionable: who they are, where they work, the source page and intent, the tier and reason, and one-click links to the record and their LinkedIn. The Slack ping with context is what drives fast action. An assignment buried in the CRM gets noticed hours later, by which point speed-to-lead is already gone.

Start the speed-to-lead clock on assignment and put it in the message. A rep who reads 'this came in 90 seconds ago, reach out now' moves differently than one who has no idea how fresh the lead is.

Watch speed-to-lead and tune

Track two things: time from submission to first touch, and routing accuracy. If reps flag mis-routed or low-quality 'hot' leads, tighten the rubric, because a hot tier that is often wrong trains reps to ignore the tier entirely. If enrichment is thin for a meaningful share of leads, send the misses to the human fallback rather than letting a blank field drive a bad auto-classification.

Keep half an eye on model and research usage at volume. Cache what you already know: skip re-enriching a domain you enriched last week, and do not research the same company on every fill from it. Inbound spikes unpredictably, and an unbounded per-lead cost is a budget surprise waiting to happen.

Audit the nurture bucket for false negatives on a schedule, the real buyer who got mis-scored as nurture and quietly buried. That cost is invisible, you never hear about the deal you did not get, so you have to go looking for it. Once tuned, the agent runs itself, and you have faster speed-to-lead and reps focused only on qualified inbound.

💡

TipAudit the nurture bucket for buyers you mis-scored. A mis-routed hot lead generates a complaint; a mis-scored nurture lead generates silence, because you never learn about the deal you lost by burying it. The expensive errors are the invisible ones.

Inside the prompt

Inside the prompt

The scoring prompt is short, but every line is there for a reason. Here is what each one is doing and why.

Why each line is in the scoring prompt
Use ONLY this data"Use ONLY the enriched data"
Stops the model inventing a company size or title. It scores what Clay found, not what it guesses.
Tight JSON output{tier, reason, is_existing}
The orchestrator branches on tier and is_existing programmatically. Free text cannot be routed on.
Existing-customer first"if the HubSpot match shows a customer or open deal: set is_existing true, route to the account owner"
Handles the most damaging error explicitly and early, so a current account never gets cold-pitched.
Make hot demanding"hot if ICP fit AND work email AND a buying-intent signal"
Three conditions, not one. If everything scores hot, reps triage the queue themselves and you are back where you started.
Missing data = neutral"treat missing data as neutral, do not penalize a blank field"
A failed enrichment should send a lead to a human fallback, not auto-classify it cold on thin data.
Force a one-line reason"reason: one sentence citing the facts"
This is what the rep reads in the Slack alert. It makes every tier defend itself in the rep's own glance.
What you get

What you get

A bare form submission enriched, scored, routed, written to HubSpot, and surfaced to the right rep with full context in seconds, all by one agent.

Example output
FORM SUBMISSION (t = 0s):
'Dana Ruiz, d.ruiz@meridianfreight.com, source: /pricing, message: want a demo'

AGENT ENRICHES + CHECKS HUBSPOT + SCORES (t = 8s):
Web research: VP Operations, Meridian Freight, 620 employees, freight & logistics, work email. HubSpot check over MCP: no existing record.
{
  "tier": "hot",
  "reason": "VP Ops at a 620-person logistics firm (ICP fit), work email, requested a demo from the pricing page.",
  "is_existing": false
}

HUBSPOT via MCP (t = 12s): Lead created, owner = Marcus (logistics territory, round-robin), tier = Hot, all enriched fields written.

SLACK via MCP to @marcus (t = 14s):
:fire: *Hot inbound*, Dana Ruiz, VP Operations @ Meridian Freight (620 emp, logistics)
Requested a *demo* from /pricing just now. ICP tier A. Work email, not an existing account.
Record: <link>  |  LinkedIn: <link>
Speed-to-lead clock started 14s ago, reach out now.

---
EXISTING-CUSTOMER CASE (different lead): HubSpot check returns a match -> is_existing true -> routed to the account owner + CS, never to new business.
Anatomy of one routed lead
Dana Ruiz · d.ruiz@meridianfreight.com · source: /pricing
tier"hot"
The field the orchestrator branches on. Make hot demanding or reps stop trusting it and triage the queue anyway.
reasonVP Ops at a 620-person logistics firm, work email, demo from /pricing
The line the rep reads. A tier with no reason gets ignored the first time it is wrong.
is_existingfalse
The most important field. If true, route to the account owner, never new business. This is the check that prevents the worst routing error there is.
t = 0sform submitted, webhook hands it to the agent
The clock starts here. Everything after is one agent racing intent that decays in minutes.
t = 8sagent enriched, checked HubSpot, and scored
Company, size, role, CRM match, tier, all in seconds. This is what makes second-level speed-to-lead real instead of aspirational.
t = 12s → 14sHubSpot record written over MCP, Slack alert sent
Owner assigned, rep pinged with context and links. The whole chain is done before the buyer has closed the tab.
Pitfalls to avoid

Pitfalls to avoid

⚠️

Routing existing customers to new-business repsSkip the HubSpot check as an early, explicit branch and a current customer's inbound gets cold-pitched, which is embarrassing and erodes the account. Always route existing accounts and open deals to the owner or CS, never to new business.

⚠️

Slow enrichment defeating the purposeIf enrichment and scoring add minutes, you lose the speed-to-lead advantage that justified the build. Keep the agent lean, measure submission-to-alert time, and protect it. A slow 'fast' pipeline is just a queue with extra steps.

⚠️

No fallback ownerLeads that match no rule can silently vanish, and those edge cases are often the unusual, high-value ones (eleven days, one perfect account, no owner). Always set a default human who works the fallback bucket so nothing is ever dropped without anyone noticing.

⚠️

Over-trusting the tierA mis-scored 'nurture' lead buries a real buyer in silence, since you never hear about the deal you lost. Audit the nurture bucket for false negatives and tune the rubric; the expensive routing errors are the invisible ones.

⚠️

Unbounded cost at volumeInbound spikes, and per-lead research and model calls add up. Cache what you already know and skip re-enriching repeat domains, or a traffic spike turns into a budget surprise.

FAQ

Questions people ask

What is lead enrichment?
Lead enrichment is filling in what a form doesn't capture: the company's size, industry, funding, and tech stack, the person's real seniority, and the buying signals that say 'why now.' On inbound it does two jobs at once, it scores the lead against your ICP so routing is automatic, and it hands the rep enough context to write a first line that isn't generic. The agent here does it from web research in seconds, so speed-to-lead survives.
How fast does the whole chain actually run?
Submission to rep alert should finish in well under a minute, and in practice it is seconds: t=0 the form hands the payload to the agent, t=8 Claude has researched, checked HubSpot, and scored, t=12 the record is written over MCP and assigned, t=14 the Slack ping lands. That speed is the entire value proposition, so measure submission-to-alert time and protect it. A slow 'fast' pipeline is just a queue with extra steps.
Do I still need Clay for the enrichment?
Not for everyday inbound. For a work email, Claude's web research resolves company, size, and role in one pass, and the existing-account check is a HubSpot read over MCP. Clay earns its keep on bulk cold lists where waterfall coverage matters; here you can keep it as an optional deep-enrichment source the agent calls, but the default path does not need it. Fewer tools, fewer bills, less to keep alive.
What happens to a lead that fails to enrich?
It goes to a human fallback owner, never to nurture on missing data. Inbound is higher-value than a cold list, so a thin row is more likely a real buyer with a personal email than junk. Build the fallback owner before the clever rules: a lead that silently vanishes is worse than one routed imperfectly, and nothing should ever have no owner.
How do I keep a current customer from getting cold-pitched?
Two places. The agent reads HubSpot over MCP during enrichment and sets is_existing true with a reason that says route to the account owner. Then the routing branches on is_existing as the first, explicit rule, before any new-business assignment can fire. Handle this case first, then make the rest fast.
Related

Related plays

Want playbooks like this in your inbox?

A new AI use case, prompt, or teardown every couple of weeks.

Subscribe →