chore: dependency bumps, homepage rebuild, spacing token system - #75
Merged
Conversation
Patches all four open advisories:
- sharp 0.34.5 -> 0.35.3 (high): inherited libvips CVE-2026-33327/33328/
35590/35591, fixed in 0.35.0
- astro 6.4.8 -> 7.1.3: XSS via unescaped spread attribute names in
renderHTMLElement (fixed 7.0.6), XSS via transition:* directive values on
hydrated islands (fixed 7.0.4), reflected XSS via View Transition animation
properties (fixed 7.1.0)
@astrojs/mdx 5 does not load under Astro 7 ("Cannot find module
'astro/jsx/rehype.js'"), so mdx goes to 7.0.3 alongside sitemap 3.7.3 and
check 0.9.9.
Verified on the new major: 46 pages built, 7 shorts, 6 Quest Log items,
3 blog RSS items, newsletter redirect and inlined search all intact.
Lint clean, astro check 0 errors, 17/17 tests.
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_016LwTTPEHxQZZQ6MJyKaBcw
…ontact Restores the pixel voice to section headings while keeping the serif tier for content, and rebuilds the homepage around the castle rather than around a card grid that duplicated the nav three times over. Homepage - Hero H1 spans the container so it runs at full scale in two lines; one lede paragraph, and the trust line drops the platform links so it stops wrapping into a stranded separator. - Lead story moves into the hero's empty right column, which also stops it repeating as the first Quest Log row. - Card grid deleted; the castle becomes the wayfinding band under "Map of the Realm". Quest Log rows carry pixel category icons. - Newsletter gets its own band below the podcast band. Signup is a hosted Riverside page, so the CTA links out until there is an endpoint to POST to. - "Our Quest" becomes "The Party". Components - VideoFacade gains a poster slot. The lead story was a short WITH an embed, so it took the facade branch and kept showing a raw Riverside webcam grid; the branded poster now sits in the slot and the player still loads on click. - EpisodePoster has poster and card variants, so the on-site card does not repeat the title that is already HTML directly beneath it. - SubscribeChip: outlined cartridges had a transparent face, so filter drop-shadow traced the letterforms and stamped an offset ghost of each label across itself. An opaque face fixes the strikethrough. - Castle labels become hanging signboards at a consistent height, reachable by keyboard, with pixel link chips below 640px and a visually-hidden link list. role="img" became role="group" so the links are exposed to screen readers. - Search collapses to a bare icon at the far right; results are styled with :global because Astro scoped styles never match runtime-created nodes. Content - toSummary truncates at the last complete sentence, handles abbreviations, and normalises em dashes. Search index descriptions are summarised at build time. - Copy pass across home, about, 404 and the four section intros: puffery and audience flattery out, D&D imagery kept. No claims about publishing schedule or episode length. - Chris is a seven-time MVP in AI and Developer Technologies; Josh is two-time. Chrome - Nav 8 items to 5. Three-column footer with the RSS feeds that existed but were never linked, and a corrected licence split: site text CC BY-SA 4.0, code MIT. - New privacy and contact pages. Every privacy claim is drawn from the code. - Realm accents retuned to one metallic family; --colour-stone raised to clear AA where it carries live timestamps. - CI content lint fails the build on em dashes or "delve" in rendered prose. Known outstanding: one em dash still reaches the talks page summary, which the new lint will flag. The manual-talks branch appears to bypass toSummary. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_016LwTTPEHxQZZQ6MJyKaBcw
The talks page rendered "the CIA triangle of security—confidentiality, in...", which the new CI content lint fails on. Traced it past toSummary: the string lives in src/content/talks/securing-the-realm-purview-mcp-and-agentic-communi.json, a manual talk we wrote, and manual summaries render verbatim by design. It had been pasted from the YouTube description complete with the em dash and a hand-truncated "in..." tail. Rewritten as a real sentence rather than patched around in code. No other manual summary carries a truncation artefact. Also carries the excerpt agent's toSummary work: clause-boundary fallback when no sentence break fits, plus its tests. Rendered prose now has zero em dashes and zero instances of "delve" across all 48 pages. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_016LwTTPEHxQZZQ6MJyKaBcw
Rhythm pass. Every uneven seam was an ad-hoc value; this replaces them with a token layer and applies it. Spacing and width - --space-section (96px desktop, 56px mobile), --space-heading (40px) and --space-inner (24px), all on the 8px grid. - Sections own padding, nothing owns margin. The old margin-bottom plus padding-block mix was why each seam stacked differently. - --measure was 66ch, which resolves per font-size, so the Listen subhead and The Party paragraph came out different widths. Now a fixed 720px. Hero - Row two is start-aligned, not centred. Centring split the void and put half of it between the H1 and its deck, which breaks the reading gravity; start-align moves the whole void below the trust line where trailing space reads as rest. The H1 keeps its full scale and its two lines. - A 3% starfield (--colour-star) runs into the castle band below, so the hero's empty bottom-left reads as sky rather than absence. - Trust line uses the pixel diamond utility instead of middots. Castle - Six labels become hanging signboards on one baseline rule, each a consistent 16 units above its roofline. They were eyeballed per building before, which is where most of the residual scatter came from. - Chips below 640px double as the visually-hidden link list above it, revealed on :focus-within so a sighted keyboard user never hits an invisible tab stop. Elsewhere - Heading rules fixed-width, so they no longer flex with heading length. - Quest Log rows spaced so the accent bars read as five marks, not one spine; moonlight bar to 4px to clear non-text contrast. - Arcane Scrolls gets a notched panel, so it has edges instead of floating. - Episode poster shows the category glyph, not the show shield: the shield is already in the header, and the thumbnail should say what the episode is. - About's "Meet the Hosts" becomes "Meet the Party", matching the homepage CTA that links to it. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_016LwTTPEHxQZZQ6MJyKaBcw
Four deletions in index.astro that were fighting the new spacing tokens. All
four were overrides written before the token layer existed.
- The Party section carried an inline margin: var(--space-16) auto 0 auto. That
64px top margin stacked on the newsletter's 96px padding-bottom, making the
one remaining broken seam 160px. Now margin-inline only.
- A scoped .section-heading { margin-bottom: var(--space-8) } duplicated and
overrode the global rule, so homepage headings sat at 32px while every other
page used --space-heading at 40px.
- .map-subhead had a negative top margin clawing back the old 32px heading gap,
which double-corrected once --space-heading applied.
- A mobile .newsletter-band padding override forced 48px over the 56px mobile
section token on both sides of that one section.
Measured in the browser after the change, at 1248px: every seam is exactly 96px,
and every section's spacing lives in its own padding with zero margins between
boxes. Bands read 96px to the colour edge then 96px inside it, which is the
intended two-step rather than a doubled seam. At 390px the token steps to 56px
and every seam follows.
Also confirmed at 390px: scrollWidth equals clientWidth equals 390, so the
full-bleed band maths (width: 100vw with margin-inline: calc(50% - 50vw)) lands
flush and nothing is hiding behind body { overflow-x: hidden }.
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_016LwTTPEHxQZZQ6MJyKaBcw
Sections own their whole seam symmetrically: .section-stack carries padding-block: var(--space-section) on both edges and .page-shell drops its own block padding when it holds a section stack, so no seam is the sum of one section's padding and a shell's. Removes the 4px optical correction under the Listen band's secondary cartridge row. It compensated for a drop-shadow that every other section's trailing button also paints, so it made one seam a special case for a condition that was not special. Six of the seven boundaries now bisect at exactly 96/96. header -> hero does not and cannot at that value: the header is a 16px-padded nav bar with no background of its own, so there is no colour edge there to bisect, and 96px under the logo would make the bar 160px tall. Adds qa/measure.mjs, which walks the page's background blocks and prints the gap above and below every seam. Screenshots stay out of git. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_016LwTTPEHxQZZQ6MJyKaBcw
Hero starfield now matches the castle band's sky instead of being three percent of it: same --colour-parchment at the same 0.6 the castle's twinkle floors at, with the restraint moved from alpha into density. At three percent the dots were mathematically present and visually absent, so the hero's empty bottom-left still read as absence rather than sky. Hero card glyph moves from a 43px corner mark to a 56px one centred on the tile. It is positioned rather than laid out because VideoFacade forces display:block on the slotted poster, so the poster's own grid does not apply inside the hero. Arcane Scrolls box drops from 900px to the 720px measure with even 48px padding, and its heading loses the flanking dashes: inside a notched panel the box is already the frame, so the rules were a second border 48px in from the first. Quest Log excerpts now end on the sentence's own punctuation. toSummary keeps whole sentences only, and returns a first sentence that overruns the budget rather than clipping it, up to twice the budget. Three of the five homepage rows were ending mid-clause on an ellipsis. "All talks and episodes" aligns with the row titles by composing the row's own inset from the same tokens the row uses, so it tracks the accent bar and thumb column rather than being nudged 4px. Footer licence holds together with nowrap, not alone: non-breaking spaces still let the browser break at the hyphen inside "BY-SA". Adds --space-subhead for the subhead-to-content gap, which was borrowing --space-heading. Verified: seams still bisect at 96/96 at 1440 and 56/56 at 390 for six of seven boundaries, glyph centre 1045 against a card centre of 1045, box 720px, no ellipsis in any rendered excerpt, 66 tests pass. Castle signboards needed no change: one SIGN_GAP = 16 rule already places all six plaques 16px above their own building's roofline. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_016LwTTPEHxQZZQ6MJyKaBcw
Updated the description to better reflect the podcast's focus on Microsoft AI governance and security. (cherry picked from commit 0ce7c20)
KnowledgeRatio
approved these changes
Jul 31, 2026
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Dependabot alert clearance plus the homepage identity rebuild and spacing-token work that landed on top of it.
--space-section.qa/measure.mjsadded to check section gaps).VideoFacadeandEpisodePostercomponents so embeds load on interaction rather than on page load.src/utils/youtube.test.ts(456 lines) and a.github/workflows/test.ymlrunning lint + typecheck + build.31 files changed, +3075 / −764.
Test plan
bun run buildpasses (zero TypeScript errors, zero Biome errors)bun run testpasses🤖 Generated with Claude Code
https://claude.ai/code/session_017hz2KqeTRM4cvABX5Tfcwb