liu
3 天以前 31f8c28b502a3f963a2651194112584371448e37
src/views/srm/supplierApply/index.vue
@@ -2,118 +2,38 @@
import type { VxeTableGridOptions } from '#/adapter/vxe-table';
import type { SrmSupplierApplyApi } from '#/api/srm/supplierApply';
import { computed, ref } from 'vue';
import { useRouter } from 'vue-router';
import { Page, useVbenModal } from '@vben/common-ui';
import { message } from 'ant-design-vue';
import { useVbenForm } from '#/adapter/form';
import { ACTION_ICON, TableAction, useVbenVxeGrid } from '#/adapter/vxe-table';
import {
  deleteApply,
  getApproveProcessList,
  getApplyPage,
  submitApply,
  reviewPurchase,
  reviewQuality,
  reviewFinance,
} from '#/api/srm/supplierApply';
import { $t } from '#/locales';
import { useGridColumns, useGridFormSchema } from './data';
import ApplyForm from './modules/form.vue';
import ProcessSelectModal from './modules/process-select-modal.vue';
import { APPLY_STATUS } from '../enums';
defineOptions({ name: 'SrmSupplierApply' });
// ---------- reviewModal ----------
const reviewFormData = ref({
  applyId: 0,
  reviewType: '' as 'purchase' | 'quality' | 'finance',
  passed: true,
  comment: '',
});
const reviewTitle = computed(() => {
  const labels: Record<string, string> = {
    purchase: '采购审核',
    quality: '质量审核',
    finance: '财务审核',
  };
  return labels[reviewFormData.value.reviewType] || '审核';
const router = useRouter();
const [FormModal, formModalApi] = useVbenModal({
  connectedComponent: ApplyForm,
  destroyOnClose: true,
});
const [ReviewForm, reviewFormApi] = useVbenForm({
  commonConfig: {
    componentProps: { class: 'w-full' },
    labelWidth: 100,
  },
  wrapperClass: 'grid-cols-1',
  layout: 'horizontal',
  schema: [
    {
      fieldName: 'passed',
      label: '审核结果',
      component: 'RadioGroup',
      rules: 'required',
      componentProps: {
        options: [
          { label: '通过', value: true },
          { label: '拒绝', value: false },
        ],
        buttonStyle: 'solid',
        optionType: 'button',
      },
    },
    {
      fieldName: 'comment',
      label: '审核意见',
      component: 'Textarea',
      componentProps: { placeholder: '请输入审核意见', rows: 3 },
    },
  ],
  showDefaultActions: false,
const [ProcessModal, processModalApi] = useVbenModal({
  connectedComponent: ProcessSelectModal,
  destroyOnClose: true,
});
const [ReviewModal, reviewModalApi] = useVbenModal({
  async onConfirm() {
    const { valid } = await reviewFormApi.validate();
    if (!valid) {
      return;
    }
    reviewModalApi.lock();
    const data = (await reviewFormApi.getValues()) as { passed: boolean; comment?: string };
    try {
      const payload: SrmSupplierApplyApi.ReviewVO = {
        id: reviewFormData.value.applyId,
        passed: data.passed,
        comment: data.comment,
      };
      if (reviewFormData.value.reviewType === 'purchase') {
        await reviewPurchase(payload);
      } else if (reviewFormData.value.reviewType === 'quality') {
        await reviewQuality(payload);
      } else if (reviewFormData.value.reviewType === 'finance') {
        await reviewFinance(payload);
      }
      await reviewModalApi.close();
      handleRefresh();
      message.success($t('ui.actionMessage.operationSuccess'));
    } finally {
      reviewModalApi.unlock();
    }
  },
});
function openReviewModal(row: SrmSupplierApplyApi.ApplyVO, reviewType: 'purchase' | 'quality' | 'finance') {
  reviewFormData.value = {
    applyId: row.id!,
    reviewType,
    passed: true,
    comment: '',
  };
  reviewFormApi.resetForm();
  reviewModalApi.open();
}
// ---------- grid ----------
function handleRefresh() {
@@ -121,11 +41,16 @@
}
function handleCreate() {
  formModalApi.setData(null).open();
  formModalApi.setData({ formType: 'create' }).open();
}
function handleEdit(row: SrmSupplierApplyApi.ApplyVO) {
  formModalApi.setData(row).open();
  formModalApi.setData({ formType: 'edit', id: row.id }).open();
}
/** 查看详情(只读) */
function handleDetail(row: SrmSupplierApplyApi.ApplyVO) {
  formModalApi.setData({ formType: 'detail', id: row.id }).open();
}
async function handleDelete(row: SrmSupplierApplyApi.ApplyVO) {
@@ -142,21 +67,38 @@
  }
}
/** 提交审批 - 先获取协同办公审批流程列表 */
async function handleSubmit(row: SrmSupplierApplyApi.ApplyVO) {
  const hideLoading = message.loading({ content: '提交中...', duration: 0 });
  const hideLoading = message.loading({
    content: '获取审批流程...',
    duration: 0,
  });
  try {
    await submitApply(row.id!);
    message.success($t('ui.actionMessage.operationSuccess'));
    handleRefresh();
  } finally {
    const processList = await getApproveProcessList();
    hideLoading();
    if (!processList || processList.length === 0) {
      message.warning('暂无可用审批流程,请先在协同办公配置审批流程');
      return;
    }
    // 打开流程选择弹窗
    processModalApi.setData({ id: row.id, processList }).open();
  } catch {
    hideLoading();
  }
}
const [FormModal, formModalApi] = useVbenModal({
  connectedComponent: ApplyForm,
  destroyOnClose: true,
});
/** 查看审批进度(跳转协同办公流程实例详情,只读查看) */
function handleViewProcess(row: SrmSupplierApplyApi.ApplyVO) {
  if (!row.processInstanceId) {
    message.warning('该申请尚未提交审批');
    return;
  }
  // viewOnly=1:隐藏审批操作按钮,仅查看审批进度
  router.push({
    name: 'BpmProcessInstanceDetail',
    query: { id: row.processInstanceId, viewOnly: '1' },
  });
}
const [Grid, gridApi] = useVbenVxeGrid({
  formOptions: {
@@ -186,9 +128,7 @@
<template>
  <Page auto-content-height>
    <FormModal @success="handleRefresh" />
    <ReviewModal :title="reviewTitle" class="w-1/3">
      <ReviewForm class="mx-4" />
    </ReviewModal>
    <ProcessModal @success="handleRefresh" />
    <Grid table-title="准入申请列表">
      <template #toolbar-tools>
        <TableAction
@@ -207,43 +147,34 @@
        <TableAction
          :actions="[
            {
              label: $t('common.edit'),
              label: $t('common.detail'),
              type: 'link',
              icon: ACTION_ICON.EDIT,
              auth: ['srm:supplier-apply:update'],
              onClick: handleEdit.bind(null, row),
              icon: ACTION_ICON.VIEW,
              auth: ['srm:supplier-apply:query'],
              onClick: handleDetail.bind(null, row),
            },
            {
              label: '提交',
              type: 'link',
              icon: ACTION_ICON.CHECK,
              icon: ACTION_ICON.AUDIT,
              auth: ['srm:supplier-apply:update'],
              ifShow: row.applyStatus === APPLY_STATUS.DRAFT,
              ifShow: () => row.applyStatus === APPLY_STATUS.DRAFT || row.applyStatus === APPLY_STATUS.REJECTED,
              onClick: handleSubmit.bind(null, row),
            },
            {
              label: '采购审核',
              label: '查看审批',
              type: 'link',
              icon: ACTION_ICON.CHECK,
              auth: ['srm:supplier-apply:update'],
              ifShow: row.applyStatus === APPLY_STATUS.PENDING_PURCHASE,
              onClick: openReviewModal.bind(null, row, 'purchase'),
              icon: ACTION_ICON.VIEW,
              ifShow: () => !!row.processInstanceId,
              onClick: handleViewProcess.bind(null, row),
            },
            {
              label: '质量审核',
              label: $t('common.edit'),
              type: 'link',
              icon: ACTION_ICON.CHECK,
              icon: ACTION_ICON.EDIT,
              auth: ['srm:supplier-apply:update'],
              ifShow: row.applyStatus === APPLY_STATUS.PENDING_QUALITY,
              onClick: openReviewModal.bind(null, row, 'quality'),
            },
            {
              label: '财务审核',
              type: 'link',
              icon: ACTION_ICON.CHECK,
              auth: ['srm:supplier-apply:update'],
              ifShow: row.applyStatus === APPLY_STATUS.PENDING_FINANCE,
              onClick: openReviewModal.bind(null, row, 'finance'),
              ifShow: () => row.applyStatus === APPLY_STATUS.DRAFT || row.applyStatus === APPLY_STATUS.REJECTED,
              onClick: handleEdit.bind(null, row),
            },
            {
              label: $t('common.delete'),
@@ -251,6 +182,7 @@
              danger: true,
              icon: ACTION_ICON.DELETE,
              auth: ['srm:supplier-apply:delete'],
              ifShow: () => row.applyStatus === APPLY_STATUS.DRAFT || row.applyStatus === APPLY_STATUS.REJECTED,
              popConfirm: {
                title: $t('ui.actionMessage.deleteConfirm', [row.supplierName]),
                confirm: handleDelete.bind(null, row),