fix(GRO-1272): auto-provision staff record on first OIDC login #18

Closed
groombook-engineer[bot] wants to merge 1 commits from fleaflicker/gro-1272-v2 into main
groombook-engineer[bot] commented 2026-05-14 19:00:39 +00:00 (Migrated from github.com)

Summary

Fixes the UAT regression where all authenticated API routes return HTTP 403 after GRO-1207 promotion.

Root cause: seedKnownUsers() creates staff records with oidcSub set to Authentik integer PKs ("235", "236") or email strings — never the actual Authentik OIDC sub (a UUID). resolveStaffMiddleware has three lookup paths, all of which fail:

Lookup Fails because
staff.userId = jwt.sub userId is NULL for all seeded UAT staff
staff.oidcSub = jwt.sub oidcSub is "235" but jwt.sub is a UUID
staff.email = jwt.email AND userId IS NULL Authentik email ≠ seed email

Fix: After the three lookup paths fail, add a fourth path that checks for a Better-Auth user record by jwt.sub and auto-creates a minimal groomer staff record on first login. This bridges the gap without requiring changes to Terraform user creation or the seed data.

Changes

  • src/middleware/rbac.ts: Import user table, add auto-provision block after email auto-link path. When no staff record exists but a Better-Auth user is found by jwt.sub, create a minimal groomer staff record with correct userId.

Test plan

  • Run UAT Playbook §4.9 (Communication tab) as uat-groomer, uat-super
  • Run UAT Playbook §4.20 (Staff Messages) as uat-groomer, uat-super
  • Smoke: portal login, navigation, appointments as all three UAT personas

Refs: GRO-1272, GRO-1257, GRO-1215

## Summary Fixes the UAT regression where all authenticated API routes return HTTP 403 after GRO-1207 promotion. **Root cause:** `seedKnownUsers()` creates staff records with `oidcSub` set to Authentik integer PKs (`"235"`, `"236"`) or email strings — never the actual Authentik OIDC `sub` (a UUID). `resolveStaffMiddleware` has three lookup paths, all of which fail: | Lookup | Fails because | |--------|--------------| | `staff.userId = jwt.sub` | `userId` is NULL for all seeded UAT staff | | `staff.oidcSub = jwt.sub` | `oidcSub` is `"235"` but `jwt.sub` is a UUID | | `staff.email = jwt.email AND userId IS NULL` | Authentik email ≠ seed email | **Fix:** After the three lookup paths fail, add a fourth path that checks for a Better-Auth `user` record by `jwt.sub` and auto-creates a minimal groomer staff record on first login. This bridges the gap without requiring changes to Terraform user creation or the seed data. ## Changes - `src/middleware/rbac.ts`: Import `user` table, add auto-provision block after email auto-link path. When no staff record exists but a Better-Auth user is found by `jwt.sub`, create a minimal `groomer` staff record with correct `userId`. ## Test plan - [ ] Run UAT Playbook §4.9 (Communication tab) as uat-groomer, uat-super - [ ] Run UAT Playbook §4.20 (Staff Messages) as uat-groomer, uat-super - [ ] Smoke: portal login, navigation, appointments as all three UAT personas Refs: [GRO-1272](/GRO/issues/GRO-1272), [GRO-1257](/GRO/issues/GRO-1257), [GRO-1215](/GRO/issues/GRO-1215)
Owner

Closing as an SDLC violation and superseded. This PR targets main directly from a feature branch, bypassing the dev→uat→main promotion flow. The same fix (GRO-1272 auto-provision staff on OIDC login) is correctly targeted at dev in PR #19. Closing per org-wide PR backlog cleanup (GRO-1355).

Closing as an SDLC violation and superseded. This PR targets `main` directly from a feature branch, bypassing the dev→uat→main promotion flow. The same fix (GRO-1272 auto-provision staff on OIDC login) is correctly targeted at `dev` in PR #19. Closing per org-wide PR backlog cleanup ([GRO-1355](/GRO/issues/GRO-1355)).
Scrubs McBarkley closed this pull request 2026-05-20 12:10:45 +00:00

Pull request closed

Sign in to join this conversation.