Sales Agent Architecture — V1 through V2
The Market Sweep Agent is an automated sales pipeline that discovers coffee shops across US markets, enriches contact information, generates AI-personalized emails, and tracks responses — all from a single dashboard.
Full Public Reader
Sales Agent Architecture — V1 through V2
System Overview
The Market Sweep Agent is an automated sales pipeline that discovers coffee shops across US markets, enriches contact information, generates AI-personalized emails, and tracks responses — all from a single dashboard.
┌─────────────────────────────────────────────────────────────────────────┐
│ Market Sweep Pipeline │
│ │
│ ┌──────────┐ ┌──────────┐ ┌──────────┐ ┌──────────┐ ┌──────────┐ │
│ │ Discovery │→│ Enrichment│→│ Import │→│AI Generate│→│ Email │ │
│ │ (SerpAPI) │ │(Scraping) │ │ (CRM) │ │(GPT-4o-m)│ │ (Resend) │ │
│ └──────────┘ └──────────┘ └──────────┘ └──────────┘ └──────────┘ │
│ ↓ ↓ ↓ ↓ ↓ │
│ sweep_prospects +email,IG inbound_leads +ai_body email_outreach│
│ +snippet +accounts +variants │
│ +vibe +locations +vibe │
└─────────────────────────────────────────────────────────────────────────┘Edge Functions
| Function | Purpose | API Used | Cost |
|---|---|---|---|
| `market-sweep-search` | SerpAPI multi-query discovery | SerpAPI | ~$1.60/city |
| `market-sweep-enrich` | Website scraping: emails, IG, snippet, vibe | None | $0 |
| `market-sweep-import` | Promote prospects to CRM leads + create accounts | None | $0 |
| `market-sweep-ai-generate` | GPT-4o-mini personalized email generation | OpenAI | ~$0.002/email |
| `market-sweep-email` | Send via Resend, prefer AI content, A/B variants | Resend | Free tier |
| `market-sweep-followup` | Follow-up sequences (max 2 per prospect) | Resend | Free tier |
| `market-sweep-classify` | GPT-4o-mini response classification | OpenAI | ~$0.001/classify |
| `background-sweep` | Google Maps Places continuous market discovery | Google Maps | Usage-based |
Database Schema
Core Tables (V1)
- `market_sweeps` — Tracks each city sweep operation with status progression
- `sweep_prospects` — Staging table for discovered cafes before lead import
- `inbound_leads` — CRM leads with zone classification and pipeline tracking
- `email_outreach` — Email send logs with sweep linking
V2 Additions
- `accounts` — Business entities with place_id dedup, Google Maps data, vibe, stage tracking
- `locations` — Physical addresses linked to accounts (multi-location support)
- `account_contacts` — Multiple contacts per business with role classification
- `sweep_queue` — Background sweep rotation through 22 markets
V2 Column Additions on `sweep_prospects`
| Column | Type | Purpose |
|---|---|---|
| `ai_subject` | text | GPT-4o-mini generated subject line |
| `ai_body` | text | GPT-4o-mini generated email body |
| `subject_variants` | jsonb | 3 A/B subject line variants |
| `selected_variant` | int | Which variant was sent |
| `ai_generation_model` | text | Model identifier (gpt-4o-mini) |
| `cafe_vibe` | text | hipster/minimalist/brunch-heavy/craft-focused/neighborhood |
| `website_snippet` | text | First 500 chars of website for AI context |
| `response_type` | text | interested/not_now/unsubscribe/wrong_contact |
| `qualification_tier` | text | hot/warm/cold based on response |
| `account_id` | uuid | Link to accounts table |
AI Email Generation Flow
1. Enrichment scrapes website → extracts snippet + classifies vibe
2. GPT-4o-mini receives: cafe name, city, rating, reviews, vibe, snippet, IG handle
3. Returns JSON: { subject, body, subject_variants[3], vibe }
4. Email function picks random variant for A/B testing
5. After response, classify function categorizes → sets qualification_tierSystem Prompt
> "You are a sales copywriter for Koji, a premium fresh oat milk brand. Write warm, concise intro emails that feel personal — not templated. Reference specific details about the cafe."
Vibe Classification Keywords
| Vibe | Keywords |
|---|---|
| hipster | vinyl, vintage, artisan, latte art, pour over, single origin |
| minimalist | minimal, clean, modern, scandinavian, zen, matcha |
| brunch-heavy | brunch, avocado toast, mimosa, eggs benedict, pancakes |
| craft-focused | roast, cupping, extraction, barista, v60, chemex, specialty |
| neighborhood | community, local, family, cozy, welcoming, regulars |
Background Sweep (Google Maps Places)
Continuous discovery across 22 US markets:
1. Queue rotation: Each call processes one city + one query type
2. 7 search queries: cafe, coffee shop, coffee roaster, espresso bar, brunch restaurant, bakery cafe, tea house
3. Mega-chain filter: Excludes Starbucks, Dunkin, McDonald's, etc.
4. Chain detection: Flags Blue Bottle, Intelligentsia, etc. as chains
5. Upsert by place_id: Updates existing accounts, creates new ones
6. Multi-location: Chains get separate location entries under same account
22 US Markets
Philadelphia, Pittsburgh, New York, Brooklyn, Los Angeles, San Francisco, Chicago, Seattle, Portland, Austin, Denver, Nashville, Miami, Boston, Washington DC, Atlanta, Minneapolis, San Diego, Detroit, Charlotte, Richmond, New Orleans
Prerequisites
- `OPENAI_API_KEY` — Set in Supabase Edge Function secrets
- `GOOGLE_MAPS_API_KEY` — Places API enabled
- `RESEND_API_KEY` — Email sending
- `SERPAPI_API_KEY` — Search discovery
Cost Summary (per city sweep)
| Component | Cost |
|---|---|
| SerpAPI discovery | ~$1.60 |
| Website enrichment | $0.00 |
| AI email generation (50 prospects) | ~$0.10 |
| Response classification | ~$0.01 |
| Email sending (Resend free tier) | $0.00 |
| Total per city | ~$1.71 |
Promotion Decision
Promote into a technical note or architecture paper with implementation anchors.
Source Anchor
milkmendelivery/docs/SALES-AGENT-ARCHITECTURE.md
Detected Structure
Method · Architecture