Commit Graph

2112 Commits

Author SHA1 Message Date
Scott Idem
1e178c14e7 leads: lead detail UX overhaul — notes editor, priority star, profile card cleanup
- Replace admin field editor with direct TipTap + Save Notes button for exhibitor notes;
  show Add Notes button when notes are empty (no dead placeholder)
- Add one-click priority star toggle in header (always visible, no edit mode required)
- Remove Exhibit Context card (exhibitors don't need to see their own booth name)
- Move Captured By into profile card with human-readable labels
  (shared_passcode → "Booth (Shared)", access type codes → Staff/Admin)
- Add location row (city/state + country) to profile card
- Gate Remove button to edit mode only to prevent accidental taps
- Fix button position stability: Edit/View always rightmost (same screen position),
  Remove grows in from left — prevents double-tap accidents
- Add unsaved-changes guard (beforeNavigate) covering both notes and custom question form
- Custom questions form: hide Save when no questions configured, show
  "Configure in Manage Tab" link instead

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-04-06 20:42:55 -04:00
Scott Idem
50e83502ff leads: UX improvements — manage tab, sign-in flow, notes editor, filter
- leads_api_access toggle in Admin Tools (manager only)
- Account Status section for end users (payment/licenses/API badges + CSV export button)
- Sign-out fix: use Object.fromEntries instead of delete on PersistedState proxy
- Shared passcode sign-in redirects directly to Manage tab (their role is config, not capture)
- Manage tab section reorder: Account Status → Lead Retrieval Config → Booth Profile → Access & Security → App Settings
- Filter dropdown: replace abstract "My Leads" with direct identity options (All / Booth (Shared) / per-licensee); auto-resolves and migrates stale 'my' values
- Lead detail: replace Element_ae_obj_field_editor notes with direct TipTap editor + Save Notes button; Add Notes button on empty state

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-04-06 19:25:38 -04:00
Scott Idem
10e9206ca4 fix(leads): persist licensed auth across reloads; manage tab UX fixes
**Session persistence bug** — leads_loc_defaults was missing __version: 1.
store_versions.ts wipes ae_leads_loc when parsed.__version !== 1 (always true
when the field is absent), so every page reload cleared auth_exhibit_kv and
forced re-login. Adding __version: 1 to both the interface and defaults fixes
this for all auth types.

**Manage tab fixes:**
- Description: collapsed by default with ChevronDown/Up toggle — same pattern
  as session_view.svelte. Avoids long promo copy dominating the manage screen.
- Staff Passcode: removed duplicate green plain-text display for admins; the
  Element_ae_obj_field_editor already shows the value (was showing twice).
- Booth Identifier: replaced static read-only display with Element_ae_obj_field_editor
  so the booth code (exhibit.code) is editable inline.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-04-06 17:19:35 -04:00
Scott Idem
f95243a9c7 fix(leads): disable sign-in submit until exhibit loads; add licensed-user auth tests
Prevents silent no-op when user clicks submit before lq__exhibit_obj is ready
(exhibit not yet written to Dexie). Button now shows 'Loading...' spinner while
the exhibit record is resolving, eliminating the two-tap workaround needed on
first page load.

Also adds 7 Playwright tests for licensed user sign-in (leads_licensed_signin.test.ts)
covering success path, wrong credentials, email/identity tagging on captured leads,
identity isolation between staff members, and returning-session bypass.

Helpers: attach_leads_routes/setup_leads_test_page now accept exhibit_overrides
(e.g. license_li_json) to inject licensed users into mocked API responses.
seed_leads_loc import added to leads_auth.test.ts multi-exhibit test.

Total leads test coverage: 29 tests.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-04-06 17:04:57 -04:00
Scott Idem
d340bbbe94 test: seed ae_leads_loc; update badge tests and helpers; docs: note Leads migration 2026-04-03 17:47:10 -04:00
Scott Idem
a952c5ddbe docs(leads): document Leads store migration and payment UI fix; note tests update 2026-04-03 17:33:23 -04:00
Scott Idem
7f79c1857a leads: event-level payment config + Stripe key migration
- New /events/[event_id]/leads/config page: administrator UI for
  mod_exhibits_json. Controls leads_require_payment toggle and Stripe
  keys (publishable key + buy button IDs per license tier).

- leads_require_payment (mod_exhibits_json) now gates all billing UI:
  header CreditCard button in exhibit +page.svelte and Licenses & Billing
  accordion in ae_tab__manage.svelte. Default false (client covers costs).

- Stripe keys migrated from site_cfg_json to mod_exhibits_json (per-event).
  ae_comp__exhibit_payment accepts them as optional props; falls back to
  site_cfg_json for events not yet migrated.

- Fixed "My Leads" bug for shared-passcode users: search_params now maps
  licensee_email 'my' → 'shared_passcode' literal (not kv.key passcode
  string) so filters correctly match stored external_person_id values.

- Event settings: Exhibits section replaced with config link + raw JSON
  fallback, matching pres_mgmt/badges pattern.

- Docs updated: README.md, MODULE__AE_Events_Exhibitor_Leads.md.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-04-03 12:36:36 -04:00
Scott Idem
48c5515131 Updated to do list 2026-04-03 01:39:55 -04:00
Scott Idem
c8eb904eb0 Minor style fix and char change 2026-04-02 21:34:49 -04:00
Scott Idem
d80202e35b Style clean up. Making things nicer again. 2026-04-02 21:31:58 -04:00
Scott Idem
055bbd9ffd events(settings): add modules config page and settings link 2026-04-02 20:01:15 -04:00
Scott Idem
0e0fc071c7 events: center module hub cards (flex-wrap + fixed card width) 2026-04-02 19:58:25 -04:00
Scott Idem
5971ca6143 fix: use file_count_all + is_null for sessions-without-files query
Two corrections to the qry_files filter:
1. Switch from file_count to file_count_all — covers files on presentations
   and presenters under the session, not just direct session files.
2. Switch "without files" from eq:0 to is_null — the view uses a LEFT JOIN
   so sessions with no files get NULL, never 0.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-04-02 19:08:43 -04:00
Scott Idem
cf7203daaf fix: implement qry_files filter in search__event_session (sessions with/without files)
qry_files was accepted as a parameter but never applied to the search query,
causing the "Sessions With/Without Files" report toggle to always return all
sessions regardless of the setting.

When qry_files !== null, automatically switch to the 'alt' view
(v_event_session_w_file_count) which exposes file_count, then add:
  true  → file_count > 0  (sessions with files)
  false → file_count = 0  (sessions without files)

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-04-02 18:58:39 -04:00
Scott Idem
0ca2408111 Updated to do list again 2026-04-02 18:44:56 -04:00
Scott Idem
62ae376e67 chore(pkg): add runed (PersistedState) to fix svelte-check 2026-04-02 18:41:18 -04:00
Scott Idem
034e25d6c4 chore(pkg): remove orphaned shadcn-svelte and bits-ui 2026-04-02 18:38:32 -04:00
Scott Idem
08fdb2bddf chore(docs): prune fully-completed subsections from TODO__Agents.md 2026-04-02 18:26:44 -04:00
Scott Idem
84875d1daa Moving older files around. 2026-04-02 18:21:39 -04:00
Scott Idem
09757d249c chore(docs): archive completed TODO items to TODO__Agents__ARCHIVE_2026-03.md and tidy main TODO 2026-04-02 18:20:03 -04:00
Scott Idem
fae4bba037 Commenting out alert/notice for now. 2026-04-02 18:19:13 -04:00
Scott Idem
7b2694e9b7 fix(lead): remove invalid 'fill' prop from Star icon 2026-04-02 18:15:52 -04:00
Scott Idem
e27ff2c67f Limit who can create a new badge. This may need to change later. 2026-04-02 18:11:54 -04:00
Scott Idem
c198ca2454 chore(badges): remove legacy badge_id_only_search; sync remote badges config into badges_loc; docs update 2026-04-02 18:03:23 -04:00
Scott Idem
0ab8b936ce badges(runtime): honor mod_badges_json flags (badge_id_only search, QR toggle, add/upload/mass-print gating) 2026-04-02 17:23:35 -04:00
Scott Idem
4a5b4bf7cd badges(config): fix duplicate keys and initialize draft when mod_badges_json missing; update settings button style 2026-04-02 17:06:23 -04:00
Scott Idem
1935564645 Quick version bump again. 2026-04-02 16:30:34 -04:00
Scott Idem
fface58751 fix: add default_qry_str to db_events Event interface, remove incorrect global augment
The field exists on the DB object but was missing from the TypeScript interface,
causing a false error in recovery_meetings search. Added it to db_events.ts where
it belongs. Removed the incorrect global DOM Event augment from the temp augments
file (was patching the wrong interface).

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-04-02 16:04:49 -04:00
Scott Idem
4a1b0dac86 pres_mgmt config: remove legacy launcher option, add back button + dirty state to config UI
- Remove show__launcher_link_legacy from PressMgmtRemoteCfg, PresMgmtLocState, and
  pres_mgmt_loc_defaults — the Flask/legacy launcher is retired
- Sync function now hardcodes hide__launcher_link_legacy=true (always hidden)
- Config page: back button to pres_mgmt, save buttons disabled until changes made
- Fix {#each} key expressions in config page
- Migrate e_app_access_type and element_manage_event_file_li to pres_mgmt_loc store
- Add temporary svelte type augments file (src/types/)

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-04-02 15:53:55 -04:00
Scott Idem
fd9e5f6dc0 pres_mgmt: migrate to typed PersistedState store, canonical config schema
Replaces untyped $events_loc.pres_mgmt (svelte-persisted-store) with a
dedicated pres_mgmt_loc (runed PersistedState) backed by a fully typed
PresMgmtLocState interface and PressMgmtRemoteCfg for the server-side JSON.

Key changes:
- ae_events_stores__pres_mgmt_defaults.ts: canonical interfaces + defaults
  covering all hide__/show__ fields, labels, report prefs, query filters,
  and lock_config sync fields; qry_enabled uses 'not_enabled' (matches API)
- ae_events_stores__pres_mgmt.svelte.ts: new PersistedState store
- ae_events__event.ts: sync_config__event_pres_mgmt() rewired to write
  directly to pres_mgmt_loc.current; launcher link inversion preserved
- All 26+ pres_mgmt templates migrated from $events_loc.pres_mgmt.* to
  pres_mgmt_loc.current.*
- New config UI at (pres_mgmt)/pres_mgmt/config/ — manager + edit mode only
- Event settings page: removed embedded pres_mgmt form, links to config page
- event_page_menu: Config button visible only when manager_access + edit_mode

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-04-02 15:27:12 -04:00
Scott Idem
21f0fe69af Quick version bump 2026-04-02 15:03:01 -04:00
Scott Idem
01c895f7ba feat(pres_mgmt): make session start/end datetime editable in edit mode
start_datetime and end_datetime were visible as chips but had no edit control.
Added two datetime-local field editors shown in edit_mode below the display chip:

- Converts stored "YYYY-MM-DD HH:mm:ss" → "YYYY-MM-DDTHH:MM" for the input
  (safe because dayjs has no timezone plugin — times are stored as local time)
- Falls back to event start date + 08:00/09:00 when session datetime is null,
  so staff only need to adjust the time rather than retype the full date
- Editors are side-by-side in a flex-wrap row with min-width so they wrap on mobile

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-04-02 13:56:06 -04:00
Scott Idem
3a4c4a1e64 feat(pres_mgmt): make session code editable in edit mode
The code badge was display-only — replaced with a field editor so staff
can correct session codes without going to a separate admin view.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-04-02 13:46:39 -04:00
Scott Idem
75664ad2e1 feat(pres_mgmt): restore location and description editing in session view
Event location (FK lookup) and description were both visible in the session
view but had no edit controls — lost during V3 migration. Restored both:

- event_location_id: select dropdown populated from this event's location list
  (liveQuery on db_events.location filtered by event_id from the session object)
- description: textarea editor shown directly in edit_mode (no collapse needed
  when actively editing)

Also added event_location_id to editable_fields__event_session, which was
missing and would have caused backend rejections on PATCH.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-04-02 13:44:00 -04:00
Scott Idem
2a5adda6cb idaa/video_conferences: restrict invite button to trusted_access staff only
The Jitsi invite dialog can expose backend room URLs and paths.
Previously invite was gated on is_moderator (any Novi group moderator).

Now restricted to $ae_loc.trusted_access (IDAA staff in Aether) so
regular member moderators cannot send invites. All other toolbar
buttons are unchanged.
2026-04-02 13:27:05 -04:00
Scott Idem
be3634d750 No longer allow regular attendees to send an invite. The moderators may be next. 2026-04-02 13:11:23 -04:00
Scott Idem
fd5d5e371b idaa/video_conferences: issue JWT to all verified Novi users
Previously only moderators received a JWT; non-moderators joined
anonymously. Now all verified Novi users get a JWT with the
is_moderator flag set appropriately, allowing the Jitsi server to
enforce authentication and respect context.user.moderator for
all participants.

Also adds JWT payload decode logging (client-side, signature not
verified) so the moderator flag and user identity can be confirmed
in the browser console during testing.
2026-04-02 12:51:05 -04:00
Scott Idem
75d85bf904 Working through bugs... Related to data stores and not using the for type and for id... They were locked. 2026-04-01 19:39:26 -04:00
Scott Idem
5e0f35d3df Working on security defaults and layout of menus. 2026-04-01 19:18:38 -04:00
Scott Idem
0767e2ff82 More cosmetic and permissions review 2026-04-01 18:41:23 -04:00
Scott Idem
38c5345060 Making things look nicer. 2026-04-01 18:09:17 -04:00
Scott Idem
601bcf94b0 Added an extra backup just in case Edit Mode toggle. 2026-04-01 17:43:36 -04:00
Scott Idem
197d136c59 Fixing stuff that was lost with the upgrade to AE v3. 2026-04-01 17:11:21 -04:00
Scott Idem
7d8981bcb5 Version bump just because. I think things are working well from a technical standpoint. 2026-04-01 16:52:10 -04:00
Scott Idem
828a2a0b10 Making things work and look a little nicer. Missing business logic and functions. 2026-04-01 16:50:37 -04:00
Scott Idem
665eb48280 fix(events): show session codes by default
hide__session_code was defaulting to true, suppressing the code badge
in the session list on fresh sessions. Flip to false so codes are
visible out of the box — users can still hide via the menu toggle.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-04-01 16:43:27 -04:00
Scott Idem
d12a4bf71f feat(events): restore inc_file_counts opt-in, session list layout + button polish
- Add `inc_file_counts` flag to `load_ae_obj_id__event_session` — maps to
  backend alt view (v_event_session_w_file_count) when true; default stays
  lightweight. Callers never pass raw view names.
- Preserve-on-write fallback in `_refresh_session_id_background` keeps
  cached file_count/file_count_all if API response omits them.
- Session detail +page.ts uses `inc_file_counts: true` so SvelteKit prefetch
  no longer clobbers counts via bulkPut on hover.
- Remove explicit `view: 'alt'` from launcher +page.ts (now invalid param).
- Session list link: flex-1 + min-w-0 for full-row width; name flex-1 pushes
  badge group right; code + file_count stacked in flex-col items-end.
- Hover styling: button-like appearance with slow fade-out (duration-500) /
  fast snap-in (hover:duration-150).
- Session +page.svelte: use url_session_id (string) for link_to_id props and
  auth__kv.session[] index — fixes TS type error from number|undefined.
- IDAA layout: dormant tech notice banner (guarded by 1==3, remove when ready).

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-04-01 16:38:13 -04:00
Scott Idem
214fca3713 fix(auth): disable access_key check — always grant access
Access keys cleared from all site_domain records. Bypassing the entire
key verification block to unblock IDAA. TODO: restore when keys are re-added.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-04-01 09:59:24 -04:00
Scott Idem
802d0ec368 fix(idaa): preserve Novi session on internal iframe navigation
When navigating within the iframe (e.g. meeting list → meeting detail),
the UUID is only present on the initial iframe src URL — internal SvelteKit
<a href> links don't carry it forward. The layout effect was unconditionally
clearing novi_verified on every navigation that lacked a UUID, causing
"Access Denied" on every internal link click.

Fix: if a valid TTL-cached Novi session exists when no UUID is in the URL,
treat it as internal navigation and preserve the session rather than wiping it.
Non-Novi paths (no session, no UUID) still clear and deny as before.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-04-01 09:55:36 -04:00
Scott Idem
113aae23a7 fix(auth): preserve key string in key_checked to prevent access denied on navigation
key_checked was set to boolean true in Case 3, which +layout.svelte then
persisted back to localStorage. On the next keyless navigation, the check
true === 'actual-key-string' always failed, causing Access Denied after
just one internal page navigation.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-04-01 09:44:34 -04:00