Skip to content

Hardening 3/3 (stacked on #372): ErrorBoundary + 500 page, axios timeout, hook error contract, CI runs lint + jest - #373

Merged
gregv merged 6 commits into
developfrom
hardening/3-safety-net
Oct 1, 2026
Merged

gregv merged 6 commits into
developfrom
hardening/3-safety-net

Conversation

@gregv

@gregv gregv commented Sep 30, 2026

Copy link
Copy Markdown
Contributor

Stacked on #372 (hardening/2-seo-ssg), which is stacked on #371. Base is #372's branch, so this shows only the safety-net changes; merge #371 → #372 → this. Last of the three frontend hardening PRs (docs/plans/hardening-security-seo-reliability-2026-09.md, sections 3.4–3.5).

What changed

Problem Fix
A render error anywhere in a page blanked the whole app (NavBar + Footer included); SSR failures showed Next's default error page src/components/ErrorBoundary.js wraps ONLY the page subtree in _app.js (NavBar/Footer and their CLS placeholders untouched), resets on client-side navigation via resetKey={router.asPath}; new static, noindex pages/500.js for SSR failures
No axios timeout — a hung backend held every caller forever axios.defaults.timeout = 30000 (30 s: admin bulk operations are slow; the 401 retry doubles the worst case)
useHackathonEvents set hackathons to undefined on a 429/5xx (it assigned data.hackathons from the axios error response), crashing every consumer's .map — reachable by design now that the backend answers 429 instead of 500 Failures yield [] plus error {status, message}; 403 stays quiet as before
No CI at all in this repo — nothing ran the suite before merge .github/workflows/ci.yml: npm ci, eslint (errors fail, warnings allowed), npm test -- --ci on PRs + pushes to develop/main. No next build in CI on purpose: Vercel is the build gate and a CI build fires ~550 requests at the production backend

New tests: src/components/__tests__/ErrorBoundary.test.js, src/pages/__tests__/500.test.js, src/hooks/__tests__/use-hackathon-events.test.js. Full suite: 61 suites / 480 tests green. The Lint + Jest check on this PR is the new workflow running for the first time.

Test plan (preview)

  1. This PR's Checks tab shows CI / Lint + Jest green.
  2. /some-page-that-does-not-exist → still the sleeping-cat 404. Temporarily throw inside any page component on a local dev build → the calm "Something went wrong on this page." card renders with the NavBar still visible; navigating to another page via the nav clears it.
  3. curl -sI <preview>/500 → 200 with <meta name="robots" content="noindex, follow"> in the body; the page has Reload + homepage actions.
  4. With the backend unreachable (e.g. NEXT_PUBLIC_API_SERVER_URL pointed at a dead host locally), / and /hack render with empty event lists instead of a client-side crash; requests give up after 30 s.

🤖 Generated with Claude Code

gregv and others added 4 commits September 30, 2026 15:16
…0 page

A render error anywhere in a page blanked the whole app (NavBar and Footer
included) and there was no 500.js, so SSR failures showed Next's default
page. ErrorBoundary wraps ONLY <Component/> in _app.js (placeholders and the
NavBar/Footer invariants untouched) with resetKey={router.asPath} so a
client-side navigation clears the fallback; pages/500.js is static (no data,
auth or router) and noindex.

Tests: src/components/__tests__/ErrorBoundary.test.js, src/pages/__tests__/500.test.js.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
…ined on a backend error

There was no axios timeout, so a hung backend held every caller forever.
useHackathonEvents' makeRequest returns the axios error.response on a
non-2xx and the effect did setHackathons(data.hackathons) with it — a 429 or
5xx set undefined and crashed every consumer's .map (the backend PR turns
tripped rate limits into 429s, so this path is now reachable by design).
Failures yield [] plus an error {status, message}; 403 stays quiet as before.

Test: src/hooks/__tests__/use-hackathon-events.test.js.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
The repo had no workflows at all, so nothing ran the 480-test suite before
merge. ci.yml runs npm ci, eslint (warnings allowed, errors fail) and jest
with dummy NEXT_PUBLIC_* env. next build is deliberately not run in CI: a
build fires ~550 getStaticProps requests at the production backend.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
… error contract, CI)

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
@vercel

vercel Bot commented Sep 30, 2026 •

Copy link
Copy Markdown
Contributor

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated
frontend-ohack-dev Ready Ready Preview Sep 30, 2026 7:21pm UTC

Request Review

gregv and others added 2 commits September 30, 2026 15:19
…te and the Vercel build failed)

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Base automatically changed from hardening/2-seo-ssg to develop October 1, 2026 20:12
@gregv
gregv merged commit 80a1c1b into develop Oct 1, 2026
2 checks passed
@gregv
gregv deleted the hardening/3-safety-net branch October 1, 2026 20:13

This branch was successfully deployed

1 active deployment
Preview — 27f7b5b0 Deployed Sep 30, 2026 by vercel[bot]
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant