<template>
  <div class="about main-background main-background-type0">
    <div class="nav-placeholder" />
    <section class="main-section large">
      <div class="content">
        <div class="title left-right">
          <a-button :icon="h(ArrowLeftOutlined)" @click="router.back()">返回</a-button>
          <h2>传承协议签署</h2>
          <div class="w-20"></div>
        </div>
        <a-spin :spinning="loader.loading.value">
          <template v-if="!loader.loading.value">
            <a-result
              v-if="!currentAgreement"
              status="info"
              title="您还未签署传承协议"
              sub-title="请先签署传承协议"
            >
              <template #extra>
                <a-button type="primary" @click="createAgreement">去签署传承协议</a-button>
              </template>
            </a-result>
            <div v-else>
              <a-alert type="info" message="请仔细阅读传承协议，确保您已理解内容，并签署传承协议。" class="mb-4" show-icon />
              <a-form
                v-if="currentAgreement"
                ref="formRef"
                :model="currentAgreement"
                :rules="formRules"
                layout="vertical"
              >
                <a-typography-title class="mt-5!" :level="4">{{ agreementTitle }}</a-typography-title>

                <AgreementBodyNational
                  v-if="currentAgreement?.level === 23"
                  :detail="(currentAgreement as AgreementDetail)"
                  :agreement-year="agreementYear"
                  :party-a-stamp-date="partyAStampDate"
                  :party-b-sign-date="partyBSignDate"
                  @update:party-a-stamp-date="partyAStampDate = $event"
                  @update:party-b-sign-date="partyBSignDate = $event"
                />
                <AgreementBodyProvincial
                  v-else-if="currentAgreement?.level === 24"
                  :detail="(currentAgreement as AgreementDetail)"
                  :agreement-year="agreementYear"
                  :party-a-stamp-date="partyAStampDate"
                  :party-b-sign-date="partyBSignDate"
                  @update:party-a-stamp-date="partyAStampDate = $event"
                  @update:party-b-sign-date="partyBSignDate = $event"
                />
                <AgreementBodyMunicipal
                  v-else-if="currentAgreement?.level === 25"
                  :detail="(currentAgreement as AgreementDetail)"
                  :agreement-year="agreementYear"
                  :party-a-stamp-date="partyAStampDate"
                  :party-b-sign-date="partyBSignDate"
                  @update:party-a-stamp-date="partyAStampDate = $event"
                  @update:party-b-sign-date="partyBSignDate = $event"
                />
              </a-form>

              <a-space direction="vertical" class="w-full mt-4" size="middle">
                <a-button type="primary" block :loading="submitLoading" @click="saveAgreement">保存传承协议</a-button>
                <a-button block :loading="submitLoading" @click="downloadAgreement">下载协议 PDF</a-button>
              </a-space>
            </div>
          </template>
        </a-spin>
      </div>
    </section>
  </div>
</template>

<script setup lang="ts">
import { computed, h, onMounted, ref, watch } from 'vue';
import { useRoute, useRouter } from 'vue-router';
import { message, Modal } from 'ant-design-vue';
import type { FormInstance } from 'ant-design-vue';
import type { Rules } from 'async-validator';
import { RequestApiError } from '@imengyu/imengyu-utils';
import { useAuthStore } from '@/stores/auth';
import AssessmentContentApi, { AgreementDetail } from '@/api/collect/AssessmentContent';
import AgreementBodyNational from './components/AgreementBodyNational.vue';
import AgreementBodyProvincial from './components/AgreementBodyProvincial.vue';
import AgreementBodyMunicipal from './components/AgreementBodyMunicipal.vue';
import type { AgreementYmdParts } from './components/AgreementDateWriteBlock.vue';
import { useSimpleDataLoader } from '@/composeables/useSimpleDataLoader';
import { ArrowLeftOutlined } from '@ant-design/icons-vue';
import { injectAppConfiguration } from '@/api/system/useAppConfiguration';

function formatErr(e: unknown): string {
  if (e instanceof RequestApiError)
    return e.errorMessage;
  if (e instanceof Error)
    return e.message;
  return String(e);
}

const router = useRouter();
const route = useRoute();
const authStore = useAuthStore();

const queryId = computed(() => Number(route.query.id) || 0);
const queryUserId = computed(() => Number(route.query.userId) || 0);

const currentAgreement = ref<AgreementDetail | null>(null);
const partyAStampDate = ref<AgreementYmdParts>({ year: '', month: '', day: '' });
const partyBSignDate = ref<AgreementYmdParts>({ year: '', month: '', day: '' });
const formRef = ref<FormInstance | null>(null);

const CN_MOBILE_RE = /^1\d{10}$/;
const CN_ID_RE = /^(?:\d{15}|\d{17}[\dXx])$/;

const formRules = computed<Rules>(() => {
  const rules: Rules = {
    partyB: [{ required: true, message: '请填写乙方（传承人）姓名' }],
    apprentice: [
      { required: true, message: '请填写本年度带徒人数' },
      { type: 'integer', min: 0, message: '须为不小于 0 的整数' },
    ],
    activity: [
      { required: true, message: '请填写本年度宣传活动场次' },
      { type: 'integer', min: 0, message: '须为不小于 0 的整数' },
    ],
    partyBSign: [
      {
        validator(_rule, value, callback) {
          const s = typeof value === 'string' ? value.trim() : '';
          if (!s)
            callback(new Error('请完成乙方签名'));
          else
            callback();
        },
      },
    ],
    idCard: [
      { required: true, message: '请填写身份证号' },
      {
        validator(_rule, value, callback) {
          const s = value != null ? String(value).trim() : '';
          if (!CN_ID_RE.test(s))
            callback(new Error('请输入正确的身份证号'));
          else
            callback();
        },
      },
    ],
    ich: [{ required: true, message: '请填写非遗项目名称' }],
    health: [{ required: true, message: '请填写身体状况' }],
    mobile: [
      { required: true, message: '请填写乙方联系电话' },
      {
        validator(_rule, value, callback) {
          const s = value != null ? String(value).trim() : '';
          if (!CN_MOBILE_RE.test(s))
            callback(new Error('请输入正确的手机号'));
          else
            callback();
        },
      },
    ],
  };
  if (currentAgreement.value?.level !== 25)
    rules.course = [
      { required: true, message: '请填写本年度研修班场次' },
      { type: 'integer', min: 0, message: '须为不小于 0 的整数' },
    ];
  return rules;
});

async function loadBasicInfo() {
  const uid = authStore.userInfo?.id ?? authStore.userId;
  const basicInfo = await AssessmentContentApi.getInheritorBasic(uid);
  const d = currentAgreement.value;
  if (!d)
    return;
  d.partyB = basicInfo.name;
  d.mobile = basicInfo.mobile;
  d.idCard = basicInfo.idCard;
  d.ich = basicInfo.ichName;
  d.level = basicInfo.level;
}

const agreementYear = computed(() => currentAgreement.value?.year ?? 2027);
const agreementTitle = computed(
  () => `${agreementYear.value} 年度${levelTitle.value}非物质文化遗产代表性传承人传承协议`,
);
const levelTitle = computed(() => {
  if (currentAgreement.value?.level === 23) return '国家级';
  if (currentAgreement.value?.level === 24) return '省级';
  return '市级';
});

const loader = useSimpleDataLoader(async () => {
  if (queryId.value > 0) {
    const detail = await AssessmentContentApi.getAgreementDetail(queryId.value, queryUserId.value || undefined);
    currentAgreement.value = detail;
    partyAStampDate.value = { year: '', month: '', day: '' };
    partyBSignDate.value = { year: '', month: '', day: '' };
    return currentAgreement.value;
  }
  const uid = authStore.userInfo?.id ?? authStore.userId;
  const basicInfo = await AssessmentContentApi.getInheritorBasic(uid);
  if (basicInfo.agreementId > 0) {
    const detail = await AssessmentContentApi.getAgreementDetail(
      basicInfo.agreementId,
      uid,
    );
    currentAgreement.value = detail;
    partyAStampDate.value = { year: '', month: '', day: '' };
    partyBSignDate.value = {
      year: detail.updatetime.getFullYear().toString(),
      month: (detail.updatetime.getMonth() + 1).toString(),
      day: detail.updatetime.getDate().toString(),
    };
  } else {
    currentAgreement.value = null;
  }
  return currentAgreement.value;
}, {
  immediate: false,
});

onMounted(() => {
  loader.load();
});

watch(
  () => [queryId.value, queryUserId.value],
  () => {
    loader.load();
  },
);

const submitLoading = ref(false);
const appConfiguration = injectAppConfiguration();

async function createAgreement() {
  const now = new Date();
  const u = authStore.userInfo;
  const nick = u?.nickname || u?.username || '';
  const uid = authStore.userInfo?.id ?? authStore.userId;
  const basicInfo = await AssessmentContentApi.getInheritorBasic(uid);
  const detail = new AgreementDetail();
  detail.userId = uid;
  detail.year = appConfiguration.value?.collectSignYear || now.getFullYear() + 1;
  detail.level = basicInfo.level;
  if (basicInfo.level === 24) {
    detail.partyA = '厦门市文化和旅游局';
  } else if (basicInfo.level === 25) {
    detail.partyA = basicInfo.regionText + '文化和旅游局';
  } else {
    detail.partyA = '福建省文化和旅游厅';
  }
  detail.partyB = nick;
  partyAStampDate.value = {
    year: now.getFullYear().toString(),
    month: (now.getMonth() + 1).toString(),
    day: now.getDate().toString(),
  };
  partyBSignDate.value = {
    year: now.getFullYear().toString(),
    month: (now.getMonth() + 1).toString(),
    day: now.getDate().toString(),
  };
  currentAgreement.value = detail;
  await loadBasicInfo();
}

async function saveAgreement() {
  try {
    await formRef.value?.validate();
  } catch {
    message.warning('请填写完整信息');
    return;
  }
  submitLoading.value = true;
  try {
    const d = currentAgreement.value;
    if (!d) {
      submitLoading.value = false;
      return;
    }
    await AssessmentContentApi.saveAgreement(d as AgreementDetail);
    message.success('保存传承协议成功');
  } catch (error) {
    Modal.error({
      title: '保存传承协议失败',
      content: formatErr(error),
    });
  }
  submitLoading.value = false;
}

async function downloadAgreement() {
  if (!currentAgreement.value?.id) {
    message.warning('请先保存传承协议后再下载 PDF');
    return;
  }
  try {
    await AssessmentContentApi.downloadAgreementPdf(currentAgreement.value.id);
    message.success('已开始下载');
  } catch (error) {
    Modal.error({
      title: '下载失败',
      content: formatErr(error),
    });
  }
}
</script>

