MISSION 003MVPPersonal project · 2026

Job Agent

AI AGENTS · BROWSER AUTOMATION · FULL STACK

An AI job-search assistant that finds jobs, scores them against a career profile, prepares applications and drives a real Chromium browser to fill forms — with human approval before anything is submitted.

Personal project — designed and built by Prince.

ROLE
Designed and built it end to end: architecture, agent state machine, browser automation, API, dashboard and test suite.
STACK
TypeScript · React · Vite · Express · Server-Sent Events · Playwright (Chromium)
OUTCOME
A working local MVP, backed by an end-to-end acceptance suite that drives real Chromium through the real orchestrator and database.
LINKS
Source code: [LINK REQUIRED]

01BRIEFING

Job applications are multi-page forms that differ on every site. Naive automation breaks on custom dropdowns, conditional questions, SPA navigation and validation errors — and, worse, reports success when it didn’t fill anything.

02OBJECTIVE

Automate the tedious parts — finding, scoring, filling — while never inventing qualifications, never bypassing CAPTCHAs or login walls, and never submitting without approval.

03ROLE

Designed and built it end to end: architecture, agent state machine, browser automation, API, dashboard and test suite.

04TECHNOLOGY

  • TypeScript
  • React
  • Vite
  • Express
  • Server-Sent Events
  • Playwright (Chromium)
  • Prisma
  • PostgreSQL
  • Docker Compose
  • Vitest
  • OpenAI-compatible LLM API

AIBACKENDFRONTENDDATABASES

05ARCHITECTURE

  1. INTERFACE

    • apps/web · React + Vite dashboard
    • Live agent log over SSE
  2. API

    • apps/server · Express
    • Agent orchestration
    • Job-source adapters
  3. AGENT

    • State machine
    • Page & question observers
    • Interaction engine
    • Navigation
    • Debug recorder
  4. INTELLIGENCE

    • AIProvider → OpenAI-compatible | Mock
    • Ranking · dedupe · field mapping
  5. DATA

    • Prisma
    • PostgreSQL
  6. TEST BED

    • apps/mock-career-site
    • Every hard form pattern, one route each
FIG · JOB AGENT — SYSTEM LAYERS
  • Every browser interaction goes through one InteractionEngine: it fills a field, reads it back and retries with a different strategy if the read-back disagrees.
  • Application state survives every page change and is persisted after each transition, so a server restart can resume a run.

06CHALLENGE

  • Real application forms are adversarial by accident: radio groups in fieldsets, JavaScript dropdowns with no <select>, async autocompletes, fields that only render when scrolled into view, conditional questions, server-side validation and SPA navigation with no URL change.
  • An agent that clicks “Next” and gets HTTP 200 can look successful while having filled nothing.

07SOLUTION

  • Built a mock career site that implements each of those patterns on its own route, so every failure mode can be tested in isolation.
  • The agent walks one page at a time: observe → detect questions → decide answers → fill → verify by reading back → check validation → find the forward control → wait for a real page change → re-observe.
  • High-risk questions — work authorisation, visa, salary, legal attestations, demographics — are never auto-answered. CAPTCHAs and login walls pause the agent for the human. A submission only counts with positive evidence: a confirmation sentence or number.
  • Loop detection watches page and question signatures; a repeated state stops the run, captures diagnostics, attempts one recovery, then asks the human.

08RESULT

  • The e2e suite asserts every stage separately — job opened, analysed, questions detected, answers generated, fields filled, fields verified, page changed, resume uploaded, review reached, approval required, submitted, confirmation recorded. A run that returns 200 without filling anything fails.
  • Per-run telemetry: a screenshot, DOM, visible text and structured snapshot per step, plus a JSONL log of prompts, answers, actions and verification results.

09EXPERIENCE

No public demo link yet. [DEMO / REPO LINK REQUIRED]

10REFLECTION

The most important feature of an agent is knowing when to stop. Most of the engineering went into pausing, refusing and proving — not into clicking faster.VERIFYUnverified — only in: Drafted copy — confirm voice

TECHNICAL LAYERWhy this stack · trade-offs · performance · implementation

WHY THIS STACK

  • Playwright drives real Chromium with a persistent profile, so browser sessions live in the profile, not the database — no website passwords are stored.
  • Server-Sent Events stream every agent action to the dashboard as it happens.

TRADE-OFFS

  • Semi-automatic by default with auto-submit off: slower than a fully autonomous agent, but no application leaves without a human seeing it.
  • A pluggable AIProvider with a mock implementation, so the whole pipeline — tests included — runs without an API key.

PERFORMANCE

  • Action, retry, navigation and time limits are enforced on every run.

IMPLEMENTATION

  • New job boards are JobSourceAdapter implementations; a site that blocks automation returns BLOCKED_REQUIRES_USER instead of attempting evasion.