import React, { useState } from 'react';
import Link from 'next/link';
import { useForm } from 'react-hook-form';
import { useTranslation } from 'react-i18next';
import { useRouter } from 'next/router';
import axios from 'axios';
import Field from '../../common/Field';
import ArrowBigRight from '../../icons/ArrowBigRight';
import RoundedButton from '../../common/RoundedButton';
import Team from '../../icons/Team';
import InviteLink from '../../common/InviteLink';
import Avatar from './Avatar';
import Legal from './Legal';
import { SignUpFormData, SignUpProps } from '../../../model/components/signUp';
import { CustomResponse } from '../../../model/common';

const SignUp: React.FC<SignUpProps> = ({
  departments,
  teams,
  selectedTeam,
}) => {
  const {
    register,
    formState: { errors },
    handleSubmit,
    getValues,
    setError,
    clearErrors,
  } = useForm<SignUpFormData>();

  const { t } = useTranslation();
  const router = useRouter();

  const [createdTeam, setTeam] = useState<string>();
  const [avatar, setAvatar] = useState<string>();

  const onCreateTeam = async (): Promise<void> => {
    if (!getValues('team')) {
      setError('team', { type: 'required', message: 'EMPTY_TEAM' });
    } else {
      try {
        const response = await axios.post<CustomResponse<string>>(
          '/api/createTeam',
          {
            team: getValues('team'),
          },
        );
        if (response.data.ok) {
          clearErrors('team');
          setTeam(response.data.data);
        } else {
          setError('team', { message: response.data.error });
        }
      } catch (err) {
        setError('team', { message: err.message || err.stack || err });
      }
    }
  };

  const onSubmit = async (data: SignUpFormData): Promise<void> => {
    const { email, existingTeam, password, department, licenseNumber, name } =
      data;
    const response = await axios.post<CustomResponse<string>>('/api/register', {
      email,
      team: selectedTeam || createdTeam || existingTeam,
      password,
      departments,
      licenseNumber,
      name,
      department,
      avatar,
      isExistingTeam: !selectedTeam && !createdTeam,
    });

    if (response.data?.ok) {
      router.push('/');
    } else if (response.data.error) {
      setError('email', { message: response.data.error });
    }
  };

  return (
    <section className="wrapper">
      <div className="scrollHolder">
        <form onSubmit={handleSubmit(onSubmit)} noValidate>
          <fieldset>
            <div className="content left">
              <div className="title">
                <Team className=" team" size="medium" />
                <h1>Registro</h1>
              </div>
              <span className="divider" />
              <p className="instructionsTitle">
                Rellena tus datos, crea o selecciona un equipo al que quieras
                unirte y regístrate para participar.
              </p>
              <p className="instructions">
                La contraseña deberá tener
                <br />8 carateres min. /
                <br />
                Mayúsculas, minúsculas y números.
              </p>
              <p className="instructions">Todos los campos son necesarios</p>
              <Legal register={register} errors={errors} />
            </div>
            <div className="content center">
              <Field
                label="Nombre"
                htmlFor="name"
                errorMessage={t(errors.name?.message)}
                error={!!errors.name}
              >
                <input
                  type="text"
                  name="name"
                  {...register('name', { required: 'REQUIRED_NAME' })}
                />
              </Field>
              <Field
                label="Nº Colegiado"
                htmlFor="collegeNumber"
                errorMessage={t(errors.licenseNumber?.message)}
                error={!!errors.licenseNumber}
              >
                <input
                  type="text"
                  name="collegeNumber"
                  {...register('licenseNumber', {
                    required: 'REQUIRED_LICENSE',
                  })}
                />
              </Field>
              <Field
                label="Email"
                htmlFor="email"
                errorMessage={t(errors.email?.message)}
                error={!!errors.email}
              >
                <input
                  type="email"
                  name="email"
                  {...register('email', {
                    required: 'REQUIRED_EMAIL',
                    pattern: {
                      message: 'INVALID_EMAIL',
                      value: /^\S+@\S+.\S$/i,
                    },
                  })}
                />
              </Field>
              <Field
                label="Especialidad"
                htmlFor="specialty"
                errorMessage={t(errors.department?.message)}
                error={!!errors.department}
              >
                <select
                  name="specialty"
                  {...register('department', {
                    validate: (value) => {
                      if (value === 'none') {
                        return 'REQUIRED_DEPARTMENT';
                      }
                      return undefined;
                    },
                  })}
                >
                  <option value="none"> ---------------------------</option>
                  {departments.map((d) => (
                    <option key={d.id} value={d.id}>
                      {d.name}
                    </option>
                  ))}
                </select>
              </Field>
              <span className="divider" />
              <Field
                label="Contraseña"
                htmlFor="password"
                errorMessage={t(errors.password?.message)}
                error={!!errors.password}
              >
                <input
                  type="password"
                  name="password"
                  {...register('password', {
                    required: 'REQUIRED_PASSWORD',
                    pattern: {
                      message: 'INVALID_PASSWORD',
                      value: /^(?=.*[a-z])(?=.*[A-Z])(?=.*\d)\S{8,}$/,
                    },
                  })}
                />
              </Field>
              <Field
                label="Repetir Contraseña"
                htmlFor="password"
                errorMessage={t(errors.repeatPassword?.message)}
                error={!!errors.repeatPassword}
                className="small"
              >
                <input
                  type="password"
                  name="password"
                  {...register('repeatPassword', {
                    required: 'REQUIRED_REPEAT_PASSWORD',
                    pattern: {
                      message: 'INVALID_PASSWORD',
                      value: /^(?=.*[a-z])(?=.*[A-Z])(?=.*\d)\S{8,}$/,
                    },
                    validate: (value) =>
                      value !== getValues('password')
                        ? 'PASSWORDS_DONT_MATCH'
                        : undefined,
                  })}
                />
              </Field>
              {!selectedTeam ? (
                <>
                  <span className="divider" />
                  <Field
                    label="Nuevo equipo"
                    htmlFor="newTeam"
                    errorMessage={t(errors.team?.message)}
                    error={!!errors.team}
                  >
                    <input
                      type="text"
                      name="team"
                      readOnly={!!createdTeam}
                      {...register('team')}
                      onChange={(): void => clearErrors('team')}
                    />
                  </Field>
                  {createdTeam ? (
                    <InviteLink team={createdTeam} />
                  ) : (
                    <div className="inviteLink">
                      <RoundedButton
                        title="Crear"
                        className="inviteButton"
                        size="small"
                        onClick={onCreateTeam}
                      />
                    </div>
                  )}
                </>
              ) : null}
              <Avatar className="mobile" onChangeAvatar={setAvatar} />
              <span className="divider" />
              <Field
                label="Equipo existente"
                className="small"
                htmlFor="existingTeam"
                errorMessage={t(errors.existingTeam?.message)}
                error={!!errors.existingTeam}
              >
                <select
                  disabled={!!createdTeam || !!selectedTeam}
                  name="existingTeam"
                  {...register('existingTeam', {
                    validate: (value) => {
                      if (value === 'none' && !createdTeam) {
                        return 'REQUIRED_TEAM';
                      }
                      return undefined;
                    },
                  })}
                >
                  {!selectedTeam ? (
                    <option value="none"> ---------------------------</option>
                  ) : (
                    <option key={selectedTeam.id} value={selectedTeam.id}>
                      {selectedTeam.name}
                    </option>
                  )}
                  {teams.length
                    ? teams.map((team) => (
                        <option key={team.id} value={team.id}>
                          {team.name}
                        </option>
                      ))
                    : undefined}
                </select>
              </Field>
              <Legal className="mobile" register={register} errors={errors} />
              <span className="divider" />
              <RoundedButton
                title="Registrarme"
                type="submit"
                size="big"
                rightIcon={<ArrowBigRight />}
              />
              <div className="goBack">
                <Link href="/login">
                  <a href="/login" title="Iniciar sesión" className="textClick">
                    <p>{t('HAVE_ACCOUNT')}</p>
                  </a>
                </Link>
              </div>
            </div>
            <div className="content right">
              <Avatar onChangeAvatar={setAvatar} />
            </div>
          </fieldset>
        </form>
      </div>
    </section>
  );
};

export default SignUp;
