screentinker/server/db
Claude 14367af5f1 Keep a workspace on schedules that outlive their device group
Deleting a device group converts its group schedules into per-device ones so the screens keep their
programming. That INSERT omitted workspace_id, which is nullable with no default, so every converted
row landed with workspace_id = NULL.

A null workspace does not merely look untidy — it makes the row unreachable in three directions at
once, and they compound into the worst possible combination:

  invisible   the schedule list and the all-screens calendar both filter on workspace_id
  undeletable PUT and DELETE refuse a row with no workspace (403)
  still live  services/scheduler.js has no workspace filter, so it keeps firing every 60 seconds

"I deleted the group but the screens still switch content at 9am, and there is nothing in the
calendar to remove." The only way out was direct database access.

The conversion now carries the workspace, preferring the schedule's own and falling back to the
group's so a legacy group schedule that itself predates workspace_id still converts into a reachable
row. A boot migration repairs rows already orphaned in the field by recovering the workspace from
the device each one targets; anything still unresolvable is left alone rather than guessed at.

4 tests: the converted row keeps its workspace, is visible to the query the list and calendar use,
preserves the actual programming rather than just the ownership, and the repair recovers a row
orphaned before this fix existed.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Uaeo9MvzKoyXuN6ZsbhtkL
2026-07-30 20:53:21 -05:00
..
database.js Keep a workspace on schedules that outlive their device group 2026-07-30 20:53:21 -05:00
schema.sql fix(android): server-provisioned settings PIN replaces hardcoded 0000 2026-07-09 19:05:24 -04:00
wal-checkpointer-worker.js fix(db): WAL checkpointer worker-death handling (respawn + inline-autocheckpoint fallback) 2026-07-06 23:50:18 -05:00
wal-checkpointer.js fix(db): WAL checkpointer worker-death handling (respawn + inline-autocheckpoint fallback) 2026-07-06 23:50:18 -05:00