Front-end debt you can see without the repo
Framework version against its published support window, TypeScript strictness, UI test coverage, build times and dependency risk are debt signals with authoritative dates behind them, not opinions you have to defend.
This is the axis where you stop arguing. Everything on the maturity axis is a judgement someone can push back on. Here, the sentence is “their framework major went out of support on this date, and the vendor published the date” — and there is nowhere for the conversation to go except to the remediation number.
Which makes the discipline of this axis simple to state and easy to break: every colour traces to a dated published fact. The moment you score a stack red because you would not have chosen it, you have converted the strongest axis on the page into the weakest, and you have done it in the one place where the target’s engineers are best equipped to notice.
Support windows are the model, and they do not match
Start with the case where the published fact is unambiguous. Angular publishes a support policy with a table: a major is supported for roughly 24 months, split into 12 months active support and 12 months long-term support. The cadence changed recently — Angular ran a six-month major cycle until v22 and moved to a major release every 12 months — and the page states outright that versions v2 through v19 are no longer supported. If a target ships one of those, the finding writes itself, and the date is theirs, not yours.
Node.js publishes the same shape with more precision: an even-numbered major gets 12 months of Active LTS, then 18 months of Maintenance, a 30-month window, with an explicit end-of-life date printed per release line. Worth knowing where that table lives — it is in the nodejs/Release repository on GitHub, not on nodejs.org, which shows current status and codenames without the dated schedule.
React does not publish an end-of-life. Ever.
React’s versioning policy commits to semantic versioning and to backporting security fixes for all major versions that are affected. It publishes no LTS window and no end-of-life dates at all. So a rubric question phrased as is this framework past its end-of-life? has no answer for a React application, and that is not a gap in your research.
Two failure modes follow, and they are opposite. The first is scoring React green by default, because no published EOL means nothing to be past — which quietly rewards a project for not making a commitment. The second, worse, is treating the absence of an LTS policy as a debt signal in itself. It is not. It is a fact your threshold has to be written around, and the way to write around it is to branch: if the project publishes a support window, score against it; if it does not, score against release recency and the gap between the target’s major and current stable, and say in the cell which branch you took.
Strictness is a setting, and it has a definition
“Do they use TypeScript?” is a weak question, because the answer is almost always yes and it tells you very little. The question with teeth is whether strict is on, and the reason it has teeth is that the setting has a published definition rather than a cultural one.
The TSConfig reference enumerates the nine flags strict turns on: alwaysStrict, strictNullChecks, strictBindCallApply, strictBuiltinIteratorReturn, strictFunctionTypes, strictPropertyInitialization, noImplicitAny, noImplicitThis and useUnknownInCatchVariables. The same page warns that future TypeScript versions may add further checks under the flag, which is a real detail for an estimate: turning strict on is not a one-time cost that stays paid.
Two precision notes that will keep you out of trouble. The single-option page for strict does not list the nine flags — cite the reference page, not that one. And true is what tsc --init writes into a fresh config; it is not the compiler’s behaviour in the absence of a config. A target on strict TypeScript is a target that decided to be, which is exactly why the answer is informative.
Retrieval check
Their engineering lead says “yes, we’re strict TypeScript, it’s on across the monorepo.” You have no repository access. What is the honest mark, and what would change it?
Check your answer
Not assessed, with the claim recorded. It came from an interested party, and unlike adoption there is no rendered artifact that shows it: compiled JavaScript looks the same either way.
Two things would change it, and both are obtainable. If they publish any package on npm, its shipped type declarations and its own tsconfig are public. If their production build ships source maps, the original filenames and often the original sources are fetchable from the browser. Neither is a full answer for a monorepo, but either converts a claim into a sample — and a sample is scoreable where a claim is not.
The follow-up question worth asking them is better than the yes/no anyway: how many @ts-expect-error and any suppressions are in the codebase, and is the count going up or down. That one is hard to answer flatteringly without having looked.
Dependency risk, without a number nobody published
Two instruments here, and both are useful in a narrow way that is easy to overstate.
OpenSSF Scorecard is published by a foundation rather than a vendor, and it defines named checks with risk levels, each scored 0 to 10 — maintenance signals, branch protection, code review, dependency update tooling, signed releases. Cite the check names. Never cite a total, and never cite a count of checks: the documentation’s own stated number is inconsistent with the checks it enumerates, and the set changes over time. It also only runs against a public repository, which for most targets means their published SDKs rather than their product.
npm audit reports five severities: info, low, moderate, high and critical. The detail worth carrying into a management conversation is that --audit-level changes the threshold at which the command fails and does not filter the report. So “our CI is green on audit” says nothing about what the report contains. It says somebody chose a threshold. Asking which threshold, and when it was last changed, is a question with an interesting answer either way.
The benchmark you will want does not exist
There is no authoritative published statistic for what fraction of dependencies a typical project has outdated. Research for this course went looking and found none: academic studies exist with incompatible methodologies and no body collects the figure. So there is no “industry average” to score a target against, and any percentage you have seen quoted for this came from somebody selling something.
Make the qualitative point instead, and make it specific: a major version behind on a framework with a published support window is a dated fact; twelve minor versions behind on everything is a signal about upgrade cadence; a direct dependency whose last release predates the target’s last funding round is a bus-factor conversation. None of those needs a benchmark.
What this axis cannot see, and saying so
Two of the six questions under this axis do not survive the access constraint, and pretending otherwise is how a rubric gets a reputation.
- UI test coverage. Nothing in a rendered application tells you whether a refactor is guarded. Test identifiers in the DOM hint that something automated exists; they do not tell you what it asserts, or whether it runs. Data-room or repository question.
- Build and CI feedback time. Entirely internal. There is no outside artifact, and no published benchmark to compare against if you had one. Interview question, and a good one, because the answer is a number they either know or do not.
Marking both not assessed on a pre-offer read is the correct outcome, not a failure. It also does something useful for the deal team: two not-assessed marks on an axis where four questions resolved is a precise, unarguable statement about what the access they negotiated was worth.
What you can reach from outside is more than people expect. Their rendered application announces its framework through bundle contents and hydration markers. Their published packages carry dependency manifests. Their job postings name the stack, and a posting for a framework migration is a target telling you about its own debt in public. Their changelog dates the last time the interface changed at all. None of it was curated for your visit.
Check your recall
Answer from memory — no scrolling back.
Hands on
Turn axis 2 into dated facts
Done when: Every question under Axis 2 in RUBRIC.md carries a threshold that names a published source, the framework question has an explicit branch for projects that publish no support window, and the two unobservable questions are labelled as second-stage.
- Open
learning/ux-diligence/RUBRIC.mdat Axis 2. For 2.1, write the threshold as two branches. Branch one: the project publishes a support window, so score against the published dates. Branch two: it publishes none, so score against distance from current stable and release recency. Write the sentence that goes in the cell naming which branch you used. - For 2.2, replace “is
stricton” with something you could actually evidence without the repo: a published package’s own config, shipped type declarations, or source maps. If none of those exist for a given target, the honest threshold ends in not assessed, and writing that into the rubric now saves you inventing a colour later. - For 2.5, write a threshold that uses no benchmark. Anchor it to the three specific signals instead: a major behind on a framework with a published window, upgrade cadence across minors, and a direct dependency with no release inside a stated period.
- Mark 2.3 and 2.4 explicitly as second-stage questions, with the evidence class that would answer each. Do not delete them — a question you can name and cannot answer is information for the deal team about access.
- Now test it. Pick any public product, spend twenty minutes, and score 2.1 and 2.5 against the thresholds you just wrote. Record how long each took and what evidence you actually used.
- Bring both thresholds and the worked scores into the chat. I will argue one of your colours from the same evidence and you should be able to point at the cell that settles it.
What this does not cover
This axis prices changing the interface. It says nothing about whether anything could ever act inside it on a user’s behalf — whether there is an API surface to act through, whether application state is reachable at all, whether there is telemetry to measure an agent’s impact against, and whether the product has ever taught its users that software proposes and a person disposes. That is the agentic readiness lesson, and it is the axis where this course is doing the most inventing, which it says so plainly.
The graftability lesson then asks the question that follows from all three: whether a surface built once somewhere else could be installed here at all.
Read this next — primary source
React versioning policyReact (the project’s own documentation) — free; the maintainers documenting their own release commitments
Read this one for what it does not say. It commits to semantic versioning and to backporting security fixes to every affected major version, and then it stops: no long-term-support window, no end-of-life dates, no supported-versions table. Most of what you will read about framework debt assumes such a table exists. Sitting with a page where it deliberately does not is the fastest way to see that “is this past end-of-life?” is a question your rubric has to be able to answer with “this project does not publish one,” without that answer defaulting to either colour.
Stuck, curious, or think this lesson is wrong? Ask your teaching agent. The lessons are the scaffold; the conversation is where the learning gets unstuck.