<script lang="ts" setup>
import { computed, ref } from 'vue';

import { useVbenModal } from '@vben/common-ui';

import { Alert, message, Select } from 'ant-design-vue';

import { useVbenForm } from '#/adapter/form';

import {
  getSelectableBankCards,
  queryStoreBankCardStatus,
  reportStoreBankCard,
  updateStoreBankCard,
} from '../api';
import {
  LABEL_UPDATE_REPORT_BANK_CARD,
  USE_TYPE_TRANSFER,
} from '../config/constants';
import { bankCardReportFormProps } from '../config/form';

const mode = ref<'report' | 'update'>('report');
const storeId = ref(0);
const storeName = ref('');
const reportInfo = ref<Record<string, any> | null>(null);
const gridApi = ref();
const selectableOptions = ref<
  Array<{ value: string; label: string; payload: Record<string, any> }>
>([]);
const selectedCardKey = ref<string | undefined>();
const importReportId = ref(0);

const onlyRemark = computed(
  () =>
    mode.value === 'update' &&
    reportInfo.value &&
    reportInfo.value.can_full_update === false,
);

const showCardSelector = computed(
  () => mode.value === 'report' && !onlyRemark.value,
);

const showImportAlert = computed(
  () => mode.value === 'report' && importReportId.value > 0,
);

const isRejectedResubmit = computed(() => {
  const status = Number(reportInfo.value?.report_status ?? 0);
  return Boolean(reportInfo.value?.id) && [3, 4].includes(status);
});

const showPendingSyncHint = computed(
  () =>
    Boolean(reportInfo.value?.id) &&
    Number(reportInfo.value?.report_status) === 1,
);

const [Form, formApi] = useVbenForm(bankCardReportFormProps);

async function loadSelectableCards() {
  if (!storeId.value || !showCardSelector.value) {
    selectableOptions.value = [];
    return;
  }
  try {
    const res = await getSelectableBankCards(storeId.value);
    selectableOptions.value = res?.options ?? [];
  } catch {
    selectableOptions.value = [];
  }
}

async function handleSelectExistingCard(value: string | undefined) {
  if (!value) {
    importReportId.value = 0;
    return;
  }
  const option = selectableOptions.value.find((item) => item.value === value);
  if (!option) {
    importReportId.value = 0;
    return;
  }
  importReportId.value = Number(option.payload.import_report_id ?? 0);
  const currentValues = await formApi.getValues();
  await formApi.setValues({
    ...currentValues,
    ...option.payload,
    store_id: storeId.value,
    use_type: USE_TYPE_TRANSFER,
    use_type_display: '转账卡（useType=2）',
    only_remark: 0,
    attachment: currentValues.attachment ?? '',
    id: undefined,
  });
}

const [Modal, modalApi] = useVbenModal({
  fullscreenButton: false,
  draggable: true,
  onCancel() {
    modalApi.close();
  },
  onConfirm: async () => {
    const result = await formApi.validate();
    if (!result.valid) {
      return;
    }
    const values = await formApi.getValues();
    modalApi.setState({ loading: true, confirmLoading: true });
    try {
      const shouldUpdate =
        mode.value === 'update' || isRejectedResubmit.value;
      if (shouldUpdate) {
        await updateStoreBankCard({
          ...values,
          id: values.id,
          use_type: USE_TYPE_TRANSFER,
        });
        message.success(
          isRejectedResubmit.value
            ? '银行卡报备已重新提交'
            : '报备银行卡修改已提交',
        );
      } else {
        await reportStoreBankCard({
          ...values,
          store_id: values.store_id,
          use_type: USE_TYPE_TRANSFER,
          import_report_id: importReportId.value,
        });
        message.success(
          importReportId.value > 0 ? '银行卡报备已导入' : '银行卡报备已提交',
        );
      }
      gridApi.value?.reload();
      modalApi.close();
    } finally {
      modalApi.setState({ loading: false, confirmLoading: false });
    }
  },
  onOpenChange(isOpen: boolean) {
    if (!isOpen) {
      selectedCardKey.value = undefined;
      importReportId.value = 0;
      selectableOptions.value = [];
      return;
    }
    const data = modalApi.getData<Record<string, any>>();
    gridApi.value = data?.gridApi;
    mode.value = data?.mode ?? 'report';
    storeId.value = data?.storeId ?? 0;
    storeName.value = data?.storeName ?? '';
    reportInfo.value = data?.report ?? null;
    importReportId.value = 0;

    const rejectedResubmit = [3, 4].includes(
      Number(reportInfo.value?.report_status ?? 0),
    );

    formApi.resetForm();
    formApi.setValues({
      store_id: storeId.value,
      only_remark: onlyRemark.value ? 1 : 0,
      use_type: USE_TYPE_TRANSFER,
      use_type_display: '转账卡（useType=2）',
      account_type: reportInfo.value?.account_type ?? '2',
      report_status: reportInfo.value?.report_status ?? 0,
      ...(reportInfo.value ?? {}),
      id: reportInfo.value?.id,
      attachment: rejectedResubmit ? '' : (reportInfo.value?.attachment ?? ''),
    });
    loadSelectableCards();

    if (reportInfo.value?.id && Number(reportInfo.value?.report_status) === 1) {
      refreshStatus({ silent: true });
    }
  },
});

const modalTitle = computed(() => {
  const prefix =
    mode.value === 'report' ? '银行卡报备' : LABEL_UPDATE_REPORT_BANK_CARD;
  return storeName.value ? `${prefix} - ${storeName.value}` : prefix;
});

async function refreshStatus(options: { silent?: boolean } = {}) {
  if (!reportInfo.value?.id) {
    return;
  }
  modalApi.setState({ loading: true });
  try {
    const res = await queryStoreBankCardStatus({ id: reportInfo.value.id });
    reportInfo.value = res;
    const rejectedResubmit = [3, 4].includes(Number(res.report_status ?? 0));
    formApi.setValues({
      ...res,
      store_id: res.store_id,
      use_type: USE_TYPE_TRANSFER,
      use_type_display: '转账卡（useType=2）',
      report_status: res.report_status ?? 0,
      only_remark: res.can_full_update === false ? 1 : 0,
      attachment: rejectedResubmit ? '' : (res.attachment ?? ''),
    });
    if (!options.silent) {
      message.success('状态已刷新');
    }
    gridApi.value?.reload();
  } finally {
    modalApi.setState({ loading: false });
  }
}
</script>

<template>
  <Modal :title="modalTitle" class="w-[560px]">
    <Alert
      v-if="reportInfo?.report_status_text"
      :message="`当前报备状态：${reportInfo.report_status_text}${reportInfo.audit_remarks ? `（${reportInfo.audit_remarks}）` : ''}`"
      class="mb-4"
      show-icon
      type="info"
    />
    <Alert
      v-if="onlyRemark"
      message="该卡已生效，仅可修改备注和摘要"
      class="mb-4"
      show-icon
      type="warning"
    />
    <Alert
      v-if="isRejectedResubmit"
      message="审核未通过，请修改信息后重新上传合同附件并提交"
      class="mb-4"
      show-icon
      type="error"
    />
    <Alert
      v-if="showPendingSyncHint"
      message="当前为待审核状态，如审核结果已久未更新，请先点击下方「刷新报备状态」"
      class="mb-4"
      show-icon
      type="warning"
    />
    <Alert
      v-if="showImportAlert"
      message="已从历史报备导入，不会重复提交易票联，请上传本门店合同附件"
      class="mb-4"
      show-icon
      type="info"
    />
    <div v-if="showCardSelector && selectableOptions.length > 0" class="mb-4">
      <div class="mb-2 text-sm text-gray-600">选择已有报备记录</div>
      <Select
        v-model:value="selectedCardKey"
        allow-clear
        class="w-full"
        :options="selectableOptions"
        placeholder="从历史报备记录选择（可跨门店）"
        @change="handleSelectExistingCard"
      />
    </div>
    <Form />
    <a
      v-if="reportInfo?.id"
      class="mt-2 inline-block text-primary"
      @click.prevent="refreshStatus"
    >
      刷新报备状态
    </a>
  </Modal>
</template>
