GitStart 846da08cbd
refactor: antdv5 notfications (#2161)
Co-authored-by: gitstart <gitstart@users.noreply.github.com>
Co-authored-by: Nitesh Singh <nitesh.singh@gitstart.dev>
Co-authored-by: gitstart-app[bot] <57568882+gitstart-app[bot]@users.noreply.github.com>
Co-authored-by: Rubens Rafael <70234898+RubensRafael@users.noreply.github.com>
Co-authored-by: RubensRafael <rubensrafael2@live.com>
Co-authored-by: niteshsingh1357 <niteshsingh1357@gmail.com>
Co-authored-by: gitstart_bot <gitstart_bot@users.noreply.github.com>
Co-authored-by: Palash Gupta <palashgdev@gmail.com>
2023-02-02 11:38:32 +05:30

292 lines
6.8 KiB
TypeScript

import { Button, Input, notification, Space, Tooltip, Typography } from 'antd';
import loginApi from 'api/user/login';
import loginPrecheckApi from 'api/user/loginPrecheck';
import afterLogin from 'AppRoutes/utils';
import ROUTES from 'constants/routes';
import history from 'lib/history';
import React, { useEffect, useState } from 'react';
import { useTranslation } from 'react-i18next';
import { PayloadProps as PrecheckResultType } from 'types/api/user/loginPrecheck';
import { FormContainer, FormWrapper, Label, ParentContainer } from './styles';
const { Title } = Typography;
interface LoginProps {
jwt: string;
refreshjwt: string;
userId: string;
ssoerror: string;
withPassword: string;
}
function Login({
jwt,
refreshjwt,
userId,
ssoerror = '',
withPassword = '0',
}: LoginProps): JSX.Element {
const { t } = useTranslation(['login']);
const [isLoading, setIsLoading] = useState<boolean>(false);
const [email, setEmail] = useState<string>('');
const [password, setPassword] = useState<string>('');
const [precheckResult, setPrecheckResult] = useState<PrecheckResultType>({
sso: false,
ssoUrl: '',
canSelfRegister: false,
isUser: true,
});
const [precheckInProcess, setPrecheckInProcess] = useState(false);
const [precheckComplete, setPrecheckComplete] = useState(false);
const [notifications, NotificationElement] = notification.useNotification();
useEffect(() => {
if (withPassword === 'Y') {
setPrecheckComplete(true);
}
}, [withPassword]);
useEffect(() => {
async function processJwt(): Promise<void> {
if (jwt && jwt !== '') {
setIsLoading(true);
await afterLogin(userId, jwt, refreshjwt);
setIsLoading(false);
history.push(ROUTES.APPLICATION);
}
}
processJwt();
}, [jwt, refreshjwt, userId]);
useEffect(() => {
if (ssoerror !== '') {
notifications.error({
message: t('failed_to_login'),
});
}
}, [ssoerror, t, notifications]);
const onNextHandler = async (): Promise<void> => {
if (!email) {
notifications.error({
message: t('invalid_email'),
});
return;
}
setPrecheckInProcess(true);
try {
const response = await loginPrecheckApi({
email,
});
if (response.statusCode === 200) {
setPrecheckResult({ ...precheckResult, ...response.payload });
const { isUser } = response.payload;
if (isUser) {
setPrecheckComplete(true);
} else {
notifications.error({
message: t('invalid_account'),
});
}
} else {
notifications.error({
message: t('invalid_config'),
});
}
} catch (e) {
console.log('failed to call precheck Api', e);
notifications.error({ message: t('unexpected_error') });
}
setPrecheckInProcess(false);
};
const onChangeHandler = (
setFunc: React.Dispatch<React.SetStateAction<string>>,
value: string,
): void => {
setFunc(value);
};
const { sso, canSelfRegister } = precheckResult;
const onSubmitHandler: React.FormEventHandler<HTMLFormElement> = async (
event,
) => {
try {
event.preventDefault();
event.persist();
if (!precheckComplete) {
onNextHandler();
return;
}
if (precheckComplete && sso) {
window.location.href = precheckResult.ssoUrl || '';
return;
}
setIsLoading(true);
const response = await loginApi({
email,
password,
});
if (response.statusCode === 200) {
await afterLogin(
response.payload.userId,
response.payload.accessJwt,
response.payload.refreshJwt,
);
history.push(ROUTES.APPLICATION);
} else {
notifications.error({
message: response.error || t('unexpected_error'),
});
}
setIsLoading(false);
} catch (error) {
setIsLoading(false);
notifications.error({
message: t('unexpected_error'),
});
}
};
const renderSAMLAction = (): JSX.Element => (
<Button
type="primary"
loading={isLoading}
disabled={isLoading}
href={precheckResult.ssoUrl}
>
{t('login_with_sso')}
</Button>
);
const renderOnSsoError = (): JSX.Element | null => {
if (!ssoerror) {
return null;
}
return (
<Typography.Paragraph italic style={{ color: '#ACACAC' }}>
{t('prompt_on_sso_error')}{' '}
<a href="/login?password=Y">{t('login_with_pwd')}</a>.
</Typography.Paragraph>
);
};
return (
<FormWrapper>
{NotificationElement}
<FormContainer onSubmit={onSubmitHandler}>
<Title level={4}>{t('login_page_title')}</Title>
<ParentContainer>
<Label htmlFor="signupEmail">{t('label_email')}</Label>
<Input
placeholder={t('placeholder_email')}
type="email"
autoFocus
required
id="loginEmail"
onChange={(event): void => onChangeHandler(setEmail, event.target.value)}
value={email}
disabled={isLoading}
/>
</ParentContainer>
{precheckComplete && !sso && (
<ParentContainer>
<Label htmlFor="Password">{t('label_password')}</Label>
<Input.Password
required
id="currentPassword"
onChange={(event): void =>
onChangeHandler(setPassword, event.target.value)
}
disabled={isLoading}
value={password}
/>
<Tooltip title={t('prompt_forgot_password')}>
<Typography.Link>{t('forgot_password')}</Typography.Link>
</Tooltip>
</ParentContainer>
)}
<Space
style={{ marginTop: '1.3125rem' }}
align="start"
direction="vertical"
size={20}
>
{!precheckComplete && (
<Button
disabled={precheckInProcess}
loading={precheckInProcess}
type="primary"
onClick={onNextHandler}
>
{t('button_initiate_login')}
</Button>
)}
{precheckComplete && !sso && (
<Button
disabled={isLoading}
loading={isLoading}
type="primary"
htmlType="submit"
data-attr="signup"
>
{t('button_login')}
</Button>
)}
{precheckComplete && sso && renderSAMLAction()}
{!precheckComplete && ssoerror && renderOnSsoError()}
{!canSelfRegister && (
<Typography.Paragraph italic style={{ color: '#ACACAC' }}>
{t('prompt_no_account')}
</Typography.Paragraph>
)}
{!canSelfRegister && (
<Typography.Paragraph italic style={{ color: '#ACACAC' }}>
{t('prompt_create_account')}{' '}
<Typography.Link
onClick={(): void => {
history.push(ROUTES.SIGN_UP);
}}
style={{ fontWeight: 700 }}
>
{t('create_an_account')}
</Typography.Link>
</Typography.Paragraph>
)}
{canSelfRegister && (
<Typography.Paragraph italic style={{ color: '#ACACAC' }}>
{t('prompt_if_admin')}{' '}
<Typography.Link
onClick={(): void => {
history.push(ROUTES.SIGN_UP);
}}
style={{ fontWeight: 700 }}
>
{t('create_an_account')}
</Typography.Link>
</Typography.Paragraph>
)}
</Space>
</FormContainer>
</FormWrapper>
);
}
export default Login;