What a finished problem is: the URL shortener's parts, where they live, what "done" meant
Paths are in the guide repo unless they start with ~. "His words" are Bruno's, quoted exactly, with the file they are
recorded in (see quality-bars.md for the full quotes and moments). Board version at the time of writing: 3.10,
origin/main 000ed34.
1. The page
- Files:
curriculum/03-production/01-system-design/problems/url-shortener.md. - Shape at the top:
# Design a URL shortener, a scenario of two sentences with the commercial on its own line, then## Design it, where the board mounts. The board's exercise names that heading, and the build raises an error if no h2 matches it exactly (site/reader.pymount_designboard). The page's AWS diagram sits in that section and becomes the reference "compare after you have drawn yours". The page ends there: it is the board and its compare diagram. The reading lives on three parts inproblems/url-shortener/, rows 14a to 14c of the chapter README: 9.14a background and sizing (its arithmetic shown), 9.14b "Build it locally", 9.14c the AWS mapping, the click storage and the follow-ups. - Done meant: his notes of 29 Sep, item 3: "Less is more", the problem in one line, two or three sentences of scenario, "Go straight into the interactive problem". The scenario has to make the numbers believable: it read as a marketing team's internal tool, "which does not fit 30 million links a day or a commercial's peak" (commit 13fd8c8), so it became a public service. The first paragraph over 60 characters becomes the page's description and search snippet (commit 14b2304): keep any line above it short. Nothing the interviewer is meant to reveal sits above the board (commit ae763f5).
2. The exercise
- Files:
problems/url-shortener.board.json, one exercise:id,heading(equals the h2),title,brief(one line with no requirement in it),requirements(four, with a bold lead word),expectations(four),checks(ids fromsite/designboard/checks.js: arrows, reachesApi, namesInDb, readsSkipDb, spread, clicksOffPath),capabilities(ids fromsim.js; Break it fails without them),heavy(a key ofheavy.jsPROBLEMS),api: true, andtipskeyed bystart, each check id, andpassing. - Done meant: the requirements and expectations above the canvas, a few words each, after the rule that sank his first heavy run "had been one clause of the brief" (commit c2f5296). While the interviewer is reachable, the requirements list is hidden and found by asking.
3. The interviewer
- Files:
site/interviewer/url-shortener.interview.json(17 requirements, 34 answers; each answer haskind,topic,match{what,not_for,examples},cues,reply,uncovers,outside_page), layered over the sharedgeneral.json; the evaluation seturl-shortener.eval.json; the serverserver.py(also run aslambda_handler.py). The knowledge base never ships with the site, so a reader cannot read the requirements in devtools. It goes live with the interviewer's own deploy, not the site build: the box'sj2s-interviewerservice, or the Lambda built on 2026-09-30 (~/soulful/aws/interviewer/stack.py deploy). Which one serves/api/interviewertoday is Iris's to say. - How it works: the reader asks; Jev (TypeSafe's decision model) only chooses among prewritten answers; a requirement is written down only when Jev's choice, Jev's yes on the topic, and one of the answer's cues in the question agree. Every reply is prewritten from the page.
- Done meant: "It should feel like an architecture interview." After "My question was very very simple and common. The fact you miss something so simple kinda scares me." (2026-09-27 21:14), it was measured on 259 real questions, 61% to 99.6% (commit f9fea5f). One exchange at a time, Written down gets the room (his notes of 29 Sep, item 1).
4. The API's vocabulary (the "API catalog")
- Files (code, shared by every problem): resource kinds and roles in
api.js(RESOURCE_KINDS,KIND_WORDS,ROLE,FITS); verbs, checks, ways and their words inflow.js(DOES,CHECKS,CHECK_WAYS,USES,nodeWords,WAY_WORDS); what the editor offers inflow-view.js(VERBS,options,reach,MEANT,WRITE_MODES). The parts catalogcatalog.jsonis neutral (no URL words in it). - Done meant: an endpoint starts empty, with nothing that gives a test away; a menu offers only steps that mean
something where they are offered; the API names what the code does, not infrastructure ("API Spec should be API
spec", 2026-10-04). Still open: "I ALSO don't see how s3 is a database here. i feel like there arent enough types of
components i can make in the api spec." (2026-10-04 18:51); the runner helper in
~/scratch/j2s-runneris adding a files kind for S3 now.
5. The tests
- Files:
problems/url-shortener.tests.json: five tests, each withid,title,source(the page's own sentence it comes from) and ascenario: calls at given times with what the page expects (status,noStore,withinin ms), events (cache-drops,pause-invalidation,slow-clicks) and click counts ({at, expect: {clicks}}); plus aheavyline that must contain the words "Heavy test" to become a button. Named specs insite/designboard/test/api-specs.mjsandtest/flow-specs.mjs: the good API, and one per known mistake, each test passed by one and failed for its own named reason by others. - Done meant: "API spec with OVERALL functionality. [...] some test behind it to make sure functionality works"
(2026-09-27 03:50,
site/designboard/README.md). Code runs them, never a model (he said yes at 08:12). Since 2026-10-04 18:51 a test must check what has to happen, not one way of doing it ("are we forcing the User to a specific answer...").
6. The simulations
- Files (code, URL-specific today): the runner
flow-run.jsand its worldresources-sim.js(people, titles, should-lines, hints); the pop-upscenes.js(order, nudges, what a person is told). The story shape is~/scratch/heavy-work/r4/SCENES-CONTRACT.mdplusnode,way,walkandstory.walks(docs/design/board-3.0-api-flow.md). - What a reader sees: "1/5 simulations passed" and "Run simulations"; each scene unlocked easiest first (
ORDERinscenes.js, or the tests file's ownorder), in a pop-up: people on the left (Maya and Sam create, Leo opens, the Click worker counts), the reader's flow in the middle with the walked way lit, what each resource holds on the right with a small diagram of who talks to whom, a title that sets up the situation and a line of what should happen, the steps listed and counted, ½× by default (1× where the voice speaks). A failure stops on its moment; the tip is locked, asks a question first, then names the pattern. - Done meant: the quotes of 2026-09-27 17:33 ("I rather there be like an IRL simulation of a person trying to create a link"), the call ("I don't wanna see any of that"), 19:27 ("I wanna unlock them as I go from easiest to complex"), 20:52 ("should def be slower to see"), and what he loved in his notes of 29 Sep. Since 2026-10-04 18:51 the titles and steps must read "Like if you were explaining it to your dad."
7. The narration
- Files:
problems/url-shortener.narration.json(prefix: "url", the voice: ElevenLabs "Katie - Audiobook & Documentary Narrator", idm4hBEimiy2ffkQ0hHMVD, modeleleven_multilingual_v2, her stored settings; 88 lines: 83 for frames, 5 introductions); the clipsassets/narration/url/<id>--<hash>.mp3(shipped in the repo so a build needs no network); the master caches3://soulful-iris-652539275920/guide-audio/;site/narration.py(the key),site/tools/narrate.py(makes only what is missing, refuses a run over--cap5,000 characters before reading the key,--checkmeasures every clip and has Deepgram transcribe it);site/designboard/voice.js(which line a frame says). - Done meant: the quotes of 2026-10-04 05:14 ("She should be saying enough and not enough to fit in the animation and not be delayed or ahead") and 08:31 (1× and an introduction after half a second). One clip serves every reader: no line names a reader's resource or a run's number. Every clip ends before its step does.
8. The drawing board
- Files: board-wide code (
board.js,sketch.js,boxes.js,copies.js,geometry.js,layout.js,checks.js,sim.js,resilience.js). Per problem only the exercise's chosen checks and their tips. - Done meant (done once, for every problem): parts drawn the way people sketch them at a whiteboard (2026-09-26), copies as boxes and groups in one frame (2026-09-27, 2026-09-28), arrows that show direction and can go both ways, arrows that go around parts, Break it's production tips.
9. The heavy test
- Files:
site/designboard/heavy.js:K(every number with a kind code H, S, D, B or R and a numbered source from~/scratch/heavy-test-research/numbers/REPORT.md) andPROBLEMS["url-shortener"](three levels: Low "Midnight", Medium "A weekday afternoon", High "The link goes viral", each with a story, a hot key andat(t));heavy-fixes.js(a card per problem the run found),heavy-improve.js(at least one next step after every run),heavy-explain.js(what each part does, what each change gains and gives up),heavy-report.js(Sonnet's optional report;BRIEFSkeyed by problem id),heavy-view.js(the window). Saved designs with their outcomes intest/heavy-designs.mjs(13: the research's A to I, Bruno's boards J and M, variants K and L) and Bruno's real runs of 2026-10-04 intest/candidate-design.mjs. - Done meant: the quotes of 2026-09-27 03:35 and 03:50 (a load that builds; numbers on the arrows; a picture of the spot, what to do, why, re-simulated), 10:16 ("always have a way of improvement"), 2026-09-28 07:08 (scaling as it really behaves, never topping out), 2026-10-04 (interview depth, not vertical-scaling specifics; why an idle part is idle).
10. Pricing
- Files:
site/designboard/heavy-cost.js(AWS Price List, us-east-1, on-demand, read 2026-09-27),site/designboard/tools/prices.mjs(checks every price used against the research'sprices.json, and rewrites them after a new read); the research~/scratch/heavy-work/pricing/REPORT.md. - Done meant: "Per component based on the simulation" (2026-09-27); since "there is too much talk regarding money in the results" (2026-10-04), one tile per part, with the price notes behind a closed summary; each card shows the cost an hour and per million redirects answered.
11. The diagrams
- Files:
assets/architecture-guides/url-shortener.svg(the page's AWS diagram, the compare-after answer);assets/diagrams/clicks-two-halves.svg(animated) with an authoredclicks-two-halves-still.svgfor reduced motion;twitter-lambda-to-kappa.svg;click-s3-vs-dynamodb.svg. - Rules:
docs/STYLE.md,docs/PROJECT-SPEC.md("It must read correctly frozen on the first frame"),scripts/check_svg_geometry.py(clips and overlaps),docs/visual-review.json(new SVGs show as review-pending until added there). Render each in Chromium and open the picture at frame one and mid-animation. - Done meant: "this is the kind of detail and to the point diagram and animations that i would expect when I go over a problem in guide" (2026-10-04 13:27).
12. How big companies do it
- Files: the section "How big companies keep and count clicks" in the page: what Twitter and Bitly built, from their own engineering posts (a third party's notes labelled as such); one record in S3 against the same record in DynamoDB; wins and losses at the page's own numbers, with prices and the date read; what the raw data is for; "The answer to give", with what to say in an interview; "Your design is this design", which names the reader's likely design and its one change; "Not covered here".
- Done meant: "we strive for hte best and proven architecture." (2026-10-04 13:27).
13. The checks that prove it
- Unit:
node --test site/designboard/test/*.test.mjs(the glob form; a bare directory runs nothing), 559 at board 3.10. - Browser, on a full build of
site/out:flow-check.mjs,sim-check.mjs,voice-check.mjs,heavy-check.mjs,designboard-check.mjs,side-panel-check.mjs,interviewer-check.mjs(its ports are fixed at 8983-8985).api-check.mjspredates board 3.0: do not run it (README correction of 2026-10-04). - Python:
site/test_narration.py,site/test_publish.py,site/interviewer/test_server.py. - Build and links:
site/build.pywith the reader venv, thensite/check.pyanddocs/check-links.py. - The release runs all of these in order:
~/scratch/guide-release/run.sh(read it; run its commands in your own worktree, not the script).
A new problem is done when
- The page opens on the problem, the scenario and the board, and its numbers come with their arithmetic.
- The interviewer reveals every requirement the tests and the heavy test depend on, measured on an evaluation set.
- The reader can write the API by hand with no key, and every test passes every design that does what the page requires.
- Each test plays as a scene with people, unlocked easiest first, in human words, with a question before the tip.
- Every rule a test or the heavy test enforces is said before a run, where the reader works, with the fix.
- The heavy test's three levels are sourced or labelled estimates, build over minutes, and every run ends with at least one next step, priced per part.
- The page has the proven answer: how big companies do it, from primary sources, the answer to give, and diagrams.
- Katie narrates every frame the tests make, timed to the steps (or the problem ships without her at ½×, which works).
- Every check above is green on a full build, each new one seen red once, and the pictures were looked at on his widths.
- A stranger who has never seen it walked it cold, and what they tripped on is fixed or listed.