From 3465b55abc98e52cf58ba46b811f4ec115d53012 Mon Sep 17 00:00:00 2001 From: Paul Nothaft Date: Mon, 18 May 2026 21:26:45 +0200 Subject: [PATCH] feat(events): default Guest Feedback ON via admin setting (#520) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit @Rekoo-PS asked for an admin-level switch so new events can have Guest Feedback enabled out of the box instead of toggling it on every time. Mirrors the existing event_default_require_password pattern (#317) — same shape end-to-end, same set of five files. - publicSettings.js: whitelist + expose event_default_feedback_enabled (defaults to false to match the prior hard-coded form default; no behaviour change for existing installs until an admin flips it). - adminEvents.js: rename `feedback_enabled = false` destructure to `feedback_enabled: feedbackEnabledInput` so we can distinguish "omitted" from "explicit false", then resolve the default from the setting only when the caller omitted it — identical to the require_password handling a few lines above. - Frontend EventSettings type + state + loader: new boolean, default false. - EventsTab: toggle UI right under "Require password by default". - CreateEventPage: one-shot useEffect that seeds feedback_settings.feedback_enabled from the public setting on first load (mirrors the require_password seed effect right above it). Sub-toggles (likes / ratings / comments) keep their hard-coded true defaults so flipping the master setting immediately gives sensible behaviour without a second admin setting to manage. Refs: #520 --- backend/src/routes/adminEvents.js | 13 ++++++++++++- backend/src/routes/publicSettings.js | 5 +++++ .../settings/hooks/useSettingsState.ts | 3 +++ .../src/features/settings/tabs/EventsTab.tsx | 19 +++++++++++++++++++ frontend/src/pages/admin/CreateEventPage.tsx | 19 +++++++++++++++++++ .../src/services/publicSettings.service.ts | 1 + 6 files changed, 59 insertions(+), 1 deletion(-) diff --git a/backend/src/routes/adminEvents.js b/backend/src/routes/adminEvents.js index ed04d418..d1bbab3e 100644 --- a/backend/src/routes/adminEvents.js +++ b/backend/src/routes/adminEvents.js @@ -439,7 +439,7 @@ router.post('/', adminAuth, requirePermission('events.create'), [ allow_presigned_download = false, require_password: requirePasswordInput, // Feedback settings - feedback_enabled = false, + feedback_enabled: feedbackEnabledInput, allow_ratings = true, allow_likes = true, allow_comments = true, @@ -507,6 +507,17 @@ router.post('/', adminAuth, requirePermission('events.create'), [ } const requirePassword = parseBooleanInput(requirePasswordInput, requirePasswordFallback); + // Default feedback_enabled from global "event_default_feedback_enabled" + // setting when the body omits it (#520 — same pattern as require_password + // above, lets admins make Guest Feedback ON the out-of-box default for + // new events instead of toggling it on every time). + let feedbackEnabledFallback = false; + if (feedbackEnabledInput === undefined) { + const setting = await readBooleanSetting('event_default_feedback_enabled'); + if (setting !== undefined) feedbackEnabledFallback = setting; + } + const feedback_enabled = parseBooleanInput(feedbackEnabledInput, feedbackEnabledFallback); + // Debug logging logger.debug('Download control values', { allow_downloads, diff --git a/backend/src/routes/publicSettings.js b/backend/src/routes/publicSettings.js index b7e9166f..c5a65f96 100644 --- a/backend/src/routes/publicSettings.js +++ b/backend/src/routes/publicSettings.js @@ -16,6 +16,7 @@ router.get('/', async (req, res) => { .orWhereIn('setting_key', [ 'seo_meta_noindex', 'seo_meta_nofollow', 'seo_meta_noai', 'event_default_require_password', + 'event_default_feedback_enabled', 'gallery_show_filter_bar', 'event_phone_field_enabled' ]); @@ -120,6 +121,10 @@ router.get('/', async (req, res) => { event_require_expiration: settingsObject.event_require_expiration !== false, // Default value for "Require password" toggle in event creation form event_default_require_password: settingsObject.event_default_require_password !== false, + // Default value for the "Guest Feedback enabled" toggle (#520). + // Defaults to false (matches the prior hard-coded form default), so + // existing installs see no behaviour change until an admin flips it. + event_default_feedback_enabled: settingsObject.event_default_feedback_enabled === true, // Phone-number field on events is opt-in (#322). event_phone_field_enabled: settingsObject.event_phone_field_enabled === true, // Whether to show the search/sort filter bar in public galleries (default: true) diff --git a/frontend/src/features/settings/hooks/useSettingsState.ts b/frontend/src/features/settings/hooks/useSettingsState.ts index d5cd5f08..5f62d13d 100644 --- a/frontend/src/features/settings/hooks/useSettingsState.ts +++ b/frontend/src/features/settings/hooks/useSettingsState.ts @@ -54,6 +54,7 @@ export interface EventSettings { event_require_event_date: boolean; event_require_expiration: boolean; event_default_require_password: boolean; + event_default_feedback_enabled: boolean; gallery_show_filter_bar: boolean; event_phone_field_enabled: boolean; } @@ -133,6 +134,7 @@ export function useSettingsState() { event_require_event_date: true, event_require_expiration: true, event_default_require_password: true, + event_default_feedback_enabled: false, gallery_show_filter_bar: true, event_phone_field_enabled: false }); @@ -220,6 +222,7 @@ export function useSettingsState() { event_require_event_date: toBoolean(settings.event_require_event_date, true), event_require_expiration: toBoolean(settings.event_require_expiration, true), event_default_require_password: toBoolean(settings.event_default_require_password, true), + event_default_feedback_enabled: toBoolean(settings.event_default_feedback_enabled, false), gallery_show_filter_bar: toBoolean(settings.gallery_show_filter_bar, true), event_phone_field_enabled: toBoolean(settings.event_phone_field_enabled, false) }); diff --git a/frontend/src/features/settings/tabs/EventsTab.tsx b/frontend/src/features/settings/tabs/EventsTab.tsx index 1365d3c7..5907c724 100644 --- a/frontend/src/features/settings/tabs/EventsTab.tsx +++ b/frontend/src/features/settings/tabs/EventsTab.tsx @@ -169,6 +169,25 @@ export const EventsTab: React.FC = ({ +
+ +
+