Trevor PaughSystems engineer
Trevor PaughProject Chronicles

Chronicles / PermitBuzz

Active · Oct 2026 to present

PermitBuzz

Plain-English morning texts that tell North Carolina roofers, plumbers, and pool builders about every new building permit near them.

18 entries Stack Next.js · Cloudflare Workers · Supabase + PostGIS · Python connectors · Telnyx · Resend · MapLibre View on timeline

PermitBuzz, called Permit Notification until it was named on 8 October, is a service that pulls building-permit data from North Carolina counties and cities, and later other states, and sends contractors a daily plain-English alert by email or SMS for the regions and trades they pick. It is designed for people who are not comfortable with technology: no passwords, and setup in about two minutes.

A one-evening sprint turned a hunch into a plan: a map of which of 22 counties publish usable permit feeds, a recommended stack, a pricing ladder, and eleven clickable mockups built around one persona, a 55-year-old roofer reading his phone in a driveway. The owner approved the lot on 7 October and the build began: county connectors for Wake and Forsyth first, then an app skeleton that sends one email digest. Milestone 2, approved on 10 October, added a map for choosing areas, a public search page that draws permits as points, account deletion, and paid tiers wired to a payment processor in test mode, all waiting on accounts and a first deploy.

Latest developments

Design

Delete my account, and the bug it found

Designing the account-deletion flow turned up a live bug in the daily digest: an alert deleted while the run was in progress made the whole run fail and dropped every send after it. The fix went in first, under one lock order for everything that touches an alert, and the reviewer's own reproduction caught a deadlock in the first version. Then the deletion flow itself: a page that stops every alert, removes the account, and purges the sign-in audit trail, with a nightly thirty-day purge for everyone else.

Decision

Go on Milestone 2

After a night held at the end of Milestone 1, the owner's answer came in three words. Milestone 2 is a map to pick areas on, a public search page with the permits drawn as points, the paid tiers, and a third city. Two side questions, a defensive domain and a project mailbox, were parked with a request to be reminded later. The accounts that would let anyone outside the team sign up are still parked too.

Progress

A health check, and a guard against a shrinking feed

The nightly data pull can now say whether it is well: a health command goes red when a scheduled source has not produced in two days or a parcel load is older than forty-five, and the nightly job runs it last. Research into the next large county found its feed with no stable key, no last-edited stamp, and a row count that fell by seven percent in a week, so full pulls got a shrink guard that refuses to overwrite good data with a short one. A smaller city with a clean, open feed got a connector plan instead.

Design

Report a bad pull honestly

One county's permit layer shrank by sixteen thousand rows in a week, and one permit number in it appears a hundred times. The runner never deletes a permit, so a short pull cannot wipe data, but it can pass as a good run and let the source go quietly stale. The design adds a count-before-and-after guard for full pulls and folds a permit's repeated rows into one stable record. A second county's connector was planned on the same desk, with a rule that research notes print only counts and field names, never sample values.

Milestone

Milestone 2 app work complete: search on a map

Ten pull requests after the go, the app had its map. The alert builder picks areas from a list or by tapping counties and towns; a public search page shows recent permits as clustered points beside a plain list and saves a search as an alert in one tap. Every limit lives on the server, the map never sees an owner's contact details, and if the tiles fail the list still works. On the data side a third city's feed was built and held, and two neighbours were ruled out pending records requests.

Decision

It has a name: PermitBuzz

After one candidate turned out to be taken, the owner asked for names that had been checked first. The research pass cleared PermitBuzz on trademark, domain, and social handles, and the owner bought the domain the same day. The repository and the mockups keep the old working title for now; the app takes its brand from one constant, so the rename is a small job.

Milestone

First code on main, and the bug the reviewer caught before it shipped

The first merge: a permit schema built to hold more than one state, a mapper from county permit types to trades, the contact scrubber, and connectors for Raleigh's building and trade permits. Backfilled locally, about 47,000 Raleigh permits since the start of 2025. The reviewer found that the nightly update window was keyed on the wrong clock and would have silently dropped nearly every record after the first pull.

Decision

First counties: Wake, then Forsyth

The Wake County bundle goes first because its feeds are licensed and clean. Forsyth County goes second so the owner can test on ground they know. Forsyth's feed has no stated licence and identifies properties by parcel number only, so it gets a parcel lookup and a written OK from the county before it is scheduled. No outside testers yet.

Milestone

Approved with the defaults. Build started.

The owner approved the mockups and the plan with every default but one, answered the open questions, and gave the go. Three builder and reviewer sessions are being stood up: one on the county connectors, one on the app skeleton, one reading only. The product still has no name.

Decision

Green, yellow, red: how a feed earns its place

Every data source gets a colour from its written terms, and anything ambiguous waits for the agency's written answer. On day one of the build that put Cary and Forsyth on yellow with connectors built but unscheduled, and Wake County on green but held, because its published file turned out five weeks stale. A freshness guard now refuses any file older than a week.

Milestone

Milestone 1 code complete, the same day it started

Seven pull requests from go to a product that runs end to end locally: Raleigh permits pulled nightly, three more connectors built and held, a daily email digest with one-click unsubscribe, a one-tap manage page, My Alerts, and a permit page that shows no owner contact details. The reviewer blocked two merges, one for a name scrubber that cut "Ralph" short. What remains needs the owner: accounts, a domain, a mailbox, and a name.

Decision

Pricing set: three flat tiers, and the free one is the trial

The proposed ladder was approved as it stood, minus the founder discount. A free tier with email only, one county, one alert, and a month of search history; a local plan; a regional plan; and a statewide add-on. No introductory pricing. The figures stay out of this history until the pricing page is live.

Milestone

Eleven mockups, sixteen questions, no code

The full mockup set is finished and in front of the owner: landing, passwordless sign-up, pricing, a four-step alert builder with a real map, sample SMS and email, permit detail, search and map, My Alerts, a one-tap manage page, and a founder dashboard. Nothing is built. The first slice waits on the owner's feedback and sixteen open decisions.

Design

Designed for a 55-year-old roofer on a phone

Eleven mockups built around one persona: 18-pixel text, 48-pixel tap targets, Atkinson Hyperlegible, one decision per screen, and every alert read back as a sentence. Free-hand map drawing was replaced by a radius around an address.

Decision

Flat tiers over per-county metering

The service will sell a small number of flat plans rather than charging per county or per alert. The specific prices are a proposal and are not recorded here.

Decision

Four constraints that do not move

Free and legal data only. Never hold a card number. Nearly free to run until there are customers. No launch date. Pricing waits for market research. Set on day two and written into the plan before any stack was chosen.

Progress

Where the data is, and how it may be taken

Of 22 North Carolina counties surveyed, eight publish machine-readable permit data and four are clearly usable at launch. The sourcing rule is official feeds and public-records requests only. No scraping.

Decision

Scope locked before a line of code

Contractors first. Building and trade permits. One daily digest, by email and SMS. Passwordless sign-in with a code. Mockups before code. Everything else was pushed out of the first version on day one.

The story, from the beginning

Scope locked before a line of code

Contractors first. Building and trade permits. One daily digest, by email and SMS. Passwordless sign-in with a code. Mockups before code. Everything else was pushed out of the first version on day one.

Read the entry
Statewide isn't essential, but it's the goal. And then eventually other states.

Where the data is, and how it may be taken

Of 22 North Carolina counties surveyed, eight publish machine-readable permit data and four are clearly usable at launch. The sourcing rule is official feeds and public-records requests only. No scraping.

Read the entry

Four constraints that do not move

Free and legal data only. Never hold a card number. Nearly free to run until there are customers. No launch date. Pricing waits for market research. Set on day two and written into the plan before any stack was chosen.

Read the entry
No target launch date. It's ready when it's ready.

Flat tiers over per-county metering

The service will sell a small number of flat plans rather than charging per county or per alert. The specific prices are a proposal and are not recorded here.

Read the entry
The My Alerts mockup, with made-up alerts and a placeholder brand.
The My Alerts mockup, with made-up alerts and a placeholder brand.

Designed for a 55-year-old roofer on a phone

Eleven mockups built around one persona: 18-pixel text, 48-pixel tap targets, Atkinson Hyperlegible, one decision per screen, and every alert read back as a sentence. Free-hand map drawing was replaced by a radius around an address.

Read the entry
The alert builder mockup. The placeholder name and the data are made up; the product has no name yet.
The alert builder mockup. The placeholder name and the data are made up; the product has no name yet.

Eleven mockups, sixteen questions, no code

The full mockup set is finished and in front of the owner: landing, passwordless sign-up, pricing, a four-step alert builder with a real map, sample SMS and email, permit detail, search and map, My Alerts, a one-tap manage page, and a founder dashboard. Nothing is built. The first slice waits on the owner's feedback and sixteen open decisions.

Read the entry
I'd like to know the basic functionality and see a few mockups before we actually begin coding.
The founder dashboard mockup, top of the page: subscribers, sends, and a failed-sends tile. All figures are made up; the revenue tile is a placeholder until prices are set.
The founder dashboard mockup, top of the page: subscribers, sends, and a failed-sends tile. All figures are made up; the revenue tile is a placeholder until prices are set.

Pricing set: three flat tiers, and the free one is the trial

The proposed ladder was approved as it stood, minus the founder discount. A free tier with email only, one county, one alert, and a month of search history; a local plan; a regional plan; and a statewide add-on. No introductory pricing. The figures stay out of this history until the pricing page is live.

Read the entry
Defaults fine, except: 9. No founder pricing.

Milestone 1 code complete, the same day it started

Seven pull requests from go to a product that runs end to end locally: Raleigh permits pulled nightly, three more connectors built and held, a daily email digest with one-click unsubscribe, a one-tap manage page, My Alerts, and a permit page that shows no owner contact details. The reviewer blocked two merges, one for a name scrubber that cut "Ralph" short. What remains needs the owner: accounts, a domain, a mailbox, and a name.

Read the entry

Green, yellow, red: how a feed earns its place

Every data source gets a colour from its written terms, and anything ambiguous waits for the agency's written answer. On day one of the build that put Cary and Forsyth on yellow with connectors built but unscheduled, and Wake County on green but held, because its published file turned out five weeks stale. A freshness guard now refuses any file older than a week.

Read the entry
Never scrape a site that forbids it, never do anything illegal.

Approved with the defaults. Build started.

The owner approved the mockups and the plan with every default but one, answered the open questions, and gave the go. Three builder and reviewer sessions are being stood up: one on the county connectors, one on the app skeleton, one reading only. The product still has no name.

Read the entry
Let's go.

First counties: Wake, then Forsyth

The Wake County bundle goes first because its feeds are licensed and clean. Forsyth County goes second so the owner can test on ground they know. Forsyth's feed has no stated licence and identifies properties by parcel number only, so it gets a parcel lookup and a written OK from the county before it is scheduled. No outside testers yet.

Read the entry

First code on main, and the bug the reviewer caught before it shipped

The first merge: a permit schema built to hold more than one state, a mapper from county permit types to trades, the contact scrubber, and connectors for Raleigh's building and trade permits. Backfilled locally, about 47,000 Raleigh permits since the start of 2025. The reviewer found that the nightly update window was keyed on the wrong clock and would have silently dropped nearly every record after the first pull.

Read the entry

It has a name: PermitBuzz

After one candidate turned out to be taken, the owner asked for names that had been checked first. The research pass cleared PermitBuzz on trademark, domain, and social handles, and the owner bought the domain the same day. The repository and the mockups keep the old working title for now; the app takes its brand from one constant, so the rename is a small job.

Read the entry
Just bought permitbuzz.com.

Milestone 2 app work complete: search on a map

Ten pull requests after the go, the app had its map. The alert builder picks areas from a list or by tapping counties and towns; a public search page shows recent permits as clustered points beside a plain list and saves a search as an alert in one tap. Every limit lives on the server, the map never sees an owner's contact details, and if the tiles fail the list still works. On the data side a third city's feed was built and held, and two neighbours were ruled out pending records requests.

Read the entry

Report a bad pull honestly

One county's permit layer shrank by sixteen thousand rows in a week, and one permit number in it appears a hundred times. The runner never deletes a permit, so a short pull cannot wipe data, but it can pass as a good run and let the source go quietly stale. The design adds a count-before-and-after guard for full pulls and folds a permit's repeated rows into one stable record. A second county's connector was planned on the same desk, with a rule that research notes print only counts and field names, never sample values.

Read the entry

A health check, and a guard against a shrinking feed

The nightly data pull can now say whether it is well: a health command goes red when a scheduled source has not produced in two days or a parcel load is older than forty-five, and the nightly job runs it last. Research into the next large county found its feed with no stable key, no last-edited stamp, and a row count that fell by seven percent in a week, so full pulls got a shrink guard that refuses to overwrite good data with a short one. A smaller city with a clean, open feed got a connector plan instead.

Read the entry

Go on Milestone 2

After a night held at the end of Milestone 1, the owner's answer came in three words. Milestone 2 is a map to pick areas on, a public search page with the permits drawn as points, the paid tiers, and a third city. Two side questions, a defensive domain and a project mailbox, were parked with a request to be reminded later. The accounts that would let anyone outside the team sign up are still parked too.

Read the entry
Go on 2.

Delete my account, and the bug it found

Designing the account-deletion flow turned up a live bug in the daily digest: an alert deleted while the run was in progress made the whole run fail and dropped every send after it. The fix went in first, under one lock order for everything that touches an alert, and the reviewer's own reproduction caught a deadlock in the first version. Then the deletion flow itself: a page that stops every alert, removes the account, and purges the sign-in audit trail, with a nightly thirty-day purge for everyone else.

Read the entry