admin.ts has no untyped reads left. Typed sites go from 43 to 49.
New ItemRecord in itemSelect.ts for the bare items row that RETURNING * gives back. Deliberately not AdminItemRow: that describes a select which joins the category and adds images and tags as subqueries, so typing a RETURNING * as it would promise three fields the result does not contain. Three shapes for one table, because three different queries return three different things.
The typing found a real defect on its first run, which is the case for doing this at all.
ItemStatus in types.ts was 'available' | 'reserved' | 'sold'. The database has four values and defaults to 'pending' — items have arrived pending since #90. itemFilters.ts declared its own copy that had all four and was correct. Two declarations of one union with nothing connecting them: one went stale and nothing said so.
It was invisible while query rows were any. Typing them turned if (status === 'pending') in admin.ts into TS2367, "this comparison appears to be unintentional because the types 'ItemStatus' and '"pending"' have no overlap" — a compiler telling us the unpublish route's guard could never be true, against a type that was simply wrong.
Confirmed against the database rather than by picking the more plausible of the two declarations: SELECT DISTINCT status FROM items returns pending, available, reserved and sold.
Fixed by removing the duplication rather than by patching both copies. types.ts now holds the only declaration and itemFilters.ts imports it, re-exporting so its existing importers are unaffected. Patching both would have left the next drift free to happen the same way.
Verified: tsc clean, unit 254/254, integration 238/238, and backend lint unchanged — the four warnings it reports are identical to those on main with these changes stashed, so none of them are new.
admin.ts has no untyped reads left. Typed sites go from 43 to 49.
New ItemRecord in itemSelect.ts for the bare `items` row that `RETURNING *` gives back. Deliberately not AdminItemRow: that describes a select which joins the category and adds images and tags as subqueries, so typing a RETURNING * as it would promise three fields the result does not contain. Three shapes for one table, because three different queries return three different things.
The typing found a real defect on its first run, which is the case for doing this at all.
`ItemStatus` in types.ts was `'available' | 'reserved' | 'sold'`. The database has four values and defaults to 'pending' — items have arrived pending since #90. itemFilters.ts declared its own copy that had all four and was correct. Two declarations of one union with nothing connecting them: one went stale and nothing said so.
It was invisible while query rows were `any`. Typing them turned `if (status === 'pending')` in admin.ts into TS2367, "this comparison appears to be unintentional because the types 'ItemStatus' and '\"pending\"' have no overlap" — a compiler telling us the unpublish route's guard could never be true, against a type that was simply wrong.
Confirmed against the database rather than by picking the more plausible of the two declarations: `SELECT DISTINCT status FROM items` returns pending, available, reserved and sold.
Fixed by removing the duplication rather than by patching both copies. types.ts now holds the only declaration and itemFilters.ts imports it, re-exporting so its existing importers are unaffected. Patching both would have left the next drift free to happen the same way.
Verified: tsc clean, unit 254/254, integration 238/238, and backend lint unchanged — the four warnings it reports are identical to those on main with these changes stashed, so none of them are new.
Refs #159
bermudalamb
self-assigned this 2026-08-24 14:44:44 -05:00
bermudalamb
added this to the Code Quality and Hardening 2 project 2026-08-24 14:44:44 -05:00
admin.ts has no untyped reads left. Typed sites go from 43 to 49.
New ItemRecord in itemSelect.ts for the bare `items` row that `RETURNING *` gives back. Deliberately not AdminItemRow: that describes a select which joins the category and adds images and tags as subqueries, so typing a RETURNING * as it would promise three fields the result does not contain. Three shapes for one table, because three different queries return three different things.
The typing found a real defect on its first run, which is the case for doing this at all.
`ItemStatus` in types.ts was `'available' | 'reserved' | 'sold'`. The database has four values and defaults to 'pending' — items have arrived pending since #90. itemFilters.ts declared its own copy that had all four and was correct. Two declarations of one union with nothing connecting them: one went stale and nothing said so.
It was invisible while query rows were `any`. Typing them turned `if (status === 'pending')` in admin.ts into TS2367, "this comparison appears to be unintentional because the types 'ItemStatus' and '\"pending\"' have no overlap" — a compiler telling us the unpublish route's guard could never be true, against a type that was simply wrong.
Confirmed against the database rather than by picking the more plausible of the two declarations: `SELECT DISTINCT status FROM items` returns pending, available, reserved and sold.
Fixed by removing the duplication rather than by patching both copies. types.ts now holds the only declaration and itemFilters.ts imports it, re-exporting so its existing importers are unaffected. Patching both would have left the next drift free to happen the same way.
Verified: tsc clean, unit 254/254, integration 238/238, and backend lint unchanged — the four warnings it reports are identical to those on main with these changes stashed, so none of them are new.
Refs #159
Blocking a user prevents them from interacting with repositories, such as opening or commenting on pull requests or issues. Learn more about blocking a user.
admin.ts has no untyped reads left. Typed sites go from 43 to 49.
New ItemRecord in itemSelect.ts for the bare
itemsrow thatRETURNING *gives back. Deliberately not AdminItemRow: that describes a select which joins the category and adds images and tags as subqueries, so typing a RETURNING * as it would promise three fields the result does not contain. Three shapes for one table, because three different queries return three different things.The typing found a real defect on its first run, which is the case for doing this at all.
ItemStatusin types.ts was'available' | 'reserved' | 'sold'. The database has four values and defaults to 'pending' — items have arrived pending since #90. itemFilters.ts declared its own copy that had all four and was correct. Two declarations of one union with nothing connecting them: one went stale and nothing said so.It was invisible while query rows were
any. Typing them turnedif (status === 'pending')in admin.ts into TS2367, "this comparison appears to be unintentional because the types 'ItemStatus' and '"pending"' have no overlap" — a compiler telling us the unpublish route's guard could never be true, against a type that was simply wrong.Confirmed against the database rather than by picking the more plausible of the two declarations:
SELECT DISTINCT status FROM itemsreturns pending, available, reserved and sold.Fixed by removing the duplication rather than by patching both copies. types.ts now holds the only declaration and itemFilters.ts imports it, re-exporting so its existing importers are unaffected. Patching both would have left the next drift free to happen the same way.
Verified: tsc clean, unit 254/254, integration 238/238, and backend lint unchanged — the four warnings it reports are identical to those on main with these changes stashed, so none of them are new.
Refs #159