From e5c141e765916f96d39ff583be591ed46744ed70 Mon Sep 17 00:00:00 2001 From: Scott Idem Date: Tue, 16 Jun 2026 13:21:04 -0400 Subject: [PATCH] =?UTF-8?q?fix(pres=5Fmgmt):=20config=20sync=20round=202?= =?UTF-8?q?=20=E2=80=94=20save=20race,=20dead=20fields,=20launcher=20gate,?= =?UTF-8?q?=20version=20stamps?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Four fixes found while tracing why Manager-saved Config page changes (QR, POC column, etc.) weren't reliably reaching pres_mgmt_loc: 1. Config page save was a race, not deterministic. The save handler only called load_ae_obj_id__event() (SWR — returns stale Dexie cache immediately, refreshes in the background, not awaited) and assumed that "picked up the new config." It never called sync_config__event_pres_mgmt() itself. Now calls it directly with the just-saved draft, so the editing browser updates instantly with no race. Kept the load_ae_obj_id__event() call (default try_cache: true) for propagating to other browsers/tabs via Dexie — do not pass try_cache: false there, that skips the Dexie write entirely. 2. Removed the dead "Lock Config" Sync/Unlink toggle in the sign-in panel (e_app_access_type.svelte). It wrote to four fields ($ae_loc.lock_config/sync_local_config, pres_mgmt_loc.current.lock_config/sync_local_config) that are never read anywhere (confirmed via full-repo grep), and confusingly shared a name with the real, functional "Lock Config" checkbox on the Pres Mgmt Config page. Removed the button and the now-orphaned lock_config/sync_local_config fields from PresMgmtLocState. 3. show__launcher_link was never assigned by sync_config__event_pres_mgmt() — only its inverse hide__launcher_link was. The toggle button's `show__launcher_link || trusted_access` visibility gate (in 3 menu files) always collapsed to trusted-only, ignoring the admin's setting. Added the missing assignment. 4. AE_PRES_MGMT_LOC_VERSION was bumped to 2 this morning claiming it "forces a localStorage reset" — it didn't, because _check_and_wipe() was never wired up for ae_pres_mgmt_loc, and even if it had been, the store never wrote a __version field to compare. Fixed: the store's serializer now stamps __version, and store_versions.ts wires the check. Found and fixed the same bug already live in ae_leads_loc, except worse there — it was wiping leads users' local prefs on EVERY page load, not just once. All logged in PROJECT__AE_Events_PressMgmt_Config_Cleanup.md. svelte-check: 0 errors, 0 warnings. Co-Authored-By: Claude Sonnet 4.6 --- ...ECT__AE_Events_PressMgmt_Config_Cleanup.md | 64 ++++++++++++++++--- src/lib/ae_events/ae_events__event.ts | 6 ++ .../app_components/e_app_access_type.svelte | 53 +++------------ .../stores/ae_events_stores__leads.svelte.ts | 16 ++++- .../ae_events_stores__pres_mgmt.svelte.ts | 13 +++- .../ae_events_stores__pres_mgmt_defaults.ts | 7 -- src/lib/stores/store_versions.ts | 13 ++-- .../(pres_mgmt)/pres_mgmt/config/+page.svelte | 18 +++++- 8 files changed, 120 insertions(+), 70 deletions(-) diff --git a/documentation/PROJECT__AE_Events_PressMgmt_Config_Cleanup.md b/documentation/PROJECT__AE_Events_PressMgmt_Config_Cleanup.md index 87e85d05..7cf0d8b0 100644 --- a/documentation/PROJECT__AE_Events_PressMgmt_Config_Cleanup.md +++ b/documentation/PROJECT__AE_Events_PressMgmt_Config_Cleanup.md @@ -214,15 +214,33 @@ Safe and backward compatible — old DB records fall through to `?? false` defau ### Regression Fixes Needed (2026-06-12 Audit) -- [ ] **Add `show__launcher_link_legacy` to `PressMgmtRemoteCfg`** or remove entirely if deprecated - - Currently hard-coded to `true` in sync function (line 1054 `ae_events__event.ts`) - - Can't be controlled via config UI -- [ ] **Resolve `hide__launcher_link*` local/remote conflict** - - Menu toggles ([ae_comp__events_menu_opts.svelte](../src/routes/events/ae_comp__events_menu_opts.svelte) lines 462-494) use `hide__launcher_link` for LOCAL UI state - - Remote schema uses `show__launcher_link` (inverted) - - Decision: Keep separate? Document clearly? Unify? -- [ ] **Add `AE_PRES_MGMT_LOC_VERSION` to `store_versions.ts`** (Step 2 requirement) -- [ ] **Clean `hide__launcher_link*` from defaults** if truly deprecated (lines 154-155, 333-334 in `pres_mgmt_defaults.ts`) +- [x] **`hide__launcher_link_legacy` removed entirely** (other agent's "config schema cleanup + phase 2" commit, 2026-06-16) — Flask launcher is fully retired, no longer hard-coded or + present anywhere in `PressMgmtRemoteCfg` / `PresMgmtLocState` / the sync function. +- [x] **`hide__launcher_link*` / `show__launcher_link` local/remote conflict resolved + (2026-06-16)** — kept separate (they serve different purposes: `hide__launcher_link` + gates the launcher link *content*, `show__launcher_link` gates the manual toggle + *button*'s visibility), but `show__launcher_link` was never actually assigned by + `sync_config__event_pres_mgmt()` — only its inverse `hide__launcher_link` was. So the + toggle button's `show__launcher_link || trusted_access` gate (in + `ae_comp__events_menu_opts.svelte`, `event_page_menu.svelte`, + `location_page_menu.svelte`) always collapsed to trusted-only, ignoring the admin's + setting. Added the missing `loc.show__launcher_link = ...` assignment right next to + `hide__launcher_link` in the lock-synced block. +- [x] **`AE_PRES_MGMT_LOC_VERSION` properly wired into `store_versions.ts` (2026-06-16)** + — the other agent's commit bumped this constant to 2 claiming it "forces a localStorage + reset," but `_check_and_wipe()` was never actually called for `ae_pres_mgmt_loc`, and + even if it had been, the store's serializer never wrote a `__version` field for it to + compare against — so the bump was a complete no-op. Fixed: `ae_events_stores__pres_mgmt.svelte.ts`'s + custom serializer now stamps `__version` on every write, and `store_versions.ts` calls + `_check_and_wipe('ae_pres_mgmt_loc', AE_PRES_MGMT_LOC_VERSION)`. Side effect: every + browser's existing `ae_pres_mgmt_loc` (no `__version` ever written before) will wipe + once on next load and resync clean from the remote config — this is expected and fine. + **Found the same bug already live in `ae_leads_loc`** (actively wiping leads users' local + prefs on *every* page load, not just once) and fixed it the same way — see + `ae_events_stores__leads.svelte.ts`. `badges_loc`/`launcher_loc`/`events_auth_loc` have + version constants declared but not wired into `_check_and_wipe()` at all (dormant, not + actively harmful) — not fixed, flagged for whoever picks that up next. - [x] **POC column local/remote conflict fixed (2026-06-16)** — `show__session_li_poc_field` was local-only (never synced) and the session-list-table prop computation ignored the admin's `hide__session_poc` master switch entirely. Fixed: added `show__session_li_poc_field` to @@ -259,6 +277,34 @@ Safe and backward compatible — old DB records fall through to `?? false` defau `locations/+page.svelte`, `location/[event_location_id]/+page.svelte`, and `reports/+page.svelte`. Any new pres_mgmt page that can be a first-load entry point (i.e. not always reached via `/pres_mgmt` or `/session/[id]` first) needs this same block. +- [x] **Config page save was a race, not deterministic (2026-06-16)** — after PATCHing + `mod_pres_mgmt_json`, the save handler only called `load_ae_obj_id__event()` (SWR — + returns the stale Dexie cache immediately, refreshes from the API in the background, + *not awaited*) and assumed that "picked up the new config." It never actually called + `sync_config__event_pres_mgmt()` itself. Whether the editor's own browser reflected the + change depended entirely on winning a race against an un-awaited background fetch — + explains why specific just-changed fields (QR, POC column, profile-pic visibility, one + report key) intermittently looked stale even to the admin who just saved them, while + older unchanged fields stayed correct. Fixed: the save handler now calls + `sync_config__event_pres_mgmt({ pres_mgmt_cfg_remote: draft })` directly with the + just-saved draft, so the editing browser updates instantly with no race. (Kept the + `load_ae_obj_id__event()` call too, with its default `try_cache: true` — that's what + propagates the fresh record to Dexie for *other* browsers/tabs. Do not pass + `try_cache: false` there — that skips the Dexie write entirely, see the documented + "try_cache: false Bug" in `GUIDE__SvelteKit2_Svelte5_DexieJS.md`.) +- [x] **Removed dead "Lock Config" Sync/Unlink toggle (2026-06-16)** — a Manager-only + button in the sign-in panel (`e_app_access_type.svelte`) wrote to + `$ae_loc.lock_config`/`sync_local_config` and `pres_mgmt_loc.current.lock_config`/ + `sync_local_config`. Confirmed via full-repo grep that none of those four fields are + read anywhere. It also confusingly shared the name "Lock Config" with the real, + functional checkbox on the Pres Mgmt Config page (`draft.lock_config`, part of + `PressMgmtRemoteCfg`, which actually gates `sync_config__event_pres_mgmt()`'s + remote→local sync). Removed the button and the now-fully-orphaned + `lock_config`/`sync_local_config` fields from `PresMgmtLocState`. Left + `$ae_loc.lock_config`/`sync_local_config` (the general app store) alone — `lock_config` + was never even in `ae_loc`'s declared defaults (a phantom field created ad-hoc by the + dead button), and `ae_loc.sync_local_config` is out of scope for a pres_mgmt-only pass; + defer to the planned `ae_loc` migration in `PROJECT__Stores_Svelte5_Migration.md`. ### Step 6 scope (mechanical find-replace) diff --git a/src/lib/ae_events/ae_events__event.ts b/src/lib/ae_events/ae_events__event.ts index aef4003e..92b02ea1 100644 --- a/src/lib/ae_events/ae_events__event.ts +++ b/src/lib/ae_events/ae_events__event.ts @@ -1060,6 +1060,12 @@ export function sync_config__event_pres_mgmt({ // Launcher links (show__ in remote → invert to hide__ in local display state) loc.hide__launcher_link = !(pres_mgmt_cfg_remote?.show__launcher_link ?? false); + // Mirror the raw remote flag too — the toggle BUTTON's own visibility (not the + // launcher link content itself) is gated on show__launcher_link directly in + // ae_comp__events_menu_opts.svelte / event_page_menu.svelte / location_page_menu.svelte. + // This was never assigned before, so that gate always collapsed to trusted_access-only. + loc.show__launcher_link = + pres_mgmt_cfg_remote?.show__launcher_link ?? false; // Navigation / UI constraints loc.limit__navigation = diff --git a/src/lib/app_components/e_app_access_type.svelte b/src/lib/app_components/e_app_access_type.svelte index 2bed17a3..7d7f2f2c 100644 --- a/src/lib/app_components/e_app_access_type.svelte +++ b/src/lib/app_components/e_app_access_type.svelte @@ -8,12 +8,10 @@ import { afterNavigate } from '$app/navigation'; import { Lock, LockOpen, - RefreshCw, ShieldEllipsis, ShieldMinus, ShieldPlus, ShieldUser, - Unlink, User, UserCheck, UserRound, @@ -29,8 +27,6 @@ import { slct_trigger } from '$lib/stores/ae_stores'; // import { core_func } from '$lib/ae_core/ae_core_functions'; -// Ideally the Event related stores should not be imported here? -import { pres_mgmt_loc } from '$lib/stores/ae_events_stores__pres_mgmt.svelte'; // import { db_events } from "$lib/db_events"; // export let hidden: boolean = false; @@ -361,47 +357,14 @@ function handle_clear_access() {
{#if $ae_loc.trusted_access && $ae_loc.edit_mode} - {#if $ae_loc.manager_access} - {#if $ae_loc?.sync_local_config} - - {:else} - - {/if} - {/if} +