2014년 2월 26일 수요일

Maven Plugins

Maven Plugins

1. Maven Plugin

  • 플러그인은 Maven의 핵심 기능으로 Goal이라는 실행 단위들의 집합으로 구성되어 있다.

기본적인 plugin 설정

  • 플러그인 정보는 build 엘리먼트의 plugins 엘리먼트 안에 설정한다.
  • 플러그인을 등록할 때 groupId가 생략된 경우도 있다. 기본으로 org.apache.maven.plugins 와 org.codehaus.mojo 는 생략해도 된다
    <plugins>
     ...
      <plugin>
        <groupId>org.apache.maven.plugins</groupId>
        <artifactId>maven-compiler-plugin</artifactId>
        <configuration>
          <source>1.5</source>
          <target>1.5</target>
        </configuration>
      </plugin>
      ..
    </plugins>
    
  • 아래와 같이 라이프사이클의 일부로 특정 Goal을 추가하고 설정 할 수 있다.
     
    <plugins>
     ...
      <plugin>
        <artifactId>maven-antrun-plugin</artifactId>
        <configuration>
         <tasks>
           <echo>The JAVA_HOME var is ${env.JAVA_HOME}</echo>
         </tasks>
        </configuration>
        <executions>
          <execution>
            <goals>
              <goal>run</goal>
            </goals>
            <phase>compile</phase>
          </execution>
        </executions>    
      </plugin>
      ..
    </plugins>
    
  • default lifecycle phase를 사용하는 예제
    <plugin>
      <groupId>org.apache.maven.plugins</groupId>
      <artifactId>maven-dependency-plugin</artifactId>
      <executions>
        <execution>
          <id>copy-dependencies</id>
          <!-- Binds by default to the lifecycle phase: process-sources.  -->
          <goals>
            <goal>copy-dependencies</goal>
          </goals>
          <configuration>
            <excludeArtifactIds>servlet-api,jsp-api</excludeArtifactIds>
            <outputDirectory>${basedir}/web/WEB-INF/lib</outputDirectory>
            <overWriteReleases>false</overWriteReleases>
            <overWriteSnapshots>true</overWriteSnapshots>
          </configuration>
        </execution>
      </executions>
    </plugin>
    

2. Maven Plugins

문서정보

Maven Profiles - 서로 다른 빌드 환경간의 이식

Maven Profiles

  • Maven에 있는 Profile의 사용 목적은 서로 다른 빌드 환경간의 이식성 이다.

Profile 간단 사용 예제

  • profile 설정 간단 예제
<profiles>
  <profile>
    <id>local</id>
    <properties>
        <env>local</env>
    </properties>            
  </profile>
  <profile>
    <id>alpha</id>          
    <properties>
        <env>alpha</env>
    </properties>
  </profile>
  <profile>
    <id>beta</id>
    <properties>
        <env>beta</env>
    </properties>
  </profile>
  <profile>
    <id>release</id>
    <properties>
        <env>release</env>
    </properties>
    
    <activation>
        <property>
            <name>bds</name>
            <value>false</value>                    
        </property>                
    </activation>
    <build>
        <plugins>
            <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-compiler-plugin</artifactId>
                <configuration>
                    <source>1.5</source>
                    <target>1.5</target>                    
                    <debug>true</debug>
                    <optimize>true</optimize>
                    <encoding>utf-8</encoding>
                    <showDeprecations>true</showDeprecations>
                    <fork>true</fork>                            
                    <executable>/usr/local/env/java/jdk1.5.0_10/bin/javac</executable>
                </configuration>
            </plugin>
        </plugins>
    </build>
  </profile>
  ..
</profiles>  

<properties>
    <env>local</env>
    <bds>false</bds>
    <clover.home>analysis_tools/clover</clover.home>
    <checkstyle.home>analysis_tools/checkstyle</checkstyle.home>
    <pmd.home>analysis_tools/pmd</pmd.home>
    <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>      
</properties>

  • 실행시 profile 옵션을 사용한다 (ex. mvn package -Palpha)
  • 실행위치의 pom.xml, 실행위치의 profiles.xml, $USER_HOME/settings.xml, $M2_HOME/conf/settings.xml 순으로 profile 항목을 찾는다.
  • profile의 id 가 동일한 경우가 나타나면 해당 profile 에서 선언된 내용을 적용한다.
    즉 사용자 정의 환경변수 env 의 값이 alpha로 변경 됨.
  • mvn -Palpha는 mvn -Denv=alpha 로 변경 사용.

Profile activation의 사용

  • activation 엘리먼트는 오직 profile 엘리먼트 내부에서만 사용할 수 있다.
  • 정의한 환경과 실행 환경이 일치하면 profile에 설정한 값들이 project에 설정한 값에 대체 한다.
  • mvn -Ddeploy=true 실행시 아래 activation 수행 됨
     
    <profiles>
    
    <profile>
      <activation>
        <property>
            <name>deploy</name>
            <value>true</value>
        </property>
      </activation>
      <build>
        <plugins>       
            <plugin>
                <artifactId>maven-antrun-plugin</artifactId>
                <executions>
                    <execution>
                        <phase>compile</phase>
                        <goals>
                            <goal>run</goal>
                        </goals>
                        <configuration>
                            <tasks>
                                <mkdir dir="../webapps" />
                                <copy todir="../webapps" overwrite="true" preservelastmodified="true">
                                    <fileset  dir="${basedir}/web">
                                        <include name="**/*" />
                                    </fileset>
                                </copy>
                            </tasks>
                        </configuration>
                    </execution>
                </executions>
            </plugin>        
        </plugins>
      </build>
    </profile>
    </profiles>        
    

문서정보

Maven Properties - 동적인 환경구성

Maven Properties

  • pom.xml 파일에서 maven 프로퍼티를 사용하여 동적인 환경 구성이 가능하다.
  • 프로퍼티의 종류에는 project 프로퍼티, settings 프로퍼티, 환경 변수 프로퍼티, Java System 프로퍼티, 사용자 정의 프로퍼티가 있다.

1. Maven Project Properties

  • Maven Project Object Model(pom.xml) 에 정의된 값.
  • prefix. : project.*
        ex) ${project.build.outputDirectory}
      
<dependencies>
  <dependency>
    <groupId>${project.groupId}</groupId>
    <artifactId>sibling-project</artifactId>
    <version>${project.version}</version>
  </dependency>
</dependencies> 
 

2. Maven Settings Properties

3. Environment Variable Properties

  • 환경 변수 값을 참조 할 수 있다.
  • prefix : env.*
  • 예제
    • env.PATH : 현재의 PATH 정보
    • env.JAVA_HOME : JDK Home 정보
    • env.HOME : 유닉스/리눅스 사용자 HOME 디렉토리
    • env.M2_HOME : Maven Home 정보
<!-- mvn antrun:run -->
<plugin>
  <artifactId>maven-antrun-plugin</artifactId>
  <configuration>
    <tasks>
      <echo>The JAVA_HOME var is ${env.JAVA_HOME}</echo>
    </tasks>
  </configuration>
</plugin>

<!--  [echo] The JAVA_HOME var is C:\jdk1.5 출력된다. -->

4. Java System Properties

  • System.getProperty() 메소드에서 제공하는 모든 프로퍼티 정보를 참조할 수 있다.
Java System Properties설명
java.versionJRE의 버전
java.vendorJRE의 vendor 정보
java.homeJDK 또는 JRE의 설치 디렉토리
java.vm.specification.versionJVM SPEC 버전
java.vm.specification.nameJVM SPEC 이름
os.nameOS 이름
os.versionOS 버전
user.home사용자 홈 디렉토리
user.name사용자 이름
user.dir현재 디렉토리

5. User-defined Properties

  • 아래와 같이 직접 정의해서 사용 할 수 있다.
<project>
...
<properties>
  <env>local</env>
  <clover.home>analysis_tools/clover</clover.home>
  <checkstyle.home>analysis_tools/checkstyle</checkstyle.home>
  <pmd.home>analysis_tools/pmd</pmd.home>
  <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>      
</properties>
...
</project>

6. Reference

문서정보

Maven Lifecycle 이란

Maven Lifecycle

1. Maven Lifecycle 이란

  • Maven에서는 clean, build, site의 세 가지 Lifecycle을 제공하고 있다.
  • 컴파일(compile), 테스트(test), 패키지(package), 배포(depooy)등의 과정은 빌드 Lifecycle에 속한다.
  • Maven은 모든 빌드 단위에 대한 Lifecycle이 예약되어 있어서 개발자가 임의로 변경 할 수 없다.
  • 각 Lifecycle은 순서를 갖는 단계(phase)로 구성된다.
  • Maven의 기본 Lifecycle을 이해하려면 Phase와 Goal의 개념을 이해해야 한다.




2. Phase와 Goal



2.1 Phase

  • Phase는 Build Lifecycle의 각각의 단계를 의미 한다.
  • Phase는 특정 순선에 따라서 goal이 실행되도록 구조를 제공 한다.
  • Phase 간에는 의존 관계가 있다.
    예를 들어 package phase가 수행되기 위해서는 이전 phase가 순서대로 수행된 다음에 실행된다.


2.2 Goal

  • Goal은 Ant의 Target과 같은 개념으로 생각하면 된다.

2.3 Phase와 Goal의 관계

  • Maven에서 제공하는 모든 기능은 플러그인 기반으로 동작한다.
  • Maven에서 기본으로 제공하는 Phase를 실행하면 해당 Phase와 연결된 플러그인의 Goal이 실행된다.
  • 각 phase는 0개 이상의 goal과 바인드 되어 있으며, 대부분 0또는 1개 이상의 Goal이 바인드 되어 있다.
  • Plugin Goal
    • Maven에서 플러그인을 실행할 때 '플러그인이름:플러그인지원골'의 형식으로 실행 할 기능을 선택 할 수 있다.
    • 예를들어 mvn compiler:compile은 'compiler' 플러그인에서 'compile' 기능(goal)을 실행한다는 것을 뜻 한다.
  • 아래는 package phase가 실행되기 전에 완료되야 하는 phase와 Goal이다.
PhaseGoal
[ resources:resources ]resources
[ compiler:compile ]compile
[ resources:testResources ]test-resources
[ compiler:testCompile ]test-compile
[ surefire:test ]test
[ jar:jar ]package
[표] 디폴트 라이프사이클의 주요 단계(phase)
 단계설명단계에 묶인 플러그인 실행
generate-sources컴파일 과정에 포함될 소스를 생성한다. 예를 들어,  DB 테이블과 매핑되는 자바 코드를 생성해주는 작업이 이 단계에서 실행된다.
process-sources필터와 같은 작업을 소스 코드에 처리한다. 
generate-resources패키지에 포함될 자원을 생성한다. 
process-resources필터와 같은 작업을 자원 파일에 처리하고, 자원 파일을 클래스 출력 디렉토리에 복사한다.resources:resources
compile소스 코드를 컴파일해서 클래스 출력 디렉터리에 클래스를 생성한다.compiler:compile
generate-test-sources테스트 소스 코드를 생성한다. 예를 들어, 특정 클래스에서 자동으로 테스트 케이스를 만드는 작업이 이 단계에서 실행된다.
process-test-sources필터와 같은 작업을 테스트 소스 코드에 처리한다.resources:testResources
generate-test-resources테스트를 위한 자원 파일을 생성한다. 
process-test-resources필터와 같은 작업을 테스트 자원 파일에 처리하고, 테스트 자원 파일을 테스트 클래스 출력 디렉터리에 복사한다. 
test-compile테스트 소스 코드를 컴파일해서 테스트 클래스 추력 디렉터리에 클래스를 생성한다.compiler:testCompile
test테스트를 실행한다.surefire:test
package컴파일 된 코드와 자원 파일들을 jar, war와 같은 배포 형식으로 패키징한다.패키징에 따라 다름
jar - jar:jar
war - war:war
pom - site:attach-descriptor
ejb - ejb:ejb
install로컬 리포지토리에 패키지를 복사한다.install:install
deploy생성된 패키지 파일을 원격 리포지토리에 등록하여, 다른 프로젝트에서 사용할 수 있도록 한다.deploy:deploy


3. Maven 디폴트 Phase와 Goal

process-resources

  • resources:resources Goal이 실행 된다.
  • Maven Resources Plugin
  • <resource> directory(/src/main/resources)를 <outputDirectory>에 생성 한다.

compile

  • resources:resources, compiler:compile Goal이 실행 된다.
  • Maven Compiler Plugin
  • 소스 코드를 컴파일해서 클래스를 <outputDirectory>에 생성 한다.

test-compile

  • compiler:compile, compiler:testCompile Goal이 실행 된다.
  • 테스트 소스 코드를 컴파일 한다.

test

  • compiler:compile, compiler:testCompile, surefire:test Goal이 실행 된다.
  • Maven Surefire Plugin
  • junit과 같은 테스트 코드를 실행, 테스트가 실패하면 빌드를 멈춘다
  • target/surefie-reports디렉토리 안에 test 리포트 파일을 생성한다
  • 단위 테스트 코드가 깨져도 빌드를 성공시키려면 maven.test.skip 속성을 true로 설정하면 된다.
    <properties>
            <maven.test.skip>true</maven.test.skip>
    </properties>       
     

package

  • package를 실행하면 compile, test-compile, test 순으로 실행된 다음 jar, war파일이 target 디렉토리 아래에 생성된다.
  • 패키징에 따라 아래의 플러그 인을 사용한다.
  • Maven Jar Plugin
  • Maven WAR Plugin
  • Maven EAR Plugin

install

deploy

  • 원격 리파지토리에 등록하여, 다른 프로젝트에서 사용 할 수 있도록 한다.
  • Maven Deploy Plugin

clean

Reference

문서정보

Maven 핵심개념 - Plugin,Goal,Phase,생명주기

원문 : http://demon92.tistory.com/14

1. Plugin,Goal

이번글에서는 maven에 관련된 몇가지 개념과 maven 생명주기에 대해서 정리해본다.
이전(http://demon92.tistory.com/12) 글에서 아래의 명령으로 기본적인 프로젝트를 생성했다

mvn archetype:generate -> archetype은 plugin, generate는 Goal이다.
단순하게 말해서 Maven은 설치만 해서는 아무것도 못한다. 즉 maven은 자체로는 아무런 처리능력이 없다. 몇개의 XML 문서를 파싱하고 생명주기와 몇가지 플러그인의 추적을 유지하는 것 이외에는 어떻게 처리할지 모른다.
maven으로 의미있는 작업을 하기위해서는 Plugin을 다운 받아야 한다.(명령을 실행하면 자동적으로 다운을 받는다).  Maven은 대부분의 책임을 maven 생명주기에 영향을 주고 goal에 대한 접근을 제공하는 Plugin에 위임하도록 되어 있다. Plugin은 여러개의 Goal를 가지고 있고 Goal은 Plugin에 포함되어 있는 명령이다. 즉 Maven의 Plugin은 하나이상의 Goal의 집합체이다. 

 
그럼 Goal은?  goal은 Maven에서 단위 작업 즉 명령이라고 생각하면 된다. 
소스코드를 compile하는 compiler Plugin의 compile goal 또는 단위 테스트를 실행할수 있는 Surefire Plugin의 test goal를 들수 있다. 아울러 goal은 기능을 변경하는데 사용될 수 있는 설정 속성을 설정된다.
예를 들면 Compiler plugin의 compile goal은 대상 JDK버전을 지정할수 있다 뒤에 이 부분은 다시 다룬다.

2. Phase

Phase를 이야기하기 전에 maven의 Lifecycle에 대해 간단히 알아보면 Maven Lifecycle은 프로젝트를 
빌드하는데 관련된 순차적인 단계들이다 ( maven defaule lifecycle(http://demon92.tistory.com/2) 참고)
Maven은 수많은 생명주기를 지원하지만 가장 자주 사용되는것은 기본 Mavne 생명주기로 프로젝트의 기본적인 통합을 검증하는 단계로 시작해서 제품으로 프로젝트를 배포하는 것과 관련된 단계로 끝난다.
                
            

Phase는  maven의 Build Lifecycle의 한부분으로 각각의 Phase는 어떤 일을 할지 정의하지 않고 어떤 Goal을 실행할지 설정한다. 즉 Plugin의 goal은 생명주기 단계에 붙을수 있다
package Phase에서 Jar Plugin의 jar goal를 실행한다.        
        

각각의 Phase는 그 안에 0개이상의 goal를 가질수 있다  package Phase는 jar packaging과 같은 프로젝트의 jar 파일을 생성하는것으로 알고 있지만 maven은 생명주기의 특정 Phase가 실행이 되면 그 이전의 
모든 Phase를 순차적으로 모두 수행한다.  즉 mvn package를 실행할때 maven은 package단계까지 모든 Phase를 실행하고 생명주기 Phase를 거치는 과정에서 해당 Phase에 속한 모든 goal들을 실행한다. 
(아래 그림 참조)

mvn package를 실행하는 대신에 다음과 같이 일련의 plugin goal들을 지정함으로써 동일한 결과를 얻을수 있다
mvn resources:resources compiler:compile resource:testResources compiler:testCompile surefire:test jar:jar