2024-05-28 11:39:46 +03:00

154 lines
4.0 KiB
TypeScript
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

/* eslint-disable react/jsx-curly-newline */
/* eslint-disable sonarjs/no-small-switch */
import TelegramIcon from '../public/assets/images/telegram.svg';
import styles from './Form.module.scss';
import { publicRuntimeConfig } from '@/config/runtime';
import { FormStateContext } from '@/context/form-state';
import type { LdapUser } from '@/types/user';
import axios from 'axios';
import Image from 'next/image';
import type { PropsWithChildren } from 'react';
import { useContext } from 'react';
import { useForm } from 'react-hook-form';
const ERROR_INVALID_CREDENTIALS = 'Неверный логин или пароль';
const ERROR_SERVER = 'Не удалось войти. Повторите попытку позже';
const { APP_BASE_PATH } = publicRuntimeConfig;
type FormData = {
readonly login: string;
readonly password: string;
};
type FormProps = {
readonly onSubmit: (data: FormData) => void;
};
function BaseForm({ children, onSubmit }: FormProps & PropsWithChildren) {
const { handleSubmit, register } = useForm<FormData>();
const {
state: { error, step },
} = useContext(FormStateContext);
return (
<form className={styles.form} onSubmit={handleSubmit(onSubmit)}>
<input
disabled={step === 'telegram'}
type="text"
placeholder="Логин"
required
autoComplete="on"
{...register('login', { required: true })}
/>
<input
disabled={step === 'telegram'}
type="password"
placeholder="Пароль"
required
autoComplete="on"
{...register('password', { required: true })}
/>
{error ? <span className="error">{error}</span> : null}
{children}
</form>
);
}
export const Form = {
Default() {
const { dispatch } = useContext(FormStateContext);
function handleLogin(data: FormData) {
const redirectUrl =
(window.location.pathname.replace(APP_BASE_PATH, '') || '/') +
(window.location.search || '');
return axios
.post('/login', data)
.then(() => window.location.replace(redirectUrl))
.catch(() =>
dispatch({
payload: { error: ERROR_INVALID_CREDENTIALS },
type: 'set-error',
})
);
}
return (
<BaseForm onSubmit={(data) => handleLogin(data)}>
<button className={styles['button-submit']} type="submit">
Войти
</button>
</BaseForm>
);
},
Telegram() {
const {
dispatch,
state: { step, user },
} = useContext(FormStateContext);
function handleLogin(data: FormData) {
axios
.post<LdapUser>('/login', data)
.then((res) => {
dispatch({
payload: {
step: 'telegram',
user: res.data,
},
type: 'set-step',
});
})
.catch(() =>
dispatch({
payload: { error: ERROR_INVALID_CREDENTIALS },
type: 'set-error',
})
);
}
function handleTelegramLogin() {
axios
.post<LdapUser>('/login-telegram')
.then((res) => {
// eslint-disable-next-line no-console
console.log('🚀 ~ .then ~ res:', res);
})
.catch(() =>
dispatch({
payload: { error: ERROR_SERVER },
type: 'set-error',
})
);
}
if (step === 'telegram') {
return (
<BaseForm onSubmit={(data) => handleLogin(data)}>
<button type="button" className={styles['button-telegram']}>
<Image
className={styles['button-telegram-icon']}
src={TelegramIcon}
width={24}
height={22}
alt="Telegram icon"
/>
Войти как &nbsp; <b>{user?.displayName}</b>
</button>
</BaseForm>
);
}
return (
<BaseForm onSubmit={() => handleTelegramLogin()}>
<button className={styles['button-submit']} type="submit">
Войти
</button>
</BaseForm>
);
},
};