Openstatus
www.openstatus.dev
1import { useState } from "react";
2
3import { COOKIE_NAME } from "./shared";
4import type { PreferredSettings } from "./validation";
5import { preferencesSchema } from "./validation";
6
7function getPreferredSettingsCookie() {
8 const cookie = document.cookie
9 .split(";")
10 .find((cookie) => cookie.trim().startsWith(`${COOKIE_NAME}=`));
11 if (!cookie) return {};
12 const settings = preferencesSchema.safeParse(
13 JSON.parse(cookie.split("=")[1]),
14 );
15 if (!settings.success) return {};
16 return settings.data;
17}
18
19function setPreferredSettingsCookie(value: Record<string, unknown>) {
20 const month = 30 * 24 * 60 * 60 * 1000;
21 const expires = new Date(Date.now() + month).toUTCString();
22 document.cookie = `${COOKIE_NAME}=${JSON.stringify(
23 value,
24 )}; path=/; expires=${expires}`;
25}
26
27/**
28 * Update user preferences and store them in a cookie accessible on the client and server
29 */
30export function usePreferredSettings(defaultValue: PreferredSettings) {
31 const [settings, setSettings] = useState<PreferredSettings>(defaultValue);
32
33 const handleChange = (value: Record<string, unknown>) => {
34 const settings = preferencesSchema.safeParse(value);
35
36 if (!settings.success) return;
37
38 const currentSettings = getPreferredSettingsCookie();
39 const newSettings = { ...currentSettings, ...settings.data };
40
41 setPreferredSettingsCookie(newSettings);
42 setSettings(newSettings);
43 };
44
45 return [settings, handleChange] as const;
46}