Breakthrough Preferences jobs-apply

AutoHunt: 15K-line job automation monorepo scaffolded in one day

No automation: manual job applications only -> Full monorepo: 9 packages, 107 files, 10 platform adapters, Socket.io dashboard, AI-powered matching

breakthroughjobs-applycareerarchitecture
Key Metric
Before
No automation: manual job applications only
After
Full monorepo: 9 packages, 107 files, 10 platform adapter...

Changelog

DateSummary
2026-04-07Created during temporal gap audit
2026-02-26Original work

Context

Before this commit, every job application was a manual affair: open the listing, read the description, tailor a resume, fill out a form, hit submit, repeat. At maybe 10 to 15 applications per week it was neither the volume nor the quality a competitive search demands. The deeper problem was that each platform (LinkedIn, Workday, Greenhouse, Lever, iCIMS, and half a dozen others) implemented its own form conventions, which meant human throughput was bounded by context-switching rather than by any real constraint on information content. The whole thing begged for an orchestrator: one engine, many adapters, a state machine per application, and a dashboard that showed what was happening in real time.

What Changed

I scaffolded the entire AutoHunt job automation engine from scratch in a single day. The initial commit weighed in at 15,030 lines across 107 files, organized into 9 packages: types, database, browser, captcha, ai, engine, adapters, dashboard, and shared utilities.

Architecture decisions made on day one: Turborepo plus pnpm workspaces for multi-package builds; Drizzle ORM over SQLite for a lightweight relational store that survives a laptop reboot; Playwright plus stealth scripts for browser automation (later replaced by a CDP-to-real-Chrome strategy); XState v5 for a per-application state machine that made every transition visible and testable; 10 platform adapters covering LinkedIn, Indeed, Workday, Greenhouse, Lever, iCIMS, Glassdoor, Google Jobs, Direct, and ZipRecruiter; a Next.js 14 dashboard with Socket.io for real-time event streaming; an AI provider layer that accepted OpenRouter and Claude interchangeably.

Every interface boundary (adapter shape, state machine contract, database schema, AI provider interface) was set on day one and has survived every subsequent refactor.

Impact

This architecture carried forward through three renames (autohunt to autojob to autosearch to jobs-apply) and a full SaaS migration. The core decisions made on day one (monorepo structure, state machine per application, per-platform adapters, real-time dashboard, AI provider abstraction) all survived. Every package boundary, every adapter interface, every state machine transition defined on day one is still load-bearing today.

The meta-lesson: single-day scaffolding of a complex system that proved durable enough to survive four renames and a full SaaS migration. The architecture was not throwaway prototyping. It was production-grade from the start because the interfaces were designed around the domain constraints (per-platform variance, per-application state, real-time observability) rather than around a first implementation. Every feature added since plugged into existing seams rather than forcing a new shape.

Source

experiments/jobs-apply/2026-02-26-vision-screenshot-ats-analysis