Agentic BD,
built end to end.
Two AI systems replaced 39 hand-run HubSpot cadences, one drafts outbound overnight, one answers reps live in Slack. A human still approves every send.
Nobody knew which companies were even worth working.
39 HubSpot cadences. Reps copy-pasting skill outputs into templates by hand. Nothing flipped a contact to PQL automatically, so the whole pipeline downstream was guessing. The brief from Clarke Shipley: turn an overworked HubSpot setup into a system that scores, triages, enriches, and drafts on its own.
Foundation before sequence agents.
The original plan jumped straight to sequence agents. Auditing all 39 cadences showed the order was wrong: without viability scoring and triage, agents personalize emails to the wrong people. Foundation first.
Viability Scoring
Every company scored Red / Yellow / Green overnight. Reps know where to spend Apollo credits.
Cold-Lead Triage
New contacts auto-routed nightly, hobbyists to DevRel, technical titles to Sales. No noise in Sales views.
Contact Enrichment
Phone, mobile, LinkedIn filled on working contacts only. A timestamp stops credits burning on re-checks.
PQL Automation
PostHog webhook flips lifecycle stage and sets pql_tier. The missing piece, nothing flipped PQL before.
Draft Pre-Population
An agent writes a personalized draft into the CRM overnight. Reps review and approve instead of writing cold.
The Stark Agent.
Fork or star the repo at 2am. By morning a researched, personalized draft is waiting in the CRM, a rep only has to approve it.
A signal comes in, four sources get researched, Claude turns that into a hook and a confidence score, and the draft writes back to HubSpot with a 4-step Apollo cadence queued behind it. The SDR reviews in Slack and sends, the agent never touches a mailbox.
A drafted email is worthless if it lands in spam. So the send path sits on infrastructure I built and monitor: an email-validation layer that verifies every address before enrollment, and a dedicated warm-up system that ramps sender reputation and watches inbox placement across the sending pool.
The engineering underneath
Research pulls GitHub (repos, forks, pinned via GraphQL), Firecrawl (company tone), Reo.dev (fit), LinkedIn (title). Email writes 3 subject variants and runs a humanness gate that rejects generic openers and regenerates once. Claude falls back to Gemini on auth errors, rate limits, or malformed JSON.
5 dedup guardrails run before any draft: do-not-contact flag · already in HeyReach · already in a live Apollo sequence (checked live) · AI review already pending/sent · prior verified send.
3 scheduled jobs on Cloud Run keep it self-healing: cadence scheduler (08:00 IST daily) · reply poller (every 4h, Apollo has no webhook) · reconcile sweep (06:00 IST nightly, syncs drift when an SDR edits Apollo directly).
Deliverability is its own layer: addresses run through a validation service before enrollment, and a warm-up system ramps sender reputation with SPF / DKIM / DMARC aligned and inbox placement monitored, so volume scales without tanking the domain.
The GTM Copilot, Iris.
A rep asks in Slack, “who's worth reaching out to this week?”, and Iris researches, checks the CRM, and drafts, without anyone leaving the thread.
A LangGraph ReAct agent decides which of 15 tools to call, remembers the thread so follow-ups don't re-run expensive searches, and shares its research + email code with the Stark Agent, so live answers and the overnight pipeline never disagree about the same developer. The same tool suite is now re-exposed over an authenticated MCP server, so Claude Code, Claude Desktop, and claude.ai connectors call it directly, no Slack round-trip.
The engineering underneath
MCP server: the whole 15-tool suite is re-exposed over an authenticated MCP server, so Claude Code, Claude Desktop, and claude.ai connectors run the same tools with no Slack round-trip. Dual auth in one gate, a static bearer and full WorkOS AuthKit OAuth 2.0 (JWKS RS256 verify, protected-resource discovery, tenancy gate by org / email domain), and the server fails closed, it refuses to start unauthenticated.
Call intelligence: search_calls and get_lead_timeline run hybrid retrieval over recorded-call summaries, Postgres full-text and pgvector fused with reciprocal-rank, then a Voyage rerank pass. One timeline call merges Apollo touches, every call, and the live deal stage into a single dated view.
Reflection + self-correction: high-stakes output (deep research, drafted emails) gets a second pass from Claude Haiku, and on a wrong ordering or filter it triggers exactly one corrective re-run, e.g. re-running a call search sorted by recency, then footnotes the fix. It never edits the reply directly.
Latency: the system prompt is an ephemeral cache block (0.1× reads on every ReAct round-trip), orchestration rules fire parallel tool calls and prefer one merged timeline over ~20 serial lookups, and a Haiku / Sonnet difficulty cascade keeps the cheap turns cheap.
Write gate: the one line Iris can't cross alone is writing to HubSpot or Apollo. She stages the write; it only fires after a rep replies with a passphrase in-thread.
Runtime: Slack Bolt over Socket Mode, plus the MCP transport, on Cloud Run kept warm so a reply never waits on a cold start. Tool output is scrubbed for prompt injection before the model sees it, and per-user rate limits and a per-run LLM budget cap spend. Every question, tool call, and latency logged to Postgres to tune on what reps actually ask.
Autonomous and interactive, sharing a brain.

Clarke Shipley, GTM Leader at OpenHands, the day-to-day stakeholder I build with. LinkedIn ↗
Available as a reference on request

Smit Patel, Fractional Exec at OpenHands. Ex-VP at Postman, ex-Datadog, ex-COO at Pieces. Ran the engagement with me. LinkedIn ↗
Available as a reference on request
The rep's job becomes review-and-approve.
← Back to the systems