feat(search): one state school group, not academy and council-run #171

Merged
tudor merged 1 commits from feat/single-state-school-group into main 2026-10-02 15:33:14 +00:00
Owner

Problem

#170 split state schools into "State school: academy or free school" and "State school: council-run". As a filter the split earns little:

  • It's two near-halves of one pool (11,186 and 9,316 schools), so picking one rarely rules anything out for a parent.
  • It doesn't follow the difference parents feel most, admissions. Voluntary aided and foundation schools set their own admissions, as academies do; community and voluntary controlled schools have theirs set by the council. So "council-run" mixed both kinds.
  • Faith, which voluntary aided mostly meant, now has its own filter.

Change

  • One group, state "State school (free)": the union of the two (GIAS codes 28, 34, 35, 40, 41, 6, 1, 2, 3, 5, 15). That leaves five groups: State · Independent · Special (SEND) · Sixth form or college · Alternative provision.
  • The old keys academy and council resolve to state via type_group_key(), so a link made with them keeps working instead of falling through to the raw-label path and returning nothing. Production hasn't been promoted with #170 yet, so only staging links can carry them today.
  • The precise GIAS type still shows on the school page.
  • Spec revised with the reasoning; the frontend is unchanged apart from a comment, since its options come from /api/filters.

Testing

  • Backend: group order, name lookups, type_group_key (keys, old keys, any case, raw labels → none), school_type=state|academy|council all return every state school, and /api/filters lists state first. CI suite 318/318.
  • Frontend: 569/569, typecheck clean.
  • E2E: no change. The #170 journey selects "Special school (SEND)", and the switching journey picks the first group by its text.

🤖 Generated with Claude Code

## Problem #170 split state schools into **"State school: academy or free school"** and **"State school: council-run"**. As a filter the split earns little: - It's two near-halves of one pool (11,186 and 9,316 schools), so picking one rarely rules anything out for a parent. - It doesn't follow the difference parents feel most, admissions. Voluntary aided and foundation schools set their own admissions, as academies do; community and voluntary controlled schools have theirs set by the council. So "council-run" mixed both kinds. - Faith, which voluntary aided mostly meant, now has its own filter. ## Change - One group, **`state` "State school (free)"**: the union of the two (GIAS codes 28, 34, 35, 40, 41, 6, 1, 2, 3, 5, 15). That leaves five groups: State · Independent · Special (SEND) · Sixth form or college · Alternative provision. - **The old keys `academy` and `council` resolve to `state`** via `type_group_key()`, so a link made with them keeps working instead of falling through to the raw-label path and returning nothing. Production hasn't been promoted with #170 yet, so only staging links can carry them today. - The precise GIAS type still shows on the school page. - Spec revised with the reasoning; the frontend is unchanged apart from a comment, since its options come from `/api/filters`. ## Testing - Backend: group order, name lookups, `type_group_key` (keys, old keys, any case, raw labels → none), `school_type=state|academy|council` all return every state school, and `/api/filters` lists `state` first. CI suite 318/318. - Frontend: 569/569, typecheck clean. - E2E: no change. The #170 journey selects "Special school (SEND)", and the switching journey picks the first group by its text. 🤖 Generated with [Claude Code](https://claude.com/claude-code)
tudor added 1 commit 2026-10-02 14:51:36 +00:00
feat(search): one state school group, not academy and council-run
PR Checks / Frontend Typecheck + Tests (pull_request) Successful in 1m13s
PR Checks / Backend Smoke (pull_request) Successful in 9s
PR Checks / Build Backend (no push) (pull_request) Successful in 19s
PR Checks / Build Frontend (no push) (pull_request) Successful in 1m21s
PR Checks / Build Pipeline (no push) (pull_request) Successful in 11s
PR Checks / AI Code Review (Claude) (pull_request) Successful in 20s
e78ec14e2e
The School type filter split state schools into "academy or free
school" and "council-run". The two were near-halves of one pool (11,186
and 9,316 schools), so choosing one rarely narrowed anything, and the
split did not follow the difference a parent feels most, admissions:
voluntary aided and foundation schools set their own, as academies do.
Faith, which voluntary aided mostly meant, has its own filter.

They are now one group, "State school (free)", leaving five. The old
keys academy and council resolve to state, so a link made with them
keeps working instead of falling through to the raw-label path and
returning nothing.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>

🤖 AI Code Review (Claude Code)

This PR merges the 'academy' and 'council' school type groups into a single 'state' group. Old academy and council keys are kept as aliases, so existing links still work. The backend change is small and consistent: the removed TYPE_GROUP_KEYS import has no other use in app.py, and the tests and spec are updated to match. The change looks healthy.

🟡 Minor

  • nextjs-app/components/FilterBar.tsx: An old link such as ?school_type=academy or council now filters correctly on the backend. But /api/filters only offers state, so the select has no matching option and may show blank or unselected while the filter is still applied. Consider normalising the legacy keys to state on the frontend, or redirecting them.
## 🤖 AI Code Review (Claude Code) This PR merges the 'academy' and 'council' school type groups into a single 'state' group. Old `academy` and `council` keys are kept as aliases, so existing links still work. The backend change is small and consistent: the removed `TYPE_GROUP_KEYS` import has no other use in `app.py`, and the tests and spec are updated to match. The change looks healthy. ### 🟡 Minor - **nextjs-app/components/FilterBar.tsx**: An old link such as `?school_type=academy` or `council` now filters correctly on the backend. But `/api/filters` only offers `state`, so the select has no matching option and may show blank or unselected while the filter is still applied. Consider normalising the legacy keys to `state` on the frontend, or redirecting them.
tudor merged commit 19c574edb0 into main 2026-10-02 15:33:14 +00:00
Sign in to join this conversation.
No Reviewers
No labels
2 Participants
Notifications
Due Date
No due date set.
Dependencies

No dependencies set.

Reference: tudor/school_compare#171