fix/split-uuid
safe5492f0a · fullPR #285reviewed 2026-07-09 01:43 UTC0H · 0M · 1L · 3I- Purpose
- One-shot data remediation: split sites incorrectly merged (same RPU assigned to multiple site records), creating separate site records per contract.
- Goal
- Fix the postgres.js driver-level bug caught during staging rehearsal so the prod remediation run succeeds
- Sub-goals
- SG-1: Add ::uuid casts to all sql`` parameter bindings that land in uuid-typed columns
- SG-2: Preserve all existing split logic (site INSERT, location copy, assignee copy, contract repoint)
- What
- Added ::uuid casts to 8 parameter bindings in splitSite(): FOR UPDATE SELECT, site INSERT (RETURNING-derived newSiteId), site_locations INSERT (×4), site_assignees INSERT, UPDATE site_utility_contracts. Added explanatory comment on driver-level cause.
- Why
- postgres.js binds JS strings as text; Postgres rejects text in uuid assignment position. First staging run failed 8/8 — clean rollbacks (correct failure mode), requiring this fix before prod.
- Areas
- scripts/split-merged-sites.ts+14−10
- Blast
- 1 file, +14/−10 lines. One-shot script only — no production code, no schema changes, no API surface.
Findings · 4
conventions1
Comment placement is one statement early — appears before step 2 but first cast is in step 1
scripts/split-merged-sites.ts:223
The NOTE explaining ::uuid cast rationale is placed before site_locations INSERT (step 2) but the first cast appears in the site INSERT immediately above. Minor discoverability issue.
improvement3
Explanatory comment only covers step 2; steps 1/3/4 have unadorned ::uuid casts
scripts/split-merged-sites.ts:223
Moving the comment before step 1 or to the top of the transaction block would make the pattern self-documenting throughout.
Uncast ${ORG_FILTER}/${SITE_FILTER} are intentional (text columns) — worth a note for future auditors
scripts/split-merged-sites.ts:170
A maintainer auditing for ::uuid casts and adding one here would break the filter. A brief inline note prevents an incorrect future 'fix'.
Broader audit: other scripts using sql`` with uuid-typed bindings may share this issue
The postgres.js text-vs-uuid problem applies to any script using Drizzle sql`` with uuid-typed columns. A grep for sql`` + ${...} in scripts/ would surface candidates.