import React, { Fragment, useCallback, useEffect, useMemo, useRef, useState } from 'react'; import { Title, TableStyle, FormWrapper, TableWrapper, TableActionButton, TableDetailRow, TableDetailContainer, TableDetailFlex, TableDetailColumn, DetailTableInfo, } from '../../styles/Components'; import { withAuth } from '../../hooks/hook'; import { authType, modalTypes, } from '../../assets/data'; import { INITIAL_PAGE_LIMIT, INITIAL_PAGE_SIZE } from '../../assets/data/adminConstants'; import { useTranslation } from 'react-i18next'; import { DownloadProgress, DynamicModal, ExcelDownButton, Pagination, TopButton, ViewTableInfo, } from '../../components/common'; import { TableSkeleton } from '../../components/Skeleton/TableSkeleton'; import BusinessLogSearchBar, { useBusinessLogSearch } from '../../components/ServiceManage/searchBar/BusinessLogSearchBar'; import styled from 'styled-components'; import FrontPagination from '../../components/common/Pagination/FrontPagination'; import Loading from '../../components/common/Loading'; import CircularProgress from '../../components/common/CircularProgress'; const BusinessLogView = () => { const token = sessionStorage.getItem('token'); const { t } = useTranslation(); const tableRef = useRef(null); const [alertMsg, setAlertMsg] = useState(''); const [expandedRows, setExpandedRows] = useState({}); const [downloadState, setDownloadState] = useState({ loading: false, progress: 0 }); const [currentPage, setCurrentPage] = useState(1); const [itemsPerPage, setItemsPerPage] = useState(500); const [displayData, setDisplayData] = useState([]); const { searchParams, loading: dataLoading, data: dataList, handleSearch, handleReset, handlePageChange, handleOrderByChange, updateSearchParams } = useBusinessLogSearch(token, 500, setAlertMsg); const handlePageSizeChange = (newSize) => { setItemsPerPage(newSize); setCurrentPage(1); }; const handleClientPageChange = useCallback((slicedData) => { setDisplayData(slicedData); }, []); useEffect(() => { setCurrentPage(1); if (dataList?.generic_list && dataList.generic_list.length > 0) { const initialData = dataList.generic_list.slice(0, itemsPerPage); setDisplayData(initialData); } else { setDisplayData([]); } }, [dataList, itemsPerPage]); const toggleRowExpand = (index) => { setExpandedRows(prev => ({ ...prev, [index]: !prev[index] })); }; const tableHeaders = useMemo(() => { return [ { id: 'logTime', label: '일시', width: '120px' }, { id: 'userGuid', label: 'GUID', width: '200px' }, { id: 'accountId', label: 'account ID', width: '100px' }, { id: 'userNickname', label: '아바타명', width: '150px' }, { id: 'tranId', label: '트랜잭션 ID', width: '200px' }, { id: 'action', label: '액션', width: '150px' }, { id: 'domain', label: '도메인', width: '120px' }, { id: 'details', label: '상세 정보', width: '100px' } ]; }, []); const renderActorData = (actor) => { if (!actor || typeof actor !== 'object') return <>; return ( Actor 정보 {Object.entries(actor).map(([key, value]) => ( {key} {typeof value === 'object' && value !== null ? JSON.stringify(value) : String(value) } ))} ); }; const renderInfosData = (infos) => { if (!infos || !Array.isArray(infos) || infos.length === 0) return <>; return ( Infos 정보 {infos.map((info, infoIndex) => ( {Object.entries(info).map(([key, value]) => ( {key} {typeof value === 'object' && value !== null ? JSON.stringify(value) : Array.isArray(value) ? value.join(', ') : String(value) } ))} ))} ); }; const handleModalSubmit = async (type, param = null) => { switch (type) { case "warning": setAlertMsg('') break; } } return ( <> 비즈니스 로그 조회 { if (executeSearch) { handleSearch(newParams); } else { updateSearchParams(newParams); } }} onReset={handleReset} /> {downloadState.loading && ( )} {dataLoading ? : <> {tableHeaders.map(header => ( {header.label} ))} {displayData?.map((item, index) => ( {item.logTime} {item.userGuid} {item.accountId} {item.userNickname} {item.tranId} {item.action} {item.domain === 'None' ? '-' : item.domain} toggleRowExpand(index)}> {expandedRows[index] ? '접기' : '상세보기'} {expandedRows[index] && ( {renderActorData(item.header?.Actor)} {renderInfosData(item.body?.Infos)} )} ))} {dataList?.generic_list && } } handleModalSubmit('warning')} /> ); }; export default withAuth(authType.businessLogRead)(BusinessLogView); const DownloadContainer = styled.div` display: flex; align-items: center; gap: 10px; `; const CircularProgressWrapper = styled.div` display: flex; align-items: center; justify-content: center; `;