diff --git a/src/apis/Log.js b/src/apis/Log.js index 62254f8..02ed93f 100644 --- a/src/apis/Log.js +++ b/src/apis/Log.js @@ -127,4 +127,80 @@ export const GameCurrencyDetailLogExport = async (token, params, fileName) => { throw new Error('GameCurrencyDetailLogExport Error', e); } } +}; + +export const getItemDetailList = async (token, searchType, searchData, tranId, logAction, itemLargeType, itemSmallType, countDeltaType, startDate, endDate, order, size, currentPage) => { + try { + const response = await Axios.get(`/api/v1/log/item/detail/list?search_type=${searchType}&search_data=${searchData}&tran_id=${tranId} + &log_action=${logAction}&item_large_type=${itemLargeType}&item_small_type=${itemSmallType}&count_delta_type=${countDeltaType}&start_dt=${startDate}&end_dt=${endDate} + &orderby=${order}&page_no=${currentPage}&page_size=${size}`, { + headers: { + Authorization: `Bearer ${token}`, + 'Content-Type': 'application/json', + }, + }); + + return response.data; + } catch (error) { + console.error('getItemDetailList API error:', error); + throw error; + } +}; + +export const GameItemDetailLogExport = async (token, params, fileName) => { + try { + console.log(params); + await Axios.post(`/api/v1/log/item/detail/excel-export`, params, { + headers: { Authorization: `Bearer ${token}` }, + responseType: 'blob', + timeout: 300000 + }).then(response => { + + responseFileDownload(response, { + defaultFileName: fileName + }); + }); + } catch (e) { + if (e instanceof Error) { + throw new Error('GameItemDetailLogExport Error', e); + } + } +}; + +export const getCurrencyItemList = async (token, searchType, searchData, tranId, logAction, currencyType, amountDeltaType, startDate, endDate, order, size, currentPage) => { + try { + const response = await Axios.get(`/api/v1/log/currency-item/list?search_type=${searchType}&search_data=${searchData}&tran_id=${tranId} + &log_action=${logAction}¤cy_type=${currencyType}&amount_delta_type=${amountDeltaType}&start_dt=${startDate}&end_dt=${endDate} + &orderby=${order}&page_no=${currentPage}&page_size=${size}`, { + headers: { + Authorization: `Bearer ${token}`, + 'Content-Type': 'application/json', + }, + }); + + return response.data; + } catch (error) { + console.error('getItemDetailList API error:', error); + throw error; + } +}; + +export const GameCurrencyItemLogExport = async (token, params, fileName) => { + try { + console.log(params); + await Axios.post(`/api/v1/log/currency-item/excel-export`, params, { + headers: { Authorization: `Bearer ${token}` }, + responseType: 'blob', + timeout: 300000 + }).then(response => { + + responseFileDownload(response, { + defaultFileName: fileName + }); + }); + } catch (e) { + if (e instanceof Error) { + throw new Error('GameCurrencyItemLogExport Error', e); + } + } }; \ No newline at end of file diff --git a/src/assets/data/adminConstants.js b/src/assets/data/adminConstants.js index 90658f4..b1cee6a 100644 --- a/src/assets/data/adminConstants.js +++ b/src/assets/data/adminConstants.js @@ -11,6 +11,7 @@ export const IMAGE_MAX_SIZE = 5242880; export const STORAGE_MAIL_COPY = 'copyMailData'; export const STORAGE_BUSINESS_LOG_SEARCH = 'businessLogSearchParam'; export const STORAGE_GAME_LOG_CURRENCY_SEARCH = 'gameLogCurrencySearchParam'; +export const STORAGE_GAME_LOG_ITEM_SEARCH = 'gameLogItemSearchParam'; export const LOG_ACTION_FAIL_CALIUM_ECHO = 'FailCaliumEchoSystem'; export const BATTLE_EVENT_OPERATION_TIME_WAIT_SECONDS = 300; diff --git a/src/assets/data/options.js b/src/assets/data/options.js index f2ebabf..2abdaa4 100644 --- a/src/assets/data/options.js +++ b/src/assets/data/options.js @@ -6,7 +6,8 @@ export const languageType = [ export const TabGameLogList = [ { value: 'CURRENCY', name: '재화 로그' }, - // { value: 'ITEM', name: '아이템 로그' }, + { value: 'ITEM', name: '아이템 로그' }, + { value: 'CURRENCYITEM', name: '재화(아이템) 로그' }, // { value: 'TRADE', name: '거래 로그' }, ]; @@ -95,6 +96,12 @@ export const landAuctionStatus = [ { value: 'FAIL', name: '실패' }, ]; +export const questStatus = [ + { value: 'WAIT', name: '미완료' }, + { value: 'COMPLETE', name: '완료' }, + { value: 'RUNNING', name: '진행중' }, +]; + export const currencyItemCode = [ { value: '19010001', name: '골드' }, { value: '19010002', name: '사파이어' }, @@ -225,6 +232,24 @@ export const amountDeltaType = [ {value: 'None', name: '' }, ] +export const countDeltaType = [ + {value: 'Acquire', name: '획득' }, + {value: 'Consume', name: '소모' } +] + +export const itemTypeLarge = [ + {value: 'TOOL', name: '도구' }, + {value: 'EXPENDABLE', name: '소모품' }, + {value: 'TICKET', name: '티켓' }, + {value: 'RAND_BOX', name: '랜덤 박스' }, + {value: 'CLOTH', name: '의상' }, + {value: 'AVATAR', name: '아바타' }, + {value: 'PROP', name: '프랍(오브젝트)' }, + {value: 'TATTOO', name: '타투' }, + {value: 'CURRENCY', name: '재화' }, + {value: 'SET_BOX', name: '세트 박스' } +] + export const battleEventStatus = [ { value: 'ALL', name: '전체' }, { value: 'WAIT', name: '대기' }, diff --git a/src/components/DataManage/CurrencyItemLogContent.js b/src/components/DataManage/CurrencyItemLogContent.js new file mode 100644 index 0000000..de149fe --- /dev/null +++ b/src/components/DataManage/CurrencyItemLogContent.js @@ -0,0 +1,167 @@ +import React, { Fragment, useEffect, useMemo, useRef, useState } from 'react'; + +import styled from 'styled-components'; +import { + CircularProgressWrapper, + FormWrapper, + TableStyle, + TableWrapper, +} from '../../styles/Components'; +import { amountDeltaType, CurrencyType } from '../../assets/data'; +import { useTranslation } from 'react-i18next'; +import { numberFormatter } from '../../utils'; +import { TableSkeleton } from '../Skeleton/TableSkeleton'; +import { CurrencyItemLogSearchBar, useCurrencyItemLogSearch } from '../searchBar'; +import { TopButton, ViewTableInfo } from '../common'; +import Pagination from '../common/Pagination/Pagination'; +import { + INITIAL_PAGE_LIMIT, + STORAGE_BUSINESS_LOG_SEARCH, + STORAGE_GAME_LOG_CURRENCY_SEARCH, +} from '../../assets/data/adminConstants'; +import ExcelExportButton from '../common/button/ExcelExportButton'; +import CircularProgress from '../common/CircularProgress'; +import { GameCurrencyItemLogExport } from '../../apis'; + +const CurrencyItemLogContent = ({ active }) => { + const { t } = useTranslation(); + const token = sessionStorage.getItem('token'); + const tableRef = useRef(null); + const [downloadState, setDownloadState] = useState({ + loading: false, + progress: 0 + }); + + const { + searchParams, + loading: dataLoading, + data: dataList, + handleSearch, + handleReset, + handlePageChange, + handleOrderByChange, + handlePageSizeChange, + updateSearchParams + } = useCurrencyItemLogSearch(token, 500); + + useEffect(() => { + if(active) { + // 세션 스토리지에서 복사된 메일 데이터 가져오기 + const paramsData = sessionStorage.getItem(STORAGE_GAME_LOG_CURRENCY_SEARCH); + + if (paramsData) { + const searchData = JSON.parse(paramsData); + + handleSearch({ + start_dt: new Date(searchData.start_dt), + end_dt: new Date(searchData.end_dt), + search_data: searchData.guid + }); + + // 사용 후 세션 스토리지 데이터 삭제 + sessionStorage.removeItem(STORAGE_GAME_LOG_CURRENCY_SEARCH); + } + } + }, [active]); + + const tableHeaders = useMemo(() => { + return [ + // { id: 'logDay', label: '일자', width: '120px' }, + { id: 'logTime', label: '일시', width: '150px' }, + { id: 'accountId', label: 'account ID', width: '80px' }, + { id: 'userGuid', label: 'GUID', width: '200px' }, + { id: 'userNickname', label: '아바타명', width: '150px' }, + { id: 'tranId', label: '트랜잭션 ID', width: '200px' }, + { id: 'action', label: '액션', width: '150px' }, + { id: 'currencyType', label: '재화종류', width: '120px' }, + { id: 'amountDeltaType', label: '증감유형', width: '120px' }, + { id: 'deltaAmount', label: '수량', width: '80px' }, + // { id: 'deltaAmount', label: '수량원본', width: '120px' }, + { id: 'currencyAmount', label: '잔량', width: '80px' }, + { id: 'itemId', label: '아이템ID', width: '150px' }, + ]; + }, []); + + if(!active) return null; + + return ( + <> + + { + if (executeSearch) { + handleSearch(newParams); + } else { + updateSearchParams(newParams); + } + }} + onReset={handleReset} + /> + + + + {downloadState.loading && ( + + + + )} + + {dataLoading ? : + <> + + + + + {tableHeaders.map(header => ( + {header.label} + ))} + + + + {dataList?.currency_item_list?.map((item, index) => ( + + + {item.logTime} + {item.accountId} + {item.userGuid} + {item.userNickname} + {item.tranId} + {item.action} + {CurrencyType.find(data => data.value === item.currencyType)?.name} + {amountDeltaType.find(data => data.value === item.amountDeltaType)?.name} + {numberFormatter.formatCurrency(item.deltaAmount)} + {numberFormatter.formatCurrency(item.currencyAmount)} + {item.itemIDs} + + + ))} + + + + {dataList?.currency_item_list && + + } + + + } + + ); +}; +export default CurrencyItemLogContent; \ No newline at end of file diff --git a/src/components/DataManage/ItemLogContent.js b/src/components/DataManage/ItemLogContent.js new file mode 100644 index 0000000..677f9d7 --- /dev/null +++ b/src/components/DataManage/ItemLogContent.js @@ -0,0 +1,170 @@ +import React, { Fragment, useEffect, useMemo, useRef, useState } from 'react'; + +import styled from 'styled-components'; +import { + CircularProgressWrapper, + FormWrapper, + TableStyle, + TableWrapper, +} from '../../styles/Components'; +import { amountDeltaType, CurrencyType } from '../../assets/data'; +import { useTranslation } from 'react-i18next'; +import { numberFormatter } from '../../utils'; +import { TableSkeleton } from '../Skeleton/TableSkeleton'; +import { ItemLogSearchBar, useItemLogSearch } from '../searchBar'; +import { TopButton, ViewTableInfo } from '../common'; +import Pagination from '../common/Pagination/Pagination'; +import { + INITIAL_PAGE_LIMIT, + STORAGE_BUSINESS_LOG_SEARCH, + STORAGE_GAME_LOG_CURRENCY_SEARCH, STORAGE_GAME_LOG_ITEM_SEARCH, +} from '../../assets/data/adminConstants'; +import ExcelExportButton from '../common/button/ExcelExportButton'; +import CircularProgress from '../common/CircularProgress'; +import { countDeltaType, itemTypeLarge } from '../../assets/data/options'; + +const CurrencyLogContent = ({ active }) => { + const { t } = useTranslation(); + const token = sessionStorage.getItem('token'); + const tableRef = useRef(null); + const [downloadState, setDownloadState] = useState({ + loading: false, + progress: 0 + }); + + const { + searchParams, + loading: dataLoading, + data: dataList, + handleSearch, + handleReset, + handlePageChange, + handleOrderByChange, + handlePageSizeChange, + updateSearchParams + } = useItemLogSearch(token, 500); + + useEffect(() => { + if(active) { + // 세션 스토리지에서 복사된 메일 데이터 가져오기 + const paramsData = sessionStorage.getItem(STORAGE_GAME_LOG_ITEM_SEARCH); + + if (paramsData) { + const searchData = JSON.parse(paramsData); + + handleSearch({ + start_dt: new Date(searchData.start_dt), + end_dt: new Date(searchData.end_dt), + search_data: searchData.guid + }); + + // 사용 후 세션 스토리지 데이터 삭제 + sessionStorage.removeItem(STORAGE_GAME_LOG_ITEM_SEARCH); + } + } + }, [active]); + + const tableHeaders = useMemo(() => { + return [ + // { id: 'logDay', label: '일자', width: '120px' }, + { id: 'logTime', label: '일시', width: '150px' }, + { id: 'accountId', label: 'account ID', width: '80px' }, + { id: 'userGuid', label: 'GUID', width: '200px' }, + { id: 'userNickname', label: '아바타명', width: '150px' }, + { id: 'tranId', label: '트랜잭션 ID', width: '200px' }, + { id: 'action', label: '액션', width: '120px' }, + { id: 'itemId', label: '아이템ID', width: '80px' }, + { id: 'itemName', label: '아이템명', width: '150px' }, + { id: 'itemTypeLarge', label: 'LargeType', width: '100px' }, + { id: 'itemTypeSmall', label: 'SmallType', width: '100px' }, + { id: 'countDeltaType', label: '증감유형', width: '80px' }, + { id: 'deltaCount', label: '수량', width: '80px' }, + { id: 'stackCount', label: '총량', width: '80px' }, + ]; + }, []); + + if(!active) return null; + + return ( + <> + + { + if (executeSearch) { + handleSearch(newParams); + } else { + updateSearchParams(newParams); + } + }} + onReset={handleReset} + /> + + + + {downloadState.loading && ( + + + + )} + + {dataLoading ? : + <> + + + + + {tableHeaders.map(header => ( + {header.label} + ))} + + + + {dataList?.item_detail_list?.map((item, index) => ( + + + {item.logTime} + {item.accountId} + {item.userGuid} + {item.userNickname} + {item.tranId} + {item.action} + {item.itemId} + {item.itemName} + {itemTypeLarge.find(data => data.value === item.itemTypeLarge)?.name || item.itemTypeLarge} + {item.itemTypeSmall} + {countDeltaType.find(data => data.value === item.countDeltaType)?.name || item.countDeltaType} + {numberFormatter.formatCurrency(item.deltaCount)} + {numberFormatter.formatCurrency(item.stackCount)} + + + ))} + + + + {dataList?.item_detail_list && + + } + + + } + + ); +}; +export default CurrencyLogContent; \ No newline at end of file diff --git a/src/components/common/Header/Profile.js b/src/components/common/Header/Profile.js index 2afd2aa..13357f1 100644 --- a/src/components/common/Header/Profile.js +++ b/src/components/common/Header/Profile.js @@ -145,7 +145,6 @@ const ProfileContainer = styled.div` `; const StyledAvatar = styled(Avatar)` - background-color: #1677ff; `; const StyledUsername = styled(Text)` diff --git a/src/components/searchBar/CurrencyItemLogSearchBar.js b/src/components/searchBar/CurrencyItemLogSearchBar.js new file mode 100644 index 0000000..3185345 --- /dev/null +++ b/src/components/searchBar/CurrencyItemLogSearchBar.js @@ -0,0 +1,241 @@ +import { TextInput, InputLabel, SelectInput, InputGroup } from '../../styles/Components'; +import { SearchBarLayout, SearchPeriod } from '../common/SearchBar'; +import { useCallback, useEffect, useState } from 'react'; +import { + amountDeltaType, + countDeltaType, + CurrencyType, + itemTypeLarge, + logAction, + userSearchType2, +} from '../../assets/data/options'; +import { + getCurrencyItemList, +} from '../../apis/Log'; +import { useAlert } from '../../context/AlertProvider'; +import { alertTypes } from '../../assets/data/types'; + +export const useCurrencyItemLogSearch = (token, initialPageSize) => { + const {showToast} = useAlert(); + + const [searchParams, setSearchParams] = useState({ + search_type: 'GUID', + search_data: '', + tran_id: '', + log_action: 'None', + currency_type: 'None', + amount_delta_type: 'None', + start_dt: (() => { + const date = new Date(); + date.setDate(date.getDate() - 1); + return date; + })(), + end_dt: (() => { + const date = new Date(); + date.setDate(date.getDate() - 1); + return date; + })(), + order_by: 'ASC', + page_size: initialPageSize, + page_no: 1 + }); + + const [loading, setLoading] = useState(false); + const [data, setData] = useState(null); + + useEffect(() => { + // const initialLoad = async () => { + // await fetchData(searchParams); + // }; + // + // initialLoad(); + }, [token]); + + const fetchData = useCallback(async (params) => { + if (!token) return; + + try { + setLoading(true); + const result = await getCurrencyItemList( + token, + params.search_type, + params.search_data, + params.tran_id, + params.log_action, + params.currency_type, + params.amount_delta_type, + params.start_dt.toISOString(), + params.end_dt.toISOString(), + params.order_by, + params.page_size, + params.page_no + ); + if(result.result === "ERROR_LOG_MEMORY_LIMIT"){ + showToast('LOG_MEMORY_LIMIT_WARNING', {type: alertTypes.error}); + }else if(result.result === "ERROR_MONGODB_QUERY"){ + showToast('LOG_MONGGDB_QUERY_WARNING', {type: alertTypes.error}); + }else if(result.result === "ERROR"){ + showToast(result.result, {type: alertTypes.error}); + } + setData(result.data); + return result.data; + } catch (error) { + showToast('error', {type: alertTypes.error}); + throw error; + } finally { + setLoading(false); + } + }, [token]); + + const updateSearchParams = useCallback((newParams) => { + setSearchParams(prev => ({ + ...prev, + ...newParams + })); + }, []); + + const handleSearch = useCallback(async (newParams = {}, executeSearch = true) => { + const updatedParams = { + ...searchParams, + ...newParams, + page_no: newParams.page_no || 1 // Reset to first page on new search + }; + updateSearchParams(updatedParams); + + if (executeSearch) { + return await fetchData(updatedParams); + } + return null; + }, [searchParams, fetchData]); + + const handleReset = useCallback(async () => { + const now = new Date(); + now.setDate(now.getDate() - 1); + const resetParams = { + search_type: 'GUID', + search_data: '', + tran_id: '', + log_action: 'None', + currency_type: 'None', + amount_delta_type: 'None', + start_dt: now, + end_dt: now, + order_by: 'ASC', + page_size: initialPageSize, + page_no: 1 + }; + setSearchParams(resetParams); + return await fetchData(resetParams); + }, [initialPageSize, fetchData]); + + const handlePageChange = useCallback(async (newPage) => { + return await handleSearch({ page_no: newPage }, true); + }, [handleSearch]); + + const handlePageSizeChange = useCallback(async (newSize) => { + return await handleSearch({ page_size: newSize, page_no: 1 }, true); + }, [handleSearch]); + + const handleOrderByChange = useCallback(async (newOrder) => { + return await handleSearch({ order_by: newOrder }, true); + }, [handleSearch]); + + return { + searchParams, + loading, + data, + handleSearch, + handleReset, + handlePageChange, + handlePageSizeChange, + handleOrderByChange, + updateSearchParams + }; +}; + +const CurrencyItemLogSearchBar = ({ searchParams, onSearch, onReset }) => { + const handleSubmit = event => { + event.preventDefault(); + + onSearch(searchParams, true); + }; + + const searchList = [ + <> + + onSearch({search_type: e.target.value }, false)}> + {userSearchType2.map((data, index) => ( + + ))} + + onSearch({ search_data: e.target.value }, false)} + /> + + , + <> + 트랜잭션 ID + onSearch({ tran_id: e.target.value }, false)} + /> + , + ]; + + const optionList = [ + <> + 일자 + onSearch({ start_dt: date }, false)} + endDate={searchParams.end_dt} + handleEndDate={date => onSearch({ end_dt: date }, false)} + /> + , + <> + 액션 + onSearch({ log_action: e.target.value }, false)} > + {logAction.map((data, index) => ( + + ))} + + , + <> + 재화종류 + onSearch({ currency_type: e.target.value }, false)} > + + {CurrencyType.map((data, index) => ( + + ))} + + , + <> + 증감유형 + onSearch({ amount_delta_type: e.target.value }, false)} > + + {amountDeltaType.map((data, index) => ( + + ))} + + , + ]; + + return ; +}; + +export default CurrencyItemLogSearchBar; \ No newline at end of file diff --git a/src/components/searchBar/ItemLogSearchBar.js b/src/components/searchBar/ItemLogSearchBar.js new file mode 100644 index 0000000..0f8b967 --- /dev/null +++ b/src/components/searchBar/ItemLogSearchBar.js @@ -0,0 +1,252 @@ +import { TextInput, InputLabel, SelectInput, InputGroup } from '../../styles/Components'; +import { SearchBarLayout, SearchPeriod } from '../common/SearchBar'; +import { useCallback, useEffect, useState } from 'react'; +import { + amountDeltaType, + countDeltaType, + CurrencyType, + itemTypeLarge, + logAction, + userSearchType2, +} from '../../assets/data/options'; +import { getCurrencyDetailList, getItemDetailList } from '../../apis/Log'; +import { useAlert } from '../../context/AlertProvider'; +import { alertTypes } from '../../assets/data/types'; + +export const useItemLogSearch = (token, initialPageSize) => { + const {showToast} = useAlert(); + + const [searchParams, setSearchParams] = useState({ + search_type: 'GUID', + search_data: '', + tran_id: '', + log_action: 'None', + item_large_type: 'None', + item_small_type: '', + count_delta_type: 'None', + start_dt: (() => { + const date = new Date(); + date.setDate(date.getDate() - 1); + return date; + })(), + end_dt: (() => { + const date = new Date(); + date.setDate(date.getDate() - 1); + return date; + })(), + order_by: 'ASC', + page_size: initialPageSize, + page_no: 1 + }); + + const [loading, setLoading] = useState(false); + const [data, setData] = useState(null); + + useEffect(() => { + // const initialLoad = async () => { + // await fetchData(searchParams); + // }; + // + // initialLoad(); + }, [token]); + + const fetchData = useCallback(async (params) => { + if (!token) return; + + try { + setLoading(true); + const result = await getItemDetailList( + token, + params.search_type, + params.search_data, + params.tran_id, + params.log_action, + params.item_large_type, + params.item_small_type, + params.count_delta_type, + params.start_dt.toISOString(), + params.end_dt.toISOString(), + params.order_by, + params.page_size, + params.page_no + ); + if(result.result === "ERROR_LOG_MEMORY_LIMIT"){ + showToast('LOG_MEMORY_LIMIT_WARNING', {type: alertTypes.error}); + }else if(result.result === "ERROR_MONGODB_QUERY"){ + showToast('LOG_MONGGDB_QUERY_WARNING', {type: alertTypes.error}); + }else if(result.result === "ERROR"){ + showToast(result.result, {type: alertTypes.error}); + } + setData(result.data); + return result.data; + } catch (error) { + showToast('error', {type: alertTypes.error}); + throw error; + } finally { + setLoading(false); + } + }, [token]); + + const updateSearchParams = useCallback((newParams) => { + setSearchParams(prev => ({ + ...prev, + ...newParams + })); + }, []); + + const handleSearch = useCallback(async (newParams = {}, executeSearch = true) => { + const updatedParams = { + ...searchParams, + ...newParams, + page_no: newParams.page_no || 1 // Reset to first page on new search + }; + updateSearchParams(updatedParams); + + if (executeSearch) { + return await fetchData(updatedParams); + } + return null; + }, [searchParams, fetchData]); + + const handleReset = useCallback(async () => { + const now = new Date(); + now.setDate(now.getDate() - 1); + const resetParams = { + search_type: 'GUID', + search_data: '', + tran_id: '', + log_action: 'None', + item_large_type: 'None', + item_small_type: '', + count_delta_type: 'None', + start_dt: now, + end_dt: now, + order_by: 'ASC', + page_size: initialPageSize, + page_no: 1 + }; + setSearchParams(resetParams); + return await fetchData(resetParams); + }, [initialPageSize, fetchData]); + + const handlePageChange = useCallback(async (newPage) => { + return await handleSearch({ page_no: newPage }, true); + }, [handleSearch]); + + const handlePageSizeChange = useCallback(async (newSize) => { + return await handleSearch({ page_size: newSize, page_no: 1 }, true); + }, [handleSearch]); + + const handleOrderByChange = useCallback(async (newOrder) => { + return await handleSearch({ order_by: newOrder }, true); + }, [handleSearch]); + + return { + searchParams, + loading, + data, + handleSearch, + handleReset, + handlePageChange, + handlePageSizeChange, + handleOrderByChange, + updateSearchParams + }; +}; + +const ItemLogSearchBar = ({ searchParams, onSearch, onReset }) => { + const handleSubmit = event => { + event.preventDefault(); + + onSearch(searchParams, true); + }; + + const searchList = [ + <> + + onSearch({search_type: e.target.value }, false)}> + {userSearchType2.map((data, index) => ( + + ))} + + onSearch({ search_data: e.target.value }, false)} + /> + + , + <> + 트랜잭션 ID + onSearch({ tran_id: e.target.value }, false)} + /> + , + <> + LargeType + onSearch({ item_large_type: e.target.value }, false)} > + + {itemTypeLarge.map((data, index) => ( + + ))} + + , + ]; + + const optionList = [ + <> + 일자 + onSearch({ start_dt: date }, false)} + endDate={searchParams.end_dt} + handleEndDate={date => onSearch({ end_dt: date }, false)} + /> + , + <> + 액션 + onSearch({ log_action: e.target.value }, false)} > + {logAction.map((data, index) => ( + + ))} + + , + <> + SmallType + onSearch({ item_small_type: e.target.value }, false)} + /> + , + <> + 증감유형 + onSearch({ count_delta_type: e.target.value }, false)} > + + {countDeltaType.map((data, index) => ( + + ))} + + , + ]; + + return ; +}; + +export default ItemLogSearchBar; \ No newline at end of file diff --git a/src/components/searchBar/index.js b/src/components/searchBar/index.js index 3161121..5a33a50 100644 --- a/src/components/searchBar/index.js +++ b/src/components/searchBar/index.js @@ -25,6 +25,8 @@ import ReportListSearchBar from './ReportListSearchBar'; import BattleEventSearchBar from './BattleEventSearchBar'; import BusinessLogSearchBar, { useBusinessLogSearch } from './BusinessLogSearchBar'; import CurrencyLogSearchBar, { useCurrencyLogSearch } from './CurrencyLogSearchBar'; +import ItemLogSearchBar, { useItemLogSearch } from './ItemLogSearchBar'; +import CurrencyItemLogSearchBar, { useCurrencyItemLogSearch } from './CurrencyItemLogSearchBar'; import CurrencyIndexSearchBar, { useCurrencyIndexSearch } from './CurrencyIndexSearchBar'; import LandAuctionSearchBar from './LandAuctionSearchBar'; import CaliumRequestSearchBar from './CaliumRequestSearchBar'; @@ -62,6 +64,10 @@ export { LandAuctionSearchBar, CaliumRequestSearchBar, CurrencyIndexSearchBar, - useCurrencyIndexSearch + useCurrencyIndexSearch, + useItemLogSearch, + ItemLogSearchBar, + CurrencyItemLogSearchBar, + useCurrencyItemLogSearch, }; diff --git a/src/i18n.js b/src/i18n.js index d6d0bee..cd07e91 100644 --- a/src/i18n.js +++ b/src/i18n.js @@ -129,6 +129,7 @@ const resources = { BATTLE_EVENT_MODAL_START_DT_WARNING: "시작 시간은 현재 시간으로부터 10분 이후부터 가능합니다.", BATTLE_EVENT_MODAL_TIME_CHECK_WARNING :"해당 시간에 속하는 이벤트가 존재합니다.", BATTLE_EVENT_MODAL_OPERATION_TIME_MIN_CHECK_WARNING :"진행시간은 최소 10분 이상이여야 합니다.", + BATTLE_EVENT_MODAL_OPERATION_TIME_MAX_CHECK_WARNING :"진행시간은 최대 1400분까지 가능합니다.", BATTLE_EVENT_REGIST_CONFIRM: "이벤트를 등록하시겠습니까?", BATTLE_EVENT_UPDATE_CONFIRM: "이벤트를 수정하시겠습니까?", BATTLE_EVENT_SELECT_DELETE: "선택된 이벤트를 삭제하시겠습니까?", @@ -165,6 +166,8 @@ const resources = { FILE_BUSINESS_LOG: 'Caliverse_Log.xlsx', FILE_BATTLE_EVENT: 'Caliverse_Battle_Event.xlsx', FILE_GAME_LOG_CURRENCY: 'Caliverse_Game_Log_Currency', + FILE_GAME_LOG_ITEM: 'Caliverse_Game_Log_Item', + FILE_GAME_LOG_CURRENCY_ITEM: 'Caliverse_Game_Log_Currecy_Item', FILE_CURRENCY_INDEX: 'Caliverse_Currency_Index', //서버 에러메시지 DYNAMODB_NOT_USER: '유저 정보를 확인해주세요.', diff --git a/src/pages/DataManage/GameLogView.js b/src/pages/DataManage/GameLogView.js index a419424..3dca6b2 100644 --- a/src/pages/DataManage/GameLogView.js +++ b/src/pages/DataManage/GameLogView.js @@ -24,82 +24,11 @@ import { authType } from '../../assets/data'; import { TabGameLogList } from '../../assets/data/options'; import CurrencyLogContent from '../../components/DataManage/CurrencyLogContent'; import { STORAGE_GAME_LOG_CURRENCY_SEARCH } from '../../assets/data/adminConstants'; +import ItemLogContent from '../../components/DataManage/ItemLogContent'; +import CurrencyItemLogContent from '../../components/DataManage/CurrencyItemLogContent'; registerLocale('ko', ko); -const ItemLogContent = () => { - const mokupData = [ - { - date: '2023-08-05 12:11:32', - name: '칼리버스', - id: '16CD2ECD-4798-46CE-9B6B-F952CF11F196', - action: '획득', - route: '아이템 제작', - itemName: 'Item_name', - serialNumber: 'Serial_number', - itemCode: 'Item_code', - count: 1, - key: 'User_trade_key', - }, - ]; - return ( - <> - - 총 : 117건 / 000 건 - - - - - - - - - -