신규 filter 추가
- 기존에 properties를 통해 직접 controller를 매핑하는 방식과 if문을 통해 분기처리를하는 굉장히 난잡한 방식을 사용했다..
- 기존 Controller
@Override
protected ModelAndView handleRequestInternal(HttpServletRequest request, HttpServletResponse response) {
String requestName = null; // 요청 명
ModelAndView mav = new ModelAndView(); // 기본 뷰어
mav.setViewName("common/error");
try {
requestName = CommonUtil.getURItoFileName(request);
if(requestName.startsWith("http://") || requestName.startsWith("https://")){
this.logger.info("REDIRECT : " + requestName);
RedirectView rv = new RedirectView(requestName);
rv.setExposeModelAttributes(true);
mav = new ModelAndView(rv);
return mav;
}
String ip = getAccessIp(request);
this.logger.info("===============================================================");
this.logger.info("요청 : " + requestName);
this.logger.info("주소 : " + ip);
Enumeration<String> paramNames = request.getParameterNames();
Map<String, String> parameters = new HashMap<String, String>();
parameters.put("requestName", requestName);
this.logger.info( "request.getCharacterEncoding() : " + request.getCharacterEncoding() ) ;
this.logger.info( "request.getMethod() : " + request.getMethod() ) ;
while(paramNames.hasMoreElements()){
String key = paramNames.nextElement();
this.logger.info("parameter : " + key.toLowerCase() + "[" + CommonUtil.decodeUrl(request.getParameter(key)) + "]");
if("login/loginCheck".equals(requestName) || "login/login".equals(requestName)) {
parameters.put(key.toLowerCase(), request.getParameter(key));
continue;
}
parameters.put(key.toLowerCase(), CommonUtil.decodeUrl(request.getParameter(key)));
}
//로그인 정보 반환
HttpSession session = request.getSession();
parameters = SessionUtil.getSession(request,session, parameters);
if("login/loginForm".equals(requestName)) { // ## 로그인 폼
mav = this.processLoginForm(parameters, request, response);
} else if("login/loginCheck".equals(requestName)) { // ## 로그인 체크
mav = this.processloginCheck(parameters, request, response);
} else if("login/login".equals(requestName)) { // ## 로그인
mav = this.processLogin(parameters, request, response, ip);
} else if("login/logout".equals(requestName)) { // ## 로그아웃
mav = this.processLogout(parameters, session, response);
} else if("login/rePassword".equals(requestName)) { // ## 비밀번호 재설정 이메일 전송폼
mav = this.processRepassword(parameters, request);
} else if("login/rePasswordComp".equals(requestName)) { // ## 비밀번호 이메일 전송 완료
mav = this.processRepasswordComp(parameters, request);
} else if("login/newPassword".equals(requestName)) { // ## 비밀번호 재설정 폼
mav = this.processNewpassword(parameters, request);
} else if("login/newPasswordComp".equals(requestName)) { // ## 비밀번호 재설정 완료
mav = this.processNewpasswordComp(parameters, request);
} else if("login/newPasswordComp".equals(requestName)) { // ## 비밀번호 재설정 완료
mav = this.processNewpasswordComp(parameters, request);
} else if("login/newPasswordComp".equals(requestName)) { // ## 비밀번호 재설정 완료
mav = this.processNewpasswordComp(parameters, request);
}
if(mav != null) {
mav.addObject("param" , parameters);
// mav.addObject("serverUrl" , CommonUtil.getProperties("daemon", "common.server.addr"));
}
} catch (Exception e) {
e.printStackTrace();
}
return mav;
}
- 그래서 interceptor를 통해 전후처리를 하고 requestmappfing방식으로 변경하였으나 parameter를 조작하는것은 interceptor가 아닌 filter를 통해 처리해야하기에 추가로 커스텀 필터를 만들고 적용해야했다.
- (시키지도않은거 괜히 사서 고생하는거 같으나 어짜피 개발은 내가 하니까.. 유지보수에도 좋은 코드로 변경해야겠다 생각함)
- 그 많은 컨트롤러 및 서비스단을 수정할수 없기에 HttpServeltRequestWrapper 를 상속받아 session값을 파라미터에 추가했다
public class HttpsRequestWrapper extends HttpServletRequestWrapper {
private HttpServletResponse response;
public HttpsRequestWrapper(HttpServletRequest request) {
super(request);
// session 값 parameter추가
Map<String,String[]> parameterMap = request.getParameterMap();
Map<String,String> parameters = SessionUtil.getSession(request,request.getSession());
for(Map.Entry<String,String> entry : parameters.entrySet()){
String key = entry.getKey();
String value = entry.getValue();
parameterMap.put(key, new String[]{value});
}
}
}
public class RequestWrapperFilter extends OncePerRequestFilter {
//private static final Logger logger = LoggerFactory.getLogger(RequestWrapperFilter.class);
@Override
protected void doFilterInternal(HttpServletRequest request, HttpServletResponse response,
FilterChain filterChain) throws ServletException, IOException {
HttpsRequestWrapper httpsRequest = new HttpsRequestWrapper((HttpServletRequest)request);
filterChain.doFilter(cleanRequest, response);
}
}
Tomcat 설정
- 기존 운영중인 프로젝트와 포트만 다르게 띄워서 나중에 테스트 완료후 포트번호만 교체할 예정
- 9버전대 톰캣 서버에 업로드 & JVM 옵션 추가 & 권한 설정 & 포트설정
- tomcat 포트 변경 ( ~/tomcat/server.xml )
<!-- Note: A "Server" is not itself a "Container", so you may not
define subcomponents such as "Valves" at this level.
Documentation at /docs/config/server.html
-->
<Server port="8405" shutdown="SHUTDOWN">
<!-- ~~ -->
<!-- A "Connector" represents an endpoint by which requests are received
and responses are returned. Documentation at :
Java HTTP Connector: /docs/config/http.html
Java AJP Connector: /docs/config/ajp.html
APR (HTTP/AJP) Connector: /docs/apr.html
Define a non-SSL/TLS HTTP/1.1 Connector on port 8080
-->
<Connector port="8480" protocol="HTTP/1.1"
connectionTimeout="20000"
redirectPort="8443" />
<!-- ~~ -->
<!-- Define an AJP 1.3 Connector on port 8009 -->
<Connector port="8409" protocol="AJP/1.3" redirectPort="8443" />
# root 권한이 아닌 다른 계정사용시
chown -R enber:enber /home/apache-tomcat-9.0.14
# sh 파일 명령어 권한 수정
sudo find /home/apache-tomcat-9.0.14 -type f -name "*.sh" -exec chmod +x {} \;
# 추가로 심볼릭 링크 수정 필요 시
ln -sfn apache-tomcat-9.0.14 tomcat
- jvm옵션 추가 (~/tomcat/bin/set.env)
# setenv.sh
export JAVA_HOME="/usr/local/src/java1.8"
export PATH=$JAVA_HOME/bin:$PATH
export CATALINA_OPTS="-Xms512m -Xmx1024m"
export JAVA_OPTS="-Dfile.encoding=UTF-8 -Dspring.profiles.active=dev -Dlog4j.configurationFile=classpath:profile/dev/log4j2.xml"
Gradle을 통한 SSH 자동배포 배포스크립트
- ssh 접속을 위해 선행작업으로 공개키 설정을 해야한다
- 로컬 cmd를 통해 키확인 : ssh-keygen -t rsa -b 4096 -m PEM -f ~/.ssh/id_rsa
- 개발서버 ssh 접속 후 붙여넣기 : echo "ssh-rsa AAAAB3...복사한키..." >> ~/.ssh/authorized_keys
- 로컬에서 ssh 접속 시 비밀번호 없이 접속되면 적용완료 : sh -i ~/.ssh/id_rsa root@<서버_IP>
- deploy.gradle
def deployProps = new Properties()
file("$rootDir/deploy.properties").withInputStream { deployProps.load(it) }
// ssh
def deployHost = deployProps.getProperty("dev.deployHost")
def deployUser = deployProps.getProperty("dev.deployUser")
def tomcatDir = '/home/tomcat'
def warFile = file("$buildDir/libs/${project.name}-${version}.war")
def renamedWar = file("$buildDir/libs/ROOT.war")
apply plugin: 'war'
ssh.settings {
knownHosts = allowAnyHosts // 처음 연결도 허용
}
remotes {
decServer {
host = deployHost
user = deployUser
identity = file("${System.properties['user.home']}/.ssh/id_rsa")
}
}
tasks.register('prepareRootWar') {
dependsOn 'clean', 'build'
build.mustRunAfter(clean)
doLast {
println "📦 Rename ${warFile.name} → ROOT.war"
copy {
from warFile
into renamedWar.parent
rename { "ROOT.war" }
}
}
}
tasks.register('deployWar') {
group = 'deploy'
description = 'Build WAR and deploy to remote Tomcat server via SSH'
dependsOn 'prepareRootWar'
doLast {
ssh.run {
session(remotes.decServer) {
// 1. tomcat stop
try {
println "🛑 Stopping Tomcat..."
execute "if [ -f \\"${tomcatDir}/bin/shutdown.sh\\" ]; then sudo -u enber ${tomcatDir}/bin/shutdown.sh || true; fi"
} catch (Exception e) {
println "⚠️ Tomcat shutdown failed or already stopped (ignorable): ${e.message}"
}
println "⏳ Waiting for Tomcat to fully stop..."
execute "sleep 3"
// 2. tomcat clean
println "🧹 Cleaning up previous ROOT WARs and exploded ROOT directories..."
execute "rm -f ${tomcatDir}/webapps/ROOT.war"
execute "rm -rf ${tomcatDir}/webapps/ROOT"
println "🧹 Cleaning up Tomcat work/temp cache..."
execute "rm -rf ${tomcatDir}/work/*"
execute "rm -rf ${tomcatDir}/temp/*"
println "🧹 Cleaning up ROOT context XML (if any)..."
execute "rm -f ${tomcatDir}/conf/Catalina/localhost/ROOT.xml"
// 3. war deploy
println "⬆️ Uploading WAR: ROOT.war"
put from: file("$buildDir/libs/ROOT.war"), into: "${tomcatDir}/webapps/"
execute "sleep 2"
// 4. tomcat start
println "🚀 Starting Tomcat..."
execute "sudo -u enber ${tomcatDir}/bin/startup.sh"
// 5. 권한 변경 추가
execute "sleep 3"
println "🔐 Setting permissions for WAR and exploded directory"
execute "chown enber:enber ${tomcatDir}/webapps/ROOT.war"
execute "chown -R enber:enber ${tomcatDir}/webapps/ROOT || true"
}
}
}
}