Tagged: java

Error – The server time zone value ‘KST’ is unrecognized

Java 와 MySQL 을 연동하는 상황에서 다음과 같은 오류를 만나기도 한다.

자세히 보면 java.sql.SQLException 이 보인다. 이 경우는 결국에는 데이터베이스쪽에 문제가 있다는 것이며, MySQL을 사용할 경우에 보이게 된다. 이는 MySQL의 시간을 나타내는 타임존 설정이 맞지 않아 생기는 오류다.

MySQL 5.7, MariaDB 10

MySQL 5.7 과 MariaDB 10 을 사용한다면 my.cnf 에서 다음과 같이 설정함으로써 문제 해결이 가능하다.

설정할 수 있는 타임존 리스트는 MySQL 메뉴얼을 참조하기 바란다. 이렇게 했는데도 다음과 같은 오류를 만날 가능성도 있다.

이럴때는 다음과 같이 해준다.

Tomcat 설치 디렉토리 구성

과거에 Tomcat Multi Instance 설치에 관해서 쓴 글이 있다. Multi Instance 설치에서 핵심은 CATANINA_HOME과 CATALINA_BASE 를 분리하는데 있다.

오늘은 한발 더 들어가서 배포를 위한 설정과 시작, 종료 스크립트의 변경등에 대해서 이야기해보고자 한다.

Multi Instance 구성

Tomcat 을 다운로드 받아 압축을 풀면 그것이 곧 CATALINA_HOME 이 된다. 그리고 CATALINA_BASE 를 위해서 conf 디렉토리를 복사해주고 bin, lib, logs, temp, webapps, work 디렉토리를 생성해준다. 그리고 더블어서 war 파일을 배포를 위한 디렉토리를 Deployments 를 생성해주고 PID 저장을 위한 run 디렉토리도 생성해준다.

CATALINA_HOME 에서 복사해주는 디렉토리는 conf 밖에 없다는걸 상기해야 한다.

setenv.sh 작성

catalina.sh 스크립트를 보면 Tomcat 를 위한 설정등은 setenv.sh 를 읽어오도록 되어 있다.

CATALINA_BASE/bin/setsenv.sh 를 먼저 확인하고 없으면 CATALINA_HOME/bin/setenv.sh 를 찾도록 되어 있다.

setenv.sh 에는 CATALINA_OPTS, JAVA_OPTS 등의 환경변수등을 설정할 수 있다.  환경변수에 대해서는 catalina.sh 파일을 열어보면 자세히 나온다.

‘-Dport.http’ 와 같은 변수 선언은 server.xml 에 다음과 같이 활용할 수 있다.

그리고 이제 start.sh 와 shutdown.sh 는 다음과 같이 아주 간단하게 작성하면 된다.

CATALINA_HOME, CATALINA_BASE 디렉토리를 함께 정의해 준다.

기본적은 환경 변수를 start.sh, shutdown.sh 에 넣어주거나 하니면 별도로 빼서 소스해줘도 된다.

배포

Tomcat 에는 appBase, docBase 와 같은 지시자가 존재한다. 이것을 별도로 지정하지 않으면 webapps 디렉토리가 appBase, docBase 가 된다. 이를 분리하면 war 파일 배포와 app 실행 디렉토리를 분리할 수 있게 된다.

이를 위해서 먼저 server.xml 에서 다음과 같이 설정을 변경한다.

위와같이 Context 에서 docBase 로 war 파일을 지정하면 된다. 이렇게하면 war 파일을 읽어서 webapps 디렉토리에 압축을 해제하게 된다.

이렇게해야 하는 이유가 있는데, war 파일을 배포하는 디렉토리의 소유권을 배포계정으로 하고 others 에 읽기(read) 퍼미션만 준다. 즉, 운영계정과 배포 계정을 분리해서 운영할 수 있게 된다는 것이다.

배포는 conf/CATALINA/${virtualhost}/ 디렉토리에 context 이름으로 xml 파일을 작성해도 배포가 된다. Multi Instance 를 구성하게 되면 Manager 가 없게 된다. 그런데, 많은 사람들은 이를 CATALINA_HOME/webapps/manager 디렉토리를 CATALINA_BASE/webapps 디렉토리에 복사해 넣는다. 하지만 그렇게 하지 않아도 된다.

이를 ${catalina.base}/conf/Catalina/localhost/manager.xml 파일로 작성한다.

그러면 Tomcat 은 이를 읽어서 manager context 를 실행 준다.

왜 이렇게 하나?

CATALINA_HOME 과 CATALINA_BASE 를 분리하면 좋은 점이 업그레이드를 해야할 경우 나타난다.

몇몇 프로젝트하는 곳에서 Tomcat 설치된 것을 보면 CATALINA_HOME 에 startup.sh 파일이나 catalina.sh 파일을 직접 수정하는 경우를 볼 수 있다. 만일 보안 업데이트가 발생해 이를 Tomcat 업데이트를 해야한 경우라면 startup.sh, catalina.sh 파일을 새롭게 수정해줘야 한다.

하지만 CATALINA_HOME 과 CATALINA_BASE 를 분리하면 CATALINA_HOME 은 건드린게 없기 때문에 그냥 새로운 버전의 Tomcat 으로 바꿔치기하면 그만이다.

이는 휴먼 에러를 줄이는 확실한 방법이며 보안 업데이트 시간을 단축시켜준다.

 

Spring5 requirements

Spring5 를위한 필요사항들을 정리.

  1. java 8. 원래 Spring5 는 Java 9를 기반으로 하려고 했지만 변경됐다. 이로 인해서 Reactive Programming을 하기 위해서는 의존성 라이브러리를 필요로 한다. 현재Java 9 은 지원이 중단된 상태다. Java 10 을 사용해도 된다.
  2. Java EE 8 호환. Servlet 4.0, Bean Validation 2.0 등을 지원한다.
  3. HTTP/2 지원한다.
  4. Jackson 2.9, Protobuf 3.0 지원.

 

시간 대역 체크하기

Java 프로그래밍을 하다보면 시간을 다루게 된다. 만일 점심시간인지 아닌지를 시간을 체크하고 싶다면 어떻게 할까? 대략 다음과 같이 할 수 있다.

isAfter, isBefore 메소드를 이용하면 손쉽게 체크할 수 있다.

Java BookMark

Maven 저장소 URL 변경하기

Maven 3 을 쓰다보면  Update나 Build 시에 Maven은 어딘서가 의존성 패키지를 다운받는다. 다운받은 파일을 어디에 저장할 것인가 를 지정하는것이 localRepository 이다.

문제는 어딘가에서 받아오는 저장소 URL 이 간혹 접속이 불가할 경우가 문제가 된다. 나 같은 경우에 일하고 있는 사무실 환경에서는 어찌된 영문인지 Maven이 패키지를 제대로 가지고 오지 못하고 있었다. 원인은 “Connection Time Out” 으로서 “https://repo.maven.apache.org/maven2” 에 접속이 되지 않아 발생 했다. 자세히 보니 https 로 접속이 안되는 문제였다.

이와같이 접속이 불가능 할 경우에는 Maven 저장소 URL 을 바꿀 필요가 있다.

pom.xml 에서 바꾸기

일차적인 방법으로는 프로젝트의 pom.xml 파일에서 저장소 위치를 지정하는 것이다. 먼저 저장소 위치가 어떻게 되는지 알수가 있다. 그것은 Eclipse 에서 pom.xml 을 열면 편집영역 하단에 “Effective POM” 탭이 보인다. 여기서 중간쯤에 보면 다음과 같은 저장소 URL 이 보인다.

Maven 3 에서 기본 세팅된 저장소 URL 을 살펴 볼수 있다.

아니면 pom..xml 이 있는 프로젝트 디렉토리에서 다음과 같은 명령어로 Effective POM 상태를 출력해 볼 수 있다.

이제 기본적인 저장소 URL 을 알았으니 이것을 바꿔보자. pom.xml 탭을 클릭해 다음과 같이 바꿔보자.

이렇게 하면 Maven의 기본 저장소 URL을 변경이 된다.

Maven settings.xml 설정 파일에서 바꾸기

만일 프로젝트가 아주 많이 있다면 일일이 프로젝트마다 앞에 방법대로 pom.xml 을 수정한다는 것이 바보같은 짓이된다. 이럴때에는 Maven의 설정 파일인 settings.xml 에서 설정 해주면 된다.

다음과 같이 설정 해준다.

이렇게 변경 후 저장하고 Eclipse 를 재시작하면 모든 프로젝트에 Effective POM 을 보면 저장소 위치가 변경된 것을 확인할 수 있다.

Maven 다중 모듈 프로젝트 구성

STS Eclipse를 이용하면 손쉽게 Spring MVC 프로젝트를 구성할 수 있다. Spring MVC 프로젝트에는 Java 파일과 Web Content 파일을 모두 포함한다. 이를 Dynamic Content, Static Content 등로 구분하기도 한다.

문제는 이렇게 하나의 프로젝트에 모든 것을 담을 경우에 다음과 같은 문제가 발생할 수 있다.

  • 분리 배포가 불가능 하다. 요즘에는 WAS 앞에 Web 서버를 따로 두어 Static Content 를 서비스 하는 아키텍쳐가 많은데 하나의 프로젝트에 모든 것을 담게 되면 분리 배포가 어렵다.

단 하나의 큰 문제인데 이 문제를 가볍게 여길 수 없다. 실제 프로젝트를 할때에 이것을 간과해 나중에 아주 힘들어지는 경우가 허다 하다.

그래서 Spring MVC 기반의 프로젝트를 할때에는 Dynamic Content, Static Content를 분리해 진행하는 것이 좋은데, Maven 에서는 이를 ‘다중 모듈 프로젝트 구성’ 이라는 기능으로 제공하고 있다.

Root 프로젝트 생성

다중 모듈 프로젝트를 생성하는 첫번째는 Root 프로젝트 생성이다. 이름에서도 알수 있듯이 이 모든 모듈 프로젝트에 뿌리가 되는 프로젝트를 말한다.

이는 ‘Maven Project’ 를 통해서 생성 할 수 있다.

Maven Project 생성
Maven Project 생성

위와같이 Maven Project를 통해서 생성할때 한가지 주의해야 하는 것이 있는데, Pakaging 형태를 pom으로 해야만 한다. Root 프로젝트는 하위 프로젝트에 기반을 제공하는 것으로 별도 was 배포용 패키지를 만들지 않는다.

Root Project 에 pom Packaging
Root Project 에 pom Packaging

이렇게 하면 Root Project가 생성이 된다.

이 상태를 그대로 두고 Static Content를 위한 하위 프로젝트를 먼저 생성한다.

하위 프로젝트 생성(Static Content)

Static Content 를 위한 하위 프로젝트는 오로지 CSS, Java Script, Images 만을 위한 것이여서 Spring Mvc 샘플 프로젝트를 만들 필요는 없다. 간단하게 Maven Module 로 제작하면 된다.

앞에서 생성한 Root Project 에서 마우스 오른쪽 버튼을 눌러 Maven Module 생성하기를 시작한다. 그리고 다음과 같이 ‘maven-archetype-webapp’ 를 선택해준다.

Maven 으로 webapp 생성
Maven 으로 webapp 생성

이렇게 하면 Root Project 밑에 디렉토리로 하위 프로젝트가 위치하는게 보이고 이와 별도로 이클립스에 프로젝트로도 보인다.

Root 와 Static 프로젝트 모습
Root 와 Static 프로젝트 모습

Static 프로젝트에 pom.xml 를 보면 Root 프로젝트와 연결된 설정이 보인다.

이제 Static 의 디렉토리 구조를 바꾼다. 이는 이전에 글을 참고 하면 잘 나와 있는데 여기서는 WebContent 디렉토리만 인식시켜주면 되기 때문에 pom.xml 에 설정해주고 파일을 옮기면 된다.

그리고 Static 파일을 위한 디렉토리를 생성한 다음에 가짜 파일을 하나 만든다.

Static 파일을 위한 CSS, JS, Images 디렉토리 생성
Static 파일을 위한 CSS, JS, Images 디렉토리 생성

이렇게 한 후에 Build 를 하면 WebContent 이하 디렉토리 내용이 war 파일로 작성되어 진다. war 파일이긴하지만 Static만 있으면 되기 때문에 이 Static 파일만 담기도록 해보자. pom.xml 을 다음과 같이 수정 한다.

** 위와같이 설정해도 원하는데로 동작하지 않습니다. 아신다면 덧글 남겨 주시면 고맙겠습니다. **

이렇게 한 후에 SystemVLabs-Static 에 빌드를 하면 WebContent 디렉토리에 내용들이 war로 만들어진다. 또, RootProject 에서 빌드를 하면 하위 모듈로등록된 SystemVLabs-Static 도 빌드가 되면 정상적으로 프로젝트가 세팅된 것이다.

하위 프로젝트 생성(Dynamic Content)

이제 Dynamic Content 를 위한 하위 모듈 프로젝트를 생성해야 한다. 이는 여러 방법이 존재하는데, 내가 보기에 가장 손쉬운 방법을 설명하고자 한다.

먼저 STS Eclipse 의 Spring MVC 샘플 프로젝트를 생성한다. 그러면 기존의 RootProject와는 별도로 프로젝트가 생길 것이다.

Spring5 샘플 프로젝트
Spring5 샘플 프로젝트

이제 이것을 export 를 해주는데, File System 으로 export 를 한다.

Export를 File System 으로 한다.
Export를 File System 으로 한다.

대상 디렉토리는 RootProject 로 지정한다.

Spring5의 RootProject 로 Export
Spring5의 RootProject 로 Export

이렇게 한 후에 RootProject 를 ReFresh 하면 방금 Export 한 Spring5 디렉토리가 보인다.

이제 기존의 Spring5 프로젝트는 디스크에서 삭제도 체크해  삭제한다. 그리고 이제 프로젝트를 Import 한다.

Existing Project into Workspace
Existing Project into Workspace

“Existing Projects into Workspace” 를 선책하고 Next,

Export된 Spring5 디렉토리 지정
Export된 Spring5 디렉토리 지정

이렇게 하면 RootProject 하위가 아닌 독립된 프로젝트로 나타난다.

마지막으로 RootProject 의 pom.xml 에 방금 등록한 하위 모듈 프로젝트로 등록해 준다.

그리고 새로 등록한 하위 모듈 프로젝트의 pom.xml 에는 parent 모듈을 등록해 준다.

이렇게 함으로써 Dynamic Content 를 하위 모듈 프로젝트 등록은 다 된 것이다.

 

Tomcat plugin 을 이용한 배포.

만일 WAS 서버를 Tomcat 을 이용해 개발을 하고 있다면 Maven tomcat7 플러그인을 이용해서 배포를 할 수 있다. 참고로 이클립스의 tomcat add-on 과는 다른 것이다. 이것은 Tomcat 에서 제공하는 Manager 기능을 이용한 것이다.

그리고 이 문서의 내용은 Tomcat 8 버전에서도 이용 가능 하다.

Tomcat 설정

Tomcat 의 Manager 기능을 이용하는 것이여서 Tomcat Manager 설정을 먼저 해줘야 한다. 아시겠지만 Manager 접근을 위해서는 인증 설정을 해줘야 하는데 이 인증은 Tomcat 의 ㅊCATALINA_HOME/conf/tomcat-users.xml 파일을 다음과 같이 설정 해준다.

Tomcat 방화벽 설정

앞서 설정을 한다고 해도 원격에서 Manager 접속은 불가능 하다. 왜냐하면 Tomcat 자체에 Manager 접속을 로컬호스트만 허용하도록 되어 있기 때문이다. 이것은 “CATALINA_HOME/webapps/manager/META-INF/context.xml” 파일에 설정되어 있다.

위 설정을 보면 ‘192.168.96.2,192.168.96.3’ 두개의 원격아이피가 허용되어 있다.

이 설정은 매우 중요하다. 모든 설정이 정상인데도 배포 실패가 나온다면 이 설정을 잘 살펴봐냐 한다.

Maven 설정(pom.xml)

이제 pom.xml 설정을 해야 한다. Maven 에서는 Tomcat Manager 에 원격 접속해 배포할수 있도록 도와주는 플러그인을 제공하는데 그 설정은 다음과 같다.

package tomcat7:[deploy|undeploy|redeploy]

tomcat7 maven 플러그인은 위 주제와 같이 사용하면 된다. Maven Build 시에 위 내용을 입력하면 설정한 Manager URL 로 배포 파일을 업로드 해주는데 이때 업로드 되는 파일 이름은 path 설정 이름으로 된다.

web.xml 스키마 예제 헤더

web.xml 스키마 헤더 예제는 버전별로 다음과 같다.

Servlet 2.5

Servlet 3.0

Servlet 3.1

Servlet 4.0

 

참고: IBM Knowledge Center

Windows JDK 1.8 Portable

최근에(2017년 11월) JAVA 9 가 발표 되었다. 이와 관련해서 이미 JAVA 9로 많은 소프트웨어가 포팅되고 배포되고 있다. 대표적으로 자바 개발 도구인 이클립스의 경우 최신버전은 JAVA 9 에서 매우 잘 동작 한다.

하지만 여전히 많은 소프트웨어가 JAVA 8 을 필요로 한다. 한 시스템에서 JDK 를 두가지 버전을 설치하는게 썩 좋아보이지 않다. 시스템에서 JAVA 9 를 메인으로 하고 JAVA 8은 포터블하게 설치해서 사용하면 얼마나 좋을까?

이 문서는 Windows 에 JDK 1.8 을 포터블 제작에 대한 것이다.

환경

  • Windows 10 64bit
  • JDK 1.8 u152
  • 7-zip 64bit

JDK 1.8 의 포터블 제작을 위한 환경은 위와 같다. 압축 프로그램이면 아무거나 다 되는거 아니냐 하겠지만 7-Zip 을 권장 한다.

압축 해제

다운받은 JDK 1.8 u152 설치 파일을(exe) 오른쪽 클릭한 후에 압축 해제한다.

JDK 1.8 u152 압축해제

압축을 해제하고 나후 디렉토리를 펼치면 위와같이 나온다.

tools.zip 파일

포터블 JDK 의 핵심은 바로 tools.zip 이다. 이 파일에는 java 의 실행파일, 라이브러리 파일등이 들어 있다. 문제는 이 파일이 안보이는데, JAVA_CAB10 디렉토리에 111 파일이 보인다. 이 파일을 압축 해제한다.

tools.zip

위 파일을 압축 해제하면 드디어 익숙해 보이는 파일들이 보인다.

tools.zip 압축해제

문제는 이걸 그대로 사용할 수가 없다는 것이다. 이 안에 많은 파일들이 *.pack 인채다.  cmd 창에서 tools.zip 압축해제한 디렉토리로 이동한 후에 다음과 같이 해준다.

그러면 다음과 같이 pack 파일이 jar 파일로 변경된다.

pack 파일을 jar로 변환.

src.zip 파일

JDK 1.8 의 소스 파일인데, 이는 다음과 같이 110 파일을 압축 해제하면 된다.

src.zip 파일

src.zip 파일을 tools.zip 압축 해제했던 디렉토리에 넣어준다.

COPYRIGHT 파일

JDK 에 COPYRIGHT 파일이 있어야 한다. 이는 다음과 같은 디렉토리에 112 파일을 압축해제하면 나온다.

JDK 1.8 COPYRIGHT 파일

압축해제해 나온 COPYRIGHT 파일을 tools.zip 압축해제한 디렉토리에 넣는다.

JDK 1.8 Portable

tools.zip 압축해제하고 pack 파일을 jar 로 전환하고 src.zip, COPYRIGHT 파일을 작성해 tools 압축해제한 디렉토리로 옮겨놨다.

이제 이 tools 디렉토리를 JDK 1.8 로 바꾸고 적당한 디렉토리로 옮겨서 사용하면 된다.

JDK 1.8 Portable

 

참고

  • https://portableapps.com/node/53015
  • https://techtavern.wordpress.com/2014/03/25/portable-java-8-sdk-on-windows/