diff --git a/egovframe-template-simple-react-contribution/src/components/alert/FormDialog.jsx b/egovframe-template-simple-react-contribution/src/components/alert/FormDialog.jsx index 30b570a..3913079 100644 --- a/egovframe-template-simple-react-contribution/src/components/alert/FormDialog.jsx +++ b/egovframe-template-simple-react-contribution/src/components/alert/FormDialog.jsx @@ -7,7 +7,7 @@ import DialogContent from '@mui/material/DialogContent'; import DialogContentText from '@mui/material/DialogContentText'; import DialogTitle from '@mui/material/DialogTitle'; -export default function FormDialog( {open, setOpen, title, contentText, children} ) { +export default function FormDialog( {open, setOpen, title, contentText, children, handleOk} ) { const handleClickOpen = () => { setOpen(true); @@ -43,7 +43,7 @@ export default function FormDialog( {open, setOpen, title, contentText, children - + diff --git a/egovframe-template-simple-react-contribution/src/components/list/ListCreateUpdateDelete.jsx b/egovframe-template-simple-react-contribution/src/components/list/ListCreateUpdateDelete.jsx index f7e0fef..eaeb9ca 100644 --- a/egovframe-template-simple-react-contribution/src/components/list/ListCreateUpdateDelete.jsx +++ b/egovframe-template-simple-react-contribution/src/components/list/ListCreateUpdateDelete.jsx @@ -12,9 +12,6 @@ import Grid from '@mui/material/Grid'; import Typography from '@mui/material/Typography'; import DeleteIcon from '@mui/icons-material/Delete'; import AddIcon from '@mui/icons-material/Add'; -import TextField from '@mui/material/TextField'; - -import FormDialog from '../../components/alert/FormDialog'; import styledComponent from "styled-components"; @@ -26,19 +23,27 @@ const StyledDiv = styledComponent.div` function generate(items, element, onClickListner,nameKey, idKey) { - return items.map((value, index) => - React.cloneElement(element, { - key: value[nameKey], - }, - {onClickListner(e, index);}}> - - - - ), - ); + + let returnValue = []; + let nIndex = 0; + Object.keys(items).forEach(function(key) { + returnValue = [ + ...returnValue, + React.cloneElement(element, { + key, + }, + {onClickListner(e, key);}}> + + + + ), + ]; + nIndex++; + }); + return returnValue; } const Demo = styled('div')(({ theme }) => ({ @@ -55,32 +60,36 @@ const Item = styled(Paper)(({ theme }) => ({ function ListCreateUpdateDelete(props) { - const [dense, setDense] = React.useState(false); - - const [open, setOpen] = React.useState(false); - const handleClickOpen = () => { - setOpen(true); - }; - - const handleClose = () => { - setOpen(false); + if( props.depthSelectedArrayIndex === 0 ) { + props.setCreateCondition({...props.createCondition, paramCodeLevel : props.paramCodeLevel, paramOrgId : "00"}); + } else { + if( props.itemIndex[props.depthSelectedArrayIndex-1] === undefined ) { + alert('상위 코드를 선택해주세요.'); + props.setIsPopupOpen(false); + return false; + } + props.setCreateCondition({...props.createCondition, paramCodeLevel : props.paramCodeLevel, paramOrgId : props.itemIndex[props.depthSelectedArrayIndex-1]}); + } + props.setIsPopupOpen(true); }; const onClickItem = (e, index) => { - + index = Number(index); // 기존 active를 모두 해제 한다. let siblingEle = e.currentTarget.parentNode.parentNode.firstChild; do { siblingEle.firstChild.classList.remove('active'); + // eslint-disable-next-line no-cond-assign } while (siblingEle = siblingEle.nextSibling); - // 선택된 것만 active로 지정한다. - if( Number(e.currentTarget.getAttribute('data-index')) === index ) { - e.currentTarget.classList.add('active'); - } - props.setItemIndex(index); + e.currentTarget.classList.add('active'); + const myKey = Number(index); + props.itemIndex[props.depthSelectedArrayIndex] = myKey; + let forChangeObject = [...props.itemIndex]; + props.setItemIndex(forChangeObject); }; + return ( @@ -99,7 +108,7 @@ function ListCreateUpdateDelete(props) { - + {generate( props.items, - } - > + } + > , onClickItem, props.nameKey, props.idKey )} - - - - - + diff --git a/egovframe-template-simple-react-contribution/src/pages/admin/config/CommitteeCodeMgt.jsx b/egovframe-template-simple-react-contribution/src/pages/admin/config/CommitteeCodeMgt.jsx index b4f1f58..3422ad1 100644 --- a/egovframe-template-simple-react-contribution/src/pages/admin/config/CommitteeCodeMgt.jsx +++ b/egovframe-template-simple-react-contribution/src/pages/admin/config/CommitteeCodeMgt.jsx @@ -7,6 +7,8 @@ import * as EgovNet from 'api/egovFetch'; +import CommitteeCodeRegistrationPopup from './CommitteeCodeMgt/CommitteeCodeRegistrationPopup'; + import ListCreateUpdateDelete from '../../../components/list/ListCreateUpdateDelete' import ListLabelInputs from '../../../components/list/ListLabelInputs' @@ -19,49 +21,63 @@ import { default as EgovLeftNav } from 'components/leftmenu/EgovLeftNavAdmin'; function CommitteeCodeMgt(props) { const [searchCondition, setSearchCondition] = useState({ paramCodeGroup: null, paramCodeLevel: 'LV_01' }); + const [createCondition, setCreateCondition] = useState(); + + const [depth01List, setDepth01List] = useState({}); + const [depth02List, setDepth02List] = useState({}); + const [depth03List, setDepth03List] = useState({}); + const [depth04List, setDepth04List] = useState({}); - const [depth01List, setDepth01List] = useState([]); - const [depth02List, setDepth02List] = useState([]); - const [depth03List, setDepth03List] = useState([]); - const [depth04List, setDepth04List] = useState([]); const [summaryArray, setSummaryArray] = useState({}); - - const [depth01SelectedIndex, setDepth01SelectedIndex] = React.useState(undefined); - const [depth02SelectedIndex, setDepth02SelectedIndex] = React.useState(undefined); - const [depth03SelectedIndex, setDepth03SelectedIndex] = React.useState(undefined); - const [depth04SelectedIndex, setDepth04SelectedIndex] = React.useState(undefined); + const [depthSelectedIndex, setDepthSelectedIndex] = useState([]); + + // 위원회 코드 등록 팝업을 보이거나 닫는다. + const [isCommitteeCodeRegistrationPopupOpen, setIsCommitteeCodeRegistrationPopupOpen] = React.useState(false); // '중앙건설기술심의'에서 특정 item선택 시, 하위 '총괄위원회'목록을 불러온다. useEffect(function () { - if( typeof depth01SelectedIndex !== 'undefined' ) { - setSearchCondition({ paramCodeGroup: depth01List[depth01SelectedIndex].orgId, paramCodeLevel: 'LV_02' }); - setDepth02SelectedIndex(undefined); - setDepth03SelectedIndex(undefined); - setDepth04SelectedIndex(undefined); - } + if( typeof depthSelectedIndex[0] !== "undefined" && depth01List[depthSelectedIndex[0]].orgId !== undefined) { + setSearchCondition({ paramCodeGroup: depth01List[depthSelectedIndex[0]].orgId, paramCodeLevel: 'LV_02' }); + setDepth02List({}); + setDepth03List({}); + setDepth04List({}); + depthSelectedIndex[1] = undefined; + depthSelectedIndex[2] = undefined; + depthSelectedIndex[3] = undefined; + let forChangeObject = [...depthSelectedIndex]; + setDepthSelectedIndex(forChangeObject); + } // eslint-disable-next-line react-hooks/exhaustive-deps - }, [depth01SelectedIndex]); + }, [depthSelectedIndex[0]]); // '총괄위원회'에서 특정 item선택 시, 하위 '건설기준위원회'목록을 불러온다. useEffect(function () { - if( typeof depth02SelectedIndex !== 'undefined' ) { - setSearchCondition({ paramCodeGroup: depth02List[depth02SelectedIndex].orgId, paramCodeLevel: 'LV_03' }); - setDepth03SelectedIndex(undefined); - setDepth04SelectedIndex(undefined); + if( typeof depthSelectedIndex[1] !== 'undefined' ) { + setSearchCondition({ paramCodeGroup: depth02List[depthSelectedIndex[1]].orgId, paramCodeLevel: 'LV_03' }); + setDepth03List({}); + setDepth04List({}); + depthSelectedIndex[2] = undefined; + depthSelectedIndex[3] = undefined; + let forChangeObject = [...depthSelectedIndex]; + setDepthSelectedIndex(forChangeObject); } // eslint-disable-next-line react-hooks/exhaustive-deps - }, [depth02SelectedIndex]); + }, [depthSelectedIndex[1]]); // '건설기준위원회'에서 특정 item선택 시, 하위 '실무위원회'목록을 불러온다. useEffect(function () { - if( typeof depth03SelectedIndex !== 'undefined' ) { - setSearchCondition({ paramCodeGroup: depth03List[depth03SelectedIndex].orgId, paramCodeLevel: 'LV_04' }); - setDepth04SelectedIndex(undefined); + if( typeof depthSelectedIndex[2] !== 'undefined' ) { + setSearchCondition({ paramCodeGroup: depth03List[depthSelectedIndex[2]].orgId, paramCodeLevel: 'LV_04' }); + setDepth04List({}); + depthSelectedIndex[3] = undefined; + let forChangeObject = [...depthSelectedIndex]; + setDepthSelectedIndex(forChangeObject); } // eslint-disable-next-line react-hooks/exhaustive-deps - }, [depth03SelectedIndex]); + }, [depthSelectedIndex[2]]); + // 검색 조건이 변경되면 데이터를 불러온다. useEffect(function () { @@ -72,6 +88,13 @@ function CommitteeCodeMgt(props) { }, [searchCondition]); + + useEffect(function () { + if( typeof createCondition !== 'undefined' ) { + console.log('%o', createCondition); + } + // eslint-disable-next-line react-hooks/exhaustive-deps + }, [createCondition]); const requestOptions = { @@ -81,46 +104,54 @@ function CommitteeCodeMgt(props) { } } + const arrayToJson = (myArray, key) => { + let tempObj = {}; + + // eslint-disable-next-line array-callback-return + myArray.map((value, index) => { + tempObj = {...tempObj, [value[key]] : value}; + }); + + return tempObj; + }; + const getList = (searchCondition) => { EgovNet.requestFetch(`/admin/config/committee-code-management?paramCodeGroup=${searchCondition.paramCodeGroup}¶mCodeLevel=${searchCondition.paramCodeLevel}`, requestOptions, function (resp) { if( searchCondition.paramCodeLevel === 'LV_01' ) { - setDepth01List(resp.result.list); + setDepth01List(arrayToJson(resp.result.list, "orgId")); } else if( searchCondition.paramCodeLevel === 'LV_02' ) { - setDepth02List(resp.result.list); + setDepth02List(arrayToJson(resp.result.list, "orgId")); } else if( searchCondition.paramCodeLevel === 'LV_03' ) { - setDepth03List(resp.result.list); + setDepth03List(arrayToJson(resp.result.list, "orgId")); } else if( searchCondition.paramCodeLevel === 'LV_04' ) { - setDepth04List(resp.result.list); + setDepth04List(arrayToJson(resp.result.list, "orgId")); } } - ); - + ); } + useEffect(function () { setSummaryArray( { - "중앙건설기술심의" : depth01List[depth01SelectedIndex] && depth01List[depth01SelectedIndex].orgNm ? depth01List[depth01SelectedIndex].orgNm : "", - "총괄위원회" : depth02List[depth02SelectedIndex] && depth02List[depth02SelectedIndex].orgNm ? depth02List[depth02SelectedIndex].orgNm : "", - "건설기준위원회" : depth03List[depth03SelectedIndex] && depth03List[depth03SelectedIndex].orgNm ? depth03List[depth03SelectedIndex].orgNm : "", - "실무위원회" : depth04List[depth04SelectedIndex] && depth04List[depth04SelectedIndex].orgNm ? depth04List[depth04SelectedIndex].orgNm : "", + "중앙건설기술심의" : depth01List[depthSelectedIndex[0]] && depth01List[depthSelectedIndex[0]].orgNm ? depth01List[depthSelectedIndex[0]].orgNm : "", + "총괄위원회" : depth02List[depthSelectedIndex[1]] && depth02List[depthSelectedIndex[1]].orgNm ? depth02List[depthSelectedIndex[1]].orgNm : "", + "건설기준위원회" : depth03List[depthSelectedIndex[2]] && depth03List[depthSelectedIndex[2]].orgNm ? depth03List[depthSelectedIndex[2]].orgNm : "", + "실무위원회" : depth04List[depthSelectedIndex[3]] && depth04List[depthSelectedIndex[3]].orgNm ? depth04List[depthSelectedIndex[3]].orgNm : "", } - ); - console.log(`${depth01List[depth01SelectedIndex]}[${depth01SelectedIndex}]`); + ); // eslint-disable-next-line react-hooks/exhaustive-deps }, [ depth01List, depth02List, depth03List, depth04List, - depth01SelectedIndex, - depth02SelectedIndex, - depth03SelectedIndex, - depth04SelectedIndex]); - + depthSelectedIndex + ]); + const Location = React.memo(function Location() { return ( @@ -165,10 +196,64 @@ function CommitteeCodeMgt(props) { }, }} > - - - - + + + + + { true && @@ -186,7 +271,14 @@ function CommitteeCodeMgt(props) { } - + {/* */} diff --git a/egovframe-template-simple-react-contribution/src/pages/admin/config/CommitteeCodeMgt/CommitteeCodeRegistrationPopup.jsx b/egovframe-template-simple-react-contribution/src/pages/admin/config/CommitteeCodeMgt/CommitteeCodeRegistrationPopup.jsx new file mode 100644 index 0000000..2a7061d --- /dev/null +++ b/egovframe-template-simple-react-contribution/src/pages/admin/config/CommitteeCodeMgt/CommitteeCodeRegistrationPopup.jsx @@ -0,0 +1,75 @@ +import React from 'react'; +import TextField from '@mui/material/TextField'; + +import * as EgovNet from 'api/egovFetch'; +import FormDialog from '../../../../components/alert/FormDialog'; + +function CommitteeCodeRegistrationPopup(props) { + + + const handleClickCreateCommitteeCodeManagement = (createCondition) => { + + if( createCondition.paramOrgId === undefined ) { + alert('상위 코드를 선택해주세요.'); + props.setOpen(false); + return false; + } + const formData = new FormData(); + + for (let key in createCondition) { + formData.append(key, createCondition[key]); + } + + const requestOptions = { + method: "POST", + body: formData, + }; + + EgovNet.requestFetch(`/admin/config/committee-code-management`, + requestOptions, + function (resp) { + //window.location.reload(); + //방금 추가한 것만 새로 읽어 드린다. + props.setSearchCondition({...props.searchCondition, paramCodeLevel : props.createCondition.paramCodeLevel}); + + props.setOpen(false); + } + ); + } + + const handleTextFieldChange = (event) => { + const elName = event.target.getAttribute('name'); + const elValue = event.target.value; + props.setCreateCondition({...props.createCondition, [elName]:elValue}); + }; + + return ( + {handleClickCreateCommitteeCodeManagement(props.createCondition);}} > + + + + ); +} + +export default CommitteeCodeRegistrationPopup; \ No newline at end of file diff --git a/egovframe-template-simple-react-contribution/src/pages/admin/schedule/EgovAdminScheduleList.jsx b/egovframe-template-simple-react-contribution/src/pages/admin/schedule/EgovAdminScheduleList.jsx index 0044ef0..643ae36 100644 --- a/egovframe-template-simple-react-contribution/src/pages/admin/schedule/EgovAdminScheduleList.jsx +++ b/egovframe-template-simple-react-contribution/src/pages/admin/schedule/EgovAdminScheduleList.jsx @@ -294,7 +294,7 @@ function EgovAdminDashboard(props) { - 주간 현황 + 이번주 현황 총 {totalDownloads}건 diff --git a/egovframe-template-simple-react-contribution/src/pages/admin/users/UserInfoModal.jsx b/egovframe-template-simple-react-contribution/src/pages/admin/users/UserInfoModal.jsx index d660a88..2d54780 100644 --- a/egovframe-template-simple-react-contribution/src/pages/admin/users/UserInfoModal.jsx +++ b/egovframe-template-simple-react-contribution/src/pages/admin/users/UserInfoModal.jsx @@ -67,7 +67,7 @@ function UserInfoModal({savedInfo, reloadFunction}){ } }, (resp) => { - debugger + } ) } diff --git a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/config/AdminConfigController.java b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/config/AdminConfigController.java index 4b5b478..fad1f72 100644 --- a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/config/AdminConfigController.java +++ b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/config/AdminConfigController.java @@ -1,6 +1,7 @@ package com.dbnt.kcscbackend.admin.config; import com.dbnt.kcscbackend.admin.config.entity.TcMenu; +import com.dbnt.kcscbackend.admin.config.model.CreateCommitteeCodeManagementVO; import com.dbnt.kcscbackend.admin.config.service.AdminCommitteeCodeManagementService; import com.dbnt.kcscbackend.admin.standardResearch.service.AdminStandardResearchService; import com.dbnt.kcscbackend.commonCode.entity.TcCodeGrp; @@ -402,6 +403,48 @@ public class AdminConfigController extends BaseController { return resultVO; } + + @Operation( + summary = "'위원회 코드 관리' 페이지에서 위원회 코드 추가하는 API", + description = "관리자 단에서 '환경설정' > '위원회코드 관리' 페이지에서 +(추가) 버튼으로 항목 추가하는 API", + tags = {"AdminConfigController"} + ) + @ApiResponses(value = { + @ApiResponse(responseCode = "200", description = "조회 성공"), + @ApiResponse(responseCode = "303", description = "만료된 토큰"), + @ApiResponse(responseCode = "403", description = "인가된 사용자가 아님") + }) + @PostMapping(value = "/committee-code-management") + public ResultVO createCommitteeCodeManagement( + @AuthenticationPrincipal LoginVO user, + HttpServletRequest request, + CreateCommitteeCodeManagementVO createCommitteeCodeManagementVO + ) throws Exception { + + ResultVO resultVO = new ResultVO(); + if(user == null) { + resultVO.setResultCode(ResponseCode.TOKEN_EXPIRED.getCode()); + } else { + try { + resultVO = adminCommitteeCodeManagementService.createCommitteeCodeManagement(resultVO, request, user, createCommitteeCodeManagementVO); + } catch (Exception e) { + resultVO.setResultCode(ResponseCode.FAILED.getCode()); + resultVO.setResultMessage(e.getMessage()); + } + } + + System.out.println( + "\n--------------------------------------------------------------\n" + + request.getRequestURI() + " OUT:" + + "\n--------------------------------------------------------------\n" + + "resultVO.toString():" + "\n" + + resultVO.toString() + "\n" + + "\n--------------------------------------------------------------\n" + ); + + return resultVO; + } + /* ---- 관련사이트 관리 ----- */ @Operation( summary = "관련사이트 목록 조회", diff --git a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/config/model/CreateCommitteeCodeManagementVO.java b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/config/model/CreateCommitteeCodeManagementVO.java new file mode 100644 index 0000000..93c8af8 --- /dev/null +++ b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/config/model/CreateCommitteeCodeManagementVO.java @@ -0,0 +1,34 @@ +package com.dbnt.kcscbackend.admin.config.model; + +import io.swagger.annotations.ApiModel; +import io.swagger.annotations.ApiModelProperty; +import lombok.Getter; +import lombok.RequiredArgsConstructor; +import lombok.Setter; +import lombok.ToString; + +import java.io.Serializable; + +@ApiModel(value = "CreateCommitteeCodeManagementVO", description = + "관리자 단에서 '환경설정' > '위원회코드 관리' 페이지에서 +(추가) 버튼으로 항목 추가하는 API에 사용된다." + "" +) +@RequiredArgsConstructor +@Getter +@Setter +@ToString +public class CreateCommitteeCodeManagementVO implements Serializable { + private static final long serialVersionUID = -603047540959527181L; + + @ApiModelProperty(value = "현재 등록하고 있는 항목의 level이 들어간다. '중앙건설기술심의'인 경우, LV_01이다. '총괄위원회'인 경우, LV_02이다. 이런 식으로 값이 들어간다.") + private String paramCodeLevel; + + @ApiModelProperty(value = "현재 등록하고 있는 항목의 상위 코드 값이 들어간다. '중앙건설기술심의'인 경우, 값이 00이다. 하지만 tn_cmt_org table에 cmt_seq 값이 00인 레코드는 존재하지 않는다.") + private String paramOrgId; + + @ApiModelProperty(value = "명칭") + private String paramOrgNm; + + @ApiModelProperty(value = "위원회 설명") + private String paramOrgDesc; + +} diff --git a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/config/service/AdminCommitteeCodeManagementService.java b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/config/service/AdminCommitteeCodeManagementService.java index 7e6ae13..4d83564 100644 --- a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/config/service/AdminCommitteeCodeManagementService.java +++ b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/config/service/AdminCommitteeCodeManagementService.java @@ -1,5 +1,6 @@ package com.dbnt.kcscbackend.admin.config.service; +import com.dbnt.kcscbackend.admin.config.model.CreateCommitteeCodeManagementVO; import com.dbnt.kcscbackend.admin.standardResearch.model.CreateStandardResearchVO; import com.dbnt.kcscbackend.admin.standardResearch.model.UpdateStandardResearchVO; import com.dbnt.kcscbackend.auth.entity.LoginVO; @@ -12,7 +13,7 @@ import org.springframework.web.multipart.MultipartHttpServletRequest; import javax.servlet.http.HttpServletRequest; public interface AdminCommitteeCodeManagementService { - public ResultVO createCommitteeCodeManagement(ResultVO resultVO, HttpServletRequest request, LoginVO user, final MultipartHttpServletRequest multiRequest, CreateStandardResearchVO createStandardResearchVO) throws Exception; + public ResultVO createCommitteeCodeManagement(ResultVO resultVO, HttpServletRequest request, LoginVO user, CreateCommitteeCodeManagementVO createCommitteeCodeManagementVO) throws Exception; public ResultVO getCommitteeCodeManagement(ResultVO resultVO, HttpServletRequest request, LoginVO user, Long upCmtSeq, String cmtType) throws Exception; public ResultVO setCommitteeCodeManagement(ResultVO resultVO, HttpServletRequest request, LoginVO user, UpdateStandardResearchVO updateStandardResearchVO, Long popupId) throws Exception; public ResultVO deleteCommitteeCodeManagement(ResultVO resultVO, HttpServletRequest request, LoginVO user, Long popupId) throws Exception; diff --git a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/config/service/AdminConfigService.java b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/config/service/AdminConfigService.java index 8ee4045..d48118c 100644 --- a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/config/service/AdminConfigService.java +++ b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/config/service/AdminConfigService.java @@ -93,25 +93,25 @@ public class AdminConfigService extends EgovAbstractServiceImpl { } @Transactional - public String modifyCodeItem(TcCodeItem codeItem) { - TcCodeItem savedItem = codeItemRepository.findById( - new TcCodeItem.TcCodeItemId(codeItem.getItemCd(), codeItem.getGrpCd()) - ).orElse(null); - if (savedItem != null) { - savedItem.setItemNm(codeItem.getItemNm()); - savedItem.setLastChgId(codeItem.getLastChgId()); - savedItem.setLastChgDt(codeItem.getLastChgDt()); - savedItem.setGrpOrder(codeItem.getGrpOrder()); - savedItem.setUseYn(codeItem.getUseYn()); - codeItemRepository.save(savedItem); - return "modified"; - }else{ - return "validGrpCd"; + public String modifyCodeItem(TcCodeItem codeItem) { + TcCodeItem savedItem = codeItemRepository.findById( + new TcCodeItem.TcCodeItemId(codeItem.getItemCd(), codeItem.getGrpCd()) + ).orElse(null); + if (savedItem != null) { + savedItem.setItemNm(codeItem.getItemNm()); + savedItem.setLastChgId(codeItem.getLastChgId()); + savedItem.setLastChgDt(codeItem.getLastChgDt()); + savedItem.setGrpOrder(codeItem.getGrpOrder()); + savedItem.setUseYn(codeItem.getUseYn()); + codeItemRepository.save(savedItem); + return "modified"; + }else{ + return "validGrpCd"; + } } - } - public List selectMenuList() { - return menuMapper.selectMenuList(); + public List selectMenuList() { + return menuMapper.selectMenuList(); } @Transactional @@ -174,4 +174,4 @@ public class AdminConfigService extends EgovAbstractServiceImpl { return tnPartnerSiteRepository.findAllByOrderBySiteOrder(); } -} +} \ No newline at end of file diff --git a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/config/service/impl/AdminCommitteeCodeManagementServiceImpl.java b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/config/service/impl/AdminCommitteeCodeManagementServiceImpl.java index 60b0f01..5970a59 100644 --- a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/config/service/impl/AdminCommitteeCodeManagementServiceImpl.java +++ b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/config/service/impl/AdminCommitteeCodeManagementServiceImpl.java @@ -1,5 +1,6 @@ package com.dbnt.kcscbackend.admin.config.service.impl; +import com.dbnt.kcscbackend.admin.config.model.CreateCommitteeCodeManagementVO; import com.dbnt.kcscbackend.admin.config.service.AdminCommitteeCodeManagementService; import com.dbnt.kcscbackend.admin.standardResearch.model.CreateStandardResearchVO; import com.dbnt.kcscbackend.admin.standardResearch.model.UpdateStandardResearchVO; @@ -28,28 +29,68 @@ public class AdminCommitteeCodeManagementServiceImpl extends EgovAbstractService private final TnCmtOrgRepository tnCmtOrgRepository; @Override - public ResultVO createCommitteeCodeManagement(ResultVO resultVO, HttpServletRequest request, LoginVO user, MultipartHttpServletRequest multiRequest, CreateStandardResearchVO createStandardResearchVO) throws Exception { - return null; + public ResultVO createCommitteeCodeManagement(ResultVO resultVO, HttpServletRequest request, LoginVO user, CreateCommitteeCodeManagementVO createCommitteeCodeManagementVO) throws Exception { + System.out.println( + "\n--------------------------------------------------------------\n" + + request.getRequestURI() + " IN:" + + "\n--------------------------------------------------------------\n" + + "user.getEmail():" + "\n" + + user.getEmail() + "\n" + + "\n--------------------------------------------------------------\n" + ); + + // 아래 null로 전달 되는 부분 확인하기. + // 유효성 검사 실시 + if(createCommitteeCodeManagementVO.getParamCodeLevel().trim().isEmpty()) { + throw new Exception("오류가 발생했습니다. 시스템 담당자에게 문의 바랍니다. paramCodeLevel is empty."); + } + Integer upCmtSeq = null; + if( createCommitteeCodeManagementVO.getParamOrgId().trim().equals("00") == false ) { // 00은 '중앙건설기술심의' 항목의 부모 sequnce이다. 그러나 DB에 실제 00이란 sequence는 존재하지 않는다. + upCmtSeq = Integer.parseInt(createCommitteeCodeManagementVO.getParamOrgId()); + } + + Map response = tnCmtOrgRepository.spAddTnCmtOrg( + createCommitteeCodeManagementVO.getParamOrgNm(), // 위원회 이름 + createCommitteeCodeManagementVO.getParamCodeLevel(), // 위원회 등급 + createCommitteeCodeManagementVO.getParamOrgDesc(), // 위원회 설명 + upCmtSeq, // 상위 위원회 sequence + 1, // 정렬 순서 + user.getId(), + null, + null, + null, + null + ); + + Map dto = new HashMap(); + dto.put("id", response.get("_cmt_seq") ); + + resultVO.setResult(dto); + resultVO.setResultCode(ResponseCode.SUCCESS.getCode()); + resultVO.setResultMessage(ResponseCode.SUCCESS.getMessage()); + + return resultVO; } @Override public ResultVO getCommitteeCodeManagement(ResultVO resultVO, HttpServletRequest request, LoginVO user, Long upCmtSeq, String cmtType) throws Exception { System.out.println( - "\n--------------------------------------------------------------\n" + - request.getRequestURI() + " IN:" + - "\n--------------------------------------------------------------\n" + - "user.getEmail():" + "\n" + - user.getEmail() + "\n" + - "\n--------------------------------------------------------------\n" + "\n--------------------------------------------------------------\n" + + request.getRequestURI() + " IN:" + + "\n--------------------------------------------------------------\n" + + "user.getEmail():" + "\n" + + user.getEmail() + "\n" + + "\n--------------------------------------------------------------\n" ); List> list = tnCmtOrgRepository.findByUseYnAndUpCmtSeqAndCmtTypeOrderByCmtOrder("Y", upCmtSeq, cmtType).stream() .map(item -> { Map returnMap = new HashMap<>(); - returnMap.put("orgId", item.getCmtSeq()); - returnMap.put("orgNm", item.getCmtNm()); - returnMap.put("orgDesc", item.getCmtDesc()); + returnMap.put("orgId", item.getCmtSeq()); + returnMap.put("orgNm", item.getCmtNm()); + returnMap.put("orgDesc", item.getCmtDesc()); + returnMap.put("omtOrder", item.getCmtOrder()); return returnMap; }) .collect(Collectors.toList()); diff --git a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/dashboard/AdminDashboardController.java b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/dashboard/AdminDashboardController.java index 1358ff0..5ee6130 100644 --- a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/dashboard/AdminDashboardController.java +++ b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/dashboard/AdminDashboardController.java @@ -1,6 +1,5 @@ package com.dbnt.kcscbackend.admin.dashboard; -//import com.dbnt.kcscbackend.admin.dashboard.dto.MonthlyUserLogDTO; import com.dbnt.kcscbackend.admin.dashboard.service.AdminDashboardService; import com.dbnt.kcscbackend.auth.entity.LoginVO; import com.dbnt.kcscbackend.config.common.BaseController; @@ -13,17 +12,12 @@ import io.swagger.v3.oas.annotations.tags.Tag; import lombok.RequiredArgsConstructor; import org.springframework.http.MediaType; import org.springframework.security.core.annotation.AuthenticationPrincipal; -import org.springframework.web.bind.annotation.RequestBody; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RequestMethod; import org.springframework.web.bind.annotation.RestController; -import java.math.BigInteger; -import java.time.LocalDate; import java.util.HashMap; -import java.util.List; import java.util.Map; -import java.util.stream.Collectors; @RestController @RequiredArgsConstructor @@ -71,7 +65,7 @@ public class AdminDashboardController extends BaseController { @ApiResponse(responseCode = "403", description = "인가된 사용자가 아님") }) @RequestMapping(method = RequestMethod.POST, value = "/file", consumes = MediaType.APPLICATION_JSON_VALUE) - public ResultVO getfile(@AuthenticationPrincipal LoginVO user) + public ResultVO getFile(@AuthenticationPrincipal LoginVO user) throws Exception { ResultVO resultVO = new ResultVO(); @@ -90,60 +84,4 @@ public class AdminDashboardController extends BaseController { - - -// @Operation( -// summary = "일별 사용자 현황 차트 조회", -// description = "일별 사용자 현황 차트 조회", -// tags = {"AdminDashboardController"} -// ) -// @ApiResponses(value = { -// @ApiResponse(responseCode = "200", description = "조회 성공"), -// @ApiResponse(responseCode = "403", description = "인가된 사용자가 아님") -// }) -// @RequestMapping(method = RequestMethod.GET, value = "/daily-user-log-list", consumes = MediaType.APPLICATION_JSON_VALUE) -// public ResultVO getDailyUserLogList() throws Exception { -// ResultVO resultVO = new ResultVO(); -// Map resultMap = new HashMap<>(); -// -// // 현재 날짜 -// // todo endDate 뒤에 .minus 지워야함 -// LocalDate endDate = LocalDate.now().minusMonths(6); -// // 3개월 전 날짜 계산 -// LocalDate startDate = endDate.minusMonths(3); -// -// resultMap.put("dailyUserLogList", adminDashboardService.selectDailyUserLogList(startDate, endDate)); -// resultVO.setResult(resultMap); -// return resultVO; -// } -// -// @Operation( -// summary = "월별 사용자 현황 차트 조회", -// description = "월별 사용자 현황 차트 조회", -// tags = {"AdminDashboardController"} -// ) -// @ApiResponses(value = { -// @ApiResponse(responseCode = "200", description = "조회 성공"), -// @ApiResponse(responseCode = "403", description = "인가된 사용자가 아님") -// }) -// @RequestMapping(method = RequestMethod.GET, value = "/monthly-user-log-list", consumes = MediaType.APPLICATION_JSON_VALUE) -// public ResultVO getMonthlyUserLogList() throws Exception { -// ResultVO resultVO = new ResultVO(); -// Map resultMap = new HashMap<>(); -// -// // 현재 날짜 -// // todo endDate 뒤에 .minus 지워야함 -// LocalDate endDate = LocalDate.now().minusMonths(6); -// // 3개월 전 날짜 계산 -// LocalDate startDate = endDate.minusMonths(3); -// -// List result = adminDashboardService.selectMonthlyUserLogList(startDate, endDate); -// List monthlyUserLogDTOList = result.stream() -// .map(row -> new MonthlyUserLogDTO((String) row[0], (BigInteger) row[1])) -// .collect(Collectors.toList()); -// -// resultMap.put("dailyUserLogList", monthlyUserLogDTOList); -// resultVO.setResult(resultMap); -// return resultVO; -// } } diff --git a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/dashboard/dto/MonthlyUserLogDTO.java b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/dashboard/dto/MonthlyUserLogDTO.java deleted file mode 100644 index 430ee35..0000000 --- a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/dashboard/dto/MonthlyUserLogDTO.java +++ /dev/null @@ -1,22 +0,0 @@ -package com.dbnt.kcscbackend.admin.dashboard.dto; - -import com.dbnt.kcscbackend.admin.dashboard.entity.TnDailyUserLog; -import lombok.AllArgsConstructor; -import lombok.Data; -import lombok.ToString; - -import java.math.BigInteger; -import java.time.LocalDate; - -@Data -@AllArgsConstructor -@ToString -public class MonthlyUserLogDTO { - private String logDt; - private BigInteger logCnt; - - public MonthlyUserLogDTO(Object[] row) { - this.logDt = (String) row[0]; - this.logCnt = (BigInteger) row[1]; - } -} diff --git a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/dashboard/entity/TnDailyUserLog.java b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/dashboard/entity/TnDailyUserLog.java deleted file mode 100644 index 30cd0ad..0000000 --- a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/dashboard/entity/TnDailyUserLog.java +++ /dev/null @@ -1,39 +0,0 @@ -package com.dbnt.kcscbackend.admin.dashboard.entity; -import com.fasterxml.jackson.annotation.JsonFormat; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; -import org.hibernate.annotations.DynamicInsert; -import org.hibernate.annotations.DynamicUpdate; - -import javax.persistence.*; -import java.math.BigInteger; -import java.time.LocalDate; - -@Getter -@Setter -@Entity -@NoArgsConstructor -@DynamicInsert -@DynamicUpdate -@Table(name = "tn_daily_user_log") -public class TnDailyUserLog { - @Id - @GeneratedValue(strategy = GenerationType.IDENTITY) - @Column(name = "dul_seq") - private Long dulSeq; - - @Column(name = "log_dt") - private LocalDate logDt; - - @Column(name = "log_cnt") - private Integer logCnt; - - @Column(name = "mobile_cnt") - private Integer mobileCnt; - - @Column(name = "pc_cnt") - private Integer pcCnt; - - -} \ No newline at end of file diff --git a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/dashboard/repository/TnDailyUserLogRepository.java b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/dashboard/repository/TnDailyUserLogRepository.java deleted file mode 100644 index 4074153..0000000 --- a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/dashboard/repository/TnDailyUserLogRepository.java +++ /dev/null @@ -1,22 +0,0 @@ -package com.dbnt.kcscbackend.admin.dashboard.repository; - -import com.dbnt.kcscbackend.admin.dashboard.entity.TnDailyUserLog; -import org.springframework.data.jpa.repository.JpaRepository; -import org.springframework.data.jpa.repository.Query; -import org.springframework.data.repository.query.Param; - -import java.time.LocalDate; -import java.util.List; - -public interface TnDailyUserLogRepository extends JpaRepository { - List findByLogDtBetweenOrderByLogDt(LocalDate startDate, LocalDate endDate); - - @Query(value = "SELECT TO_CHAR(log_dt, 'YYYYMM') as log_dt, " - + "SUM(log_cnt) as log_cnt " - + "FROM tn_daily_user_log " - + "WHERE log_dt BETWEEN :startDate AND :endDate " - + "GROUP BY TO_CHAR(log_dt, 'YYYYMM') " - + "ORDER BY log_dt", nativeQuery = true) - List selectMonthlyUserLogStatistics(@Param("startDate") LocalDate startDate, @Param("endDate") LocalDate endDate); - -} diff --git a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/logs/entity/ThLoginLog.java b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/logs/entity/ThLoginLog.java new file mode 100644 index 0000000..cfbe5c9 --- /dev/null +++ b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/logs/entity/ThLoginLog.java @@ -0,0 +1,44 @@ +package com.dbnt.kcscbackend.admin.logs.entity; + +import lombok.Getter; +import lombok.NoArgsConstructor; +import lombok.Setter; +import lombok.experimental.Accessors; +import org.hibernate.annotations.DynamicInsert; +import org.hibernate.annotations.DynamicUpdate; +import org.springframework.format.annotation.DateTimeFormat; + +import javax.persistence.*; +import java.time.LocalDate; +import java.time.LocalDateTime; + +@Getter +@Setter +@Accessors(chain = true) +@Entity +@NoArgsConstructor +@DynamicInsert +@DynamicUpdate +@Table(name = "th_login_log") +public class ThLoginLog { + @Id + @GeneratedValue(strategy = GenerationType.IDENTITY) + @Column(name = "ll_seq") + private Long llSeq; + + @Column(name = "user_id") + private String userId; + + @Column(name = "access_dt") + @DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss") + private LocalDateTime accessDt; + + @Column(name = "ip_address") + private String ipAddress; + + @Column(name = "session_id") + private String sessionId; + + @Column(name = "access_type") + private String accessType; +} diff --git a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/logs/entity/TnDailyUserConnLog.java b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/logs/entity/TnDailyUserLog.java similarity index 78% rename from kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/logs/entity/TnDailyUserConnLog.java rename to kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/logs/entity/TnDailyUserLog.java index 9ae62a7..d9f6f5f 100644 --- a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/logs/entity/TnDailyUserConnLog.java +++ b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/logs/entity/TnDailyUserLog.java @@ -10,7 +10,6 @@ import org.springframework.format.annotation.DateTimeFormat; import javax.persistence.*; import java.time.LocalDate; -import java.awt.*; @Getter @Setter @@ -20,15 +19,22 @@ import java.awt.*; @DynamicInsert @DynamicUpdate @Table(name = "tn_daily_user_log") -public class TnDailyUserConnLog { +public class TnDailyUserLog { @Id + @GeneratedValue(strategy = GenerationType.IDENTITY) @Column(name = "dul_seq") private Long dulSeq; - @Column(name = "log_cnt") - private Long logCnt; - @Column(name = "log_dt") @DateTimeFormat(pattern = "yyyy-MM-dd") private LocalDate logDt; + + @Column(name = "log_cnt") + private Long logCnt; + + @Column(name = "mobile_cnt") + private Long mobileCnt; + + @Column(name = "pc_cnt") + private Long pcCnt; } diff --git a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/logs/repository/PrivacyLogsRepository.java b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/logs/repository/PrivacyLogsRepository.java index ad0fe00..df86bd4 100644 --- a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/logs/repository/PrivacyLogsRepository.java +++ b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/logs/repository/PrivacyLogsRepository.java @@ -5,6 +5,6 @@ import org.springframework.data.jpa.repository.JpaRepository; import java.util.List; -public interface PrivacyLogsRepository extends JpaRepository { +public interface PrivacyLogsRepository extends JpaRepository { List findAllByOrderByUplSeqDesc(); } diff --git a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/logs/repository/ThLoginLogRepository.java b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/logs/repository/ThLoginLogRepository.java new file mode 100644 index 0000000..f79973b --- /dev/null +++ b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/logs/repository/ThLoginLogRepository.java @@ -0,0 +1,12 @@ +package com.dbnt.kcscbackend.admin.logs.repository; + +import com.dbnt.kcscbackend.admin.logs.entity.ThLoginLog; +import org.springframework.data.jpa.repository.JpaRepository; + +import java.time.LocalDateTime; +import java.util.List; + +public interface ThLoginLogRepository extends JpaRepository { + + List findByUserIdAndAccessDtAfter(String userId, LocalDateTime accessDt); +} diff --git a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/logs/repository/UserLogsRepository.java b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/logs/repository/UserLogsRepository.java index 8c8d67e..9d175a3 100644 --- a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/logs/repository/UserLogsRepository.java +++ b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/logs/repository/UserLogsRepository.java @@ -1,13 +1,15 @@ package com.dbnt.kcscbackend.admin.logs.repository; -import com.dbnt.kcscbackend.admin.logs.entity.TnDailyUserConnLog; +import com.dbnt.kcscbackend.admin.logs.entity.TnDailyUserLog; import org.springframework.data.jpa.repository.JpaRepository; import org.springframework.data.jpa.repository.Query; import org.springframework.data.repository.query.Param; +import java.time.LocalDate; import java.util.List; +import java.util.Optional; -public interface UserLogsRepository extends JpaRepository { +public interface UserLogsRepository extends JpaRepository { @Query(value = "SELECT COUNT(DISTINCT log_dt) " + "FROM tn_daily_user_log " @@ -21,5 +23,5 @@ public interface UserLogsRepository extends JpaRepository selectCountUser(@Param("startDate") String startDate, @Param("endDate") String endDate); - + Optional findByLogDt(LocalDate logDt); } diff --git a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/logs/service/AdminLogsService.java b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/logs/service/AdminLogsService.java index 8059cf6..5ac6529 100644 --- a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/logs/service/AdminLogsService.java +++ b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/admin/logs/service/AdminLogsService.java @@ -1,13 +1,18 @@ package com.dbnt.kcscbackend.admin.logs.service; +import com.dbnt.kcscbackend.admin.logs.entity.ThLoginLog; import com.dbnt.kcscbackend.admin.logs.entity.ThPrivacyLog; +import com.dbnt.kcscbackend.admin.logs.entity.TnDailyUserLog; import com.dbnt.kcscbackend.admin.logs.repository.PrivacyLogsRepository; +import com.dbnt.kcscbackend.admin.logs.repository.ThLoginLogRepository; +import com.dbnt.kcscbackend.admin.logs.repository.UserLogsRepository; import lombok.RequiredArgsConstructor; import org.egovframe.rte.fdl.cmmn.EgovAbstractServiceImpl; import org.springframework.stereotype.Service; import org.springframework.transaction.annotation.Transactional; import java.time.LocalDate; +import java.time.LocalDateTime; import java.util.HashMap; import java.util.List; import java.util.Map; @@ -17,6 +22,8 @@ import java.util.Map; public class AdminLogsService extends EgovAbstractServiceImpl { private final PrivacyLogsRepository privacyLogsRepository; + private final ThLoginLogRepository loginLogRepository; + private final UserLogsRepository userLogsRepository; public Map selectPrivacyList() { Map resultMap = new HashMap<>(); @@ -46,4 +53,44 @@ public class AdminLogsService extends EgovAbstractServiceImpl { log.setTargetUserId(targetUserId); privacyLogsRepository.save(log); } + + @Transactional + public void insertLoginLog(String userId, String ipAddress, String accessToken, String accessType, String webType){ + ThLoginLog loginLog = new ThLoginLog(); + loginLog.setUserId(userId); + loginLog.setIpAddress(ipAddress); + loginLog.setSessionId(accessToken); + loginLog.setAccessType(accessType); + loginLog.setAccessDt(LocalDateTime.now()); + loginLogRepository.save(loginLog); + + // 로그인 기록이면 tn_daily_yser_log 카운트 조정 + if(accessType.equals("Y")){ + //오늘 일자 로그 조회 + TnDailyUserLog userConnLog = userLogsRepository.findByLogDt(LocalDate.now()).orElse(null); + if(userConnLog==null){ + userConnLog = new TnDailyUserLog(); + userConnLog.setLogDt(LocalDate.now()); + userConnLog.setLogCnt(0L); + userConnLog.setMobileCnt(0L); + userConnLog.setPcCnt(0L); + } + if(webType.equals("PC")){ + userConnLog.setPcCnt(userConnLog.getPcCnt()+1); + }else{ + userConnLog.setMobileCnt(userConnLog.getMobileCnt()+1); + } + //같은 일자 로그인 기록 확인 + LocalDateTime now = LocalDateTime.now(); + now = now.minusHours(now.getHour()); + now = now.minusMinutes(now.getMinute()); + now = now.minusSeconds(now.getSecond()); + List todayLoginLog = loginLogRepository.findByUserIdAndAccessDtAfter(userId, now); + if(todayLoginLog.size()==1){ + userConnLog.setLogCnt(userConnLog.getLogCnt()+1); + } + userLogsRepository.save(userConnLog); + + } + } } diff --git a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/commonCode/repository/TnCmtOrgRepository.java b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/commonCode/repository/TnCmtOrgRepository.java index c3ff2ac..5ab14c3 100644 --- a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/commonCode/repository/TnCmtOrgRepository.java +++ b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/commonCode/repository/TnCmtOrgRepository.java @@ -2,12 +2,42 @@ package com.dbnt.kcscbackend.commonCode.repository; import com.dbnt.kcscbackend.commonCode.entity.TnCmtOrg; import org.springframework.data.jpa.repository.JpaRepository; +import org.springframework.data.jpa.repository.Query; +import org.springframework.data.repository.query.Param; import java.util.List; +import java.util.Map; public interface TnCmtOrgRepository extends JpaRepository { List findByUseYnAndUpCmtSeqOrderByCmtOrder(String useYn, Long upCmtSeq); TnCmtOrg findByUseYnAndCmtSeq(String useYn, Long cmtSeq); List findByUseYnAndUpCmtSeqAndCmtTypeOrderByCmtOrder(String useYn, Long upCmtSeq, String cmtType); + + @Query(value = "CALL sp_add_tn_cmt_org (" + + ":_cmt_nm, " + + ":_cmt_type, " + + ":_cmt_desc, " + + ":_up_cmt_seq, " + + ":_cmt_order, " + + ":_modi_id, " + + ":_cmt_seq, " + + ":_result_count, " + + ":_result_code, " + + ":_error_message)", + nativeQuery = true) + Map spAddTnCmtOrg( + @Param("_cmt_nm") String cmtNm, + @Param("_cmt_type") String cmtType, + @Param("_cmt_desc") String cmtDesc, + @Param("_up_cmt_seq") Integer upCmtSeq, + @Param("_cmt_order") Integer cmtOrder, + @Param("_modi_id") String modiId, + @Param("_cmt_seq") Integer evtSeq, + @Param("_result_count") Integer resultCount, + @Param("_result_code") String resultCode, + @Param("_error_message") String errorMessage + ); + + } diff --git a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/config/security/CustomLogoutSuccessHandler.java b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/config/security/CustomLogoutSuccessHandler.java index ccab17e..f90126d 100644 --- a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/config/security/CustomLogoutSuccessHandler.java +++ b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/config/security/CustomLogoutSuccessHandler.java @@ -1,7 +1,11 @@ package com.dbnt.kcscbackend.config.security; + +import com.dbnt.kcscbackend.admin.logs.service.AdminLogsService; import com.dbnt.kcscbackend.auth.entity.UserInfo; import com.dbnt.kcscbackend.config.jwt.EgovJwtTokenUtil; +import com.dbnt.kcscbackend.config.util.ClientUtils; +import lombok.RequiredArgsConstructor; import org.springframework.context.annotation.Configuration; import org.springframework.http.MediaType; import org.springframework.http.converter.json.MappingJackson2HttpMessageConverter; @@ -9,11 +13,7 @@ import org.springframework.http.server.ServletServerHttpResponse; import org.springframework.security.core.Authentication; import org.springframework.security.core.context.SecurityContextHolder; import org.springframework.security.core.userdetails.UserDetails; -import org.springframework.security.web.authentication.SimpleUrlAuthenticationSuccessHandler; import org.springframework.security.web.authentication.logout.LogoutSuccessHandler; -import org.springframework.security.web.savedrequest.HttpSessionRequestCache; -import org.springframework.security.web.savedrequest.RequestCache; -import org.springframework.security.web.savedrequest.SavedRequest; import javax.servlet.ServletException; import javax.servlet.http.Cookie; @@ -23,7 +23,10 @@ import java.io.IOException; import java.util.HashMap; @Configuration +@RequiredArgsConstructor public class CustomLogoutSuccessHandler implements LogoutSuccessHandler { + private final EgovJwtTokenUtil jwtTokenUtil; + private final AdminLogsService adminLogsService; @Override public void onLogoutSuccess(HttpServletRequest request, HttpServletResponse response, Authentication authentication) throws IOException, ServletException { @@ -37,6 +40,11 @@ public class CustomLogoutSuccessHandler implements LogoutSuccessHandler { HashMap resultMap = new HashMap(); resultMap.put("resultCode", "200"); + + //로그아웃 이력 생성 + String accessToken = request.getHeader("Authorization"); + adminLogsService.insertLoginLog(jwtTokenUtil.getUserIdFromToken(accessToken), ClientUtils.getRemoteIP(request), accessToken, "N", ClientUtils.getWebType(request)); + if (jsonConverter.canWrite(resultMap.getClass(), jsonMimeType)) { jsonConverter.write(resultMap, jsonMimeType, new ServletServerHttpResponse(response)); } diff --git a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/config/security/CustomUrlAuthenticationSuccessHandler.java b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/config/security/CustomUrlAuthenticationSuccessHandler.java index 04d3650..d55c441 100644 --- a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/config/security/CustomUrlAuthenticationSuccessHandler.java +++ b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/config/security/CustomUrlAuthenticationSuccessHandler.java @@ -1,5 +1,6 @@ package com.dbnt.kcscbackend.config.security; +import com.dbnt.kcscbackend.admin.logs.service.AdminLogsService; import com.dbnt.kcscbackend.auth.entity.UserInfo; import com.dbnt.kcscbackend.config.common.ResponseCode; import com.dbnt.kcscbackend.config.egov.EgovProperties; @@ -26,11 +27,13 @@ import java.util.Arrays; import java.util.HashMap; import java.util.List; -@RequiredArgsConstructor + @Configuration +@RequiredArgsConstructor public class CustomUrlAuthenticationSuccessHandler extends SimpleUrlAuthenticationSuccessHandler { private final EgovJwtTokenUtil jwtTokenUtil; + private final AdminLogsService adminLogsService; private RequestCache requestCache = new HttpSessionRequestCache(); private static final List adminIpList = Arrays.asList(EgovProperties.getProperty("Globals.admin.allow-ip").split(",")); @@ -53,12 +56,14 @@ public class CustomUrlAuthenticationSuccessHandler extends SimpleUrlAuthenticati securityUser = (UserInfo) principal; } } + String accessIp = ClientUtils.getRemoteIP(request); + // application/json(ajax) 요청일 경우 아래의 처리! MappingJackson2HttpMessageConverter jsonConverter = new MappingJackson2HttpMessageConverter(); MediaType jsonMimeType = MediaType.APPLICATION_JSON; HashMap resultMap = new HashMap<>(); - - /*if(securityUser.getUserId().equals("admin") && !adminIpList.contains(ClientUtils.getRemoteIP(request))){ + + /*if(securityUser.getUserId().equals("admin") && !adminIpList.contains(accessIp)){ resultMap.put("resultCode", ResponseCode.FAILED.getCode()); resultMap.put("resultMessage", "관리자 계정은 지정된 아이피에서만 접속할 수 있습니다.\n필요한 경우 관리자에게 요청하십시오.\n접속자 아이피: "+ClientUtils.getRemoteIP(request)); }else{ @@ -78,6 +83,9 @@ public class CustomUrlAuthenticationSuccessHandler extends SimpleUrlAuthenticati resultMap.put("accessToken", accessToken); resultMap.put("refreshToken", refreshToken); + //로그인 로그 기록 + adminLogsService.insertLoginLog(securityUser.getUserId(), accessIp, accessToken, "Y", ClientUtils.getWebType(request)); + if (jsonConverter.canWrite(resultMap.getClass(), jsonMimeType)) { jsonConverter.write(resultMap, jsonMimeType, new ServletServerHttpResponse(response)); } diff --git a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/config/security/SecurityConfig.java b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/config/security/SecurityConfig.java index 6c81b8a..db4eea9 100644 --- a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/config/security/SecurityConfig.java +++ b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/config/security/SecurityConfig.java @@ -1,5 +1,6 @@ package com.dbnt.kcscbackend.config.security; +import com.dbnt.kcscbackend.admin.logs.service.AdminLogsService; import com.dbnt.kcscbackend.config.jwt.EgovJwtTokenUtil; import com.dbnt.kcscbackend.config.jwt.JwtAuthenticationEntryPoint; import com.dbnt.kcscbackend.config.jwt.JwtAuthenticationFilter; @@ -49,6 +50,7 @@ public class SecurityConfig { private UserDetailsService loginService; private final ObjectMapper objectMapper; private final EgovJwtTokenUtil egovJwtTokenUtil; + private final AdminLogsService adminLogsService; //Http Methpd : Get 인증예외 List private String[] AUTH_GET_WHITELIST = { @@ -131,7 +133,7 @@ public class SecurityConfig { http.addFilterBefore(jsonUsernamePasswordAuthenticationFilter(), UsernamePasswordAuthenticationFilter.class); - http.logout().logoutRequestMatcher(new AntPathRequestMatcher("/auth/logout")).logoutSuccessHandler(new CustomLogoutSuccessHandler()); + http.logout().logoutRequestMatcher(new AntPathRequestMatcher("/auth/logout")).logoutSuccessHandler(new CustomLogoutSuccessHandler(egovJwtTokenUtil, adminLogsService)); return http.build(); } @@ -145,7 +147,7 @@ public class SecurityConfig { @Bean public JsonAuthenticationFilter jsonUsernamePasswordAuthenticationFilter() { - JsonAuthenticationFilter jsonAuthenticationFilter = new JsonAuthenticationFilter(objectMapper, new CustomUrlAuthenticationSuccessHandler(egovJwtTokenUtil), loginFailureHandler()); + JsonAuthenticationFilter jsonAuthenticationFilter = new JsonAuthenticationFilter(objectMapper, new CustomUrlAuthenticationSuccessHandler(egovJwtTokenUtil, adminLogsService), loginFailureHandler()); jsonAuthenticationFilter.setAuthenticationManager(authenticationManager()); return jsonAuthenticationFilter; } diff --git a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/config/util/ClientUtils.java b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/config/util/ClientUtils.java index 0581e9f..ee2a028 100644 --- a/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/config/util/ClientUtils.java +++ b/kcsc-back-end/src/main/java/com/dbnt/kcscbackend/config/util/ClientUtils.java @@ -29,4 +29,20 @@ public class ClientUtils { return ip; } + + public static String getWebType(HttpServletRequest request) { + String filter = "iphone|ipod|android|windows ce|blackberry|symbian|windows phone|webos|opera mini|opera mobi|polaris|iemobile|lgtelecom|nokia|sonyericsson|lg|samsung"; + String filters[] = filter.split("\\|"); + String webType = ""; + + for(String tmp : filters){ + if (request.getHeader("User-Agent").toLowerCase().contains(tmp)) { + webType = "MOBILE"; + break; + } else { + webType = "PC"; + } + } + return webType; + } }