Files
Investidor-V2/resources/js/hooks/use-interest-draft.ts
T
2026-11-02 20:31:15 +02:00

64 lines
2.3 KiB
TypeScript

import { useEffect, useState } from 'react';
import { newSubmissionKey } from '@/lib/portal-api';
export function useInterestDraft<T>(name: string, initial: T) {
const storage = 'investemoz-interest:' + name;
const [draft, setDraft] = useState<{ form: T; key: string }>(() => {
try {
const value = JSON.parse(sessionStorage.getItem(storage) ?? 'null');
if (value?.form && typeof value.key === 'string') return value;
} catch {
/* unavailable storage leaves the current form usable */
}
return { form: initial, key: newSubmissionKey() };
});
useEffect(() => {
try {
sessionStorage.setItem(storage, JSON.stringify(draft));
} catch {}
}, [storage, draft]);
const setForm = (value: T | ((old: T) => T)) =>
setDraft((old) => ({
...old,
form:
typeof value === 'function'
? (value as (old: T) => T)(old.form)
: value,
}));
return {
form: draft.form,
setForm,
key: draft.key,
clear: () => {
try {
sessionStorage.removeItem(storage);
sessionStorage.removeItem('investemoz-participation-identity');
} catch {
/* Storage failure must not turn a confirmed submission into an error. */
}
},
authenticate: () => {
const identity = draft.form as {
name?: string;
fullName?: string;
email?: string;
};
try {
sessionStorage.setItem(
'investemoz-participation-identity',
JSON.stringify({
name: identity.fullName ?? identity.name ?? '',
email: identity.email ?? '',
}),
);
sessionStorage.setItem(storage, JSON.stringify(draft));
} catch {
/* Authentication remains available when browser persistence is blocked. */
}
window.location.assign(
'/participar/entrar?return=' +
encodeURIComponent(location.pathname + location.search),
);
},
};
}