Maven과 Gradle

양치는 하셨나요·2024년 7월 22일
0
post-thumbnail

둘을 조사 하기 전에 gradle은 들어보고 어느 정도 사용 해 본 경험이 있다. 바로 안드로이드 스튜디오에서!

모바일 프로그래밍을 배우는 수업 시간에 gradle 파일에 라이브러리를 추가하기도 하고 binding(ui의 동작을 가져오는 함수)을 키거나 끄기도 하는 등 해당 액티비티의 설정? 같은 것을 만졌던 기억이 난다.

일단 설명 하기 전에 먼저 말하자면 둘 다 빌드 관리 도구에 속한다.

이번 글에서는 빌드 관리 도구란 무엇인지, maven과 gradle 전에는 무엇이 있었는지, 두 도구의 개념과 차이는 무엇인지 설명하고자 한다.


빌드

  • 코드를 사용하거나 실행 가능한 형태로 컴파일링, 링킹, 패키징 하는 것을 말한다. → 소스코드 파일을 컴퓨터에서 실행할 수 있는 독립적인 형태로 변환하는 과정과 결과를 말한다.
  • 예를 들어 java에서는 프로젝트를 실행하면 개발자가 작성한 java와 여러 정적 파일 등에 해당하는 resource가 존재한다. 이를 Build 하면 소스코들를 컴파일 해서 .class 파일로 변환, resource를 .class가 참조할 수 있는 위치로 옮기고 여러 파일을 하나로 압축하는 과정을 의미한다.

빌드 관리 도구(Build Tool)

개념

빌드 관리 도구는 빌드를 통한 어플래케이션 생성을 자동화 하기 위한 도구이다.
즉, 소프트웨어 개발에 있어 소스코드를 실행 가능한 애플리케이션으로 만들어주는 도구이며 이런 빌드 과정을 자동화, 간편화하여 관리하기 때문에 빌드 관리 도구 또는 빌드 자동화 도구라고 불린다.

수행 작업

    1. 종속성 다운로드 - 전처리(Preprocessing)
    2. 소스코드를 바이너리 코드로 컴파일(Compile)
    3. 바이너리 코드를 패키징(Packaging)
    4. 테스트 실행(Testing)
    5. 프로덕션 시스템에 배포(distribution)

사용 이유

즉 빌드 관리 도구는 빌드를 더욱 쉽게 하기 위해 만들어진 것이다.

  • 대규모 프로젝트와 같이 큰 규모의 소스코드를 가진 파일을 빌드 할 땐 빌드 프로세스를 수동으로 지정 하는 것이 실용적이지 않다.
    • 무엇을 빌드 할지, 어떤 순서로 할지, 어떤 의존성이 있는지 모두 파악하기 어렵기 때문이다.
  • 따라서 빌드 관리 도구에 이와 같은 것을 미리 명시해 둔다면 일관된 처리를 통해 효율적으로 관리가 가능해진다.

역사

maven과 gradle은 아래에서 설명할 것이므로 간략히 적는다.

  1. Make
    1. 빌드 개념을 확립
    2. Unix 계열 OS에서 사용.
    3. makefile 안에서 정의한다.
      1. Target(대상), Dpendency(의존성), Recipe(명령어)로 구성되어있다.

        1. Target: 명령어에 의해 생성되는 파일. 컴파일된 오브젝트 파일 등이 여기에 해당.
        2. Dependency: Target 생성시 필요한 파일, 즉 의존하는 파일을 의미하고 의존하는 파일이 변경되었을 경우 여기에 의존하는 Target은 자동으로 리빌드 된다.
        3. Recipe: 빌드 대상을 생성하는 명령어. gcc(컴파일 명령어)와 같은 명령어들을 사용한다.

        예시.

        $(TARGET) : $(OBJS) 
            $(CC) -o $(TARGET) $(OBJS)
  2. Ant
    1. 크로스 플랫폼에 대응해 범용성을 높였다.

      1. Java 기반으로 독립적 시행된다. 이에 따라 운영체제에 구애받지 않고 프로젝트를 진행 가능하다.
    2. Make를 java에 적용할 때 생긴 문제를 보완하기 위해 탄생했다.

      1. Make와 흡사한 기능을 제공하는데 Java에 맞도록 수정했다.
    3. Java + XML을 도입했다.

      1. 미리 정의된 Task를 사용해 쉽고 빠른 배치 작업을 설정 가능하다.
      2. 새로운 Task 추가로 배치작업의 확장이 가능하다.

      예시.

      <project name="프로젝트이름" default="기본타겟이름" basedir="." > <!--빌드파일의 루트태그.--> 
         
          <target name="타겟이름"> <!--실제 프로젝트가 수행할 작업(Task지정) -->
            <property name="프로퍼티이름1" value="프로퍼티값1"/> 
            <property name="프로퍼티이름2" value="프로퍼티값2"/>
          </target>
          
          <target name="타겟이름1">
            <태스크명/>
            <태스크명1 dir="${build}"/>
            <property name="프로퍼티이름3" value="프로퍼티값3"/>
          </target>
          
          <target name="타겟이름2" depends="타겟이름1">
            <태스크명2 속성1="값1" 속성2="값2"/> <!--타겟 내에서 실제로 수행할 작업 -->
          </target>
        </project>
      출처: https://cheershennah.tistory.com/192 [Today I Learned. @cheers_hena 치얼스헤나:티스토리]
  3. Maven
    1. 작성 효율을 높임.
    2. 빌드 생명주기와 프로젝트 객체모델 개념 도입 → Ant의 문제점인 복잡한 빌드스크립트 문제를 해결.
  4. Gradle
    1. 스크립트 언어로 유연성 증대
    2. Maven 보다 빠르다.
    3. 기존 빌드 도구와 호환 가능하다.

Maven

위의 역사를 보면 알 수 있듯 Maven은 Ant 빌드도구를 개선하기 위해 나온 것이다. 이를 유념하고 조사를 시작해본다.

개념

  • Java 전용 프로젝트 관리 도구로 Lifecycle 관리 목적 빌드 도구이다.
  • Ant의 대안으로 만들어졌다.
  • 오픈 소스 소프트웨어로 아파치 라이센스로 배포된다.
    • 오픈 소스 소프트웨어: 소스코드가 공개되어 다양한 라이센스에 따라 상업적 혹은 비상업적 용도로 사용 가능하도록 한 소프트웨어를 말한다.
    • 아파치 라이센스: 아파치 재단에서 웹서버의 배포를 위해 만들어진 라이센스.
      복제, 배포, 수정의 권한 허용가능
      배포시 라이선스 사본 첨부가능
      저작권 고지사항 또는 Attribution 고지사항 유지가능
      배포시 소스코드 제공의무(Reciprocity)와 범위명시되어있지않음
      조합저작물(Lager Work) 작성 및 타 라이선스 배포 허용가능
      수정 시 수정내용 고지명시되어있지않음
      명시적 특허 라이선스의 허용가능
      라이선시가 특허소송 제기 시 라이선스 종료명시되어있지않음
      이름, 상표, 상호에 대한 사용제한가능
      보증의 부인가능
      책임의 제한가능

특징

  • 개념에서 알 수 있듯 Java의 Lifecycle 관리 도구이며 정해진 Lifecycle이 존재하고 이에 의해 작업을 수행하며 전반적인 프로젝트를 관리한다.

  • 라이프사이클

    clean - validate - compile - test - package - verify - install - site - deploy 순서의 사이클을 가진다. 이때 각 단계를 Phase(페이즈)라고 한다.

    • Clean : 이전 빌드에서 생성된 파일들을 삭제하는 단계
    • Validate : 프로젝트가 올바른지 확인학고 필요한 모든 정보를 사용할 수 있는 지 확인하는 단계
    • Compile : 프로젝트의 소스코드를 컴파일하는 단계
    • Test : 유닛(단위) 테스트를 수행하는 단계(테스트 실패시 빌드 실패로 처리, 스킵 가능)
    • Package : 실제 컴파일된 소스 코드와 리소스들을 jar등의 배포를 위한 패키지로 만드는 단계
    • Verify : 통합테스트 결과에 대한 검사를 실행하여 품질 기준을 충족하는지 확인하는 단계
    • Install : 패키지를 로컬 저장소에 설치하는 단계
    • Site : 프로젝트 문서를 생성하는 단계
    • Deploy : 만들어진 Package를 원격 저장소에 release하는 단계
  • 위의 사이클 외에도 다양한 사이클이 있으며 크게 Clean, Build, Site로 나눈다. 각 단계를 모두 수행하는 것이 아니라 원하는 부분까지만 할 수도 있다. 특히 test 단계는 프로젝트 규모에 따라 오랜 시간이 걸릴 수 있으니 스킵이 가능하도록 되어있다.

    • 위에 잠깐 말했던 Phase는 각각 의존 관계를 가지고 있어 해당 Phase가 수행되려면 앞선 Phase가 모두 수행되어야 한다.
  • Maven은 필요한 라이브러리를 pom.xml 파일에 저장한다.

    • 이를 프로젝트 모델링 이라고 한다.
      • POM Project Object Model의 약자로 xml 형식으로 프로젝트 실행에 필요한 설정값들이 저장되어 있다.
        • 프로젝트 정보(이름, 라이센스)
        • 빌드 설정(소스, 리소스, 라이프, 사이크 별 실행한 플러그인 등 빌드 관련 설정)
        • 빌드 환경(사용자 환경 별 변동 될 수 있는 프로필 정보)
        • pom 연관 정보(의존 프로젝트, 모듈, 상위 프로젝트 등)

장점

  • 간단한 구조와 설정. 복잡한 빌드 작업을 쉽게 만든다. 또한 의존성 관리가 용이하다. Maven은 라이브러리와 플러그인을 쉽게 추가하고 다운로드 받아준다.
  • 프로젝트에 대한 정보를 XML 형태로 정의한 pom.xml에 저장해 프로젝트 구조를 이해하는 데 도움이 된다.
  • 다양한 프로젝트와 잘 통합한다.

단점

  • XML을 통한 설정이 복잡하다 → 시간 소요, 빌드 속도 느림.
  • 빌드 프로세스는 명확하지만 유연성이 떨어진다. → 커스터마이징이 힘들 수 있다.

Gradle

역사의 순서에서 알 수 있듯 gradle은 maven의 강점을 계승하면서 단점을 보완하려는 시도로 만들어졌다. 따라서 gradle은 유연성과 성능 향상을 목표로 개발 되었다.

개념

  • Maven을 대체할 수 있는 프로젝트 구성 관리 및 범용 빌드 툴.
  • Ant Builder와 Groovy script를 기반으로 구축, Ant의 역할과 배포 스크립의 기능을 모두 사용 가능하며 스프링부트와 안드로이드에서 사용된다.
    • Groovy: 자바에 파이썬, 루비, 스몰토크등의 특징을 더한 동적 객체 지향 프로그래밍 언어. Groovy소스는 스크립트 파일 그대로 실행시킬 수 있고 자바초럼 컴파일하여 사용할 수도 있다. 대부분의 자바 소스는 파일 확장자만 변경하면 수정 없이 Groovy에서도 사용 가능하다.
  • 빌드 속도가 Maven에 비해 10~100배 빠르며 Java, C/C++, Python 등을 지원한다.

구조


Gradel의 구조는 위의 사진과 같다.

  • .gradle: Gradle이 사용하는 폴더. 작업 파일이 생성되며 이 내부를 편집하는 일은 없다고 봐도 된다.
  • src: 프로젝트에서 만든 프로그램 관련 디렉토리. 프로젝트에서 사용하는 파일은 모두 포함된다.
  • build.gradle: 기본 빌드 설정 파일이다. 이 안에 빌드 처리에 대한 내용이 작성되어 있다.
  • gradlew, gradlew.bat: Gradle 명령어이다. 아무것도 없는 것이 맥 및 리눅스용, bat 파일이 윈도우용이다.
  • settings.gradle: 프로젝트에 대한 설정 정보가 작성되어있다.

동작

build.gradle은 파일 자체가 Project Object이다. 이는 프로젝트 단위에서 필요한 작업을 수행하기 위해 모든 메서드와 속성을 모아둔 객체이다.
이때 대표적인 것엔 plugins, repogitories, dependencies, application 등이 있다.

// 프로젝트에서 사용하는 Gradle 플러그인 설정
plugins {
    id 'java'
    ..
}

// 프로젝트 생성 시 GroupId, Application 버전, Java 버전
group = 'com.example'
version = '0.0.1-SNAPSHOT'
sourceCompatibility = 1.8

// 필요한 라이브러리를 다운로드할 저장소 설정
// 공개 저장소(jcenter)와 Apache Maven 중앙 저장소(mavenCentral) 이용
repositories {
    mavenCentral()
}

// 의존 라이브러리 설정
dependencies {
		// compile, api: 의존 라이브러리 수정시 본 모듈을 의존하는 모듈들도 모두 재빌드 (api로 사용을 권장)
		//               A(api) <- B <- C 로 의존하는 구조라면, A 수정 시 B,C 모두 빌드
		// implementation: 의존 라이브러리 수정시, 해당 모듈을 직접 의존하는 모듈만 빌드 (비교적 빠름)
		//               A(implementation) <- B <- C 로 의존하는 구조라면, A 수정 시 B 만 빌드
		// compileOnly: 컴파일시에만 의존하고, 빌드 결과물에는 포함하지 않음 (runtime시 필요없는 라이브러리)
		// runtimeOnly: runtime 시에만 필요한 라이브러리
		// testCompile: test에서만 적용되는 compile 속성
		// testImplementation: test에서만 적용되는 implementation 속성
		// testCompileOnly: test에서만 적용되는 compileOnly 속성
		// testRuntimeOnly: test에서만 적용되는 runtimeOnly 속성
		// annotationProcessor: 어노테이션 기반 라이브러리를 컴파일러가 인식하도록 함 (lombok, queryDSL 등)
		..
    testImplementation 'org.springframework.boot:spring-boot-starter-test'
}

특징

  • 코딩에 의한 간결한 정의로 가독성이 좋다.
  • 설정 주입 방식을 사용하므로 재사용에 용이하다.
    • 이 방식으로 Maven의 상속 구조보다 재사용이 용이하다.
  • Groovy 기반의 DSL(Domail Specific Language)를 사용해 코드로서 설정 정보를 구성하므로 구조적인 장점이 있다.
    • DSL: 특정 도메인(특정 영역)에 특화된 언어. 여기선 설정 정보에 대해 특화된 언어를 사용했다는 뜻이다.
  • 별도의 Gradle 설치 없이 Gradle wrapper를 이용해 빌드를 지원한다.
  • 멀티 프로젝트 빌드를 지원하기 위해 설계된 빌드 관리 도구이다.
  • Maven을 완전 지원한다.

장점

  • 유연성이 크다.
    • gradle은 groovy나 kotlin DSL을 기반으로 작성되며 기능 추가나 변경이 상대적으로 쉽다. 빌드 캐시, 병렬 실행 등으로도 시간을 크게 단축 시킬 수 있다.
  • Maven과 호환성이 좋다. Maven의 pom.xml을 gradle 스크립트로 변환 가능하다. 이런 점과 더불어 다양한 프로젝트와 통합된다.

단점

  • Maven의 XML 기반 설정보다 배우기 어려울 수 있다.
  • 상대적으로 최근의 도구이기 때문에 문서화가 완벽하지 않을 수 있다.

Maven VS Gradle

차이점

MavenGradle
1. 빌드 스크립트 언어XMLGroovy/Kotlin DSL
2. 확장성준수더 좋음
3. 성능느림빠름
4. 컨벤션 오버 구성강조, 사전 정의더 유연, 자유롭게 정의
5. 학습 곡선초기 설정 간단, 낮음초기 설정 및 고급 기능 사용에 있어 높음
  1. xml 보다 groovy가 더 유연하고 가독성이 좋다.

  2. gradle의 특징에서 봤듯 10배 이상의 성능 차이가 있다. 이는 gradle의 캐싱, 병렬처리 등에 요인이 있다.

  3. Maven은 이미 있는 플러그인들로 확장이 가능. gradle은 사용자 정의 플러그인 작성이 더욱 쉬워 플러그인 생태계가 더 풍부하다.

  4. 표와 같이 차이가 있고 각 장단점이 있지만 유연한 것이 실제 적용하기에 더 수월한 면이 있다.

이러한 점들을 고려해 Maven와 gradle을 선택 가능하다. 하지만 결국 나는 이제 개발자를 준비하는 과정 중이고 gradle은 가장 최신에 나온 tool이므로 어떤 것을 공부해야 하는가를 물어본다면 gradle이라고 할 수 있을 듯 하다.


결론

  • Maven 구조가 간단하고 일관성이 있는 프로젝트, 또는 빌드 프로세스가 복잡하지 않은 프로젝트에 적합하다. Maven은 잘 문서화되어 있고, 넓은 범위의 플러그인을 지원하므로 이러한 경우에 잘 맞다.
  • Gradle 빌드 프로세스가 복잡하거나 많은 커스터마이징이 필요한 프로젝트에 적합하다. 또한 빌드 속도가 중요한 대규모 프로젝트에도 적합하다다. Gradle은 빌드 스크립트의 유연성과 빌드 성능 향상을 제공하기 때문에 이러한 경우에 잘 맞는다.
  • 최종 선택은 여러 가지 요소를 고려해야 한다. 프로젝트의 복잡성, 빌드 속도 요구, 팀원들의 기술 능력, 유지 보수 및 확장성 등. 이를 통해 프로젝트에 가장 적합한 도구를 선택할 수 있을 것이다.
profile
프로그래밍을 잘하고 싶어요..

0개의 댓글

관련 채용 정보