import { useMutation } from "@apollo/client";

import { Button, Form, Modal, notification } from "antd";
import React, { useEffect, useState } from "react";
import { useTranslation } from "react-i18next";
import { connect } from "react-redux";
import { createStructuredSelector } from "reselect";
import {
  INSERT_NEW_PAYMENT,
  UPDATE_PAYMENT,
} from "../../graphql/payments.queries";
import { setEmailOptions } from "../../redux/email/email.actions";
import { toggleModalVisible } from "../../redux/modals/modals.actions";
import { selectPayment } from "../../redux/modals/modals.selectors";
import {
  selectBodyshop,
  selectCurrentUser,
} from "../../redux/user/user.selectors";
import { GenerateDocument } from "../../utils/RenderTemplate";
import { TemplateList } from "../../utils/TemplateConstants";
import PaymentForm from "../payment-form/payment-form.component";

const mapStateToProps = createStructuredSelector({
  paymentModal: selectPayment,
  bodyshop: selectBodyshop,
  currentUser: selectCurrentUser,
});

const mapDispatchToProps = (dispatch) => ({
  setEmailOptions: (e) => dispatch(setEmailOptions(e)),
  toggleModalVisible: () => dispatch(toggleModalVisible("payment")),
});

function PaymentModalContainer({
  paymentModal,
  toggleModalVisible,
  bodyshop,
  currentUser,
  setEmailOptions,
}) {
  const [form] = Form.useForm();
  const [enterAgain, setEnterAgain] = useState(false);
  const [insertPayment] = useMutation(INSERT_NEW_PAYMENT);
  const [updatePayment] = useMutation(UPDATE_PAYMENT);

  const { t } = useTranslation();
  const { context, actions, visible } = paymentModal;

  const [loading, setLoading] = useState(false);

  const handleFinish = async (values) => {
    const { useStripe, sendby, ...paymentObj } = values;

    setLoading(true);
    let updatedPayment; //Moved up from if statement for greater scope.
    try {
      if (!context || (context && !context.id)) {
        const newPayment = await insertPayment({
          variables: {
            paymentInput: {
              ...paymentObj,
            },
          },
        });

        if (!!!newPayment.errors) {
          notification["success"]({ message: t("payments.successes.payment") });
        } else {
          notification["error"]({ message: t("payments.errors.payment") });
        }
        const Templates = TemplateList("payment");
        if (sendby !== "none") {
          GenerateDocument(
            {
              name: Templates.payment_receipt.key,
              variables: {
                id: newPayment.data.insert_payments.returning[0].id,
              },
            },
            {
              // to: [appData.email],
              replyTo: bodyshop.email,
              subject: Templates.payment_receipt.subject,
            },
            sendby === "email" ? "e" : "p",
            paymentObj.jobid
          );
        }
      } else {
        updatedPayment = await updatePayment({
          variables: {
            paymentId: context.id,
            payment: paymentObj,
          },
        });

        if (!!!updatedPayment.errors) {
          notification["success"]({ message: t("payments.successes.payment") });
        } else {
          notification["error"]({ message: t("payments.errors.payment") });
        }
      }

      if (actions.refetch)
        actions.refetch(
          updatedPayment && updatedPayment.data.update_payments.returning[0]
        );

      if (enterAgain) {
        const prev = form.getFieldsValue(["date"]);

        form.resetFields();
        form.setFieldsValue(prev);
      } else {
        toggleModalVisible();
      }
      setEnterAgain(false);
    } catch (error) {
      console.log("error", error);
    } finally {
      setEnterAgain(false);
      setLoading(false);
    }
  };

  const handleCancel = () => {
    toggleModalVisible();
  };

  useEffect(() => {
    if (visible) {
      form.resetFields();
      form.resetFields();
      form.setFieldsValue(context);
    }
  }, [visible, form, context]);

  useEffect(() => {
    if (enterAgain) form.submit();
  }, [enterAgain, form]);

  return (
    <Modal
      title={
        !context || (context && !context.id)
          ? t("payments.labels.new")
          : t("payments.labels.edit")
      }
      visible={visible}
      destroyOnClose
      okText={t("general.actions.save")}
      onOk={() => form.submit()}
      width="50%"
      onCancel={handleCancel}
      okButtonProps={{
        loading: loading,
      }}
      afterClose={() => form.resetFields()}
      footer={
        <span>
          <Button onClick={handleCancel}>{t("general.actions.cancel")}</Button>
          <Button loading={loading} onClick={() => form.submit()}>
            {t("general.actions.save")}
          </Button>
          {paymentModal.context && paymentModal.context.id ? null : (
            <Button
              type="primary"
              loading={loading}
              onClick={() => {
                setEnterAgain(true);
              }}
            >
              {t("general.actions.saveandnew")}
            </Button>
          )}
        </span>
      }
    >
      <Form
        onFinish={handleFinish}
        autoComplete={"off"}
        form={form}
        layout="vertical"
        initialValues={context || {}}
      >
        <PaymentForm form={form} />
      </Form>
    </Modal>
  );
}

export default connect(
  mapStateToProps,
  mapDispatchToProps
)(PaymentModalContainer);
