Nikita Boiko
Contact
All case studies
AI pipeline200 sites in one day

Instead of a cold pitch, a finished website: 200 of them in one day

Finds US small businesses with no website and builds each one a site: 272 sites at 2.4–4.1¢ of AI apiece

Instead of a cold pitch, a finished website: 200 of them in one day

At a glance

Built for
An AI automation consultant introducing their brand and services to US small businesses.
My role
Design and the whole build: research, data pipeline, prompts, site template, hosting, email and tracking. Coded with Claude Code and OpenAI Codex.
Task
Turn "I can help your business" into the owner's own finished site, built from what customers already say and judged in ten seconds.
What I built
A pipeline that finds businesses without a site, verifies a contact, builds and publishes the site, emails the owner, then runs a short survey and file handover.
Timeline
September 9–17, 2026, from the first file to a 200-site run.
Output
24,128 businesses in 100 cities across 13 states; 19,100 listed websites checked; 272 sites in 29 niches, 200 of them in one day.
AI cost
2.4–4.1¢ per site; hosting on Cloudflare's free plan. Data, search and email weren't tracked separately.
Safeguards
Phones and prices come from data — the model never writes them. Every site passes automatic checks. An email goes out only with saved evidence that the address belongs to the business. Captchas are never bypassed.

The idea

Google Maps is full of small businesses with no website: a florist with 25 reviews, a shoe-repair shop with 185, a motorcycle shop with photos of every bike it has rebuilt. Customers did the marketing; there's just nowhere to send new ones.

For a consultant selling automation, that's an opening. A cold pitch is easy to ignore. A finished site with the business's own photos, hours and services takes seconds to judge, before any conversation.

So the client asked for software that builds such sites in bulk and introduces their services. Five rules:

  1. No "AI slop": most owners could publish the site as is.
  2. Nothing invented. Photos from the listing, not stock. Services from the listing, reviews and the business's own pages; prices only if the business published them. Services seen only in reviews aren't confirmed by the business. Too little data, no site.
  3. The right person or nobody: email only an address that saved evidence ties to the business.
  4. Cheap at volume: at least 20–30 sites a day on a tight AI budget.
  5. No purchase required: the site stays up whether or not the owner answers the survey or buys anything, and comes down only on request.

What the owner gets

The owner's path: email, survey, handover
  1. A personal email with a screenshot of their finished site and two sentences on where it came from. Instead of a pitch, one question with buttons: what takes the most time in your week? A link below skips straight to the site.
  2. A four-question survey: the time sink, hours, who does it, what they'd hand off. The link identifies the business, so no typing names or emails. The answers show the consultant where automation could really help.
  3. The handover page: files, plain instructions for a free host or their own domain, and an offer of paid help: edits, a domain move, booking reminders, review requests, projects from scratch.

The site opens right from the email; the files sit behind the survey. Useful first, questions later, on purpose.

By the way, email clients strip out forms, so the question is a set of link buttons. A click records the answer and opens the survey with it preselected.

What's on every site

Anatomy of a generated site

One template, filled with the business's own data:

  • First screen: the best photo, an "open now" tag computed from the hours and time zone, the Google rating, call and services buttons.
  • About: from what reviews actually mention.
  • Services in tabs. Prices only if the business published them, say on an old site or a menu; otherwise none, and "call us for prices" is cut.
  • Gallery of listing photos with a full-screen viewer.
  • Why customers come back: three or four recurring positive review themes, paraphrased, not quoted.
  • Visit: hours with today highlighted, tap-to-call, directions and a map.

Each site is one HTML file plus a photo folder. It opens straight from the download, runs on any free host and can be edited in Notepad. A plain-text guide comes along for someone who has never touched a website.

How it ran

The September campaign on this pipeline introduced the client's brand and services to small businesses in 13 states.

I ran it on a Windows PC, from the command line or a simple menu. One command per stage (staged, qualify, make, deploy, mail); mail without --send only drafts emails for review.

A command guide and project notes cover every stage. Since the campaign, the pipeline has sat idle, ready for new cities and niches.

Scale and cost

The pipeline in numbers
  • AI: 2.4–4.1¢ per site at list prices, measured on five production batches.
  • Hosting: $0, with one Cloudflare Pages project on the free plan and a folder per business.
  • Data, search and email are billed by their providers per request or per plan. They aren't included here: I didn't track them separately in this build.

How it works

The pipeline

Photos needed the most care: listings are full of menus, blurry shots, duplicates and decor. In one early run, a site's hero image was a restroom sink😅 Now a vision model screens every photo before it reaches a page.

Facts come from data. Words come from the model.

Facts versus copy

Claude built the first site end to end in a chat: research, writing, checking. It looked fine. But a model writing the whole page can "improve" a phone number or invent a price.

So every page splits in two:

  • Facts from data: name, phone, email, address, hours, rating, photos and published prices. The template inserts them, and the structured contact fields never reach the copy prompts. Review texts and photos still go to Claude for analysis.
  • Words from the model: headlines, about text, service descriptions and review themes — each written separately for its section of the page.

Mechanical guards sit on top. Promises like "I'll fix it", "reply to me" or "the same day" fail the build, and "call us for prices" is cut. The prompt bans quoting reviews word for word (they belong to their authors) and keeps criticism out of "why customers come back": "better three honest positive themes than four with a criticism among them."

Bonus: it got cheaper too. Splitting facts from copy meant $0.18 a site on the most capable model. Moving copy to Claude Sonnet, photos and classification to Claude Haiku, and caching every step brought it to 2.4–4.1¢ per site.

An email address only with proof

How a contact email is accepted

The hardest part wasn't building sites but finding someone to send them to. Businesses without a site rarely publish an email, and a loose search happily "finds" someone else's.

Version one took an address whenever the business name appeared anywhere in the page URL. It "found" emails for 14 of 27 businesses; about 3 were right. The rest belonged to a gift-card marketplace, a map website, an awards vendor and a different cleaner in another town.

Aggregators put business names in their URLs, so I rebuilt the rule for precision:

  • a distinctive word from the name must be in the mailbox, email domain or page host, not just the path; generic words like "nails" or "cleaners" don't count;
  • platform domains are blacklisted;
  • three search steps: open web → social pages → the owner's name; most genuine addresses were on the businesses' own social pages;
  • in production, an address stays only if the same page shows the business's phone or street address with the city, and that snippet is saved as evidence.

The moral: precision over coverage. Better to miss a lead than email the wrong business.

Who really needs a site

An empty "website" field on a listing doesn't prove there's no site. In the first test batch, four of the ten businesses judged to have no usable site had a working one: a booking site, an ordering page, a JavaScript app.

Wix, Squarespace, Square and ordering apps render with JavaScript, so a live site's raw HTML can hold as few as 27 words. Hence conservative rules:

  • if a page loads, it's a site;
  • a site found off the listing counts only if its host has two distinctive words from the name (one is often just the city);
  • social profiles and link-in-bio pages don't count.

Listed sites that failed the automated check form a separate group: of 19,100 checked, about 470 didn't respond or only redirected to a social profile. Those businesses got a different email: "The website on your Google Maps profile is down. I made a working one."

Honestly, "is down" was too confident: the automated check only shows the site didn't open for it, not that it's down for everyone.

Takedowns

If an owner asks, their site is replaced with a short "removed at the owner's request" notice and the business goes onto a suppression list. Discovery, build and sending all check it, so the site is never rebuilt or re-sent.

The catch was caching: Cloudflare's edge first kept pages for seven days, so an edit or a takedown would have taken a week to show. Pages now revalidate every five minutes, while images, which don't change, stay cached.

Development: 9 days

Date What happened
Sep 9 Niche research, the first site by hand with Claude, the template-plus-JSON architecture and the first deploy to Cloudflare Pages. Bypassing Google's captcha was ruled out; the data comes officially from Google.
Sep 10 The client reviewed ten sites and the emails. Two problems: sites for businesses that already had one, and for ones with no email. New rule: no website and an evidence-backed email first, with a stricter search. First fully automatic run of ten sites.
Sep 11–12 Two sweeps of 1,500 city-and-niche pairs (24,128 businesses) and an audit of 19,100 listed websites. The first emails went to owners.
Sep 11–16 Strict contact evidence, a memory against repeat emails, logs, and open-and-click tracking. Batches of 10–20 sites, each model on the task it does best, caching at every step. Survey and handover pages, cache headers, takedowns, the suppression list.
Sep 17 200 sites in one day🚀 The owners' emails went out the same day.

Who this is for

  • Web studios and freelancers selling sites to local businesses: show the finished site before the first call.
  • Agencies that sell through outreach: a personal landing page or demo for every prospect.
  • Software for local businesses (booking, reviews, ordering): a ready-made demo on each prospect's own data.
  • Consultants who, like this client, want to introduce their services through something useful.

The same data could feed review summaries, local search audits or ad landing pages; this version is built for targeted outreach, with contact checks, draft review and suppression handling.

Engineering details

Engineering details

Stage details

  • Find: a "niche in city, state" search, then full details per result: address, hours, rating, review texts and photo references.
  • Qualify: a rating of 3.8 or higher, 10–1,500 reviews and listed hours; chains and listings outside the niche are excluded.
  • Photos: at least 1,000 px, duplicates removed by checksum, reviewed on contact sheets (many per image, to save cost); menus, dark shots and repeats are dropped and the hero shot picked.
  • Build: facts, guards, the owner page, instructions and a ZIP.
  • Measure: opens, clicks, survey answers and handovers, per email.

Every command writes a full transcript to a log, and model results are cached per business, so a re-run doesn't pay twice. Before any work, each business is checked against history by place ID, slug, and name with street and city, so it's never processed or contacted twice.

One platform gotcha: serverless functions only get the paths listed in the routes file. A function left out fails silently and the request gets a static page, so every new function now gets its route.

Data and privacy in this build

  • Public information only: the Google listing and public pages found through search. Review texts and photos go to Claude for analysis and can themselves contain contact details.
  • Source disclosure: every site and email says it was built from public information.
  • Survey: no name or contact details asked. Answers, opens and clicks are linked to the business through the email's tracking ID.
  • Opt-outs: every email ends with "Reply 'stop' and I won't write again". In this campaign, replies were handled by hand: the address went onto the suppression list, and the site came down if the owner asked.
  • Retention: tracking events and survey answers stay in Cloudflare D1; nothing is deleted automatically.
  • Photos: from the businesses' public listings. Being public doesn't grant permission to republish them, and the uploader isn't necessarily the copyright owner.
  • Keys live in a local .env file, outside the published folder.

Added for each client deployment

The outreach module is set up per client:

  • sending from the client's own domain with SPF, DKIM and DMARC, a warm-up schedule and daily limits;
  • a clear opt-out and the sender's valid postal address in every email, as US law (CAN-SPAM) requires: an unsubscribe link with automatic suppression, plus a separate notice about open and click tracking;
  • a legal check of outreach rules for the target regions;
  • photos the business owns or approved, or licensed stock; map data within the provider's terms;
  • follow-ups and a CRM connection;
  • human review before sending, already built in: drafts first, then --send.

Quality

Automatic guards on every build (forbidden promises, price filler, empty sections), batch validation and a live check of the published URLs after each deploy. Unit tests cover repeat protection, photo sheets, profile links, sending and the search budget.

Tech stack

Layer Technology
Pipeline Python 3.12 with requests, aiohttp, Jinja2, Pillow and Playwright; a CLI with 18 commands and a Windows menu
Data Google Places API; Serper for search, Tavily as fallback
AI Claude Sonnet 5 writes the copy; Claude Haiku 4.5 screens photos, analyzes reviews and classifies listings. Every call's cost is logged
Site One Jinja2 template with inline CSS and JavaScript, plus a mobile call bar
Hosting and tracking Cloudflare Pages (free plan), Pages Functions in JavaScript, Cloudflare D1, Wrangler
Email SMTP; HTML and plain text with an inline screenshot, one email per address

About 6,000 lines of Python, 500 of JavaScript and 1,100 of templates and CSS.

Want something similar?

Tell me about your task, and I'll come back with a plan: what we'll build, how long it'll take and how we'll know it worked.

Discuss a project
Contact