> Quick Definition, Claude Code cold email loops: A scheduled Claude Code prompt that researches a prospect, drafts a personalized first-touch and follow-ups, queues them for human approval, then logs replies and subject-line performance, on a clock, with a compliance gate before every send. It is the difference between "I wrote 40 emails on Monday" and "an outbound pipeline drafts, gates, and reports itself every morning."
Cold email reply rates climb from ~1% to ~8% when personalization references a specific trigger event, a Salesforge outbound benchmark that still dominates the SERP. What does not exist is a published /loop-native Claude Code cold email pipeline with compliance gates. This article is the pattern: a beginner /loop setup for cold email, step-by-step from zero setup, with four named loops, real .loop files, cron, and a Compliance Gate that keeps every sequence approve-and-send.
If you read the hub article on Claude Code Loop Engineering for Modern GTM you already know the ESG Framework (Enable → Schedule → Govern) and the 5 GTM Loop Archetypes. Every loop here is a Nurture or Optimize archetype applied to Claude Code cold email. The discipline transfers; the configs do not. The goal is cost-bounded automation you can ship without learning to code, four loops, four cron entries, one persona file, and a gate that never sends without approval.
TL;DR
- The Outbound Loop Pipeline (research → personalize → send → analyze → optimize) + Compliance Gate is the original framework in this article. Four named loops, one approval queue, one suppression file, that is the Claude Code cold email stack for a founder-led or agency pod.
- A daily research-and-draft loop costs under $8/month in tokens for 50 net-new prospects per weekday. A $99, $250 sequencer seat still wins when you need native warmup, inbox rotation, and sending reputation as a product.
- Claude Code /loop is not Instantly, Smartlead, or Salesforge, it is a scheduler and reasoner on top of your list, your ESP, and your human approver. The loop drafts; a person marks
approved; a throttled job fires only those rows. - Deliverability guidance and compliance are the parts nobody publishes with /loop, SPF/DKIM/DMARC, warmup, honest from-lines, a physical postal address, CAN-SPAM, GDPR, and unsubscribe all sit in front of the send step.
The outbound multiplier: why Claude Code cold email loops change economics
Outbound has always been a "research ten accounts, write ten emails, follow up three times, forget the rest" discipline. Sequencers schedule sends. Enrichment dumps fields into a CSV. Neither one reads the prospect's last three posts, drafts a trigger-specific first line, checks suppression, and refuses to send until you approve the packet. The gap between "I have a list" and "I have a compliant, personalized pipeline" is where reply rates stay stuck near 1%.
A scheduled Claude Code cold email prompt closes that gap. The loop runs at 7 a.m., reads yesterday's qualified accounts, writes a first-touch plus two follow-ups that cite a real trigger, drops the packet into an approval queue, and posts a Slack digest before you open the inbox. That is a different workflow than "I will personalize on Friday."
The directional data point: cold email reply rates climb from ~1% to ~8% when the first line references a specific trigger, a hire, a funding round, a product launch, a talk, a job post, rather than a {FirstName} merge tag. Your mileage depends on list quality, offer, domain reputation, and whether you honor unsubscribes in hours rather than weeks. The direction is consistent: personalization is the multiplier; loops make it repeatable without turning the mailbox into an unsupervised blast.
The economic flip is labor, not stamps. Fifty researched emails a day is a full-time SDR if each packet takes 12 minutes. The same 50 packets, drafted by a Claude Code cold email loop and approved in two minutes each, is an hour of review. You still pay for the ESP, the domain, and the human who hits approve. You stop paying a person to re-derive the same research ritual every morning.
Setting up email API access for /loop (SMTP, SES, Resend, Mailgun)
The CLAUDE.md file is the persona and tooling layer every Claude Code cold email loop in this article shares. Without it, each run re-derives your ICP, from-line, and legal footer and burns tokens re-reading the brand file. With it, every run starts from "you are the outbound agent for company X, here is the approval rule, here is the suppression path, here is the physical address that must appear on every message."
This is the step-by-step from zero setup. You need a repo, an ESP or SMTP credential in the environment, a suppression CSV, and a queue folder the send job is allowed to read. Claude Code talks to email the same way a script does: SMTP for a mailbox you control, Amazon SES for volume with IAM keys, Resend or Mailgun for an HTTP API. Pick one provider and keep the rest of the loop identical. The provider is a transport. The Compliance Gate is the product.
Beginner /loop setup for Claude Code cold email
The persona block tells Claude Code who it is for the duration of the loop. Claude Code cold email is a domain where judgment matters, a generic assistant will produce generic pitches and will try to send them. A named persona with a hard approve-and-send rule produces drafts a human can ship.
# CLAUDE.md (excerpt)
You are the outbound agent for metaflow.life.
Your job: research, personalize, and queue, never send without an approved row.
Your list lives in data/outbound/prospects/, first-party or contractually sourced only.
Your suppression file is data/outbound/suppression.csv (email, reason, date).
Your queue is data/outbound/queue/{pending,approved,sent,replied}/.
Your alert channel is #outbound-alerts on Slack.
Your from-line is a real person at a real domain. Never a role alias that hides identity.
Your footer always includes: physical postal address, unsubscribe URL, company legal name.
Rules:
- Never send. Write to pending/. A separate send job reads approved/ only.
- Never scrape, buy, or infer emails from harvested lists.
- Never write a subject line that misrepresents the body.
- If a prospect is on suppression.csv, skip and log. Do not draft.
- If the suppression file is older than 24 hours, flag stale and skip the send job.Tools and providers
For Claude Code cold email, the typical stack is a prospect CSV you already own, a fetcher for public pages the prospect published, an ESP send API used only by the approved-send job, and a mailbox export for reply detection. SMTP is the lowest-infrastructure path: a transactional mailbox and a daily cap. SES, Resend, and Mailgun are better when you need signed DKIM, bounce webhooks, and an audit log. Store keys in the environment. The loop reads RESEND_API_KEY or SMTP_URL; it does not invent a from-domain.
Data sources and the approval queue
If suppression.csv is missing, the send job must not fire, it should post an alert and exit. If pending/ is empty, that is a successful no-op, not a reason to widen the list. Research writes pending/, a human moves a packet to approved/ after reading it, and only then does a throttled send job call SES, Resend, Mailgun, or SMTP. Official /loop scheduling lives in the Claude Code scheduled tasks docs. The cron lines below are the operator layer on top of that command.
Loop #1: Prospect research + personalization generation
The Research loop is the first Claude Code cold email loop most teams ship. It does not send. It produces an approval packet: one markdown file per prospect with the trigger cited, the first-touch body, two follow-ups, a subject-line pair for later A/B testing, and a compliance checklist (from-line matches the persona, physical address present, unsubscribe URL present, not on suppression). You approve the packet or you reject it. You do not edit 50 emails from a blank page.
The loop reads a qualified account row, pulls public context you are allowed to use (company blog, a post the prospect wrote, a changelog, a hiring page), and writes a first line that could only belong to that person. Generic "saw you're in {Industry}" copy is a failed run, not a draft.
# .loops/outbound-research.md
Every weekday at 07:00:
1. Read data/outbound/prospects/due-YYYY-MM-DD.csv (today's qualified accounts).
2. For each row, skip if email is in data/outbound/suppression.csv.
3. Fetch only public URLs listed on the row (blog, changelog, talk, job post). If fetch fails, flag and skip.
4. Draft a packet: trigger citation, first-touch, follow-up 1 (day 3), follow-up 2 (day 7), two honest subject lines.
5. Append the required footer: legal name, physical postal address, unsubscribe URL.
6. Write to data/outbound/queue/pending/{email}-YYYY-MM-DD.md.
7. Post a digest of packet count and skipped-suppressed count to #outbound-alerts.# crontab
0 7 * * 1-5 cd /path/to/repo && claude code /loop .loops/outbound-research.mdFifty packets with a short public page each produce roughly 80,000 input tokens and 25,000 output tokens per weekday, about $0.35 per run, or about $7.50/month for a daily weekday loop. The loop wins on draft cost; it does not replace list quality. Garbage in still prints 50 confident wrong emails, which is why skip-on-suppression and skip-on-fetch-fail exist before a single subject line is written.
Loop #2: Sequence execution (staggered sends, follow-ups, timing)
The Sequence loop is a Nurture archetype with a hard gate. It reads approved/, respects quiet hours, staggers sends so a domain does not dump 50 messages in one minute, and only then calls the ESP. Follow-ups fire on day 3 and day 7 only if there is no reply and no unsubscribe. Timing is local-business-hours for the prospect, not UTC convenience for the cron host.
Stagger is deliverability, not courtesy. A new domain that sends 50 emails in 40 seconds looks like a botnet even when every message is a hand-approved note with a physical address in the footer. A typical beginner cap is 20, 40 new threads per mailbox per day after warmup, with 60, 120 seconds between messages. Raise the cap only when bounce rate stays under 2% and spam complaints stay under 0.1%.
Research and send stay in separate .loop files on purpose. Mixing them is how unsupervised blast sneaks in. Research can fail open (skip a row). Send must fail closed (no suppression file, no send).
# .loops/outbound-sequence.md
Every weekday at 09:15:
1. Abort if data/outbound/suppression.csv is missing or older than 24 hours.
2. Read data/outbound/queue/approved/*.md. Skip any email on suppression or already in sent/.
3. Cap today's new threads at MAILBOX_DAILY_CAP (start at 20). Stagger remaining follow-ups.
4. For each due packet, send via Resend, SES, Mailgun, or SMTP using the approved from-line and footer.
5. Log message-id, timestamp, variant (subject A or B) to data/outbound/log/sends-YYYY-MM-DD.csv.
6. Move the packet to data/outbound/queue/sent/.
7. If bounce or complaint webhook fired overnight, add the address to suppression.csv and stop that thread.# crontab
15 9 * * 1-5 cd /path/to/repo && claude code /loop .loops/outbound-sequence.mdToken cost here is small because the copy is already written. The loop is orchestration: cap, stagger, log, move. The value is the refusal to send unapproved or suppressed rows, which is the entire difference between a Claude Code cold email sequence and a blast script with a language model glued on.
Loop #3: Reply detection + contextual follow-up drafting
The Reply loop protects relationships. A sequencer that keeps dripping after "not now" or "please unsubscribe" is how domains die and how you pick up a GDPR complaint. This loop reads the mailbox (IMAP export or ESP reply webhook), classifies each inbound thread, and either stops the sequence or drafts a contextual next message for approval. It never auto-replies to a human.
Classification is the work. "Interested, send times" is a meeting packet. "Not now, Q4" is a snooze with a date. "Unsubscribe" or "remove me" is an immediate suppression write, even if they did not click the link. "Out of office" is a pause, not a follow-up. A generic "list new replies" prompt produces a list nobody acts on. A classification prompt produces a queue a human can clear in fifteen minutes.
# .loops/outbound-replies.md
Every weekday at 11:00 and 16:00:
1. Read data/outbound/inbox/YYYY-MM-DD.json (ESP webhook dump or IMAP export).
2. Match each inbound to a message-id in data/outbound/log/.
3. Classify: interested, objection, unsubscribe, ooo, bounce, other.
4. For unsubscribe, bounce, or complaint: append suppression.csv, halt the thread, do not draft.
5. For interested or objection: draft a contextual reply into data/outbound/queue/pending/reply-{email}.md.
6. Move the original thread marker to data/outbound/queue/replied/.
7. Post interested-count and unsubscribe-count to #outbound-alerts.# crontab
0 11,16 * * 1-5 cd /path/to/repo && claude code /loop .loops/outbound-replies.mdA day's inbox is smaller than a research run, and the downside of skipping this loop is larger than the token bill. Every unhandled "stop emailing me" that receives Follow-up #2 is a compliance event. The Reply loop is how Claude Code cold email stays a Nurture system. Drafts still wait in pending/. The human still sends the yes-thread. The loop's job is to notice, classify, and stop.
Loop #4: Performance analysis + subject line optimization
(A/B testing)
The Analysis loop is an Optimize archetype on a weekly cadence. It reads the send log, the reply classifications, and the two subject lines you stored on each packet, then reports which variant won on replies, not opens. Open rates are a broken proxy under Apple Mail Privacy Protection. Reply rate and positive-reply rate are the numbers that pay for the domain.
A/B testing in a Claude Code cold email loop is deliberately boring. You do not generate 40 clever subjects and spray them. You ship two honest variants per offer (trigger-in-subject vs. offer-in-subject), assign them round-robin at approval time, and refuse to call a winner before 100 sends per variant or two weeks, whichever is later. The loop can propose next week's pair from the losers' failure modes, but it does not silently swap copy on a live thread.
Deceptive subject lines are out of bounds. CAN-SPAM requires that the subject accurately reflect the content. "Re: our call" when there was no call is not a test variant; it is a violation. The Analysis loop should flag any logged subject that does not appear as an idea in the body, and it should drop that variant from the next round.
# .loops/outbound-analyze.md
Every Monday at 08:00:
1. Read data/outbound/log/sends-*.csv and data/outbound/queue/replied/ for the last 14 days.
2. Compute reply rate and positive-reply rate by subject variant, from-line, and daypart.
3. Ignore open rate as a primary KPI.
4. Call a winner only if each variant has n >= 100. Otherwise mark "underpowered" and keep running.
5. Draft two new honest subject lines for next week from the losing variant's failure notes.
6. Save the report to data/outbound/briefs/YYYY-MM-DD-performance.md.
7. Post the winner, sample sizes, and any subject-body mismatches to #outbound-alerts.# crontab
0 8 * * 1 cd /path/to/repo && claude code /loop .loops/outbound-analyze.mdToken cost is the smallest of the four, one weekly rollup over CSVs, under $0.20 per run. The value is the decision: keep the trigger-in-subject line, kill the cute one, and carry the sample-size rule so you do not chase noise. That is A/B testing as governance, not as a slot machine.
Deliverability best practices in a Claude Code cold email loop
Deliverability guidance is the intent gap the SERP leaves next to every "AI writes your cold email" post. A Claude Code cold email loop that drafts beautiful packets onto a cold domain with no SPF, no DKIM, no DMARC, and a 200-email first day will land in spam regardless of personalization. The loop does not create reputation. The domain, the mailbox, the warmup, and the complaint rate do.
Authenticate before you cron anything. SPF must authorize SES, Resend, Mailgun, or your SMTP host. DKIM must sign with a key the ESP controls. DMARC should start at p=none with a rua mailbox you actually read, then move to quarantine once alignment is clean. From-lines must be a real person (Alex at Metaflow <alex@yourdomain.com>), not noreply@, not a spoofed prospect name. The physical postal address in the footer is a CAN-SPAM requirement and a trust signal.
Warmup is a calendar, not a prompt. New domains send 10, 20 per day in week one, 20, 40 in week two, and only then approach the 50-packet research volume in Loop #1. The Sequence loop's MAILBOX_DAILY_CAP is the warmup expressed as a number. If bounce rate crosses 2%, the cap drops and the research loop still runs, you approve fewer packets, you do not push through. List hygiene is the other half: no harvested lists, no scraped Whois, no purchased files of unknown provenance. If you cannot document how the address was sourced, it does not enter prospects/.
Throttle, one-click unsubscribe, and a suppression file that the send job cannot override are the remaining controls. The Addy Osmani loop engineering essay is about feedback-tight systems; in outbound, the feedback that matters is bounces, complaints, and unsubscribes.
Compliance architecture: CAN-SPAM, GDPR, unsubscribe
The Compliance Gate is the named control in the Outbound Loop Pipeline (research → personalize → send → analyze → optimize) + Compliance Gate. It sits between approved/ and the ESP. If any check fails, the send job exits. It does not warn and continue.
CAN-SPAM is US commercial-email law. The FTC CAN-SPAM Act compliance guide is the primary source. For a Claude Code cold email program the operational translation is: honest from-lines and header information; subject lines that match the body; a visible physical postal address; a working unsubscribe that you honor quickly; identification of the message as commercial where that is the honest reading; and monitoring of anyone sending on your behalf, including your own loop. "The model wrote it" is not a defense.
GDPR is stricter when you process personal data of people in the EEA/UK. B2B email is not a free pass. You need a documented lawful basis (often legitimate interests for relevant B2B, with a balancing test you can show, or consent where counsel says you need it), a way for the person to object, a suppression write that actually stops processing, and no harvested lists. If a prospect is in the EEA and you cannot state the basis, they do not go in due-YYYY-MM-DD.csv. Unsubscribe is both a CAN-SPAM mechanic and a GDPR objection channel: one link, one address, one CSV, honored the same day the Reply loop sees it.
# footer block every approved packet must include
Company: Metaflow, Inc.
Postal address: [street, city, region, postal code, country]
Unsubscribe: https://yourdomain.com/unsubscribe?e={email}
This email was sent to {email} because we believe our product is relevant to your role.
If that is wrong, the link above stops all further mail.Replace the address with your real one. A P.O. box can satisfy CAN-SPAM in many cases; a fake suite number does not. The unsubscribe URL must work without a login wall. Honor it for that address across every mailbox and every loop.
Full pipeline: research → personalize → send → analyze → optimize
The four loops are one system. Research writes packets. A human personalizes last-mile (or simply approves). Sequence sends on a stagger. Replies halt or draft. Analysis feeds next week's subjects. The Compliance Gate is not a fifth cron, it is the abort conditions inside Sequence and Replies. That is the Outbound Loop Pipeline (research → personalize → send → analyze → optimize) + Compliance Gate in production form.
The table below is a worked example for a founder-led B2B motion: 50 researched accounts per weekday, one mailbox, Resend as transport, daily research and sequence, twice-daily reply checks, weekly analysis. Prices are Claude tokens only; add your ESP and domain.
| Loop | Cadence | Input tokens | Output tokens | Cost per run | Monthly cost |
|---|---|---|---|---|---|
| Research + personalize | Weekday daily | 80,000 | 25,000 | $0.35 | $7.50 |
| Sequence (approve-and-send) | Weekday daily | 4,000 | 1,000 | $0.02 | $0.44 |
| Reply detection | 2× weekday | 12,000 | 3,000 | $0.06 | $2.64 |
| Subject A/B analysis | Weekly | 20,000 | 4,000 | $0.10 | $0.40 |
| Total | — | — | — | — | $10.98/month |
Research dominates cost because it fetches and writes; sequence is cheap because copy already exists; reply detection is the line item you do not cut, because skipping it is how unsubscribes get a follow-up. Under $11/month in tokens is cost-bounded automation next to a $99, $250 sequencer seat that still wins if you need native warmup pools and inbox rotation. Many teams keep the sequencer for send reputation and use Claude Code cold email loops only for research and analysis.
The second table is the cheat sheet next to the crontab: each loop, its archetype, the gate that must pass, and the failure mode that quietly turns a helpful system into a spam cannon.
| Claude Code cold email loop | Archetype | Gate that must pass | Failure mode to guard against |
|---|---|---|---|
| Research + personalize | Generate | Not on suppression; public source cited | Harvested or undocumented list |
| Sequence send | Nurture | Row in approved/; footer complete; cap OK | Unsupervised blast / missing address |
| Reply detection | Monitor | Unsubscribe writes suppression same day | Follow-up after "stop" |
| Subject A/B | Optimize | n ≥ 100; subject matches body | Deceptive or underpowered winner |
Every alert that fires should map to one row. If a send happens that does not map, an email that skipped approved/, a subject that is a fake "Re:", a list you cannot source, that is a governance failure. Fix the gate. Do not add another loop to compensate.
For a parallel nurture pattern on social rather than SMTP, see Claude Code Loop for LinkedIn. The Compliance Gate does not transfer one-for-one, but the approve-before-publish habit does.
Where This Goes Next
The Outbound Loop Pipeline (research → personalize → send → analyze → optimize) + Compliance Gate is the asset you carry out of this article. Four named loops, four cadences, one approval queue, one suppression file, and one shared CLAUDE.md persona, that is the entire Claude Code cold email stack for a founder or a small agency pod. The same pattern extends to a second mailbox once the first domain's bounce rate is boring, but that is a capacity decision, not a new architecture.
The discipline that compounds is ESG applied to outbound: Enable the persona, the footer, and the ESP once; Schedule the four loops at their natural cadences; Govern them with approve-and-send, CAN-SPAM, GDPR, unsubscribe, and a stale-suppression abort. Once those four loops run for a month without a complaint spike, the second offer you add is half the work.
Metaflow is built for this motion. The platform ships marketing agents that hold your ICP, positioning, and connected accounts as durable context, plus workflows and skills that pause for approval before anything leaves the building, which is the same boundary the Compliance Gate enforces on raw Claude Code. Context compounds across runs so the fifth week's packets are not starting from a blank ICP. If you want to skip the CLI plumbing and start from a loop that already knows your stack, that is the layer Metaflow adds on top. For the broader Claude Code marketing skills ecosystem, see the Claude Marketing Skills Ultimate Guide; for agency deployment patterns, see Best Claude Code Workflows for Marketing Agencies.
Frequently Asked Questions
Can Claude Code send emails? Yes, but it should not send unsupervised. Claude Code can call SMTP, Amazon SES, Resend, or Mailgun from a /loop send job. In this playbook the research loop only writes pending/; a human moves packets to approved/; the sequence loop sends only those rows, staggered, with a daily cap. Metaflow's marketing agents use the same pause-for-approval pattern so a workflow cannot become a blast.
How is Claude Code cold email deliverability? Deliverability is a property of the domain, the mailbox, warmup, authentication (SPF, DKIM, DMARC), list provenance, and complaint rate, not of the model. A Claude Code cold email loop that respects caps, honest from-lines, and suppression will inherit whatever reputation you built. The same loop on a cold domain with a harvested list will fail. Follow the deliverability guidance above before you raise MAILBOX_DAILY_CAP.
Is Claude Code outreach CAN-SPAM and GDPR compliant? The tool is not compliant or non-compliant. Your program is. CAN-SPAM requires honest from-lines, non-deceptive subjects, a physical postal address, and a working unsubscribe you honor promptly, see the FTC guide. GDPR adds lawful basis, objection handling, and a ban on treating harvested lists as a prospect file. The Compliance Gate in this article encodes those checks. Metaflow workflows can hold the footer, suppression list, and approval state as durable context so the gate is not a sticky note on a crontab.
Can Claude Code A/B test cold email subject lines? Yes. Store two honest variants on each packet, assign them round-robin at approval, log which variant sent, and let the weekly Analysis loop score reply rate and positive-reply rate. Call a winner only after about 100 sends per variant, and discard any subject that does not match the body. That is A/B testing as a loop, not as a trick subject line.
Sources
- FTC, CAN-SPAM Act Compliance Guide for Business, primary US commercial-email rules (from-lines, subjects, address, unsubscribe)
- Claude Code official docs on scheduled tasks,
/loopcommand reference - Addy Osmani, Loop Engineering, origin of the loop engineering concept
- Metaflow, Claude Code Loop Engineering for Modern GTM, hub article for this cluster
- Metaflow, Claude Marketing Skills Ultimate Guide, broader Claude Code marketing skills ecosystem
- Metaflow, Best Claude Code Workflows for Marketing Agencies, agency deployment patterns
- Metaflow, Claude Code Loop for LinkedIn, sibling nurture pattern on social
- Resend documentation, HTTP send API used as one transport option in the sequence loop




