wupengfei
2025-11-14 cdf4bd19d097c968a4c9e454a52960ec29fe0cec
src/views/FlexJobManage/FlexJobManage.vue
@@ -27,11 +27,10 @@
          </QueryFilterItem>
          <QueryFilterItem tip-content="灵工来源">
            <FieldRadio
              v-model="extraParamState.isReal"
              :value-enum="[]"
              v-model="extraParamState.source"
              :value-enum="EnumEnterpriseEmployeeSourceText"
              buttonStyle
              showAllBtn
              :all-btn-value="null"
              @change="getList()"
            />
          </QueryFilterItem>
@@ -79,7 +78,7 @@
          </QueryFilterItem> -->
          <QueryFilterItem>
            <FieldDatePicker
              v-model="extraParamState.createdTime"
              v-model="extraParamState.userRealTime"
              type="daterange"
              range-separator="~"
              start-placeholder="起始日期"
@@ -103,18 +102,32 @@
        <template #btn>
          <el-button
            v-if="checkSubModuleItemShow('pageButton', 'importBtn')"
            @click="handleDownloadTemplate()"
            @click="handleDownloadFlexJobTemplate()"
            type="primary"
            link
            >模板下载</el-button
          >
          <el-button
          <BlFileUpload
            v-if="checkSubModuleItemShow('pageButton', 'importBtn')"
            @click="handleBatchImportAdd()"
            type="primary"
            >批量导入</el-button
            v-model:file-url="state.flexjobUrl"
            ref="uploadRef"
            :showTip="false"
            :show-file-list="false"
            class="pro-table-operation-btn upload-style-btn"
            :on-success="(event) => handleUploadSuccess(event)"
            :limitFileSize="null"
            :limit="1"
            accept="xlsx,xls"
          >
            <el-button type="primary" class="pro-table-operation-btn">批量导入</el-button>
          </BlFileUpload>
          <el-button
            v-if="checkSubModuleItemShow('pageButton', 'addBtn')"
            @click="handleInternalStaffAdd()"
            type="primary"
            >新建</el-button
          >
          <!-- <el-button
            v-if="checkSubModuleItemShow('pageButton', 'batchUnSignBtn')"
            @click="handleBatchUnSign()"
            type="primary"
@@ -137,7 +150,7 @@
            @click="handleEnterpriseBatchSign()"
            type="primary"
            >批量企业签约</el-button
          >
          > -->
        </template>
      </ProTableQueryFilterBar>
      <ProTableV2
@@ -160,6 +173,7 @@
    />
    <SendShotMessageDialog v-bind="dialogShotMessageProps" />
    <SignDialog v-bind="dialogSignProps" />
    <AddInternalStaffDialog v-bind="dialogAddInternalStaffProps" />
  </LoadingLayout>
</template>
@@ -179,18 +193,25 @@
  useFormDialog,
  UploadUserFile,
  XLSXUtils,
  BlFileUpload,
} from '@bole-core/components';
import { EnumTaskUserHireStatusText, EnumTaskUserSignContractStatusText } from '@/constants';
import {
  EnumTaskUserHireStatusText,
  EnumTaskUserSignContractStatusText,
  EnumEnterpriseEmployeeSourceText,
} from '@/constants';
import { Message } from '@bole-core/core';
import { convertApi2FormUrlOnlyOne, downloadFileByUrl, format } from '@/utils';
import StaffInfoDialog from './components/StaffInfoDialog.vue';
import BatchImportDialog from './components/BatchImportDialog.vue';
import SendShotMessageDialog from './components/SendShotMessageDialog.vue';
import StaffDetailInfoDialog from './components/StaffDetailInfoDialog.vue';
import AddInternalStaffDialog from './components/AddInternalStaffDialog.vue';
import SignDialog from './components/SignDialog.vue';
import * as enterpriseEmployeeServices from '@/services/api/enterpriseEmployee';
import { ModelValueType } from 'element-plus';
import _ from 'lodash';
import { getEnterpriseEmployeesHooks } from './hooks';
defineOptions({
  name: 'FlexJobManageList',
@@ -199,7 +220,11 @@
const operationBtnMap: Record<string, OperationBtnType> = {
  editBtn: {
    emits: {
      onClick: (role) => openDialog(role),
      onClick: (role) => openInternalDialog(role),
    },
    extraProps: {
      hide: (row: API.GetEnterpriseEmployeesQueryResultItem) =>
        row.source === EnumEnterpriseEmployeeSource.External,
    },
  },
  detailBtn: {
@@ -208,42 +233,42 @@
        handleStaffDetailEdit({ id: role.id, tabType: 'info' }),
    },
  },
  enterpriseSignBtn: {
    emits: {
      onClick: (role) => handleEnterpriseSign(role),
    },
    extraProps: {
      hide: (row: API.GetEnterpriseEmployeesQueryResultItem) =>
        !(
          row.userSignContractStatus === EnumTaskUserSignContractStatus.Pass &&
          row.enterpriseSignContractStatus === EnumTaskUserSignContractStatus.Wait
        ),
    },
  },
  inviteSignBtn: {
    emits: {
      onClick: (role) => handleInviteSign(role),
    },
    extraProps: {
      hide: (row: API.GetEnterpriseEmployeesQueryResultItem) =>
        !(
          row.userSignContractStatus !== EnumTaskUserSignContractStatus.Pass &&
          row.hireStatus === EnumTaskUserHireStatus.Pass
        ),
    },
  },
  unSignBtn: {
    emits: {
      onClick: (role) => handleUnSign(role),
    },
    extraProps: {
      hide: (row: API.GetEnterpriseEmployeesQueryResultItem) =>
        !(
          row.userSignContractStatus === EnumTaskUserSignContractStatus.Pass &&
          row.enterpriseSignContractStatus === EnumTaskUserSignContractStatus.Pass
        ),
    },
  },
  // enterpriseSignBtn: {
  //   emits: {
  //     onClick: (role) => handleEnterpriseSign(role),
  //   },
  //   extraProps: {
  //     hide: (row: API.GetEnterpriseEmployeesQueryResultItem) =>
  //       !(
  //         row.userSignContractStatus === EnumTaskUserSignContractStatus.Pass &&
  //         row.enterpriseSignContractStatus === EnumTaskUserSignContractStatus.Wait
  //       ),
  //   },
  // },
  // inviteSignBtn: {
  //   emits: {
  //     onClick: (role) => handleInviteSign(role),
  //   },
  //   extraProps: {
  //     hide: (row: API.GetEnterpriseEmployeesQueryResultItem) =>
  //       !(
  //         row.userSignContractStatus !== EnumTaskUserSignContractStatus.Pass &&
  //         row.hireStatus === EnumTaskUserHireStatus.Pass
  //       ),
  //   },
  // },
  // unSignBtn: {
  //   emits: {
  //     onClick: (role) => handleUnSign(role),
  //   },
  //   extraProps: {
  //     hide: (row: API.GetEnterpriseEmployeesQueryResultItem) =>
  //       !(
  //         row.userSignContractStatus === EnumTaskUserSignContractStatus.Pass &&
  //         row.enterpriseSignContractStatus === EnumTaskUserSignContractStatus.Pass
  //       ),
  //   },
  // },
};
const { checkSubModuleItemShow, column, operationBtns } = useAccess({
@@ -254,6 +279,7 @@
const BaseState = {
  loading: true,
  flexjobUrl: [] as UploadUserFile[],
};
const state = reactive({ ...BaseState });
@@ -263,75 +289,8 @@
  state.loading = false;
});
const {
  getDataSource: getList,
  proTableProps,
  paginationState,
  extraParamState,
  reset,
} = useTable(
  async ({ pageIndex, pageSize }, extraParamState) => {
    try {
      let params: API.GetEnterpriseEmployeesQuery = {
        pageModel: {
          rows: pageSize,
          page: pageIndex,
          orderInput: extraParamState.orderInput,
        },
        keywords: extraParamState.searchWord,
        createdTimeStart: format(extraParamState.createdTime?.[0] ?? '', 'YYYY-MM-DD 00:00:00'),
        createdTimeEnd: format(extraParamState.createdTime?.[1] ?? '', 'YYYY-MM-DD 23:59:59'),
        signContractTimeStart: format(
          extraParamState.signContractTime?.[0] ?? '',
          'YYYY-MM-DD 00:00:00'
        ),
        signContractTimeEnd: format(
          extraParamState.signContractTime?.[1] ?? '',
          'YYYY-MM-DD 23:59:59'
        ),
        hireStatus: extraParamState.hireStatus,
        isReal: extraParamState.isReal,
        userSignContractStatus: extraParamState.userSignContractStatus,
        enterpriseSignContractStatus: extraParamState.enterpriseSignContractStatus,
      };
      let res = await enterpriseEmployeeServices.getEnterpriseEmployees(params, {
        showLoading: !state.loading,
      });
      return res;
    } catch (error) {
      console.log('error: ', error);
    }
  },
  {
    defaultExtraParams: {
      searchWord: '',
      orderInput: [{ property: 'createdTime', order: EnumPagedListOrder.Desc }],
      createdTime: [] as unknown as ModelValueType,
      signContractTime: [] as unknown as ModelValueType,
      hireStatus: '' as any as EnumTaskUserHireStatus,
      isReal: null as any as boolean,
      userSignContractStatus: '' as any as EnumTaskUserSignContractStatus,
      enterpriseSignContractStatus: '' as any as EnumTaskUserSignContractStatus,
    },
    queryKey: ['enterpriseEmployeeServices/getEnterpriseEmployees'],
    columnsRenderProps: {
      gender: { type: 'enum', valueEnum: EnumUserGenderTextForPerson },
      hireStatus: { type: 'enum', valueEnum: EnumTaskUserHireStatusText },
      userIsReal: {
        formatter: (row: API.GetEnterpriseEmployeesQueryResultItem) => {
          return row.userIsReal ? '已实名' : '未实名';
        },
      },
      userSignContractStatus: { type: 'enum', valueEnum: EnumTaskUserSignContractStatusText },
      hireTime: { type: 'date' },
      userRealTime: { type: 'date' },
      userSignContractTime: { type: 'date' },
      enterpriseSignContractStatus: { type: 'enum', valueEnum: EnumTaskUserSignContractStatusText },
      enterpriseSignContractTime: { type: 'date' },
    },
  }
);
const { getList, proTableProps, paginationState, extraParamState, reset } =
  getEnterpriseEmployeesHooks();
const proTable = ref<InstanceType<typeof ProTableV2>>();
@@ -354,7 +313,7 @@
  handleAdd: handleStaffInfoAdd,
  editForm: staffInfoEditForm,
} = useFormDialog({
  onConfirm: handleAddOrEdit,
  onConfirm: editEnterpriseEmployee,
  defaultFormParams: {
    id: '',
    name: '',
@@ -395,7 +354,7 @@
  } catch (error) {}
}
async function handleAddOrEdit() {
async function editEnterpriseEmployee() {
  try {
    let params: API.EditEnterpriseEmployeeCommand = {
      name: staffInfoEditForm.name,
@@ -497,6 +456,10 @@
function handleDownloadTemplate() {
  downloadFileByUrl(ImportEnterpriseEmployeesTempPath, '批量导入模板');
}
function handleDownloadFlexJobTemplate() {
  downloadFileByUrl(ImportFlexJobTempPath, '批量导入模板');
}
const {
@@ -661,4 +624,121 @@
    await Message.deleteMessage();
  } catch (error) {}
}
function handleUploadSuccess(response: UploadUserFile & { file: File & { uid: number } }) {
  if (response.path) {
    importEnterpriseEmployees(response.path);
  }
}
async function importEnterpriseEmployees(excelUrl: string) {
  try {
    let params: API.ImportEnterpriseEmployeesCommand = {
      excelUrl: excelUrl,
    };
    let res = await enterpriseEmployeeServices.importEnterpriseEmployees(params);
    if (res.failCount > 0) {
      await Message.tipMessage('存在错误数据,是否导出?');
      XLSXUtils.exportToXLSX({
        workbookDataList: res.errors,
        fileName: '灵工批量导入-错误数据',
        workbookHeaderMap: {
          name: '姓名',
          contactPhoneNumber: '手机号',
          identity: '身份证号',
          contractBegin: '协议起始时间',
          contractEnd: '协议终止时间',
          errorMessage: '错误信息',
        },
      });
    } else {
      Message.successMessage('导入成功');
      getList();
    }
  } catch (error) {
  } finally {
    state.flexjobUrl = [] as UploadUserFile[];
  }
}
const {
  dialogProps: dialogAddInternalStaffProps,
  handleAdd: handleInternalStaffAdd,
  handleEdit: handleInternalStaffEdit,
  editForm: internalStaffEditForm,
  dialogState: internalDialogState,
} = useFormDialog({
  onConfirm: addEnterpriseEmployee,
  defaultFormParams: {
    id: '',
    name: '',
    identity: '',
    contactPhoneNumber: '',
    gender: EnumUserGender.Male,
    age: null as any as number,
    identityImg: [] as UploadUserFile[],
    identityBackImg: [] as UploadUserFile[],
    contractUrl: [] as UploadUserFile[],
    regiterTime: '',
    userRealTime: '',
    userSignContractTime: '',
    contractTime: [] as unknown as ModelValueType,
  },
  closeAfterConfirm: false,
});
async function openInternalDialog(row: API.GetEnterpriseEmployeesQueryResultItem) {
  try {
    let detail = await enterpriseEmployeeServices.getEnterpriseEmployee({ id: row.id });
    handleInternalStaffEdit({
      id: row.id,
      name: row.name,
      identity: row.identity,
      contactPhoneNumber: row.contactPhoneNumber,
      gender: detail.gender,
      age: detail.age ?? null,
      identityImg: convertApi2FormUrlOnlyOne(detail.identityImg),
      identityBackImg: convertApi2FormUrlOnlyOne(detail.identityBackImg),
      contractUrl: convertApi2FormUrlOnlyOne(detail.contractUrl, {
        fileName: detail.contractUrl ? detail.contractUrl.split('/').pop() : '合同',
      }),
      regiterTime: detail.applyTime ?? '',
      userRealTime: row.userRealTime ?? '',
      userSignContractTime: row.userSignContractTime ?? '',
      contractTime: [row.contractBegin, row.contractEnd],
    });
  } catch (error) {}
}
async function addEnterpriseEmployee() {
  try {
    const isEdit = !!internalStaffEditForm.id;
    let params: API.AddEnterpriseEmployeeCommand = {
      name: internalStaffEditForm.name,
      identity: internalStaffEditForm.identity,
      contactPhoneNumber: internalStaffEditForm.contactPhoneNumber,
      gender: internalStaffEditForm.gender,
      age: internalStaffEditForm.age,
      identityImg: internalStaffEditForm.identityImg[0]?.path ?? '',
      identityBackImg: internalStaffEditForm.identityBackImg[0]?.path ?? '',
      contractUrl: internalStaffEditForm.contractUrl[0]?.path ?? '',
      contractBegin: format(internalStaffEditForm.contractTime[0], 'YYYY-MM-DD 00:00:00'),
      contractEnd: format(internalStaffEditForm.contractTime[1], 'YYYY-MM-DD 23:59:59'),
    };
    let res;
    if (isEdit) {
      (params as API.EditEnterpriseEmployeeCommand).id = internalStaffEditForm.id;
      res = await enterpriseEmployeeServices.editEnterpriseEmployee(params);
    } else {
      res = await enterpriseEmployeeServices.addEnterpriseEmployee(params);
    }
    if (res) {
      Message.successMessage('操作成功');
      getList(paginationState.pageIndex);
      internalDialogState.dialogVisible = false;
    }
  } catch (error) {
    internalDialogState.dialogVisible = true;
  }
}
</script>