Case study
Scout
Scout — a job-search tool that builds every resume from claims I've already verified. When a posting asks for something it can't back up, it asks me instead of making it up.
My role: everything. The rules, the interview design, the data model, and the code, built with Claude Code.

2The short story
Scout is my third try at the same tool. The first two used AI to write my resume bullets, and they wrote good ones much of the time — which was the problem, because I couldn't tell which run was the bad one without reading every line. So Scout never writes a claim. It picks from bullets I've written and checked, and when a posting needs something my record doesn't cover, it interviews me instead of filling the gap. The result is a tool where the AI is the smallest part: 28 scripts, none of which call a model.
Between March and May 2026 I built two resume tools, one after the other: resume-tailor, nine
versions, and then Hunter, from v1 to v5.10. Hunter was a five-stage AI pipeline — it read a job
description, generated bullets, had a second model critique them, assembled the page and scored
it for applicant-tracking systems. It worked. The PDFs came out, and they often read well.
I stopped trusting it anyway, and the reason is the whole story. Section 3 is what died. Sections 4 to 8 are the rules that replaced it, each of which exists because I watched the alternative fail — including one feature I built, measured, and then retired because nobody, including me, ever used it.
This is a tool study with one user, and that user is me. I haven't hidden that in the limitations: the research here is measurement of what the tool actually did, not interviews. What I can offer instead is a complete record — every decision written down on the day it was made, with what lost and why.
Every day, on its own
- Scripts1ScanCompany boards and a market-wide dataset, every morning. New means first seen.
- Scripts2StoreEach posting’s text saved before it is taken down.
- Scripts3ShortlistSorted into tiers by place and title.
For one posting
- Judgment4ScreenIs this a real job? A fake one never enters the record.
- Scripts5ReadEvery requirement, with its heading, beside the whole record. Ranks nothing.
- Judgment6VerdictCovered, partial or gap. Nothing covered without a named bullet.
- You7Check the verdictOne requirement, one named bullet: agree or not.
- Scripts8ProposeStart from a standing resume and swap within each role.
- Judgment9HeaderPick the summary, write the line under the name — the one field no check guards.
- Scripts10RenderHTML, PDF, and a Google Doc to comment on.
- You11Read the pageComments come back as edits to the record, never to the doc.
- You12SendOnly you mark it applied.
When the record can’t cover it
- Judgment13InterviewOnce per job, never per posting. The posting stays hidden.
- You14AnswerIn your own words.
- Scripts15Write it downRefuses any number or name you have not declared. Every future resume can use it.
- Scripts 7
- Judgment 4
- You 4
3What died — Hunter
Hunter generated my resume bullets with AI, and a second AI critic scored every bullet out of ten and rewrote anything under eight. The bullets were good most of the time. But "most of the time" meant reading every line of every resume to find the invented number, the achievement restated three ways, or the role that got seven bullets while the last one got three. Six weeks and ten versions in, I trusted it less than when I started. I kept its data and threw away its method.
Three bugs killed Hunter, and all three turned out to be properties of generation rather than problems a better prompt could fix:
- It invented. A model writing from context fills in numbers and scope. Some were close to true; closeness is not the standard for a resume.
- Bullet counts drifted. One role got three bullets, another got seven, run to run.
- It restated. Two bullets describing the same achievement in different words — which reads worse than either bullet alone, and tells a recruiter you're padding.
The critic was my fix, and it was the wrong one. A second model scoring the first one's output is a patch over the wrong primitive: it made the good runs better and did nothing to tell me which run was the bad one.
The measurable part is the size of it. The last version, Hunter v5.10, is 50 code files, with a model at five stages of the pipeline. And across April its own ATS score climbed from roughly 58 to roughly 92 — approximate figures, but the direction is the point. Over the same weeks, my trust in its output fell.
And the fix was already sitting inside Hunter's own data, unused. Its master resume stored every achievement several times, each version written by hand from a different angle — one achievement, told as impact, as process, as research. Which meant tailoring didn't need to write anything. It only needed to choose.
- resume-tailorv1v2v3v4v5v6v7v8v9
- Hunterv1v2v3v3.1v3.2v4v5v5.1v5.2v5.3v5.4v5.5v5.6v5.7v5.8v5.9v5.10
- Scoutin use
| Question | Hunter v5.10 | Scout |
|---|---|---|
| How a bullet reaches the page | Written by a model, scored out of ten by a second model, rewritten if under eight | Chosen from bullets written by hand — at most one per achievement |
| Where a model runs | At five stages: read the posting, write, critique, assemble, score | In none of its 28 scripts. Judgment lives in 4 instruction files |
| Size | 50 code files | 28 scripts |
| How it measured itself | An ATS score — roughly 58 to roughly 92 across April | Counts of what is covered and what is not. Never a match score |
4The rule — choose, never write
Scout picks at most one bullet per achievement from versions I wrote by hand. That one rule removes all three of Hunter's failures by construction rather than by instruction: every word is mine, so nothing can be invented; the count is chosen, so it can't drift; and one bullet per achievement means two bullets can never describe the same thing. Improving a resume now means editing text I own, not tuning a prompt I don't.
The rule has one enforcement point that matters more than the rest, and it's the one I'm proudest of. Every achievement in the corpus records the numbers and names it asserts — and the employer it belongs to. Anything that ever changes a bullet's wording is checked against that employer's facts, not against the whole corpus.
The obvious design pools everything I've ever verified and asks "is this in there?" It fails on a single sentence: "Supervised a team of 7–9, scheduling floor coverage in Figma." Every word in that line is somewhere in my record. Figma is all over it. It is true of my design job and false of my retail job, and a corpus-wide check waves it through without pausing. Scoping the check to the owner of the claim is what catches it.
Four of the check's first fifteen tests failed when I wrote them. Three were my expectations being wrong — the check was stricter than I'd predicted. One was a real defect: "scheduling" rewritten as "scheduled" was flagged as a new claim. It's a tense change, and a check that makes you sign off on every tense change gets rubber-stamped, which is worse than no check. So it learned to ignore inflection — and only inflection, because "negotiations" existing in my record is not the same as me having negotiated.
I wrote down what it can't catch, because a guard trusted past its range is worse than none. It catches invention. It can't catch distortion — two true claims welded into an implication neither makes, or "supervised" quietly becoming "managed". A person still reads the page.
ff_1One achievement at a design internship, written four ways
- technicalDesigned how AI model output reads as a clinical decision — blastocyst-likelihood scores, probability distributions, and per-oocyte predictions — across the clinician and patient report suite.3 of 6
- impactLed design of the patient-facing report for an AI egg-quality assessment product, and contributed component layout to the clinician suite — both now live in production for clinics in 35+ countries.1 of 6
- processDerived the patient report from the clinician version by cutting diagnostic depth without losing meaning, then stress-tested both across 4 languages so hierarchy and layout survived localization.1 of 6
- researchSat in on pilot sessions with the product’s first users — clinicians at a Spanish IVF clinic — recording how the reports were read in practice.1 of 6
Every resume carries at most one of the four. Which one depends on who is reading.
Supervised a team of 7–9, scheduling floor coverage in Figma.
A true line from the retail job, with a design tool added to it.
Against everything in the record
- 7–9found in the retail job
- Figmafound in the design jobs
Passes — and the sentence is false
Against the retail job’s own facts
- 7–9found in the retail job
- Figmanot a fact of this job
Refused
5Research on one user
The scanner was supposed to be the product. Then one resume for a bank's customer-service role took an entire session, and I wrote down exactly what I'd complained about while it happened. Four complaints, one root cause: the tool had no way to learn anything new about me. The scanner wasn't the bottleneck. The way information got in was. Scout became a resume engine that also scans, instead of a scanner that also tailors.
On 28 August I built a resume for a customer-service role — outside design, which is the point: my corpus held design work, and this posting needed my retail years. It cost a whole session. This is my own account of what went wrong, next to what each thing actually was:
| What I said | What it actually was |
|---|---|
| "Scout has a set of experience for me but it didn't want to take any more information" | The root cause. The corpus was closed |
| "Scout was building new layouts for my CSR resume" | A symptom. My retail jobs weren't in the corpus, so no template could render them, and a one-off layout got hand-built around the gap |
| "I had to explain a few times what I did in my retail experience as I didn't quite remember" | The real work. No tool had ever helped with recall |
| "The whole process was based on this chat window" | Where the cost landed. A chat holds no state, so the next application pays again from zero |
The proof was sitting in the output. The most expensive thing that session produced — thirteen bullets of retail duties I'd had to remember — had been written into a throwaway file instead of the corpus. Harvesting them afterwards took a fraction of the time it took to recall them.
This is self-observation, n=1, and I've labelled it that way. It was also the most useful research the project did, because it pointed at a problem I'd never have designed for from the outside: recall. Nobody remembers what they did at a job two years ago on demand.
6Designing the interview
When a posting asks for something my record doesn't cover, Scout interviews me. Designing that conversation took two reversals of my own first answers. Open questions alone lose the unusual things worth putting on a resume, so the tool cues generously. And a question can't invent anything — only a written answer can — so all the strictness sits on what gets written, not on what gets asked. It interviews per employer, not per posting, so I'm only ever asked about a job once.
My first design was a worksheet: a list of questions per posting. It fails at recall. A form is excellent at collecting what you know you need, and useless for what you don't remember until something adapts to your last answer — "who did you escalate to when a customer wouldn't leave?" is only askable after hearing about the customer. A static list of twenty questions gets abandoned around question four. So the interview is a conversation.
The first reversal. I'd planned open questions only, to avoid putting words in my own mouth. But free recall returns the ordinary day — serving, stocking, closing. A one-off, like the afternoon the till broke and someone had to work out why, is never part of "walk me through a normal shift" — and the unusual events are exactly what's worth a line on a resume, because nobody else's shift contained them. Open questions come before cues, not instead of them.
The second reversal. Then I planned to hold every bullet down to my exact phrasing. It sounded safe and it fails every single time: people understate in conversation. Something like "yeah, I fixed the till a few times" is someone being brief, not making a careful claim, and a corpus that can never exceed it guarantees a resume weaker than the truth. So the line is narrower. Words for the activity — fixed, diagnosed, resolved — need only that it happened. Words for frequency or scale — "routinely", "across the store", "40+ incidents" — need a recorded fact, and the owner-scoped check from section 4 enforces it.
One rule survived both reversals: the posting is never shown during the interview. Gaps choose the topic — "the record is thin on your retail job, and this posting leans on service work" — but never the question. "Did you handle cash reconciliation?", asked of someone who wants the job, pulls toward yes.
7A verdict that says what it doesn't know
Before building a resume, Scout decides whether each requirement in a posting is covered, partly covered, or a gap. My first plan was to label the matches and let me decide. I rejected it: a label is a warning, and warnings get ignored under exactly the conditions that make them necessary. So the tool makes the call, under four rules. Everything starts as a gap. Nothing is "covered" without naming the bullet that covers it. Every covered call says, in one clause, what it doesn't prove. And the report counts its own weak spots.
My own words when the "label it and let me decide" version was proposed: "I would want the tool to try and do it itself since it's backed with Claude. But yes, final check can be done by me." A tool that hands the hard half of the work back to its user has only done the easy half.
The four rules, in order of how much work they do:
- Every requirement starts as a gap. Something has to actively move it.
- No "covered" without a cited bullet. A verdict that can't name its evidence drops to "gap" on its own. This is what makes checking it fast: read the requirement, read the one named bullet, agree or don't.
- Every "covered" states its edge. "Covers handling upset customers; says nothing about doing it on phone or chat." The danger isn't the wrong call. It's the overconfident one.
- The report counts its weak spots — for example, "9 requirements — 3 covered, 2 partial, 4 gaps. Two of the covered calls rest on a single bullet each." A tool that states its own composition is harder to over-read.
What it deliberately doesn't do: produce a match percentage. A number like "78% match" compresses a judgment into a figure that reads as measurement. Counts, yes. A score, no.
This doesn't make the verdict right. It will get calls wrong, mostly on the generous side, because shared vocabulary looks like shared meaning. What it does is make a wrong call visible in seconds instead of buried in a confident paragraph.
8The feature I measured, then retired
I built a safe way for Scout to reword a bullet — the check in section 4 exists to guard it — and planned a bigger feature on top: rewording my design work so it would read for other fields. Before building that, I measured. Across all 14 resumes Scout had tailored, the rewording channel had been used zero times, by the tool or by me. The hand-written angles were already doing the job. So I retired the feature — not deferred, retired — and wrote down what would bring it back.
The feature was called adjacency: take a bullet about reviewing designs with clinicians and product managers, and reframe it as stakeholder handling for a service role. It was the capability I would have felt first. It was also the most dangerous thing in the project, because reframing "reviewed iterations with clinicians" as "handled customer escalations" is a lie in which no number changes. The check from section 4 would pass it.
Then the measurement:
14 tailored resumes — rewrites used in 0
Not one bullet reworded, by the tool or by me — and a month later the count is still zero. Building an automatic feeder for a channel nothing had put a single item into by hand was speculative by definition. And the need behind it was already met twice over: the coverage step reads my whole record and notices material that fits in different words, and the angles I'd written by hand are adjacency done in advance — by the only person who can tell whether the reframing is still true.
A retirement, not a deferral, on purpose. A deferred item sits at the bottom of a to-do list forever and gets re-proposed every time someone reads the plan. What would bring it back is written down: a real posting where my record provably covers a requirement and no existing bullet can say so.
The honest remainder: one field is still written fresh for every posting — the title line under my name, the first thing anyone reads after it. It is now the only place Scout writes anything, and it's guarded by a person, not the check. On 31 August the word "marketplace" nearly went into one with nothing in my record behind it.
- The line under the nameWritten fresh for each postingThe one field no check guards. A person reads it
- SummaryChosen from 9 written by handSelected by id, like a bullet
- Experience and projectsChosen from 74 bullets written by handRewording used in 0 of 14 tailored resumes
9Where it stands, and its limits
Scout is finished and in use. A daily scan runs on its own and has logged 1,664 postings from 60 company boards and the major job boards. It has rendered 20 resumes from 74 bullets I wrote. Two applications have gone out through it, and one came back — a rejection, five days later. That's the whole outcome record, and I'd rather show it than a projection. The code is going public so anyone can run it on their own record.
What it can't do, stated plainly:
- One user. Every rule here was tested against my record and my job search. That it would work for someone else is a hypothesis — which is why the public version ships with an invented person whose tests pass without any of my data in the copy.
- Outcomes are thin. Two applications and one result prove nothing about whether a Scout resume gets more interviews than a hand-written one. What they prove is that it holds up in real use.
- The check catches invention, not distortion — section 4.
- The title line is written fresh every time, and no check guards it — section 8.
- The AI is the smallest part, and replaceable. The scripts make zero model calls; everything that needs judgment lives in four plain instruction files. That's why it can run on any AI agent with a file system — and why making it public was worth doing at all. Hunter was the inverse.
10What this project taught me
The rising score was the warning sign, not the reassurance. A tool that was right most of the time cost me more trust than one that was obviously broken, because I couldn't tell which run to check. What fixed it wasn't a better model — it was a rule that made the failure impossible, and the discipline to measure what I'd built before building more on top of it.
- "Most of the time" is a failure mode, not a success rate. If a user can't tell which output is the bad one, every output costs a full review. Designing that out beats improving the average.
- Put the constraint where the harm happens. A question can't invent a fact; a written answer can. A label can't stop a mistake; a rule about evidence can. Every strong decision in this project moved a guard from where it felt safe to where the damage actually occurs.
- Measure before you build the next layer. Zero rewrites across 14 resumes retired the most dangerous feature on the plan before it cost anything. The measurement was a single count.
- Refuse where the damage is permanent; warn where it isn't. A bad bullet in the corpus poisons every future resume, so Scout refuses it. A missing note in one run's record affects nothing else, so it doesn't. Same-shaped problem, very different blast radius.
- Fix the form, not the instance. When a heading pattern failed for the fourth time, patching that posting would have fixed 6 occurrences. Sweeping all 2,236 stored headings fixed 128 and broke none. The previous three fixes had each been the narrow kind.
Patch the one posting
6
Sweep all 2,236 stored headings
128
Headings newly recognised. Headings the change reclassified wrongly: 0.