import type { Payload } from "payload"; import { randomUUID } from "node:crypto"; const SESSION_IDLE_WINDOW_MS = 30 * 60 * 1000; /** * Groups events into sessions without any client-side identifier: looks up * the most recent event from the same `visitorHash` within the last 30 * minutes and reuses its sessionId, or mints a new one. One extra indexed * read per tracked request - acceptable at this site's traffic volume, and * simpler/safer than trying to hold a lock across an unauthenticated, * high-frequency public endpoint (unlike lib/booking/lock.ts's advisory * lock, an occasional extra spurious session here has no correctness * consequences worth the added complexity). */ export async function resolveSessionId(payload: Payload, visitorHash: string): Promise { const since = new Date(Date.now() - SESSION_IDLE_WINDOW_MS).toISOString(); const { docs } = await payload.find({ collection: "analytics-events", where: { and: [{ visitorHash: { equals: visitorHash } }, { createdAt: { greater_than_equal: since } }], }, sort: "-createdAt", limit: 1, depth: 0, }); return docs[0]?.sessionId ?? randomUUID(); }