빌드가 끝난 후 Finished: "SUCCESS" 나 "FAILURE" 둘 중 하나만 받을 수 있었다.


빌드 스크립트 상에서 System.exit(1) 을 만나거나 Exception을 만나게 되면 무조건 "FAILURE" 메시지가 떨어진다.

하지만 상황에 따라 경고성 메시지가 필요했다.


예를 들어 빌드/배포 실패 시 롤백 JOB를 호출 해야 하는 상황인데 빌드/배포 시 

유효성 검사 및 기타 작업 시점에 Exception이 발생하면 "경고",

원격지 배포 중간이라면 "에러" 발생 후 롤백 JOB을 호출 해야 했다.


유효성 검사 시점에 Exception이라도 "SUCCESS" 를 떨어뜨려 해결 했더니 배포 History 가 뭔가 깔끔치 않아 "경고" 성 메시지가 필요 했다.


빌드 후 조치 에 "Trigger parameterized build on ohter projects" 에 "Trigger when build is" 옵션에 "Failed" 이외에 값들이 있는데 어떻게 이용하는지 방법을 못 찾았다.

경고 성일때는 "Unstable" 떨어 뜨리면 OK 일텐데..



새롭게 찾은 방법은 https://wiki.jenkins-ci.org/display/JENKINS/Text-finder+Plugin 을 이용한다.

스크립트 상에서 "Failed" 이외 "Unstable" 로 떨어뜨러야 할 경우

System.exit(1) 하지 말고 정상 종료 시키고, println "UNSTABLE" 출력한다.

"UNSTABLE" 의 경우 스크립트 상과 Jenkins Text-finder Plugin 과 약속이다.(다른 문자열로 해도 된다.)


그런 후 Jenkins 에서 아래와 같이 셋팅한다.


그럼 에러와 경로를 나울 수 있고, 각각의 상황에 따라 분기 하면 될듯하다.




간단한 방법이 있는데 어렵게 돌아가는게 아닌가 싶다..ㅡㅡ;;



Gradle 이용한 간단한 원격 배포 셈플링


그룹별 병렬? 배포 - WAS Instance 가 늘더라도 배포 시간 절약

  1. WAS 유입 차단 -> 5초대기 -> WAS 중지
  2. 소스 배포 -> 소스 압축 풀기 및 설정
  3. WAS 기동
  4. 필수 서비스 체크(CURL)
  5. WAS 유입 활성화


빌드 파일과 별도 분리 해도 되고...(분리된 파일을 Jenkins에서 실행)


clean build remoteDeploy


.. .. apply plugin: 'org.hidetake.ssh' .. .. buildscript { repositories { jcenter() } dependencies { classpath 'org.hidetake:gradle-ssh-plugin:2.4.2' } } task remoteDeploy << { def startTime = System.currentTimeMillis() println "project: [$project]" def PROJECT_NM = project.name def DEPLOY_SERVERS = [] if( "$targetServer" == "dev" ){ DEPLOY_SERVERS = [ group1: [ ], ] } else if( "$targetServer" == "stage" ){ DEPLOY_SERVERS = [ group1: [ ], ] } else if( "$targetServer" == "real" ){ DEPLOY_SERVERS = [ group1: [ [host: "dkwas01", user: "tomcat", wasHome: "/usr/local/tomcat/domains/test11", wasDomain: "test11", webRoot: "/data/webroot/app-test", isWait: true,], [host: "dkwas02", user: "tomcat", wasHome: "/usr/local/tomcat/domains/test21", wasDomain: "test21", webRoot: "/data/webroot/app-test", isWait: true,], ], group2: [ [host: "dkwas03", user: "tomcat", wasHome: "/usr/local/tomcat/domains/test31", wasDomain: "test31", webRoot: "/data/webroot/app-test", isWait: true,], [host: "dkwas04", user: "tomcat", wasHome: "/usr/local/tomcat/domains/test41", wasDomain: "test41", webRoot: "/data/webroot/app-test", isWait: true,], ], ] } DEPLOY_SERVERS.eachWithIndex { gItem, gIdx ---> logInfo(DEPLOY_SERVERS, gItem, gIdx, null, null, "START") gItem.value.eachWithIndex() { hItem, hIdx -> def remoteUser = hItem.user def remoteHost = hItem.host def isWait = hItem.isWait def catalinaBase = hItem.wasHome def wasDomain = hItem.wasDomain def webRoot = hItem.webRoot def warPath = webRoot + "/../" + PROJECT_NM def remoteServer = [host: remoteHost, user: remoteUser, identity: file("${System.properties['user.home']}/.ssh/id_rsa")] ssh.run { session(remoteServer) { logInfo(DEPLOY_SERVERS, gItem, gIdx, hItem, hIdx, "HTTPD(JK_MOD) BLOCK -> WAS SHUTDOWN") // 고객유입 차단 -> WAS 중지 execute "cd $catalinaBase; ./shutdown.sh " + (isWait?'wait update 5':'') logInfo(DEPLOY_SERVERS, gItem, gIdx, hItem, hIdx, "WAR REMOTE COPY") put from: war.archivePath.path, into: warPath execute "rm -Rf " + webRoot + "/*" execute "cd " + webRoot + "; jar xf " + warPath execute "chmod -Rf 755 " + webRoot + "/*" logInfo(DEPLOY_SERVERS, gItem, gIdx, hItem, hIdx, "WAR START (HTTPD(JK_MOD) BLOCKING)") // WAS 기동 (고객 유입은 차단상태) execute "cd $catalinaBase; ./start.sh" } } } gItem.value.eachWithIndex() { hItem, hIdx -> def remoteUser = hItem.user def remoteHost = hItem.host def catalinaBase = hItem.wasHome def isWait = hItem.isWait def wasDomain = hItem.wasDomain def remoteServer = [host: remoteHost, user: remoteUser, identity: file("${System.properties['user.home']}/.ssh/id_rsa")] ssh.run { session(remoteServer) { logInfo(DEPLOY_SERVERS, gItem, gIdx, hItem, hIdx, "CHECK SERVICE") while (true) { sleep(2000) def resultStr = execute "cd $catalinaBase; ./checkService.sh" if (resultStr.contains(wasDomain) && resultStr.contains("SERVICE CHECK ERROR") == false) { break } print "." } logInfo(DEPLOY_SERVERS, gItem, gIdx, hItem, hIdx, "HTTPD(JK_MOD) FLOW") // 고객 유입 execute "cd $catalinaBase; ./httpd.sh start" } } } logInfo(DEPLOY_SERVERS, gItem, gIdx, null, null, "END") } def totalExecTime = (System.currentTimeMillis() - startTime) / 1000 println "==================== TOTAL EXEC TIME: " + (totalExecTime) + "s ====================" } static logInfo(deployServers, gItem, gIdx, hItem, hIdx, msg) { println("==================== [GROUP $gItem.key " + (gIdx + 1) + "/" + deployServers.size() + (hItem?" " + (hIdx + 1) + "/" + gItem.value.size() + " $hItem.host:$hItem.wasDomain] ":" ") + msg + " ====================" ) }


일반적으로 Jenkins나 SSH(SCP) 등을 이용해서 원격지 배포 시 순차 배포 하게 된다.

하지만 원격지 서버의 수가 많으면 (1대 배포 시간 * 배포 서버 수)가 되어 배포 시간이 증가하게 된다.

급하게 배포하거나, 롤백 하는 상황에서 배포 시간이 증가하게 되면 빠른 복구가 힘들어 진다.

그에 따라서 약 2그룹으로 나누고, 각 그굽을 병렬로 처리 할 수 있도록 해보자.


하지만 이 방법은 2그룹 중 1그룹으로도 고객 서비스가 원할 해야 한다는 보장이 있어야 하며, 결국 오버스펙으로 운영 해야 한다는 말..


(war 배포아닌 파일 묶음 배포 방식)



+ Recent posts