Every question on our 20 new pages carries the URL it was reported at, and the pages show none of them
Candidates who get invited to a recorded video interview search for it by the name of the firm, not the name of the platform. "goldman sachs hirevue questions" is a real query; "video interview platform best practices" i
Candidates who get invited to a recorded video interview search for it by the name of the firm, not the name of the platform. "goldman sachs hirevue questions" is a real query; "video interview platform best practices" is not. Our general guide could not answer the first one, so this weekend we shipped 20 pages that do, one per firm, at /interview/hirevue-interview-questions.
The interesting part is not the pages. It is the field we built, shipped, and then stopped rendering 62 minutes later.
Every question is a claim, so every question got a URL
The content type for these pages has one unusual rule. A question is not prose we wrote; it is something a candidate reported somewhere, so each one is a record with the page it was reported on:
/** One reported question, with where it was seen (recorded, not rendered). */
export interface CompanyQuestion {
/** The question as reported. Light paraphrase allowed. */
q: string;
/** The division or track it was reported for, only where the source says so. */
context?: string;
/** Site the question was reported on, e.g. "eFinancialCareers". Not rendered. */
source: string;
/** Year of the report, where the page is dated. Not rendered. */
year?: number;
/** Exact URL of the page the question appears on. https only. */
url: string;
}
Across the 20 firms that comes to 271 questions. They resolve to 44 distinct URLs on 18 hosts, with a long tail: 84 questions come from one interview-advice blog, 90 from the two country editions of a finance careers site, 27 from a third, and eight hosts contribute 16 questions between them, two of them one each. 255 of the 271 carry a year, running from 2018 to 2026.
Separately from the questions, each page carries its own sources list for the stage facts and the advice: 121 URLs over 49 hosts, all https, every one opened by hand. That is where you find out how little the firms publish. The 20 pages have 146 rows describing where the interview sits in the process, how long it runs, how many questions, how much thinking time, whether you can retake. 68 of those 146 rows read "Not published." The rule in the type is that a gap stays a gap:
The format (question count, thinking and answer time, retakes) only as sources say it. Never fill a gap with the platform default.
Then we deleted the citation links
The first version rendered each question with its source underneath as a small rel="nofollow" link, because if you can cite it you should. One commit later, that came out:
- {count} questions from {entry.company} HireVue interviews, each linked to where it
- was reported. Prepare a story for each type rather than a script for each question.
+ {count} questions from {entry.company} HireVue interviews. Prepare a story for each
+ type rather than a script for each question.
Net effect of that commit: 17 insertions, 25 deletions, four files. The doc comment on the shell now says why.
* Sources are kept in the data but never rendered: the owner wants only the
* questions on the page, with no links out to the sites that reported them.
* Each question's `url` and `entry.sources` are the record behind the page.
That reads like vanity until you look at what the page is for. Someone landing on it has an interview in three days. A row of citations under every question is 271 chances to leave for a competing prep site, and it answers a question nobody on that page is asking. The URL is not there for the reader. It is there so that the sentence above it can be checked by us, and so that nobody on the team can add a question they half remember.
So the guard test does the checking instead of the reader:
it('cites an https source on every question', () => {
for (const entry of COMPANY_QUESTIONS) {
expect(companyQuestionCount(entry)).toBeGreaterThan(0);
for (const group of entry.questionGroups) {
for (const item of group.questions) {
expect(item.url).toMatch(/^https:\/\//);
expect(item.source.trim()).not.toBe('');
}
}
}
});
The rest of that file is the same set of failures every content registry needs guarding against: a registry entry with no route folder (a sitemap URL that 404s), a folder with no entry (a build that throws, because the lookup throws rather than returning undefined), a title over 48 characters (the layout appends 12 more), the same question listed twice on one page, a "read next" link to a page that does not exist, a path that robots.txt happens to block, and an em dash anywhere in the content.
See it
Open the Goldman Sachs page, view source, and search the HTML for efinancialcareers. Zero hits. Search for any of the hosts above and you get zero again. I ran that sweep over all 20 live pages just now: the only external hostnames anywhere in the served HTML of any of them are js.stripe.com and api.stripe.com.
Then count the questions in the rendered page: 20 on that one, which is exactly what the data holds. The page with the fewest has four, because Oliver Wyman is the firm with the least reported and the rule is that it gets a shorter page rather than a padded one. Six of the 20 firms also have an employer guide on the site, and only those six link to one, because the test fails if a link points at a folder with no page.tsx.
The practice the pages hand off to is at /interview.
Keeping the citation in the data and off the page felt wrong for about a day. It stopped feeling wrong when the first factual correction arrived and I could open the exact URL the line came from in four seconds.
Originally published by Dev.to WebDev. Aggregated on AIWithGhost for educational purposes — full credit and traffic to the original publisher.