import React, { useState, useEffect } from 'react';

import { TextBox, Button, ErrorMessage } from '@nova-hf/ui';
import { formatPrice, formatDate } from 'utils/helpers';
import { useSnackbar } from 'notistack';
import { useTranslation } from 'utils/i18n';

import {
  DiscountType,
  useCalculatePeriodsMutation,
  useSubscriptionPeriodDiscountMutation,
} from 'typings/graphql';

import s from './PeriodDiscount.module.scss';
interface IPeriodDiscount {
  subscriptionId: string;
  onDiscountComplete: () => void;
  periodEnd: Date | null;
  newPeriodCreated: boolean | null;
}

export const PeriodDiscount = ({
  subscriptionId,
  onDiscountComplete,
  periodEnd,
  newPeriodCreated,
}: IPeriodDiscount) => {
  const { t } = useTranslation('subscription');
  const { enqueueSnackbar } = useSnackbar();
  const [inputValue, setInputValue] = useState(0);
  const [remainingAmount, setRemainingAmount] = useState(0);
  const periodEndValue = newPeriodCreated != null && newPeriodCreated ? periodEnd : null;

  const [periodDiscount, { loading }] = useSubscriptionPeriodDiscountMutation({
    refetchQueries: ['subscriptionPeriods'],
  });

  const [originalPeriodPrice, { data: calculatedPeriodsResult, error: periodError }] =
    useCalculatePeriodsMutation({
      onCompleted: (result) => {
        const latestPeriod = result?.calculatePeriods?.data?.[0];
        if (latestPeriod?.amount !== undefined) {
          setRemainingAmount(latestPeriod?.amount);
        }
      },
    });

  const originalAmount = calculatedPeriodsResult?.calculatePeriods?.data?.[0]?.amount || 0;
  const calculatedPeriodStart =
    calculatedPeriodsResult?.calculatePeriods?.data?.[0] &&
    formatDate(
      calculatedPeriodsResult?.calculatePeriods?.data?.[0]?.periodStart as Date,
      'dd.MM.yyyy',
    );
  const calculatedPeriodEnd =
    calculatedPeriodsResult?.calculatePeriods?.data?.[0] &&
    formatDate(
      calculatedPeriodsResult?.calculatePeriods?.data?.[0]?.periodEnd as Date,
      'dd.MM.yyyy',
    );

  useEffect(() => {
    originalPeriodPrice({
      variables: {
        input: { subscriptionId, periodEnd: periodEndValue },
      },
    });
  }, []);

  const onDiscountSubmit = async () => {
    if (inputValue != null && inputValue > 0) {
      const input = {
        subscriptionId,
        periodEnd: periodEndValue,
        discount: inputValue,
        discountType: DiscountType.Amount,
      };
      try {
        const { data: periodDiscountResult } = await periodDiscount({
          variables: {
            input,
          },
        });

        if (periodDiscountResult?.subscriptionPeriodDiscount.error) {
          onDiscountComplete();
          enqueueSnackbar(t('periodDiscount.errorOnComplete'), {
            variant: 'error',
          });
        } else {
          setInputValue(0);
          onDiscountComplete();
          enqueueSnackbar(t('periodDiscount.successMessage'), {
            variant: 'success',
          });
        }
      } catch (e) {
        onDiscountComplete();
        enqueueSnackbar(t('periodDiscount.errorMessage'), {
          variant: 'error',
        });
      } finally {
        setInputValue(0);
        setRemainingAmount(originalAmount);
      }
    }
  };

  const handleInputChange = (e: React.ChangeEvent<HTMLInputElement>) => {
    const inputDiscount = +e.target.value;
    if (inputDiscount >= originalAmount) {
      setInputValue(originalAmount);
      setRemainingAmount(0);
    } else {
      setInputValue(inputDiscount);
      setRemainingAmount(originalAmount - inputDiscount);
    }
  };

  if (periodError) {
    return <ErrorMessage>Villa kom upp við að sækja gögn</ErrorMessage>;
  }

  if (calculatedPeriodsResult?.calculatePeriods?.error) {
    return <ErrorMessage>{calculatedPeriodsResult?.calculatePeriods?.error?.message}</ErrorMessage>;
  }

  return (
    <div className={s.discount__wrapper}>
      <div className={s.discount__title}>{t('periodDiscount.title')}</div>
      <div className={s.discount__description}>{t('periodDiscount.description')}</div>
      <div className={s.discount__newPeriod}>
        {t('periodDiscount.newPeriod', { calculatedPeriodStart, calculatedPeriodEnd })}
      </div>
      <div className={s.discount__inputRow}>
        <div className={s.discount__inputCol}>
          <TextBox
            label={t('periodDiscount.originalPrice')}
            name="amount"
            value={formatPrice(originalAmount)}
            type="text"
            readOnly
          />
        </div>
        <div className={s.discount__inputCol}>
          <TextBox
            label={t('periodDiscount.discount')}
            name="discountAmount"
            type="number"
            value={inputValue.toString()}
            onChange={(e: React.ChangeEvent<HTMLInputElement>) => handleInputChange(e)}
          />
        </div>
        <div className={s.discount__inputCol}>
          <TextBox
            label={t('periodDiscount.remainingAmount')}
            name="remainingAmount"
            value={formatPrice(remainingAmount)}
            type="text"
            readOnly
          />
        </div>
        <div className={s.discount__button}>
          <Button
            disabled={inputValue <= 0}
            onClick={onDiscountSubmit}
            loading={loading}
            fill
            arrowRight
          >
            {t('periodDiscount.makeDiscount')}
          </Button>
        </div>
      </div>
    </div>
  );
};
