[프로젝트 셋업] gradle-multi-project-support 플러그인 활용하기

김대니·2023년 1월 24일
0

들어가며

mono-repo, multi-project 환경에서 개발을 하다보면 java 언어 기반의 프로젝트, kotlin 언어 기반의 프로젝트 등 프로젝트 특성에 맞게 gradle 설정을 해줘야 할 때가 있습니다.

예시

하나의 repository 내 총 5개의 프로젝트가 있습니다.

  • microservice-project-A (java)
  • microservice-project-B (java)
  • microservice-project-C (java)
  • microservice-project-D (kotlin)
  • microservice-project-E (kotlin)

각각의 프로젝트에 맞게 프로젝트 설정을 build.gradle 스크립트 파일을 통해 해줘야 합니다. 예를 들면, 아래처럶 rootbuild.gradle 이렇게 해줄 수 있습니다.

project(":microservice-project-A") {
    apply(plugin = "org.gradle.java")
    apply(plugin = "io.spring.dependency-management")
    apply(plugin = "io.freefair.lombok")
    apply(plugin = "org.jetbrains.kotlin.jvm")

    the<io.spring.gradle.dependencymanagement.dsl.DependencyManagementExtension>().apply {
        imports {
            mavenBom("org.springframework.boot:spring-boot-dependencies:2.7.3")
            mavenBom("org.jetbrains.kotlin:kotlin-bom:1.6.21")
            mavenBom("org.jetbrains.kotlinx:kotlinx-serialization-bom:1.4.1")
            ...
        }

        dependencies {
            dependency("org.apache.commons:commons-lang3:3.12.0")
            ...
        }
    }

    dependencies {
        val implementation by configurations

        implementation("org.springframework.boot:spring-boot-starter-web")
    }
}

문제점

microservice-project-A, microservice-project-B, microservice-project-C 까지 동일한 설정을 해줘야 한다면 똑같은 코드가 복붙으로 여러번 생겨나게 됩니다.

gradle-multi-project-support 플러그인

이를 해결하기 위해 라인에서 제공하는 gradle-multi-project-support 플러그인을 활용해볼 수 있습니다.

최상단의 build.gradle.kts

plugins, allprojects, subprojects 까지는 일반적으로 설정합니다.

import com.linecorp.support.project.multi.recipe.configureByLabels

plugins {
    id("io.spring.dependency-management") version "1.0.11.RELEASE" apply false
    id("org.springframework.boot") version "2.7.3" apply false
    id("io.freefair.lombok") version "6.4.1" apply false
    id("com.linecorp.build-recipe-plugin") version "1.1.1"

    kotlin("jvm") version "1.6.21" apply false
    kotlin("kapt") version "1.6.21" apply false
    kotlin("plugin.spring") version "1.6.21" apply false
}

allprojects {
    group = "sample.project.kdohyeon"
    version = "1.0-SNAPSHOT"

    repositories {
        mavenCentral()
        maven {
            url = uri("https://maven.restlet.com")
        }
        maven {
            url = uri("https://jitpack.io")
        }
    }

    tasks.withType<org.jetbrains.kotlin.gradle.tasks.KotlinCompile> {
        kotlinOptions.jvmTarget = "17"
        kotlinOptions.freeCompilerArgs = listOf(
            "-Xjsr305=strict",
            "-Xjvm-default=all",
        )
    }
}

subprojects {
    apply(plugin = "idea")
}

configureByLabels("java") { // (1)
    apply(plugin = "org.gradle.java")
    apply(plugin = "io.spring.dependency-management")
    apply(plugin = "io.freefair.lombok")

    the<io.spring.gradle.dependencymanagement.dsl.DependencyManagementExtension>().apply {
        imports {
            mavenBom("org.springframework.boot:spring-boot-dependencies:2.7.3")
            mavenBom("org.jetbrains.kotlin:kotlin-bom:1.6.21")
            mavenBom("org.jetbrains.kotlinx:kotlinx-serialization-bom:1.4.1")
            mavenBom("com.google.guava:guava-bom:31.1-jre")
        }

        dependencies {
            dependency("org.apache.commons:commons-lang3:3.12.0")
            dependency("org.apache.commons:commons-collections4:4.4")
            dependency("commons-io:commons-io:2.11.0")
        }
    }

    repositories {
        mavenCentral()
        maven {
            url = uri("https://maven.restlet.com")
        }
        maven {
            url = uri("https://jitpack.io")
        }
    }

    dependencies {
        val implementation by configurations

        implementation("org.apache.commons:commons-lang3")
        implementation("org.apache.commons:commons-collections4")
        implementation("commons-io:commons-io")
        implementation("com.google.guava:guava")
    }
}

configureByLabels("boot") {
    apply(plugin = "org.springframework.boot")

    tasks.getByName<Jar>("jar") {
        enabled = false
    }

    tasks.getByName<org.springframework.boot.gradle.tasks.bundling.BootJar>("bootJar") {
        enabled = true
    }
}

(1) configureByLabels 라는 키워드를 활용하고 label 으로 java 를 입력합니다. java 라벨이 붙어있는 프로젝트는 동일한 설정을 가져갈 수 있게끔 합니다.

프로젝트 내 빌드 스크립트 설정

각 프로젝트는 gradle.properties 파일과 build.gradle.kts 파일을 포함하고 있어야 합니다.

gradle.properties

gradle.properties 파일에서는 해당 프로젝트가 어떤 label 에 해당하는지 입력합니다. 이 부분을 통해 rootbuild.gradle.kts 에서 설정한 configureByLabels("java") 를 적용할 수 있습니다.

label=java

build.gradle.kts

프로젝트에 소속된 build.gradle.kts 는 프로젝트에 필요한 설정만 해주면 됩니다.

아래는 예시입니다.

dependencies {
    implementation("org.springframework.boot:spring-boot-starter-web")
}
profile
?=!, 물음표를 느낌표로

0개의 댓글