wupengfei
2025-04-02 32c69839e3658c81e1ac7bf66ef207215c22a4a9
feat: init
3个文件已添加
4个文件已修改
9个文件已删除
1816 ■■■■■ 已修改文件
src/components/DataBoardCard/DataBoardCard.vue 44 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/components/DataBoardCard/DataBoardCardContentItem.vue 45 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/components/DataBoardCard/DataBoardCardPrice.vue 48 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/constants/index.ts 1 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/constants/insuranceClaim.ts 74 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/constants/oss.ts 2 ●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/views/Export/ExportManage.vue 229 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/views/Export/components/BatchUploadOrderDialog.vue 109 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/views/Home/Home.vue 298 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/views/Home/components/Chart.vue 121 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/views/Home/constants/index.ts 81 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/views/Home/hooks/index.ts 71 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/views/InsuranceClaim/InsuranceClaimDetail.vue 494 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/views/InsuranceClaim/hooks/index.ts 168 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/views/InsuranceClaim/utils/index.ts 29 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/views/Login/Login.vue 2 ●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/components/DataBoardCard/DataBoardCard.vue
New file
@@ -0,0 +1,44 @@
<template>
  <div class="data-board-card-wrapper">
    <div class="data-board-card-title">{{ title }}</div>
    <div class="data-board-card-content">
      <slot></slot>
    </div>
  </div>
</template>
<script setup lang="ts">
defineOptions({
  name: 'DataBoardCard',
});
type Props = {
  title?: string;
};
const props = withDefaults(defineProps<Props>(), {});
</script>
<style lang="scss" scoped>
@use '@/style/common.scss' as *;
.data-board-card-wrapper {
  display: flex;
  padding: 16px;
  border: 1px solid var(--el-border-color-light);
  border-radius: 4px;
  background-color: #ffffff;
  flex-direction: column;
  .data-board-card-title {
    margin-bottom: 12px;
    font-size: 16px;
    color: getCssVar('text-color', 'primary');
  }
  .data-board-card-content {
    flex: 1;
    min-height: 0;
  }
}
</style>
src/components/DataBoardCard/DataBoardCardContentItem.vue
New file
@@ -0,0 +1,45 @@
<template>
  <div class="data-board-card-content-item">
    <div class="data-board-card-content-item-label">{{ label }}</div>
    <div class="data-board-card-content-item-content"><slot></slot></div>
  </div>
</template>
<script setup lang="ts">
defineOptions({
  name: 'DataBoardCardContentItem',
});
type Props = {
  label?: string;
};
const props = withDefaults(defineProps<Props>(), {});
</script>
<style lang="scss" scoped>
@use '@/style/common.scss' as *;
.data-board-card-content-item {
  display: flex;
  align-items: center;
  margin-bottom: 12px;
  font-size: 14px;
  &:last-child {
    margin-bottom: 0;
  }
  .data-board-card-content-item-label {
    width: 80px;
    color: getCssVar('text-color', 'regular');
  }
  .data-board-card-content-item-content {
    flex: 1;
    min-width: 0;
    @include utils-ellipsis;
    color: getCssVar('text-color', 'primary');
  }
}
</style>
src/components/DataBoardCard/DataBoardCardPrice.vue
New file
@@ -0,0 +1,48 @@
<template>
  <div class="data-board-card-price">
    <div class="data-board-card-value">{{ displayValue }}</div>
    <div class="data-board-card-unit">{{ unit }}</div>
  </div>
</template>
<script setup lang="ts">
import { toThousand } from '@/utils';
defineOptions({
  name: 'DataBoardCardPrice',
});
type Props = {
  value?: number;
  useThousand?: boolean;
  unit?: string;
};
const props = withDefaults(defineProps<Props>(), {
  useThousand: true,
  unit: '元',
});
const displayValue = computed(() => (props.useThousand ? toThousand(props.value) : props.value));
</script>
<style lang="scss" scoped>
@use '@/style/common.scss' as *;
.data-board-card-price {
  display: flex;
  align-items: flex-end;
  .data-board-card-value {
    margin-right: 4px;
    font-size: 20px;
    font-weight: bold;
    color: getCssVar('text-color', 'primary');
  }
  .data-board-card-unit {
    font-size: 14px;
    color: getCssVar('text-color', 'primary');
  }
}
</style>
src/constants/index.ts
@@ -8,5 +8,4 @@
export * from './theme';
export * from './menu';
export * from './role';
export * from './insuranceClaim';
export * from './app';
src/constants/insuranceClaim.ts
File was deleted
src/constants/oss.ts
@@ -4,7 +4,7 @@
export const OSSBaseURL = VITE_OSS_URL;
const _basicPath = '12333/YeXing/';
const _basicPath = '12333/Government/';
export const OssHRSIE = _basicPath + 'HRSIE/';
src/views/Export/ExportManage.vue
File was deleted
src/views/Export/components/BatchUploadOrderDialog.vue
File was deleted
src/views/Home/Home.vue
@@ -1,308 +1,34 @@
<template>
  <LoadingLayout :loading="state.loading">
  <LoadingLayout :loading="isLoading">
    <AppContainer>
      <div class="home-top-view">
        <ProForm :mode="form">
          <ProFormItemV2 label="报案年份:">
            <ProFormDatePicker
              v-model="form.year"
              type="year"
              format="YYYY"
              value-format="YYYY"
              placeholder="报案年份"
              :disabled-date="disabledYear"
            ></ProFormDatePicker>
          </ProFormItemV2>
          <ProFormItemV2 label="报案月份:">
            <ProFormDatePicker
              v-model="form.month"
              type="month"
              format="M"
              value-format="M"
              placeholder="报案月份"
            ></ProFormDatePicker>
          </ProFormItemV2>
          <ProFormItemV2 label="理赔渠道:">
            <ProFormSelect
              v-model="form.claimChannel"
              placeholder="理赔渠道"
              :value-enum="insuranceClaimChannelListForSelect"
              clearable
              style="width: 100%"
            />
          </ProFormItemV2>
          <ProFormItemV2 label="报案数量:">
            <div class="home-top-view-count">{{ claimCount ?? 0 }}人</div>
          </ProFormItemV2>
        </ProForm>
        <Chart />
      </div>
      <ProTableQueryFilterBar @on-reset="reset">
        <template #query>
          <QueryFilterItem>
            <FieldSelect
              v-model="extraParamState.claimChannel"
              placeholder="理赔渠道"
              :value-enum="insuranceClaimChannelListForSelect"
              clearable
              @change="getList()"
            />
          </QueryFilterItem>
          <QueryFilterItem>
            <FieldSelect
              v-model="extraParamState.claimResult"
              placeholder="理赔结果"
              :value-enum="InsuranceClaimResultEnumText"
              clearable
              @change="getList()"
            />
          </QueryFilterItem>
          <QueryFilterItem>
            <SearchInput
              v-model="extraParamState.idNumber"
              style="width: 260px"
              placeholder="身份证号码"
              :showSearchBtn="false"
            >
            </SearchInput>
          </QueryFilterItem>
          <QueryFilterItem>
            <SearchInput
              v-model="extraParamState.laborContractEnterprise"
              style="width: 260px"
              placeholder="劳动合同公司"
              :showSearchBtn="false"
            >
            </SearchInput>
          </QueryFilterItem>
          <QueryFilterItem>
            <SearchInput
              v-model="extraParamState.workEnterprise"
              style="width: 260px"
              placeholder="用工企业"
              @on-click-search="getList"
            >
            </SearchInput>
          </QueryFilterItem>
        </template>
        <template #btn>
          <el-button @click="handleExport()" icon="Download" type="primary">导出</el-button>
          <el-button @click="handleExportPic()" icon="Download" type="primary">导出图片</el-button>
        </template>
      </ProTableQueryFilterBar>
      <ProTableV2 v-bind="proTableProps" :columns="HomeColumns" :operationBtns="operationBtns">
      </ProTableV2>
      <ChunkCell title="待处理"> </ChunkCell>
      <ChunkCell title="数据看板"> </ChunkCell>
    </AppContainer>
  </LoadingLayout>
</template>
<script setup lang="ts">
import {
  ProTableQueryFilterBar,
  OperationBtnType,
  ProTableV2,
  SearchInput,
  LoadingLayout,
  AppContainer,
  QueryFilterItem,
  useTable,
  defineOperationBtns,
  FieldSelect,
  ProForm,
  ProFormItemV2,
  ProFormSelect,
  ProFormDatePicker,
  ProFormText,
  ProFormCol,
  ProFormColItem,
  ProFormInputNumber,
  ProFormTextArea,
  ProFormRadio,
  ChunkCell,
  AppScrollContainer,
} from '@bole-core/components';
import { useInsuranceClaimChannelList, useGlobalEventContext } from '@/hooks';
import * as insuranceClaimServices from '@/services/api/InsuranceClaim';
import { Message, OrderInputType, downloadWithZip } from '@bole-core/core';
import { HomeColumns } from './constants';
import { downloadFile, setOSSLink, toThousand } from '@/utils';
import dayjs from 'dayjs';
import { useQuery } from '@tanstack/vue-query';
import { useInsuranceClaimCount } from './hooks';
import Chart from './components/Chart.vue';
import { InsuranceClaimResultEnumText, InsuranceClaimResultEnum } from '@/constants';
defineOptions({
  name: 'Home',
});
const operationBtns = defineOperationBtns([
  {
    data: {
      enCode: 'checkBtn',
      name: '详情',
    },
    emits: {
      onClick: (role) => goDetail(role),
    },
  },
]);
const { insuranceClaimChannelListForSelect } = useInsuranceClaimChannelList();
const eventContext = useGlobalEventContext();
const BaseState = {
  loading: true,
};
const state = reactive({ ...BaseState });
eventContext.addEvent('updateInsuranceClaim', () => {
  getList(paginationState.pageIndex);
});
onMounted(async () => {
  await getList();
  state.loading = false;
});
const {
  getDataSource: getList,
  proTableProps,
  paginationState,
  extraParamState,
  reset,
} = useTable(
  async ({ pageIndex, pageSize }, extraParamState) => {
    try {
      let params = createParams(pageIndex, pageSize);
      let res = await insuranceClaimServices.getInsuranceClaimPage(params, {
        showLoading: !state.loading,
      });
      return res;
    } catch (error) {}
  },
  {
    defaultExtraParams: {
      orderInput: [{ property: 'createTime', order: OrderInputType.Desc }],
      claimChannel: '',
      laborContractEnterprise: '',
      workEnterprise: '',
      idNumber: '',
      claimResult: '' as any as InsuranceClaimResultEnum,
    },
    columnsRenderProps: {
      insuranceBeginTime: {
        type: 'date',
        format: 'YYYY/MM/DD',
      },
      insuranceEndTime: {
        type: 'date',
        format: 'YYYY/MM/DD',
      },
      reportedTime: {
        type: 'date',
        format: 'YYYY/MM/DD HH:mm:ss',
      },
      accidentTime: {
        type: 'date',
        format: 'YYYY/MM/DD HH:mm:ss',
      },
      lastModificationTime: {
        type: 'date',
        format: 'YYYY-MM-DD HH:mm:ss',
      },
      disabilityRatio: {
        formatter: (row: API.InsuranceClaimListOutput) =>
          row.disabilityRatio == null ? '' : row.disabilityRatio + '%',
      },
      downPaymentAmount: {
        type: 'money',
        formatter: (row: API.InsuranceClaimListOutput) =>
          row.downPaymentAmount == null ? '' : toThousand(row.downPaymentAmount),
      },
      claimResultTime: { type: 'date', format: 'YYYY-MM-DD' },
      claimResult: { type: 'enum', valueEnum: InsuranceClaimResultEnumText },
    },
  }
);
function createParams(pageIndex: number, pageSize: number) {
  let params: API.QueryInsuranceClaimPageInput = {
    pageModel: {
      rows: pageSize,
      page: pageIndex,
      orderInput: extraParamState.orderInput,
    },
    claimChannel: extraParamState.claimChannel,
    laborContractEnterprise: extraParamState.laborContractEnterprise,
    workEnterprise: extraParamState.workEnterprise,
    idNumber: extraParamState.idNumber,
    claimResult: extraParamState.claimResult,
  };
  return params;
}
const router = useRouter();
function goDetail(row: API.InsuranceClaimListOutput) {
  router.push({
    name: 'InsuranceClaimDetail',
    params: {
      id: row.insuranceOrderId,
    },
    query: {
      backRouteName: 'Home',
      insuranceClaimId: row.id,
    },
  });
}
async function handleExport() {
  try {
    if (paginationState.total === 0) {
      Message.warnMessage('没有数据可以导出哦~');
      return;
    }
    let params = createParams(paginationState.pageIndex, paginationState.pageSize);
    let res = await insuranceClaimServices.exportInsuranceClaimList(params, {
      responseType: 'blob',
      getResponse: true,
    });
    if (res) {
      downloadFile(res.data, `理赔导出`, 'xlsx');
    }
  } catch (error) {}
}
async function handleExportPic() {
  try {
    if (paginationState.total === 0) {
      Message.warnMessage('没有数据可以导出哦~');
      return;
    }
    let params = createParams(paginationState.pageIndex, paginationState.pageSize);
    let res = await insuranceClaimServices.getInsuranceClaimAttachmentUrlList(params);
    if (res) {
      if (res.length && res.length > 0) {
        downloadWithZip(
          res.map((item) => ({ data: setOSSLink(item) })),
          '理赔图片导出'
        );
      } else {
        Message.errorMessage('报案数据中未上传图片!');
      }
    }
  } catch (error) {}
}
const { form, claimCount, disabledYear } = useInsuranceClaimCount();
const isLoading = ref(false);
</script>
<style lang="scss" scoped>
@use '@/style/common.scss' as *;
.home-top-view {
  display: flex;
  padding: 20px boleGetCssVar('proTable', 'filter-bar-horizontal-padding') 0;
  border-bottom: 1px var(--el-border-color) var(--el-border-style);
  background-color: #ffffff;
  .home-top-view-count {
    font-size: 30px;
    font-weight: bold;
  }
}
</style>
src/views/Home/components/Chart.vue
File was deleted
src/views/Home/constants/index.ts
File was deleted
src/views/Home/hooks/index.ts
File was deleted
src/views/InsuranceClaim/InsuranceClaimDetail.vue
File was deleted
src/views/InsuranceClaim/hooks/index.ts
File was deleted
src/views/InsuranceClaim/utils/index.ts
File was deleted
src/views/Login/Login.vue
@@ -138,7 +138,7 @@
import closeEye from '@/assets/svgIcons/close_eye.svg?component';
import openEye from '@/assets/svgIcons/close_eye.svg?component';
// import { useSettingStoreHook } from '@/store/modules/settings';
import { getAppSetting } from '@config/config';
import Config from '@config/config';
// const boleSetting = useSettingStoreHook();
const ctx = useProvideContext();