import { useApi } from "@/api"; import { EGender, ESourceAuthorization, ICreateAuthorizePayload } from "@/api/resources/User"; import { useAuth } from "@/auth"; import { getClientTimezone } from "@/locales"; import { getDateAsString } from "@/services/date"; import { filterNullKeysOfObject } from "@/services/filter-object"; import { actions, selectors } from "@/store"; import moment from "moment"; import { useCallback, useMemo, useState } from "react"; import { useTranslation } from "react-i18next"; import { useDispatch, useSelector } from "react-redux"; export const useAuthentication = () => { const api = useApi(); const { i18n } = useTranslation(); const dispatch = useDispatch(); const [isLoading, setIsLoading] = useState(false); const [error, setError] = useState(null); const [token, setToken] = useState(null); const { user, signUp } = useAuth(); const locale = i18n.language; const { username } = useSelector(selectors.selectUser) const { name: partnerName, birthDate: partnerBirthdateFromForm } = useSelector(selectors.selectRightUser) const { gender, birthdate: birthdateFromQuestionnaire, birthtime: birthtimeFromQuestionnaire, birthPlace, partnerGender, partnerBirthdate: partnerBirthdateFromQuestionnaire, partnerBirthPlace, partnerBirthtime, } = useSelector(selectors.selectQuestionnaire) const birthdateFromForm = useSelector(selectors.selectBirthdate); const birthtimeFromForm = useSelector(selectors.selectBirthtime); const birthdate = useMemo(() => { if (birthdateFromQuestionnaire.length) { return birthdateFromQuestionnaire; } if (birthdateFromForm.length) { return birthdateFromForm; } }, [birthdateFromForm, birthdateFromQuestionnaire]); const birthtime = useMemo(() => { if (birthtimeFromQuestionnaire.length) { return birthtimeFromQuestionnaire; } if (birthtimeFromForm.length) { return birthtimeFromForm; } }, [birthtimeFromForm, birthtimeFromQuestionnaire]); const partnerBirthdate = useMemo(() => { const fromQuestionnaire = `${partnerBirthdateFromQuestionnaire} ${partnerBirthtime}` if (partnerBirthdateFromQuestionnaire.length) { return fromQuestionnaire; } return getDateAsString(partnerBirthdateFromForm) }, [partnerBirthdateFromForm, partnerBirthdateFromQuestionnaire, partnerBirthtime]) const formatDate = useCallback((date: string) => { const _date = moment(date).format("YYYY-MM-DD HH:mm"); if (_date === "Invalid date") { return null; } return _date; }, []) const getAuthorizationPayload = useCallback((email: string, source: ESourceAuthorization): ICreateAuthorizePayload => { const timezone = getClientTimezone(); return filterNullKeysOfObject({ timezone, locale, email, source, profile: { name: username || "", gender: EGender[gender as keyof typeof EGender] || null, birthdate: formatDate(`${birthdate} ${birthtime}`), birthplace: { address: birthPlace, }, }, partner: { name: partnerName, gender: EGender[partnerGender as keyof typeof EGender] || null, birthdate: formatDate(partnerBirthdate), birthplace: { address: partnerBirthPlace, }, } }) // eslint-disable-next-line react-hooks/exhaustive-deps }, [ birthPlace, birthdate, gender, locale, partnerBirthPlace, partnerBirthdate, partnerGender, partnerName, username, birthtime, ]); const authorization = useCallback(async (email: string, source: ESourceAuthorization) => { try { setIsLoading(true); const payload = getAuthorizationPayload(email, source); const { token, userId } = await api.authorization(payload); if (userId?.length && !!window.ym) { window.ym(95799066, 'userParams', { UserID: userId }) window.ym(95799066, 'setUserID', userId); } const { user } = await api.getUser({ token }); signUp(token, user); setToken(token); dispatch(actions.status.update("registred")); } catch (error) { setError((error as Error).message); } finally { setIsLoading(false); } }, [api, dispatch, getAuthorizationPayload, signUp]) return useMemo( () => ({ isLoading, error, token, user, authorization }), [isLoading, error, token, user, authorization] ); }