167 lines
6.4 KiB
TypeScript
167 lines
6.4 KiB
TypeScript
import { useState, useMemo } from "react";
|
|
|
|
import SearchForm from "@/components/module/SearchForm";
|
|
// import { DataGrid } from "@rsone/components";
|
|
import DataGrid from "@/components/module/DataGrid";
|
|
import SubmitButton from "@/components/button/SumitButton";
|
|
import SaveButton from "@/components/button/SaveButton";
|
|
import LastYearDataButton from "@/components/button/LastYearDataButton";
|
|
import SubmitExceptionButton from "@/components/button/SubmitExceptionButton";
|
|
import { LoadingWithAnimation } from "@common/components";
|
|
|
|
import { useAlertStore } from "@/shared/lib";
|
|
import { statisticsInputAPi } from "@/entities/statistics/api/statistics-input-service";
|
|
import type { SearchFormValues } from "@/components/type/SearchForm.type";
|
|
import type {
|
|
SewerageSupplyRateItem,
|
|
SewerageSupplyRateRequestParams,
|
|
} from "@/entities/statistics/model/statistics-input-interface";
|
|
import { SeweragePenetrationRateInpColumn } from "@/components/util/column/input/SeweragePenetrationRateInpColumn";
|
|
import { toGridRows } from "@/components/util/grid/gridFunction";
|
|
|
|
function getSewerageSupplyRateParams(
|
|
values: SearchFormValues,
|
|
overrides?: { yr?: string; demoYr?: string; mode?: string }
|
|
): SewerageSupplyRateRequestParams {
|
|
return {
|
|
sido: values.sido,
|
|
gugun: values.gugun === 'ALL' ? '' : values.gugun,
|
|
bsnmCd: values.bsnmCd,
|
|
yr: overrides?.yr ?? values.year,
|
|
demoYr: overrides?.demoYr ?? values.year,
|
|
...(overrides?.mode && { mode: overrides.mode }),
|
|
};
|
|
}
|
|
|
|
// 하수도 통계 관리 > 01. 하수도 보급률
|
|
const SeweragePenetrationRateInp = () => {
|
|
const { setMessage: alert } = useAlertStore((state) => state);
|
|
const [rowData, setRowData] = useState<Record<string, string | number>[]>([]);
|
|
const [isLoading, setIsLoading] = useState<boolean>(false);
|
|
const [searchValues, setSearchValues] = useState<SearchFormValues | null>(null);
|
|
const [isEnterable, setIsEnterable] = useState<boolean>(true);
|
|
const [lastSearchedYear, setLastSearchedYear] = useState<string | null>(null);
|
|
|
|
|
|
// 최상위 관리자일땐 모든 상황에서 edit 가능하게 수정 필요.
|
|
const columnInfo = useMemo(() => {
|
|
const { columns, columnLayout } = SeweragePenetrationRateInpColumn;
|
|
return {
|
|
columnLayout,
|
|
columns: isEnterable
|
|
? columns
|
|
: columns.map((col) => ({ ...col, editable: false as const })),
|
|
};
|
|
}, [isEnterable]);
|
|
|
|
const handleReset = () => {
|
|
setRowData([]);
|
|
setLastSearchedYear(null);
|
|
};
|
|
|
|
const fetchSewerageSupplyRate = async (params: SewerageSupplyRateRequestParams) => {
|
|
try {
|
|
setIsLoading(true);
|
|
const response = await statisticsInputAPi.getSewerageSupplyRateList(params);
|
|
if (response.status === 'success' && response.data) {
|
|
const convertedData: SewerageSupplyRateItem[] = response.data.sewerageSupplyRateList.map((d) => ({
|
|
...d,
|
|
speclCntrplnAr: d.speclCntrplnAr === '' || d.speclCntrplnAr === null ? '해당없음' : d.speclCntrplnAr,
|
|
}));
|
|
|
|
setRowData(toGridRows(convertedData));
|
|
} else {
|
|
alert(response.message);
|
|
}
|
|
} catch {
|
|
alert('데이터 조회 중 오류가 발생했습니다.');
|
|
setRowData([]);
|
|
} finally {
|
|
setIsLoading(false);
|
|
}
|
|
};
|
|
|
|
const handleSearch = async (values: SearchFormValues) => {
|
|
if (values.sido === '' || values.sido === 'ALL') {
|
|
alert('시도를 선택해주세요.');
|
|
return;
|
|
}
|
|
|
|
try {
|
|
const response = await statisticsInputAPi.checkInputPeriod(values.year || '');
|
|
|
|
if (response.status === 'success') {
|
|
setIsEnterable(response.data);
|
|
setLastSearchedYear(values.year || null);
|
|
|
|
await fetchSewerageSupplyRate(getSewerageSupplyRateParams(values));
|
|
} else {
|
|
alert(response.message);
|
|
}
|
|
} catch {
|
|
alert('데이터 조회 중 오류가 발생했습니다.');
|
|
}
|
|
};
|
|
|
|
const SubmitExceptionFunc = () => {
|
|
// 예외 제출 로직
|
|
};
|
|
|
|
const getLastYearDataFunc = async (values: SearchFormValues) => {
|
|
if (values.sido === '' || values.sido === 'ALL') {
|
|
alert('시도를 선택해주세요.');
|
|
return;
|
|
}
|
|
|
|
// 실제 조회된 연도가 없으면 실행 불가
|
|
if (!lastSearchedYear) {
|
|
alert('먼저 데이터를 조회해주세요.');
|
|
return;
|
|
}
|
|
|
|
await fetchSewerageSupplyRate(getSewerageSupplyRateParams(values, { mode: 'PRE' }));
|
|
};
|
|
|
|
const submitFunc = () => {
|
|
// 제출 로직
|
|
};
|
|
|
|
const saveFunc = () => {
|
|
// 저장 로직
|
|
};
|
|
|
|
return (
|
|
<div className="relative">
|
|
<SearchForm onSubmit={handleSearch} onReset={handleReset} onValuesChange={setSearchValues} />
|
|
{rowData.length > 0 &&
|
|
<div className="card !py-0">
|
|
<div className="flex justify-end items-center gap-[0.6rem] mx-[0.6rem]">
|
|
{isEnterable && <SubmitExceptionButton SubmitExceptionFunc={SubmitExceptionFunc} />}
|
|
{isEnterable && <LastYearDataButton getLastYearDataFunc={() => getLastYearDataFunc(searchValues ?? {})} />}
|
|
{isEnterable && <SubmitButton submitFunc={submitFunc} />}
|
|
{
|
|
// 최고 관리자일땐 저장 가능하게
|
|
<SaveButton saveFunc={saveFunc} />
|
|
}
|
|
</div>
|
|
</div>
|
|
}
|
|
{isLoading && <div className="absolute inset-0 z-50 [data-theme='black']:bg-transparent rounded-lg p-10 flex justify-center items-center">
|
|
<div className="relative size-[5rem]">
|
|
<LoadingWithAnimation color="primary" />
|
|
</div>
|
|
</div>}
|
|
<DataGrid
|
|
key={isEnterable ? 'enterable' : 'readonly'}
|
|
columnInfo={columnInfo}
|
|
isExcelImport={(rowData.length > 0) && isEnterable}
|
|
rowStartNum={3}
|
|
fixedColumns={1}
|
|
rowData={rowData}
|
|
setRowData={setRowData}
|
|
/>
|
|
</div>
|
|
);
|
|
};
|
|
|
|
export default SeweragePenetrationRateInp; |