64 lines
2.3 KiB
TypeScript
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),
|
|
);
|
|
},
|
|
};
|
|
}
|