Skip to content

Feature: Event Planning Expansion — schedule, staff, fees, meals, external links, sign-in QR#434

Open
baltinerdist wants to merge 22 commits intoamtgard:masterfrom
baltinerdist:feature/event-planning-expansion
Open

Feature: Event Planning Expansion — schedule, staff, fees, meals, external links, sign-in QR#434
baltinerdist wants to merge 22 commits intoamtgard:masterfrom
baltinerdist:feature/event-planning-expansion

Conversation

@baltinerdist
Copy link
Copy Markdown
Contributor

@baltinerdist baltinerdist commented Mar 24, 2026

Summary

Unified event-planning feature work on feature/event-planning-expansion. 20 commits, 43 files, +5,481/−394, 12 migrations (9 in db-migrations/ + 3 root-level).

Event configuration

  • External links: replaces the single website field with a structured title + URL + icon picker (ticket-alt, facebook, discord, globe, clipboard, link)
  • Schedule with primary + secondary categories: primary drives color coding, secondary drives the filter bar; both shown in the schedule table with fixed-width icon alignment
  • Meeting category added to schedule alongside Administrative, Tournament, Battlegame, A&S, Class, Feast, Court, Other
  • Admission & Fees: new ork_event_fees table, dynamic add/remove rows in edit + create forms, fees card in Details tab, "Starts At" stat card replaces "Price"

Event staff & schedule leads

  • Event Staff permission model expanded for Feast and Schedule sections
  • Schedule item leads: many-to-many ork_event_schedule_lead join table, player autocomplete to assign multiple leads per session, schedule table shows a Lead(s) column with linked player names, pre-collapsed "Add from Event Staff" quick-add panel

Feast module

  • Meal table (ork_event_meal) with per-occurrence meal planning
  • Dietary & allergens fields on meal records
  • Feast staff permissions for delegated meal management

Cross-feature enhancements

  • Royal attendance indicators on Kingdom events tab (flag events Monarch/Regent are attending)
  • Sign-In Link & Self-Registration QR code for in-person park sign-ups (merged from feature/sign-in-link): generate, QR, active links, mobile-optimized
  • Event discovery improvements + creation UX polish, plus parse error fixes

Flatpickr UX fix

  • Event edit modal date/time inputs now display human-readable format ("March 28, 2026 12:00 PM") while preserving ISO value for submission

DB migrations (12 total)

Run in db-migrations/ via docker exec -i ork3-php8-db mariadb -u root -proot ork < db-migrations/<file>.sql:

  • 2026-03-16-add-event-schedule.sql
  • 2026-03-16-add-event-schedule-category.sql
  • 2026-03-16-add-event-staff.sql
  • 2026-03-19-add-event-fees.sql
  • 2026-03-19-add-event-schedule-leads.sql
  • 2026-03-23-add-event-meal.sql
  • 2026-03-23-event-staff-schedule-feast.sql
  • 2026-03-24-add-schedule-secondary-category.sql
  • 2026-03-24-event-meal-dietary-allergens.sql

Plus three root-level migration snippets for the sign-in-link merge:

  • migration_attendance_link.sql
  • migration_event_type.sql
  • migration_selfreg_link.sql

Test plan

Event configuration

  • Add external links with each icon type; verify icons render correctly
  • Schedule items with Primary + Secondary categories; confirm color follows primary, filter bar filters on secondary
  • Meeting category renders as light green fa-users
  • Schedule title column aligns whether or not a secondary icon is present
  • Add admission fees (multiple rows, $0 valid); confirm fees card appears in Details tab after save
  • Fees during event create; confirm card on resulting occurrence detail
  • Edit fees (add, remove, change amount); confirm persistence
  • "Starts At" stat card shows correct time, not ISO string

Schedule leads + event staff

  • Add one or more leads to a schedule session; Lead(s) column shows linked names after save
  • "Add from Event Staff" quick-add panel shows staff not yet assigned as leads
  • Event staff permissions for Feast and Schedule sections enforce on edit

Feast module

  • Create/edit meals, set dietary/allergens; verify persistence
  • Feast staff-level user can manage meals without full event-admin rights

Cross-feature

  • Royal attendance indicators show on Kingdom events tab when Monarch/Regent attending
  • Sign-In Link: generate, scan QR on mobile, verify attendance capture
  • Flatpickr date pickers display human-readable dates in edit modal

Migrations

  • All 12 migrations apply cleanly to a fresh DB
  • Migrations apply cleanly on top of current production schema

🤖 Generated with Claude Code

@baltinerdist baltinerdist reopened this Apr 12, 2026
@baltinerdist baltinerdist changed the title Feature: Event planning expansion — external links, schedule categories, secondary category Feature: Event Planning Expansion — schedule, staff, fees, meals, external links, sign-in QR Apr 12, 2026
Avery Krouse and others added 22 commits April 15, 2026 12:23
- Event schedule system with categories and staff assignments
- DB migrations for event schedule, schedule categories, and event staff tables
- Expanded Event and EventAjax controllers
- Updated Eventnew profile template and revised.js
- Attendance and Event class updates

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Previous append merged with .vscode/ line. Fixed to separate entries.
File removed from index so git stops tracking it.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- Add ork_event_schedule_lead table (many-to-many schedule ↔ mundane, CASCADE DELETE)
- Schedule modal: Item Lead(s) field with player autocomplete + chip display
- Schedule table: Lead(s) column showing linked player names
- Leads synced on add/update; edit modal pre-populates from data-leads attribute
- Add from Event Staff collapsible quick-add panel in leads section
- Staff members pre-filtered to exclude those already assigned as leads

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
…pansion

- Add ork_event_fees table (many-to-one per occurrence) with FK cascade delete
- Replace Price stat card with Starts At (event start time) on event detail
- Add Admission & Fees panel in event edit modal and create form with
  dynamic add/remove rows; fees serialized to JSON and synced on save
- Show fees card to the right of description in the Details tab
- Add ork_event_schedule_lead table (many-to-many) for session leads
- Schedule modal: player autocomplete to assign one or more item leads;
  pre-collapsed "Add from Event Staff" quick-add panel
- Schedule table: Lead(s) column with linked player names
- Fix flatpickr date display in edit modal (altInput human-readable format)

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- Add ork_event_meal table (title, cost, menu) via migration
- Add can_schedule / can_feast columns to ork_event_staff via migration
- Feast tab on event detail: meal cards with title, cost, menu (white-space: pre-line)
- Add/remove meal AJAX (add_meal / remove_meal) with auth check
- New staff permission flags: Can Manage Schedule, Can Manage Feast
- Staff with can_schedule can edit the Schedule tab without full event auth
- Staff with can_feast can edit the Feast tab without full event auth
- Fix StaffList SELECT to include can_schedule / can_feast columns so checkmarks render correctly

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- Detect Monarch and Regent mundane IDs from officer table
- Subquery RSVP counts for Monarch/Regent on each event occurrence
- Pass MonarchRsvp / RegentRsvp to template and AJAX calendar response
- Kingdomnew events tab can now highlight events where royals are attending

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
…egories & secondary category

- Replace single website field with External Links section (title + URL + FA icon picker: ticket-alt, facebook, discord, globe, clipboard, link)
- Add Secondary Category to schedule items; primary category drives color coding, secondary drives filters
- Add Meeting category (fa-users, light green) to schedule category options
- Add schedule filter bar with per-category toggle buttons
- DB migration: ork_event_schedule.secondary_category column
- Fix em-dash character encoding in Secondary Category "— None —" option

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Adds a complete sign-in link module for park/kingdom officers:
- Generate time-limited attendance URLs (up to 96 hours) with configurable credits
- Auto-copy to clipboard on generate; Copy and QR buttons in result row
- QR code modal (phpqrcode → base64 JSON via Controller_QR) with download link
- Active links collapsible panel with per-row Copy and Revoke
- Kingdom-level links moved into Admin Tasks modal with optional park autocomplete
- Player-facing SignIn page (Controller_SignIn + SignIn_index.tpl): quick sign-in with last class or full class picker; mobile edge-to-edge layout with iOS zoom/tap-delay fixes
- class.Attendance.php: GetAttendanceLinks, DeleteAttendanceLink, GetPlayerLastClass, CreateAttendanceLink, GetAttendanceLinkInfo, UseAttendanceLink
- model.Attendance.php: matching model wrappers
- revised.js: orkCopyToClipboard, orkOpenQrModal/orkCloseQrModal helpers; park + kingdom sign-in link wiring
- revised.css: mobile responsive fixes for tab bar, URL row, active links, QR image

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Adds a self-registration flow where park admins generate a QR code that
new players scan on their phone to create their own ORK account and join
the park — no admin data entry required. Includes:

- Self-reg QR modal on Park profile (admin-only) with 15-min expiry timer,
  anti-copy protections, and expired-state badge overlay
- Public SelfReg/form/{token} page (no login required) with email-to-username
  auto-fill, client-side countdown timer, and mobile-first full-bleed layout
- Transactional token locking (SELECT FOR UPDATE) to prevent race conditions
- Auto-assigns Color attendance credit on registration date
- Token reuse within expiry window to prevent table bloat
- Duplicate email detection before account creation
- Full session context (park/kingdom) set on auto-login after registration

Also fixes:
- class.Attendance.php: unescaped quotes in COALESCE SQL string
- Kingdomnew_index.tpl: stray endif causing parse error
- Adds migration SQL for both attendance_link and selfreg_link tables

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
The file was incorrectly gitignored and deleted during the sign-in-link merge.
class.Authorization.php is a core file and must always be tracked. Restored
from master with the production version (no login bypass).

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- SearchService: add event_type to Event() query and results for type badges
- Search_event: auto-load upcoming events on page open; EventType badge (purple) and RSVP count badge (green) on each result row
- Eventcreate: remove erroneous `required` on End Date field; default Country to "United States"
- controller.Event: fix escaped \$Lib/\$event_id backslash parse error (line 384)
- model.Attendance: fix missing closing brace in delete_attendance_link (line 108)
- Eventnew_index.tpl: fix missing <?php endif; ?> for canManageFeast block (line 2039)
- migration_event_type.sql: ADD COLUMN IF NOT EXISTS event_type on event_calendardetail

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Eventnew_index.tpl was missing a closing </div> for #ev-tab-details,
so every subsequent tab panel (Schedule, Feast, Attendance, RSVPs,
Staff, Map, Admin Tasks) was parser-recovered as a descendant of the
Details panel. When Details was hidden via display:none on tab switch,
the cascade hid all the other panels too — tabs highlighted correctly
but their content never appeared.

The Details panel's inner two-column flex layout (description + fees
card) had 4 opens and 4 closes before the schedule panel opened, with
no close for the panel itself. Added the missing </div> and corrected
the stale "Attendance Tab" comment that belonged above the schedule
panel.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
- RSVPs tab: kingdom and park abbreviations now link to their profile pages
  in a new tab. model.Event::get_rsvp_list selects p.park_id and k.kingdom_id
  alongside the existing abbreviations so the template can render anchors
  with a graceful fallback to plain text when an id or abbr is missing.
- Location dedupe: when the event's Address field already contains a fully
  formatted address (≥2 commas, e.g. from a map-picker autocomplete),
  treat it as canonical and stop re-appending city/province/country,
  which was producing "…Culpeper, VA 22701, USA, Culpeper, Virginia".
  Short addresses still fall through to the implode path.
- Details tab layout: the flex:0 0 220px Fees card was nested inside the
  flex:1 description column instead of being a sibling flex item, so it
  rendered at 100% width. Left column now closes cleanly before the right
  column opens, and the Links card is moved from the sidebar into the
  same right column under Fees, matching the requested layout.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Option B of the feast/schedule unification. Adds nullable meal columns
(menu, cost, dietary, allergens) to ork_event_schedule after the
description column, copies any existing ork_event_meal rows into the
schedule table (category='Feast and Food', start_time = event's start,
end_time = start + 1 hour), then drops ork_event_meal.

Dev DB had zero meal rows so the copy block is a no-op there; the
COPY is kept for any deployment where meal rows already exist.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Option B backend refactor. Schedule rows are now the canonical store
for both regular schedule items and meals; ork_event_meal is gone.

controller.Event.php
  - Schedule load query selects the 4 new columns (menu, cost, dietary,
    allergens) and includes them in the ScheduleList row hash.
  - MealList is no longer loaded from ork_event_meal; it is now derived
    in-place as array_filter(ScheduleList where Category='Feast and Food'
    or SecondaryCategory='Feast and Food').

controller.EventAjax.php
  - add_schedule / update_schedule accept Menu, Cost, Dietary, Allergens
    POST params and persist them; response JSON includes the meal fields.
  - Permission gating: a feast-category row (primary or secondary =
    'Feast and Food') requires can_schedule OR can_feast. Non-feast rows
    still require can_schedule. On edit, schedule-side fields (time,
    location, description, category, secondary_category, leads) are
    only written when can_schedule; meal-side fields (menu, cost,
    dietary, allergens) are only written when can_feast; title is
    shared. Silent per-field drop, not a 403.
  - add_meal / edit_meal / remove_meal handlers removed entirely.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Option B frontend. Eventnew_index.tpl now renders Feast tab cards from
the filtered ScheduleList (same rows the Schedule tab uses), and the
Schedule modal grows a Meal Details panel that reveals when the
primary or secondary category is 'Feast and Food'.

Feast tab
  - Cards carry a data-schedule-id and show time (g:ia – g:ia) and
    location pulled from the underlying schedule row.
  - "Add Feast Item" now opens the schedule modal with the category
    preset to Feast and Food via evOpenFeastScheduleModal().
  - "Edit" on a card opens the schedule modal in edit mode via
    evOpenFeastEditModal(meal) with all schedule + meal fields
    pre-populated from the PHP-emitted row data.
  - "Remove" hits EventAjax/remove_schedule and patches both the feast
    card and the schedule tab row/day-section in place.

Schedule modal
  - New collapsible #ev-sched-meal-panel (Cost input, Menu textarea,
    4 dietary checkboxes, 9 allergen checkboxes). Visible when either
    category select has the value 'Feast and Food'.
  - evSubmitSchedule is patched to append Menu/Cost/Dietary/Allergens
    (capitalized, matching the backend POST keys) right after the core
    Leads field. FormData.prototype.append is restored in a finally
    block so a throw in the inner submit cannot leave the prototype
    mutated. Earlier version of this patch used lowercase field names
    which the backend silently dropped — fixed here.
  - evOpenScheduleEditModal is also patched to populate the meal
    fields from new data-menu/cost/dietary/allergens attributes on
    schedule rows so editing a feast row from the Schedule tab
    round-trips correctly.

Schedule table
  - Feast-category rows with a non-empty Menu show a scroll icon in
    the title cell as a subtle "has menu" indicator.

Old meal modal, evOpenMealModal / evCloseMealModal / evSubmitMeal /
evAppendMealCard / evReplaceMealCard / evRemoveMeal, and every
add_meal/edit_meal/remove_meal reference — all deleted.

Also fixes a missing closing "}" on the flatpickr
if (document.getElementById('ev-fp-start')) { ... } block that was
swallowed by the feast IIFE insertion and was breaking parsing of
the entire inline script block (and in turn leaving EvConfig undefined
so revised.js threw ReferenceError).

And finally fixes a regression from earlier in the branch where the
Details tab's Fees card was nested inside the description column
instead of being a sibling flex item, and moves the Links card out of
the sidebar into the same right column as Fees. The ev-tab-details
panel's missing closing </div> — which caused every subsequent tab
panel to parser-recover as a descendant of Details and therefore
vanish when Details was hidden — is also fixed by the same pass.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Adds an "Add Image" link directly below the heraldry frame on the
create/edit event page (Eventcreate_index.tpl), opening the same
image upload modal used on the event detail page.

The heraldry frame and link are wrapped in a new ec-banner-heraldry-col
flex-column container so the link sits centered under the 64×64
heraldry instead of being clipped by the frame's overflow:hidden.

To make the modal work without forking its JS from revised.js, this
commit also defines an EvConfig stub on the create/edit page with the
minimum fields needed by revised.js (uir, eventId, canManage=true,
plus falsy flags for the other canManage* bits). This simultaneously
fixes a pre-existing ReferenceError where revised.js was throwing on
this page because EvConfig was never defined.

The upload modal HTML + the ev-img-* CSS block are ported inline from
Eventnew_index.tpl so no revised.css change is needed.

In the eventId=0 case (wholly new event with no parent event id) the
link is rendered as a disabled span with a tooltip explaining the
user should save the event first; the modal HTML is not emitted in
that case.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
…elcome

- Event sign-in links: per-event shareable URL + QR modal (button in
  attendance export bar) with required credits, expiring 24h after event end.
  Backend extends ork_attendance_link with event_id/event_calendardetail_id;
  UseAttendanceLink writes proper event-scoped attendance rows; auth supports
  event admins and event_staff with can_attendance.
- Schedule Builder: changing start time now always recomputes end to start+1h
  (removed the "only when end is blank" guard).
- Self-Reg page: big "Welcome to {Park Name}!" hero plus an intro card
  explaining what ORK is and the benefits of registering.
- Fix: add missing typeof EvConfig guard to the Event Detail IIFE so the
  ReferenceError no longer halts the rest of revised.js (which was cascading
  into pkOpenAddPlayerModal undefined on Park profiles).

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Four event-planning migrations were committed at the repo root instead
of under db-migrations/, which made them easy to miss during PR review.
Rename them to the dated convention used by the rest of the folder.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Alternate grid-style view for the event Schedule tab: time on the
left, primary categories as columns, events as positioned blocks.
Toggle between List and Grid via a segmented pill (persisted in
localStorage); mobile (<700px) falls back to list. Reuses the
existing category palette, forwards block clicks to the hidden list
row's edit button, and exposes a read-only popover for non-managers.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
@baltinerdist baltinerdist force-pushed the feature/event-planning-expansion branch from 8b8213c to 647194d Compare April 15, 2026 16:35
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant