Files
sam-react-prod/src/lib/utils/export.ts
kent e998cfa2f8 fix(WEB): E2E 테스트 버그 수정 (Phase 1-3)
Phase 1 (Critical):
- 매출관리 계정과목 일괄변경 함수 추가 (bulkUpdateAccountCode)
- 근태관리 사유 등록 페이지 생성 (/hr/documents/new)

Phase 2 (High):
- 근태 등록 서버 에러 수정 (json_details 유효성 검증)
- 직원 등록 서버 에러 수정 (snake_case 필드명 변환)
- 근태관리 엑셀 다운로드 구현 (exportAttendanceExcel)

Phase 3 (Medium):
- 급여관리 엑셀 다운로드 구현 (exportSalaryExcel)
- 급여관리 지급항목 인라인 수정 기능 구현
2026-01-15 18:36:10 +09:00

108 lines
3.0 KiB
TypeScript

/**
* 엑셀 내보내기 유틸리티
*
* 여러 모듈에서 공통으로 사용:
* - 근태관리 (AttendanceManagement)
* - 급여관리 (SalaryManagement)
* - 기타 데이터 내보내기가 필요한 모듈
*/
/**
* 엑셀 파일 다운로드 처리
*
* API 응답(Blob)을 받아 파일 다운로드를 트리거합니다.
*
* @param response - fetch Response 객체 (Content-Type: application/vnd.openxmlformats-officedocument.spreadsheetml.sheet)
* @param filename - 저장할 파일명 (확장자 포함)
*/
export async function downloadExcelFromResponse(
response: Response,
filename: string
): Promise<void> {
if (!response.ok) {
throw new Error(`엑셀 다운로드 실패: ${response.status}`);
}
const blob = await response.blob();
downloadBlob(blob, filename);
}
/**
* Blob을 파일로 다운로드
*
* @param blob - 다운로드할 Blob 데이터
* @param filename - 저장할 파일명
*/
export function downloadBlob(blob: Blob, filename: string): void {
const url = URL.createObjectURL(blob);
const link = document.createElement('a');
link.href = url;
link.download = filename;
document.body.appendChild(link);
link.click();
document.body.removeChild(link);
URL.revokeObjectURL(url);
}
/**
* 현재 날짜/시간을 포함한 파일명 생성
*
* @param prefix - 파일명 접두사 (예: '근태현황', '급여명세')
* @param extension - 파일 확장자 (기본값: 'xlsx')
* @returns 생성된 파일명 (예: '근태현황_20250115_143052.xlsx')
*/
export function generateExportFilename(
prefix: string,
extension: string = 'xlsx'
): string {
const now = new Date();
const dateStr = now.toISOString().slice(0, 10).replace(/-/g, '');
const timeStr = now.toTimeString().slice(0, 8).replace(/:/g, '');
return `${prefix}_${dateStr}_${timeStr}.${extension}`;
}
/**
* 엑셀 내보내기 API 호출을 위한 fetch 옵션 생성
*
* @param token - 인증 토큰
* @param params - 쿼리 파라미터 (선택)
* @returns fetch 옵션 객체
*/
export function createExportFetchOptions(
token: string,
params?: Record<string, string | number | boolean | undefined>
): RequestInit {
return {
method: 'GET',
headers: {
Authorization: `Bearer ${token}`,
Accept: 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet',
'X-API-KEY': process.env.NEXT_PUBLIC_API_KEY || '',
},
cache: 'no-store',
};
}
/**
* 쿼리 파라미터 문자열 생성
*
* @param params - 쿼리 파라미터 객체
* @returns URL 쿼리 문자열 (예: '?year=2025&month=1')
*/
export function buildExportQueryString(
params?: Record<string, string | number | boolean | undefined>
): string {
if (!params) return '';
const searchParams = new URLSearchParams();
Object.entries(params).forEach(([key, value]) => {
if (value !== undefined && value !== null && value !== '') {
searchParams.set(key, String(value));
}
});
const queryString = searchParams.toString();
return queryString ? `?${queryString}` : '';
}