Files
finance-master/apps/finance/src/views/statistics/common/useMonthReport.ts
chenghuan 5c39bd4113
Some checks failed
Close stale issues / stale (push) Has been cancelled
Lock Threads / action (push) Has been cancelled
Issue Close Require / close-issues (push) Has been cancelled
CodeQL / Analyze (javascript-typescript) (push) Has been cancelled
feat(报表): 重构报表模块并添加下载功能
重构各报表页面,提取公共逻辑到useMonthReport和MonthReportView组件
添加报表下载功能,支持单月下载和全年下载
统一各报表的API调用方式和数据处理逻辑
优化代码结构,减少重复代码
2026-01-22 18:29:53 +08:00

68 lines
2.1 KiB
TypeScript

import type { Dayjs } from 'dayjs';
import { ref } from 'vue';
import { downloadFileFromBlobPart } from '@vben/utils';
import dayjs from 'dayjs';
export function useMonthReport<T>(options: {
downloadFile: (p: { month: string; year: number }) => Promise<any>;
fetchMonth: (p: { month: string; year: number }) => Promise<any>;
fileNameBuilder?: (year: number, month: string) => string;
normalize: (resp: any) => T;
}) {
const year = ref<Dayjs>(dayjs());
const disabledDate = (date: Dayjs) => date.year() > dayjs().year();
const list = ref<Array<null | T>>([]);
const loading = ref<boolean>(false);
const getList = async () => {
loading.value = true;
const monthList =
year.value.year() === dayjs().year()
? Array.from({ length: dayjs().month() + 1 }, (_, i) => (i + 1).toString().padStart(2, '0'))
: Array.from({ length: 12 }, (_, i) => (i + 1).toString().padStart(2, '0'));
list.value = Array.from({ length: monthList.length }, () => null);
let pending = monthList.length;
monthList.forEach((month, idx) => {
options
.fetchMonth({
year: year.value.year(),
month,
})
.then((resp) => {
list.value[idx] = options.normalize(resp) as any;
})
.finally(() => {
pending -= 1;
if (pending === 0) {
loading.value = false;
}
});
});
};
// 下载报表
const downloadReport = async (index: number) => {
const month = index > 8 ? `${index + 1}` : `0${index + 1}`;
const filename =
options.fileNameBuilder?.(year.value.year(), month) ||
`报表_${year.value.year()}${month}月_文件.xlsx`;
const Blob = await options.downloadFile({
month,
year: year.value.year(),
});
downloadFileFromBlobPart({
source: Blob,
fileName: filename,
});
};
const downloadAllReport = async () => {
await Promise.all(list.value.map((_, index) => downloadReport(index)));
};
return { year, disabledDate, list, loading, getList, downloadReport, downloadAllReport };
}