From 61bdf41b9c0ee5dcb04bba1ff624657f0b6c9937 Mon Sep 17 00:00:00 2001 From: Usman Baig Date: Mon, 19 Jan 2026 14:35:04 +0100 Subject: [PATCH] feat: implement sampling rate adjustments in settings page with a custom range input and predefined options --- app/sites/[id]/settings/page.tsx | 40 +++++++++++++++++++++++++------- 1 file changed, 32 insertions(+), 8 deletions(-) diff --git a/app/sites/[id]/settings/page.tsx b/app/sites/[id]/settings/page.tsx index 8222a0e..26586f6 100644 --- a/app/sites/[id]/settings/page.tsx +++ b/app/sites/[id]/settings/page.tsx @@ -23,6 +23,15 @@ import { LockClosedIcon, } from '@radix-ui/react-icons' +/** Sampling rate steps (every 10%): 10, 20, …, 100. */ +const SAMPLING_RATE_OPTIONS = [10, 20, 30, 40, 50, 60, 70, 80, 90, 100] as const + +function snapSamplingRate(v: number): number { + return (SAMPLING_RATE_OPTIONS as readonly number[]).reduce( + (best, x) => (Math.abs(x - v) < Math.abs(best - v) ? x : best) + ) +} + const TIMEZONES = [ 'UTC', 'America/New_York', @@ -97,7 +106,7 @@ export default function SiteSettingsPage() { collect_screen_resolution: data.collect_screen_resolution ?? true, // Session replay settings (legacy consent_required from API mapped to anonymous_skeleton) replay_mode: ((data as { replay_mode?: string }).replay_mode === 'consent_required' ? 'anonymous_skeleton' : data.replay_mode) || 'disabled', - replay_sampling_rate: data.replay_sampling_rate ?? 100, + replay_sampling_rate: snapSamplingRate(data.replay_sampling_rate ?? 100), replay_retention_days: data.replay_retention_days ?? 30, replay_mask_all_text: data.replay_mask_all_text ?? false, replay_mask_all_inputs: data.replay_mask_all_inputs ?? true @@ -814,16 +823,31 @@ export default function SiteSettingsPage() { setFormData({ ...formData, replay_sampling_rate: parseInt(e.target.value) })} + min={0} + max={SAMPLING_RATE_OPTIONS.length - 1} + step={1} + list="sampling-rate-ticks" + value={(() => { + const i = (SAMPLING_RATE_OPTIONS as readonly number[]).indexOf(formData.replay_sampling_rate) + return i >= 0 ? i : SAMPLING_RATE_OPTIONS.length - 1 + })()} + onChange={(e) => + setFormData({ + ...formData, + replay_sampling_rate: SAMPLING_RATE_OPTIONS[parseInt(e.target.value, 10)], + }) + } className="w-full h-2 bg-neutral-200 dark:bg-neutral-700 rounded-lg appearance-none cursor-pointer accent-brand-orange" /> + + {SAMPLING_RATE_OPTIONS.map((_, i) => ( +
- 1% - 50% - 100% + {SAMPLING_RATE_OPTIONS.map((pct) => ( + {pct}% + ))}