$GRADLE_USER_HOME

아래 내용을 이해하려면 이 환경 변수를 우선 알고 있어야 한다.

Gradle 은 GRADLE_USER_HOME 이라는 환경 변수를 지원하여 사용자가 직접 지정하여 이용할 수 있도록 지원해주고 있다. 이 환경 변수에는 단순히 폴더 경로만 지정해주면 되는데 이 환경 변수는 전역 설정 property, 초기화 스크립트, 캐시, 로그 파일 등을 저장하는 용도로 쓰인다.

GRADLE_USER_HOME 이라는 환경 변수를 읽지 못했을 때는 사용자 홈 디렉토리의 .gradle 폴더를 바라본다. 프로젝트 저장소의 .gradle 폴더와는 다르기 때문에 혼동하면 안 된다.

 

Wrapper 및 의존성

Wrapper

gradle wrapper 실행 시 과정

https://docs.gradle.org/current/userguide/gradle_wrapper.html

초기에 gradlew 를 이용하여 gradle 을 이용하려고 할 때 다운로드를 하게 된다. 다운로드한 gradle 은 $GRADLE_USER_HOME/wrapper/dists 폴더에 저장된다.

왜 위 경로로 저장되는지는 프로젝트 저장소의 gradle/wrapper/gradle-wrapper.properties 파일을 보게 되면 알 수 있는데, 보통 아래와 같이 작성되어 있는 것을 볼 수 있다.

distributionBase=GRADLE_USER_HOME
distributionPath=wrapper/dists
distributionUrl=https\://services.gradle.org/distributions/gradle-8.10.2-bin.zip
networkTimeout=10000
validateDistributionUrl=true
zipStoreBase=GRADLE_USER_HOME
zipStorePath=wrapper/dists

distributionUrl을 다운로드하여 distributionBase, distributionPath 경로 구성으로 압축이 풀리게 된다. 따라서 wrapper 가 저장되는 위치는 $GRADLE_USER_HOME/wrapper 라고 생각해도 무방하다.

 

의존성

라이브러리 의존성을 이용할 때 처음에는 다운로드하게 되는데 gradle 은 이를 캐시화하여 같은 의존성을 불러오려는 경우 캐시화된 파일로 이용하게 된다.

$GRADLE_USER_HOME/caches 경로에 캐시가 저장된다.

https://docs.gradle.org/current/userguide/dependency_caching.html

 

빌드

Gradle 은 --build-cache 옵션 또는 property 항목으로 gradle.properties 파일 내에 org.gradle.caching=true 를 설정하게 되면 Gradle 의 빌드 캐싱 기능을 이용할 수 있다.

Gradle 문서에 따르면 $GRADLE_USER_HOME 경로에 캐싱된 파일이 저장된다고는 하나 정확한 경로를 확인하기 힘들다. 대신, 사용자가 빌드 캐시된 파일을 저장하는 경로를 직접 지정해줄 수 있도록 설정을 지원해주고 있다.

settings.gradle 에 아래와 같이 작성해주면 사용이 가능하다.

buildCache {
    local {
        directory = new File(rootDir, '.build-cache')
    }
}

위와 같이 설정하면 Gradle 빌드 시 .build-cache 폴더가 생기게 되고, 다시 빌드하면 캐시된 파일을 이용하여 빠른 빌드가 이루어지는 것을 확인할 수 있다.

빌드 시 캐싱 파일 기준은 입력으로 들어오는 파일들의 수정된 시간, 파일 사이즈 등의 여러 정보를 기준으로 fingerprint 를 채취하여 감지하는 방식으로 이루어진다.

https://docs.gradle.org/current/userguide/build_cache.html
https://docs.gradle.org/current/userguide/incremental_build.html#incremental_build

 

만약, 현재 여러 개의 멀티 모듈로 나누어서 관리하고 있을 경우, 변경 사항 발생 시에는 연관된 모듈과 입력 파일에 따라 다시 빌드가 이루어지고 그 외 연관되지 않은 모듈에서는 캐시화된 파일을 이용하게 된다. 즉, 변경 사항에 해당되지 않는 나머지 모듈은 그대로 캐시화된 파일을 이용하면서 빌드를 단축시킬 수 있다.

지원 Task

Java 같은 경우 JavaCompile / Javadoc, Kotlin 같은 경우 GroovyCompile / GroovyDoc 이 해당된다.

테스트는 Test Task 가 해당된다.

모든 Task 에서 캐싱 기능이 이루어지는 것은 아니며 아래 링크에서 어떤 Task 에서 캐시를 지원하는지 확인할 수 있다.

캐시에서 참조했을 경우 gradle 콘솔에 FROM-CACHE 항목이 나타난다.

FROM-CACHE 로 캐시에서 사용된 모습

https://docs.gradle.org/current/userguide/build_cache.html#sec:task_output_caching_details

 

정리

settings.gradle 에 아래와 같이 작성하여 빌드 캐싱이 이루어지는 폴더를 지정해준다. 폴더는 .build-cache 에 저장되도록 하였다.

buildCache {
    local {
        directory = new File(rootDir, '.build-cache')
    }
}

 

위 폴더는 캐시되는 경로이므로 git 저장소에서 관리할 필요가 없다. 위 경로를 무시하도록 .gitignore 에 예외를 추가한다.

/.build-cache/

 

gradle.properties 파일에 Gradle 빌드 캐싱 기능을 활성화하도록 org.gradle.caching 속성을 작성한다.

org.gradle.caching=true

 

GitLab CI/CD 기준으로 작성했다. GRADLE_USER_HOME 환경 변수를 설정해주고, cache 대상을 아래 3가지 경로를 설정해주면 캐시를 사용하면서 파이프라인 진행 시간을 단축시킬 수 있다.

.gradle-build:
  stage: build
  cache:
    key: ${SOME_MODULE_NAME}-${CI_COMMIT_REF_SLUG}
    paths:
      # Wrapper, 의존성 관련
      - .gradle/wrapper
      - .gradle/caches
      # 빌드 캐시 관련
      - .build-cache
  before_script:
    - export GRADLE_USER_HOME=`pwd`/.gradle
    - test -d "$GRADLE_USER_HOME" && echo 'gradle home exists'
  script:
    - ./gradlew clean :SOME_MODULE:build