← Selected Work

Product

Thuolo

Every open role, read from the employer and scored against your real resume

Thuolo interface

Walkthrough

Thuolo for Chrome in 34 seconds: the score on the employer's page, the gaps, the Today list and autofill.

The problem

Job sites show a copy of a posting — scraped, reposted, often already closed — and rank it by keyword. A candidate cannot tell which roles are still real, which are open to someone at their level, or which of the employer's must-haves they are actually missing until a rejection tells them.

What I did

  1. 01

    Read employers' own boards — Greenhouse, Lever, Ashby and Workday — every four hours rather than scraping aggregators, so 98% of live postings come straight from the employer

  2. 02

    Key every posting by URL with an explicit lifecycle and expiry, so a job is never silently lost or double-counted

  3. 03

    Made markets configuration rather than code: each metro is an employer list where every board is probed for live postings before it is added

  4. 04

    Grew from ten metros to 26 by measuring first: a script filed every posting the crawler would drop, by state, and found 11,785 US postings lost — then suburbs and sixteen new metros went in as batches, each re-measured before the next

  5. 05

    Showed US postings only, without deleting the rest, after finding 12,300 of 83,300 live postings were abroad and a Remote search returning jobs in Germany and India

  6. 06

    Score each match against the requirements extracted from the posting itself, and show the working — must-haves met, must-haves missed — rather than a black-box number

  7. 07

    Move candidate generation out of Python and into Postgres with pgvector and an HNSW index

  8. 08

    Metered the four Claude-backed tools — resume studio, interview coach, outreach drafter, LinkedIn analyzer — in credits under a service-wide spend fuse, with every resume and crawled description fenced as untrusted input and every claim about the candidate required to come from what they wrote

  9. 09

    Recorded every paid model call on a ledger with its outcome, priced prompt-cache writes and reads into it, and alerted at 80% of the spend ceiling, so the cost of the AI features is a number on a dashboard rather than a surprise on an invoice

  10. 10

    Added Google and Microsoft sign-in, keying Microsoft accounts by tenant and object ID rather than email so an nOAuth-style takeover cannot work, and dropping any unproven password when an account is linked

  11. 11

    Ran candidates' interview coding answers in a separate sandbox verifier with no internet access, its deploys gated on every test passing and a live no-egress check

  12. 12

    Built Thuolo for Chrome, a Manifest V3 extension that puts the match score on the employer's own posting, says whether a LinkedIn or Indeed listing is still live on the employer's site, and tracks an application when Submit is clicked — with the session token held in the service worker, where no page can read it

  13. 13

    Made autofill fill only empty fields, and only on a click, with work authorisation, sponsorship, EEO and salary questions blocked before any field is matched

  14. 14

    Let a candidate upload their LinkedIn connections so every job and company shows who they know there — parsed on the server with the email column dropped, never sent to a model, and deleted with the account

Thuolo for Chrome

  • A Greenhouse-style job posting with the Thuolo side panel open, showing an 86 strong-match score, the skills on the resume and the two gaps
    The match score on the employer's own posting, with the must-haves met and the ones missed.
  • The Thuolo popup listing this posting's score, company threads, three strong new matches and two pipeline rows that need attention
    The popup: this posting, new strong matches, and the pipeline rows waiting on the candidate.
  • An application form with name, email, phone and LinkedIn filled in, the work-authorisation and salary fields left empty, and a toast reading Filled 5 fields with an Undo button
    Autofill fills the repetitive fields and leaves work authorisation and salary to the person.
  • The autofill profile page, with name and email from the Thuolo account and contact, links, work and education fields stored in the browser
    The autofill profile. Everything beyond name and email stays in the browser.

Outcome

  • Live at thuolo.com on Cloudflare Workers, with the API, crawler and scheduled jobs on Railway — launched in ten metros and crawling sixteen more, with paid plans sold through Stripe Checkout

  • 72,000 open US roles as of 19 October 2026 — up from 659 postings at the start

  • Thuolo for Chrome went from first commit to the Chrome Web Store in two days, adding LinkedIn and Indeed and the on-page card along the way

  • The four-hourly crawl stopped rewriting about 46,000 unchanged rows a run, and known Workday postings are re-described weekly instead of every crawl — one employer's board went from 58 seconds to 16

  • Ranking 6,200 rows by cosine similarity went from 685ms to 36ms — a 19x improvement, and the single change that made search feel instant

  • Location resolution went from 0% to 99%, and postings with no seniority level from 1,126 to 119

  • 2,283 backend tests and 189 browser end-to-end tests running in GitHub Actions on every push, from a starting point of none

  • A review pass caught three job feeds that had ingested nothing for 16 days while every scheduled run reported success — one missing import, found by checking what the database held rather than what the task said

Built with

  • Python / FastAPI
  • Postgres
  • pgvector / HNSW
  • Celery / Redis
  • Next.js 16 on Cloudflare Workers
  • Claude
  • Voyage embeddings
  • Stripe
  • Chrome extension (Manifest V3)
  • Sentry
  • Playwright
  • GitHub Actions