feat(@vben/web-antd): add finance settlement page module

This commit is contained in:
2026-03-04 15:52:25 +08:00
parent 15d4272d1f
commit 4690ccdd9d
21 changed files with 1705 additions and 0 deletions

View File

@@ -0,0 +1,201 @@
import type { FinanceSettlementDetailStateMap } from '../types';
/**
* 文件职责:到账查询页面状态与动作编排。
*/
import type {
FinanceSettlementAccountDto,
FinanceSettlementListItemDto,
FinanceSettlementStatsDto,
} from '#/api/finance';
import type { StoreListItemDto } from '#/api/store';
import { computed, onActivated, onMounted, reactive, ref, watch } from 'vue';
import { useAccessStore } from '@vben/stores';
import {
createDefaultFilters,
DEFAULT_STATS,
FINANCE_SETTLEMENT_EXPORT_PERMISSION,
FINANCE_SETTLEMENT_VIEW_PERMISSION,
} from './settlement-page/constants';
import { createDataActions } from './settlement-page/data-actions';
import { createDetailActions } from './settlement-page/detail-actions';
import { createExportActions } from './settlement-page/export-actions';
import { createFilterActions } from './settlement-page/filter-actions';
/** 创建到账查询页面组合状态。 */
export function useFinanceSettlementPage() {
const accessStore = useAccessStore();
const stores = ref<StoreListItemDto[]>([]);
const selectedStoreId = ref('');
const isStoreLoading = ref(false);
const filters = reactive(createDefaultFilters());
const rows = ref<FinanceSettlementListItemDto[]>([]);
const pagination = reactive({
page: 1,
pageSize: 20,
total: 0,
});
const stats = reactive<FinanceSettlementStatsDto>({ ...DEFAULT_STATS });
const account = ref<FinanceSettlementAccountDto | null>(null);
const isListLoading = ref(false);
const isStatsLoading = ref(false);
const isAccountLoading = ref(false);
const isExporting = ref(false);
const expandedRowKeys = ref<string[]>([]);
const detailStates = reactive<FinanceSettlementDetailStateMap>({});
const storeOptions = computed(() =>
stores.value.map((item) => ({
label: item.name,
value: item.id,
})),
);
const accessCodeSet = computed(
() => new Set((accessStore.accessCodes ?? []).map(String)),
);
const canView = computed(() =>
accessCodeSet.value.has(FINANCE_SETTLEMENT_VIEW_PERMISSION),
);
const canExport = computed(() =>
accessCodeSet.value.has(FINANCE_SETTLEMENT_EXPORT_PERMISSION),
);
const { clearPageData, loadAccount, loadPageData, loadStores, resetStats } =
createDataActions({
stores,
selectedStoreId,
filters,
rows,
pagination,
stats,
account,
isStoreLoading,
isListLoading,
isStatsLoading,
isAccountLoading,
});
const {
handlePageChange,
handleSearch,
setChannel,
setEndDate,
setStartDate,
} = createFilterActions({
filters,
pagination,
loadPageData,
});
const { clearDetailStates, handleExpand } = createDetailActions({
selectedStoreId,
expandedRowKeys,
detailStates,
});
const { handleExport } = createExportActions({
canExport,
selectedStoreId,
filters,
isExporting,
});
function setSelectedStoreId(value: string) {
selectedStoreId.value = value;
}
function clearByPermission() {
stores.value = [];
selectedStoreId.value = '';
account.value = null;
clearPageData();
clearDetailStates();
resetStats();
}
watch(selectedStoreId, async (storeId) => {
clearDetailStates();
if (!storeId) {
clearPageData();
return;
}
pagination.page = 1;
await loadPageData();
});
watch(canView, async (value, oldValue) => {
if (value === oldValue) {
return;
}
if (!value) {
clearByPermission();
return;
}
await Promise.all([loadStores(), loadAccount()]);
});
onMounted(async () => {
if (!canView.value) {
clearByPermission();
return;
}
await Promise.all([loadStores(), loadAccount()]);
});
onActivated(() => {
if (!canView.value) {
return;
}
if (stores.value.length === 0 || !selectedStoreId.value) {
void loadStores();
}
if (!account.value && !isAccountLoading.value) {
void loadAccount();
}
});
return {
account,
canExport,
canView,
detailStates,
expandedRowKeys,
filters,
handleExpand,
handleExport,
handlePageChange,
handleSearch,
isAccountLoading,
isExporting,
isListLoading,
isStatsLoading,
isStoreLoading,
pagination,
rows,
selectedStoreId,
setChannel,
setEndDate,
setSelectedStoreId,
setStartDate,
stats,
storeOptions,
};
}