Day 31 — 빌드 도구 Gradle: IDE 'Run' 버튼 뒤의 비밀
목차 18
지난 시간, 우리는 모던 자바의 마지막 조각들(텍스트 블록·가드 패턴·이름 없는 변수·순서 컬렉션)을 한자리에 모으면서, 람다·Stream·Optional·record 로 이어진 긴 여정을 마무리했어요. 그러면서 한 가지 질문을 남겨뒀죠. "지금까지 IDE 의 'Run' 버튼만 누르면 코드가 실행됐는데, 그 버튼 뒤에서는 도대체 무슨 일이 일어나는 걸까?"
오늘 그 비밀을 풀어요. 우리가 Day 1 부터 30 까지 별생각 없이 눌러온 그 버튼 뒤에는 사실 빌드 도구(build tool) 라는 친구가 묵묵히 일하고 있었어요. 빌드 도구는 "코드를 컴파일하고, 필요한 라이브러리를 챙기고, 실행 가능한 결과물로 만들어주는 자동화 도구" 예요. 오늘은 그중에서도 자바 세계에서 가장 많이 쓰이는 Gradle(그레이들) 을 처음 만나봐요.
놀라운 사실 하나. 우리가 30일 내내 써온 이 프로젝트가, 알고 보면 처음부터 Gradle 프로젝트였어요. 오늘 그 정체도 직접 열어볼 거예요.
오늘은 java-basic 필수 과정의 거의 끝자락이에요. 다음 시간엔 지금까지 배운 전부를 복습하고 다음 과목으로 가는 다리를 놓을 거예요. 자, IDE 밖으로 한 걸음 나가볼까요?
🎯 학습 목표
- 컴파일과 실행을 손으로 하면 왜 번거로운지, 빌드 도구가 그걸 어떻게 대신하는지 이해해요.
- Gradle 이 자동으로 해주는 일(라이브러리 받기·컴파일·테스트·실행)을 알아요.
- 우리 프로젝트의 구조(
build.gradle.kts·settings.gradle.kts·src/main·src/test)를 읽을 수 있어요. build.gradle.kts안의 플러그인·자바 버전 설정이 무엇을 뜻하는지 알아요.- 의존성(
implementationvstestImplementation)이 무엇인지, 라이브러리를 어떻게 자동으로 받아오는지 알아요. ./gradlew명령으로 빌드·테스트·정리를 직접 해보고BUILD SUCCESSFUL을 확인해요.
오늘의 로드맵
- Step 1 — IDE 'Run' 버튼 뒤엔 무슨 일이? 빌드 도구가 왜 필요한가.
- Step 2 — Gradle 등장: 빌드 도구가 대신 해주는 일.
- Step 3 — 알고 보니 Gradle 프로젝트였다: 프로젝트 구조 둘러보기.
- Step 4 —
build.gradle.kts열어보기: 플러그인과 자바 버전. - Step 5 — 의존성 관리: 라이브러리를 자동으로 받아오기.
- Step 6 —
./gradlew명령어: 빌드·테스트·정리.
Step 1: IDE 'Run' 버튼 뒤엔 무슨 일이? — 빌드 도구가 왜 필요한가
우리가 지금까지 코드를 실행한 방법을 떠올려볼게요. IntelliJ 에서 코드를 쓰고, 초록색 'Run'(실행) 버튼을 눌렀어요. 그러면 잠깐 뒤에 아래쪽 콘솔에 결과가 짠 하고 나왔죠. 너무 당연해서 한 번도 의심해본 적 없을 거예요.
그런데 사실 그 버튼 하나가 눌리는 순간, 컴퓨터 안에서는 두 단계가 자동으로 일어나요.
① javac App.java → App.class (소스 코드를 바이트코드로 "컴파일")
② java App → 실행 결과 (바이트코드를 "실행")
javac(자바 컴파일러) 가 우리가 쓴 .java 글자를 컴퓨터가 이해하는 .class(바이트코드) 로 번역하고, java(실행기) 가 그 .class 를 실제로 돌려요. IDE 는 이 두 명령을 우리 대신 조용히 실행해줬던 거예요. 파일 한 개짜리 프로그램이라면 이 정도는 손으로 해도 별로 안 힘들어요.
문제는 프로그램이 커질 때예요. 진짜 프로젝트는 이렇게 단순하지 않거든요.
[ 손으로 직접 할 때 ]
① javac 로 컴파일 ② java 로 실행
그런데 …
- 외부 라이브러리(jar 파일)를 직접 내려받아 경로를 일일이 지정해야 하고
- 파일이 수십·수백 개가 되면 순서 맞춰 전부 컴파일해야 하고
- 팀원마다 자바 버전·라이브러리 버전이 다르면 "제 컴퓨터선 되는데요?" 사태가 나요
│ 이 귀찮은 일들을 누가 대신 해줄 수 없을까?
▼
[ 빌드 도구가 대신 할 때 ]
명령 한 줄 → 라이브러리 받기 · 컴파일 · 테스트 · 실행 까지 자동
여기서 빌드 도구가 등장해요. 비유하자면 이래요. 요리를 직접 한다고 생각해보세요. 장 보러 가서 재료 사 오고, 다듬고, 순서대로 조리하고, 불 조절하고… 손이 많이 가죠. 그런데 밀키트(meal kit) 를 쓰면 어떤가요? 재료는 손질돼서 들어 있고, 순서가 적힌 레시피 카드가 있고, 정해진 대로만 따라 하면 같은 요리가 나와요. 누가 만들어도 비슷한 결과가 나오고요.
빌드 도구가 바로 이 밀키트예요. "이 프로젝트엔 이런 라이브러리가 필요하고, 자바 몇 버전을 쓰고, 이런 순서로 컴파일·테스트해라" 를 한 번 적어두면, 누가 어느 컴퓨터에서 명령을 내리든 똑같은 방식으로 빌드해줘요.
🙋 학생 질문 — "튜터님, 그럼 지금까지 빌드 도구 없이도 잘 실행됐는데 왜 굳이 배워요?"
좋은 질문이에요. 지금까지는 IntelliJ 가 뒤에서 빌드 도구 역할을 알아서 대신 해줬기 때문에 우리가 몰라도 됐던 거예요. 하지만 두 가지 이유로 빌드 도구를 알아야 해요.
첫째, 실무 프로젝트는 거의 다 빌드 도구를 씁니다. 외부 라이브러리를 수십 개씩 가져다 쓰는데, 그걸 손으로 관리하는 건 현실적으로 불가능하거든요.
둘째, 다음 과목에서 우리가 만들 웹 서버는 IDE 버튼만으로는 다루기 어려워요. 터미널에서 명령 한 줄로 빌드하고 실행하는 게 기본이 되죠. 그래서 지금, 가장 단순한 우리 프로젝트로 빌드 도구의 감을 잡아두는 거예요.
💡 오늘의 핵심을 한 문장으로. 빌드 도구는 "컴파일·라이브러리·테스트·실행" 이라는 귀찮은 일을 자동으로 대신해주는 밀키트예요. IDE 의 'Run' 버튼 뒤에는 늘 이 친구가 일하고 있었어요.
Step 2: Gradle 등장 — 빌드 도구가 대신 해주는 일
빌드 도구가 왜 필요한지 알았으니, 이제 이름을 붙여줄 차례예요. 자바 세계에서 가장 널리 쓰이는 빌드 도구가 바로 Gradle(그레이들) 이에요. (Maven(메이븐) 이라는 친구도 있는데, 요즘 새로 시작하는 프로젝트는 Gradle 을 많이 골라요. 우리도 Gradle 로 갈게요.)
Gradle 에게 일을 시키는 방법은 의외로 단순해요. 설정 파일에 "무엇이 필요한지" 만 적어두면, "어떻게 할지" 는 Gradle 이 알아서 해줘요. 우리가 일일이 컴파일 순서를 지시하지 않아도 되는 거죠.
Gradle 이 대신 해주는 일을 정리하면 이래요.
build.gradle.kts (무엇이 필요한지 적어두는 메모지)
│ Gradle 이 이 메모를 읽고 …
▼
├─ 의존성: 필요한 라이브러리를 인터넷에서 자동으로 받아오기
├─ 컴파일: 모든 .java 를 .class 로 (순서는 알아서)
├─ 테스트: 코드가 잘 도는지 검사를 자동 실행
├─ 패키징: 결과물을 .jar 한 덩어리로 묶기
└─ 실행: 프로그램 돌리기
다시 밀키트 비유로 돌아가면, build.gradle.kts 가 바로 레시피 카드 예요. 거기에 "필요한 재료(라이브러리)" 와 "어떤 주방 도구(자바 버전)" 를 적어두면, Gradle 이라는 주방장이 장보기부터 조리까지 알아서 해주는 거죠.
여기서 한 가지 더. 이 모든 일을 우리가 시키는 통로가 ./gradlew(그레이들 래퍼) 라는 명령이에요. 터미널에 ./gradlew 로 시작하는 명령을 입력하면 Gradle 이 깨어나서 일을 시작해요. 자세한 명령은 Step 6 에서 직접 두드려볼 거예요. 지금은 "Gradle 한테는 ./gradlew 로 말을 건다" 정도만 기억하면 충분해요.
🙋 학생 질문 — "튜터님, '의존성' 이라는 말이 어려워요. 무슨 뜻인가요?"
의존성(dependency) 은 말 그대로 "내 프로그램이 의존하는(기대는) 것" 이에요. 쉽게 말해 내가 직접 만들지 않고 가져다 쓰는 외부 라이브러리 를 가리켜요.
예를 들어 날짜를 멋지게 포맷하는 기능, 엑셀 파일을 읽는 기능을 매번 직접 만들기는 벅차죠. 그래서 다른 사람이 잘 만들어둔 라이브러리를 가져다 써요. 이때 "내 프로그램은 그 라이브러리에 의존한다" 고 말하고, 그 라이브러리를 의존성이라고 불러요.
Gradle 의 큰 장점이 바로 이 의존성을 자동으로 받아주는 거예요. "이 라이브러리 필요해" 라고 한 줄 적기만 하면, 인터넷 저장소에서 알아서 내려받아요. Step 5 에서 우리 프로젝트의 의존성을 직접 들여다볼 거예요.
💡 Gradle 은 자바의 대표 빌드 도구예요.
build.gradle.kts라는 레시피에 "무엇이 필요한지" 적으면, Gradle 이 의존성·컴파일·테스트·실행을 알아서 해줘요. 우리가 말을 거는 통로는./gradlew명령이고요.
Step 3: 알고 보니 Gradle 프로젝트였다 — 프로젝트 구조 둘러보기
이제 놀라운 사실을 확인할 차례예요. 우리가 Day 1 부터 써온 이 프로젝트, 사실 처음부터 Gradle 프로젝트였어요. IntelliJ 가 그 사실을 우리 대신 처리해줘서 몰랐을 뿐이죠. 프로젝트 폴더를 열어보면 이런 파일들이 있어요.
instagram-java-basic/
├── build.gradle.kts ← 빌드 설정 (레시피 카드)
├── settings.gradle.kts ← 프로젝트 이름표
├── gradlew ← Gradle 을 실행하는 실행기 (래퍼)
├── gradle/ ← 래퍼가 쓰는 파일들
└── src/
├── main/java/ ← 우리가 짠 실제 프로그램 코드가 사는 곳
└── test/java/ ← 코드를 검사하는 코드가 사는 곳
가장 위 두 파일이 핵심이에요. build.gradle.kts 는 앞에서 말한 레시피 카드고, settings.gradle.kts 는 프로젝트 이름을 적어두는 작은 파일이에요. 그 아래 gradlew 와 gradle/ 는 Gradle 을 실행하는 도구 묶음이라 지금은 "건드릴 일 없는 것" 으로 넘어가도 돼요.
진짜 중요한 약속은 src 폴더 안에 있어요. Gradle 은 "프로그램 코드는 src/main/java, 검사 코드는 src/test/java 에 둔다" 는 규칙을 정해놨어요. 우리가 Day 8 부터 만든 com.instagram.javabasic 패키지의 모든 클래스가 바로 src/main/java 안에 차곡차곡 들어 있었던 거예요.
src/main/java/
├── day01 ~ day07 ← Phase 1 의 간단한 연습 코드
└── com/instagram/javabasic/ ← Day 8 이후 패키지로 정리된 코드
├── domain/ (Member·Post·Comment …)
├── service/ (서비스 계층)
├── modern/ (람다·Stream·record 실습)
└── … (그 외 주제별 폴더)
이 폴더 구조는 우리가 정한 게 아니라 Gradle 의 약속이에요. 그래서 어떤 자바 개발자가 와도 "아, 프로그램 코드는 src/main/java 에 있겠구나" 하고 바로 찾을 수 있어요. 약속을 정해두면 누구나 길을 잃지 않는 거죠.
💡 Gradle 프로젝트는 정해진 자리가 있어요. 설정은
build.gradle.kts·settings.gradle.kts, 프로그램 코드는src/main/java, 검사 코드는src/test/java. 우리가 30일 동안 만든 코드가 전부 이 약속 안에 있었어요.
Step 4: build.gradle.kts 열어보기 — 플러그인과 자바 버전
레시피 카드를 직접 펼쳐볼 시간이에요. build.gradle.kts 를 열면 위쪽이 이렇게 생겼어요. (이 파일은 Kotlin(코틀린) 이라는 언어 문법으로 쓰여 있는데, 지금은 "설정을 적는 칸" 으로만 봐도 충분해요.)
// build.gradle.kts
plugins {
java
}
group = "com.instagram"
version = "0.0.1-SNAPSHOT"
java {
toolchain {
languageVersion = JavaLanguageVersion.of(25)
}
}
repositories {
mavenCentral()
}
한 칸씩 읽어볼게요. 어렵지 않아요.
plugins { java }— "이건 자바 프로젝트 입니다" 하고 선언하는 칸이에요. 이 한 줄 덕분에 Gradle 이 자바 컴파일 방법을 알게 돼요.group과version— 프로젝트의 이름표예요.group은 소속(보통 회사·도메인 이름),version은 버전이에요.SNAPSHOT은 "아직 개발 중" 이라는 표시고요.java { toolchain { ... of(25) } }— 이 프로젝트는 JDK 25 로 빌드한다는 뜻이에요. 우리가 Day 1 에서 JDK 25 를 설치한 게 여기서 쓰이는 거죠. 팀원이 다른 버전을 깔아도 Gradle 이 25 로 맞춰줘요.repositories { mavenCentral() }— 라이브러리를 받아올 인터넷 창고 를 지정하는 칸이에요.mavenCentral(메이븐 센트럴) 은 전 세계 개발자들이 만든 자바 라이브러리가 모여 있는 거대한 공용 창고예요.
여기까지가 "이 프로젝트는 어떤 프로젝트인가" 를 적는 부분이에요. 자바 프로젝트고, 이름은 이렇고, 자바 25 로 만들고, 라이브러리는 저 창고에서 받는다 — 딱 이만큼이에요.
🙋 학생 질문 — "튜터님, repositories 에 창고를 적었는데, 정작 받아올 라이브러리는 어디에 적나요?"
날카로운 질문이에요. repositories 는 "어디서" 받을지(창고 위치) 를 적는 칸이고, "무엇을" 받을지(라이브러리 목록) 는 바로 다음에 나오는 dependencies 칸에 적어요.
비유하면 repositories 는 "이마트에서 장 볼 거야"(가게 지정) 고, dependencies 는 "우유, 계란, 빵 사 와"(품목 지정) 인 셈이죠. 그 dependencies 칸을 바로 다음 Step 에서 열어볼 거예요.
💡
build.gradle.kts윗부분은 프로젝트의 신분증이에요.plugins로 "자바 프로젝트" 선언,toolchain으로 "JDK 25 사용",repositories로 "라이브러리 받아올 창고" 를 정해요.
Step 5: 의존성 관리 — 라이브러리를 자동으로 받아오기
이제 레시피 카드의 핵심, 재료 목록 을 볼 차례예요. build.gradle.kts 의 아래쪽엔 dependencies(의존성) 칸이 있어요.
dependencies {
testImplementation(platform("org.junit:junit-bom:5.12.2"))
testImplementation("org.junit.jupiter:junit-jupiter")
testRuntimeOnly("org.junit.platform:junit-platform-launcher")
}
Step 2 에서 의존성은 "내가 직접 만들지 않고 가져다 쓰는 외부 라이브러리" 라고 했죠. 이 칸에 라이브러리 이름을 한 줄 적기만 하면, Gradle 이 mavenCentral 창고에서 알아서 내려받아요. 우리가 직접 jar 파일을 찾아다닐 필요가 없어진 거예요.
그런데 여기서 단어 두 개를 구분해야 해요. implementation 과 testImplementation 이에요. 요리 비유로 보면 딱 떨어져요.
implementation → 요리에 들어가는 재료 (완성된 음식에 그대로 들어감)
= 프로그램이 실제로 돌 때 필요한 라이브러리
testImplementation → 맛을 보는 간 보기용 도구 (손님상엔 안 올라감)
= 코드를 검사(테스트)할 때만 필요한 라이브러리
implementation 은 프로그램 본체가 쓰는 라이브러리예요. 예를 들어 "엑셀을 읽는 라이브러리가 필요하다" 면 implementation("...") 으로 적어요. 반면 testImplementation 은 코드가 잘 도는지 검사할 때만 쓰는 라이브러리고요.
재밌는 점 하나. 위 코드를 보면 우리 프로젝트엔 implementation 이 한 줄도 없어요. 왜일까요? 우리는 지금까지 외부 라이브러리 없이 자바가 기본으로 주는 표준 기능 만으로 코드를 짰거든요. String·List·Stream·Optional 전부 자바에 원래 들어 있는 것들이라, 따로 받아올 게 없었던 거예요.
testImplementation 에 보이는 junit(제이유닛) 은 코드를 자동으로 검사해주는 테스트 도구인데, 이건 한참 뒤 심화 과정에서 따로 배워요. 지금은 "testImplementation 칸엔 검사할 때만 쓰는 라이브러리가 들어간다" 만 봐두면 충분해요.
💡
dependencies는 레시피의 재료 목록이에요.implementation은 프로그램 본체가 쓰는 라이브러리,testImplementation은 검사할 때만 쓰는 라이브러리. 줄만 적으면 Gradle 이 창고에서 자동으로 받아와요. 우리 프로젝트는 표준 기능만 써서implementation이 비어 있어요.
Step 6: ./gradlew 명령어 — 빌드·테스트·정리
지금까지 레시피 카드를 읽기만 했으니, 이제 직접 요리를 시켜볼 차례예요. Gradle 에게 일을 시키는 통로가 ./gradlew(그레이들 래퍼) 명령이라고 했죠. IntelliJ 아래쪽의 터미널(Terminal) 창을 열고 직접 두드려봐요.
먼저 가장 많이 쓰는 명령, ./gradlew build(빌드) 예요.
$ ./gradlew build
BUILD SUCCESSFUL in 1s
BUILD SUCCESSFUL(빌드 성공) 한 줄이 떴어요. 이 짧은 한 줄 뒤에서 Gradle 은 꽤 많은 일을 했어요. 모든 .java 를 컴파일하고, 코드 검사를 돌리고, 결과물을 .jar 한 덩어리로 묶는 일까지요. 손으로 하면 한참 걸렸을 일을 1초 만에 끝낸 거예요.
이번엔 ./gradlew clean(클린) 이에요. 이전에 빌드하면서 만들어둔 결과물(build 폴더) 을 싹 지워줘요.
$ ./gradlew clean
BUILD SUCCESSFUL in 482ms
뭔가 꼬였을 때 clean 으로 깨끗이 지우고 다시 build 하면 말끔해지는 경우가 많아요. 자주 쓰게 될 조합이에요. 주요 명령을 표로 정리하면 이래요.
| 명령 | 하는 일 |
|---|---|
./gradlew build |
컴파일 + 검사 + 결과물(.jar) 묶기까지 한 번에 |
./gradlew clean |
이전에 만든 결과물(build 폴더) 싹 지우기 |
./gradlew test |
코드 검사(테스트)만 실행 |
./gradlew tasks |
이 프로젝트에서 쓸 수 있는 명령 목록 보기 |
여기서 잠깐, gradlew 의 w 가 뭘까요? 래퍼(wrapper) 의 약자예요. 래퍼는 "이 프로젝트는 Gradle 9.x 버전으로 빌드한다" 를 기억해뒀다가, 명령을 내리면 그 버전을 자동으로 맞춰서 실행해줘요. 덕분에 내 컴퓨터에 Gradle 을 따로 설치하지 않아도, 팀원과 똑같은 버전으로 빌드할 수 있어요. 밀키트가 "정해진 도구로 정해진 결과" 를 보장하는 것처럼요.
🙋 학생 질문 — "튜터님, 그럼 프로그램을 그냥 '실행' 하는 명령은 없나요? IDE 의 Run 버튼처럼요."
있어요. 프로그램을 직접 실행하는 명령(./gradlew run) 도 있어요. 다만 그 명령을 쓰려면 "어떤 코드를 시작점으로 실행할지" 를 build.gradle.kts 에 살짝 더 적어줘야 해요.
그 준비와 함께, 우리가 30일 동안 배운 걸 한 데 엮어 ./gradlew run 으로 직접 돌려보는 건 다음 시간의 즐거움으로 남겨둘게요. 오늘은 build·clean 으로 Gradle 과 인사하는 것까지면 충분해요.
💡
./gradlew build한 줄이면 컴파일·검사·묶기가 끝나고BUILD SUCCESSFUL이 떠요.gradlew의w는 래퍼(wrapper) — 프로젝트에 맞는 Gradle 버전을 자동으로 맞춰줘서, 누가 어느 컴퓨터에서 실행해도 같은 결과가 나와요.
마무리
오늘은 IDE 의 'Run' 버튼 뒤에서 묵묵히 일하던 친구, 빌드 도구를 처음 만났어요.
- 빌드 도구가 왜 필요한가 — 컴파일(
javac)·실행(java)·라이브러리 챙기기·여러 파일 관리·팀 버전 맞추기를 손으로 하면 너무 번거로워요. 빌드 도구가 이걸 밀키트처럼 자동으로 대신해줘요. - Gradle — 자바의 대표 빌드 도구.
build.gradle.kts레시피에 "무엇이 필요한지" 적으면, 의존성·컴파일·테스트·실행을 알아서 해줘요. - 프로젝트 구조 — 설정은
build.gradle.kts·settings.gradle.kts, 프로그램 코드는src/main/java, 검사 코드는src/test/java. 우리가 30일간 만든 코드가 전부 이 약속 안에 있었어요. build.gradle.kts—plugins로 자바 프로젝트 선언,toolchain으로 JDK 25,repositories로 라이브러리 창고,dependencies로 재료 목록(implementation/testImplementation)../gradlew명령 —build로 한 번에 빌드,clean으로 정리. 래퍼(w) 가 Gradle 버전을 자동으로 맞춰줘요.
이제 우리는 IDE 버튼에만 기대지 않고, 터미널에서 직접 프로젝트를 빌드할 수 있게 됐어요. IDE 밖으로 한 걸음 내디딘 거죠. 다음 과목에서 만들 웹 서버도 바로 이 ./gradlew 명령으로 다루게 돼요.
다음 시간엔 — 지금까지의 여정을 한 번에
다음 시간은 java-basic 필수 과정의 마지막 날이에요. Day 1 의 변수부터 오늘의 Gradle 까지, 지금까지 배운 전부를 4단계로 차근차근 복습해요. 그리고 그 모든 조각(람다·Stream·Optional·record…) 을 한 데 엮은 작은 프로그램을 만들어, 오늘 배운 ./gradlew run 으로 직접 실행해볼 거예요. 마지막엔 다음 과목으로 가는 다리도 놓고요. 정말 얼마 안 남았어요!
과제
오늘은 코드를 새로 짜기보다, 우리 프로젝트를 직접 열고 두드려보며 Gradle 과 친해지는 과제예요. IntelliJ 로 instagram-java-basic 프로젝트를 연 상태에서 풀어봐요.
과제 1: 레시피 카드 읽기 — build.gradle.kts · settings.gradle.kts
상황 배경: Step 3~5 에서 설정 파일을 함께 읽었어요. 이번엔 직접 열어서 값을 찾아보는 거예요.
🎯 해결 미션: 프로젝트 폴더에서 두 파일을 열고, 아래 세 가지를 찾아 적어보세요.
build.gradle.kts에서 — 이 프로젝트는 자바 몇 버전 으로 빌드하도록 설정돼 있나요? (힌트:toolchain)build.gradle.kts에서 — 라이브러리를 받아오는 창고 이름 은 무엇인가요? (힌트:repositories)settings.gradle.kts에서 — 이 프로젝트의 이름 은 무엇인가요?
과제 2: 직접 빌드해보기 — ./gradlew clean 과 build
상황 배경: Step 6 에서 본 명령을 직접 터미널에 입력해봐요. IntelliJ 아래쪽의 Terminal 창을 열면 돼요.
🎯 해결 미션:
- 먼저
./gradlew build를 실행하고,BUILD SUCCESSFUL이 뜨는지 확인하세요. 그리고 프로젝트에build라는 폴더가 새로 생겼는지 살펴보세요. - 이번엔
./gradlew clean을 실행하세요. 방금 생긴build폴더가 사라졌나요? - 다시
./gradlew build를 실행하면build폴더가 또 생기는지 확인하세요.
clean 으로 지우고 build 로 다시 만드는 흐름을 눈으로 직접 보는 게 이번 과제의 목표예요.
과제 3: 어떤 명령들이 있을까 — ./gradlew tasks
상황 배경: Gradle 에는 우리가 배운 build·clean 말고도 많은 명령이 있어요. 그 목록을 직접 꺼내봐요.
🎯 해결 미션: 터미널에 ./gradlew tasks 를 실행하면 쓸 수 있는 명령(task) 목록이 주르륵 나와요. 그중 우리가 아직 안 배운 명령을 3개 골라, 이름만 보고 "이건 무슨 일을 할까?" 를 한 줄씩 추측해서 적어보세요. (정답을 맞히는 게 아니라, 이름으로 짐작해보는 연습이에요.)
생각해볼 주제
혼자 고민해도 좋고, 동료와 토론해도 좋아요. 정답을 외우기보다 "나라면 어떻게 설명할까" 를 떠올리며 읽어보세요.
1. IDE 의 'Run' 버튼은 편한데, 왜 실무에선 굳이 터미널 빌드 명령을 쓸까?
버튼 한 번이면 끝나는 IDE 실행은 분명 편해요. 그런데도 실무에서는 ./gradlew build 같은 터미널 명령을 기본으로 써요.
"사람이 직접 클릭하는 것" 과 "명령 한 줄로 자동화하는 것" 의 차이를 떠올려보세요. 예를 들어 코드를 올릴 때마다 자동으로 빌드·검사를 돌리는 상황이라면, 버튼 클릭과 명령어 중 어느 쪽이 어울릴까요?
2. 라이브러리를 Gradle 에 맡기면 편한데, 그 라이브러리는 어디서 오고 믿어도 될까?
dependencies 에 한 줄 적으면 Gradle 이 mavenCentral 창고에서 라이브러리를 알아서 받아와요. 정말 편하죠. 그런데 그 라이브러리는 내가 만든 게 아니라 누군가가 인터넷에 올린 코드예요.
"편하게 가져다 쓰는 것" 과 "내 프로그램에 남의 코드가 들어온다는 것" 사이에서, 버전을 콕 집어 적어두는 게(예: 5.12.2) 왜 안전에 도움이 될지 생각해보세요.
3. 작은 프로그램은 빌드 도구 없이도 잘 도는데, 언제부터 꼭 필요해질까?
Day 1 의 Hello World 는 빌드 도구 없이 IDE 버튼만으로도 충분히 잘 돌았어요. 사실 파일 한두 개짜리 프로그램엔 빌드 도구가 좀 과해 보이기도 해요.
그렇다면 프로젝트가 "어느 정도" 커지면 빌드 도구가 없으면 곤란해질까요? 파일 수, 외부 라이브러리, 함께 일하는 사람 수 같은 것들을 떠올리며 그 경계를 한번 그어보세요.
✅ 예시 답안정답 보기
오늘 과제는 코드를 새로 짜기보다, 우리 프로젝트를 직접 열고 터미널을 두드려보며 Gradle 과 친해지는 흐름이에요. 과제 1 은 설정 파일(build.gradle.kts·settings.gradle.kts)에서 값을 찾고, 과제 2 는 ./gradlew clean 과 build 를 직접 실행해보고, 과제 3 은 ./gradlew tasks 로 어떤 명령들이 있는지 살펴봐요. 교안 Step 3~6 을 옆에 두고 비교하면서 보면 편해요.
과제 예시답안
과제 1 예시답안 — 레시피 카드 읽기
핵심 접근
세 가지 모두 설정 파일을 "열어서 눈으로 찾는" 과제예요. 외울 필요는 없고, 어느 칸에 어떤 값이 적혀 있는지 위치를 잡는 게 목적이에요. 자바 버전은 toolchain, 라이브러리 창고는 repositories, 프로젝트 이름은 settings.gradle.kts 에 있어요.
정답과 확인 포인트
- 자바 버전 — JDK 25.
build.gradle.kts의java { toolchain { languageVersion = JavaLanguageVersion.of(25) } }에서of(25)가 25 버전을 뜻해요. - 라이브러리 창고 —
mavenCentral.repositories { mavenCentral() }칸에 적혀 있어요. 전 세계 자바 라이브러리가 모인 공용 창고예요. - 프로젝트 이름 —
instagram-java-basic.settings.gradle.kts의rootProject.name = "instagram-java-basic"에서 찾을 수 있어요.
// build.gradle.kts (발췌)
java {
toolchain {
languageVersion = JavaLanguageVersion.of(25) // ← 자바 버전
}
}
repositories {
mavenCentral() // ← 라이브러리 창고
}
채점 포인트
| 확인할 점 | 왜 중요한가 |
|---|---|
자바 버전을 toolchain 에서 찾았는가 |
버전이 build.gradle.kts 어디에 적히는지 위치를 아는 게 목적이에요 |
창고 이름이 mavenCentral 인가 |
"어디서" 라이브러리를 받는지 가리키는 칸이에요 |
프로젝트 이름을 settings.gradle.kts 에서 찾았는가 |
두 설정 파일의 역할이 다르다는 걸 구분하는 게 핵심이에요 |
흔한 실수
- 프로젝트 이름을
build.gradle.kts의group = "com.instagram"에서 찾아요.group은 소속(도메인) 이름이고, 프로젝트 이름은settings.gradle.kts의rootProject.name이에요. - 자바 버전을
version = "0.0.1-SNAPSHOT"으로 착각해요. 이건 프로젝트의 버전이지 자바 버전이 아니에요. 자바 버전은toolchain안에 있어요.
과제 2 예시답안 — 직접 빌드해보기
핵심 접근
터미널에 명령을 입력하고, 그 결과로 build 폴더가 생겼다 사라졌다 하는 걸 눈으로 확인하는 과제예요. build 는 결과물을 만들고, clean 은 그 결과물을 지운다는 걸 직접 보는 게 목적이에요.
예상 결과
./gradlew build를 실행하면BUILD SUCCESSFUL이 뜨고, 프로젝트에build폴더가 새로 생겨요.
$ ./gradlew build
BUILD SUCCESSFUL in 1s
./gradlew clean을 실행하면 방금 생긴build폴더가 사라져요.
$ ./gradlew clean
BUILD SUCCESSFUL in 482ms
- 다시
./gradlew build를 실행하면build폴더가 또 생겨요.clean → build를 반복하면 폴더가 사라졌다 생겼다 해요.
build 폴더 안에는 컴파일된 .class 파일과 묶인 .jar 같은 결과물이 들어 있어요. clean 은 그걸 통째로 지워서 "처음부터 다시" 를 만들어줘요.
채점 포인트
| 확인할 점 | 왜 중요한가 |
|---|---|
BUILD SUCCESSFUL 을 직접 확인했는가 |
빌드가 성공했다는 신호를 눈으로 보는 게 첫걸음이에요 |
build 폴더가 생기는 걸 봤는가 |
빌드 결과물이 어디에 쌓이는지 감을 잡는 게 목적이에요 |
clean 후 build 폴더가 사라지는 걸 봤는가 |
clean 의 역할(정리)을 직접 체험하는 게 핵심이에요 |
흔한 실수
- 명령을
gradlew build로 입력해요(앞의./빠짐). 맥·리눅스 터미널에서는 현재 폴더의 실행기를 쓴다는 뜻으로./gradlew처럼./를 붙여야 해요. (윈도우는gradlew build또는gradlew.bat) build폴더가 안 보인다고 당황해요. IDE 설정에 따라 숨겨져 보일 수 있어요. 프로젝트 폴더를 파일 탐색기에서 직접 열어보면 보여요.- 첫 실행이 느리다고 멈춰요. 처음엔 Gradle 이 필요한 걸 내려받느라 시간이 좀 걸릴 수 있어요. 두 번째부터는 빨라져요.
과제 3 예시답안 — 어떤 명령들이 있을까
핵심 접근
./gradlew tasks 를 실행하면 쓸 수 있는 명령(task) 목록이 종류별로 주르륵 나와요. 정답을 맞히는 게 아니라, 명령 이름만 보고 "이건 무슨 일을 할까?" 를 짐작해보는 연습이에요. 영어 단어의 뜻에서 힌트를 얻으면 돼요.
예시 추측
./gradlew tasks 를 실행하면 예를 들어 이런 명령들이 보여요. 이름으로 추측해보면 이렇게 짐작할 수 있어요.
| 명령 이름 | 이름으로 추측한 일 |
|---|---|
assemble |
"조립하다" → 결과물(.jar) 을 만드는 일이겠다 |
check |
"검사하다" → 코드가 잘 도는지 확인(테스트)하는 일이겠다 |
javadoc |
"자바 문서" → 코드 설명 문서를 자동으로 만들어주는 일이겠다 |
dependencies |
"의존성" → 이 프로젝트가 쓰는 라이브러리 목록을 보여주는 일이겠다 |
clean |
"청소하다" → (배운 대로) 결과물을 지우는 일 |
이름의 뜻을 곱씹어보면 실제 동작과 얼추 들어맞는 경우가 많아요. 모르는 명령을 만났을 때 "이름이 뭘 말하는지" 부터 보는 습관이 도움이 돼요.
채점 포인트
| 확인할 점 | 왜 중요한가 |
|---|---|
./gradlew tasks 를 실제로 실행했는가 |
명령 목록을 직접 꺼내보는 게 과제의 출발점이에요 |
| 3개를 골라 추측을 적었는가 | 정답 여부보다 "이름으로 짐작하기" 라는 태도가 목적이에요 |
| 추측에 나름의 근거(이름 뜻)가 있는가 | 단순 찍기가 아니라 단어에서 힌트를 얻는 연습이에요 |
흔한 실수
- 추측이 틀릴까 봐 적기를 망설여요. 이 과제는 맞히는 게 아니라 짐작해보는 연습이에요. 틀려도 전혀 문제없어요.
- 이미 배운
build·clean만 골라요. 일부러 아직 안 배운 명령을 골라야 "이름으로 추측하기" 연습이 돼요.
생각해볼 주제 예시답안
생각해볼 주제 1 예시답안 — IDE 버튼은 편한데, 왜 터미널 빌드를 쓸까?
[문제 상황 요약]
버튼 한 번이면 끝나는 IDE 실행은 분명 편해요. 그런데도 실무에서는 ./gradlew build 같은 터미널 명령을 기본으로 써요. "사람이 직접 클릭하는 것" 과 "명령 한 줄로 자동화하는 것" 의 차이는 무엇일까요?
[튜터의 가이드 및 해설]
핵심은 "자동화" 와 "일관성" 이에요.
IDE 버튼은 사람이 마우스로 직접 눌러야 동작해요. 사람이 있어야만 한다는 뜻이죠. 그런데 실무에선 "코드를 올릴 때마다 자동으로 빌드하고 검사한다" 같은, 사람 없이 컴퓨터가 알아서 해야 하는 상황이 많아요. 이런 자동 처리는 마우스 클릭으로는 시킬 수 없고, ./gradlew build 같은 명령어 라야 컴퓨터가 대신 실행할 수 있어요.
또 하나는 일관성이에요. IDE 버튼은 사람마다 IDE 종류·설정이 달라서 "내 컴퓨터선 되는데요?" 가 생기기 쉬워요. 반면 ./gradlew build 는 누가 어느 컴퓨터에서 입력해도 래퍼가 같은 Gradle 버전으로 똑같이 빌드해줘요. 결과가 사람·환경에 따라 흔들리지 않는 거죠.
정리하면, IDE 버튼은 "내가 지금 한 번 돌려보기" 에 편하고, 터미널 명령은 "사람 없이 자동으로, 누구나 똑같이 돌리기" 에 어울려요. 둘은 경쟁 상대가 아니라 쓰임이 다른 도구예요.
🎯 면접관을 홀리는 핵심 멘트
"IDE 의 Run 버튼은 사람이 직접 클릭해야 동작하지만,
./gradlew build같은 명령은 사람 없이 자동으로 실행할 수 있습니다. 그래서 코드를 올릴 때마다 자동으로 빌드·검사하는 환경에서는 명령 기반 빌드가 필수입니다. 또 래퍼 덕분에 누가 어느 컴퓨터에서 실행해도 같은 버전으로 동일하게 빌드되어, 환경에 따른 결과 차이를 없애준다는 점이 핵심이라고 생각합니다."
생각해볼 주제 2 예시답안 — 라이브러리는 어디서 오고 믿어도 될까?
[문제 상황 요약]
dependencies 에 한 줄 적으면 Gradle 이 mavenCentral 창고에서 라이브러리를 알아서 받아와요. 편하죠. 그런데 그 라이브러리는 내가 만든 게 아니라 누군가가 인터넷에 올린 코드예요. 버전을 콕 집어 적어두는 게(예: 5.12.2) 왜 안전에 도움이 될까요?
[튜터의 가이드 및 해설]
핵심은 "내 프로그램에 남의 코드가 들어온다" 는 사실을 잊지 않는 거예요.
라이브러리는 시간이 지나면 새 버전이 계속 나와요. 만약 버전을 안 적고 "그냥 최신 거" 로 받아오게 두면, 받는 시점마다 다른 버전이 들어올 수 있어요. 잘 되던 게 어느 날 갑자기 안 되는, 영문 모를 사고가 날 수 있는 거죠. 그래서 junit-bom:5.12.2 처럼 버전을 콕 집어두면, 언제 받아도 똑같은 버전이 들어와서 결과가 흔들리지 않아요.
또 라이브러리는 결국 남이 만든 코드라, 가져다 쓰기 전에 "믿을 만한 곳에서 만든, 많이 쓰이는 것인가" 를 보는 눈도 필요해요. mavenCentral 같은 공식 창고에 올라온, 널리 검증된 라이브러리를 고르는 게 기본이에요. 편하다고 아무거나 받아오는 게 아니라요.
정리하면, 의존성을 Gradle 에 맡기는 건 분명 편하지만, "버전을 고정해 결과를 안정적으로 유지하고", "믿을 만한 라이브러리를 고르는" 두 가지는 사람이 챙겨야 할 몫이에요.
🎯 면접관을 홀리는 핵심 멘트
"의존성은 결국 외부에서 들어오는 남의 코드라고 생각합니다. 그래서 버전을 명시적으로 고정해 언제 빌드해도 같은 버전이 들어오도록 해서, 환경에 따라 동작이 달라지는 일을 막습니다. 또 공식 저장소의 널리 검증된 라이브러리를 고르는 판단도 중요하다고 봅니다. 편의를 얻되, 안정성과 신뢰는 사람이 챙겨야 한다는 점이 핵심이라고 생각합니다."
생각해볼 주제 3 예시답안 — 언제부터 빌드 도구가 꼭 필요해질까?
[문제 상황 요약]
Day 1 의 Hello World 는 빌드 도구 없이 IDE 버튼만으로도 잘 돌았어요. 파일 한두 개짜리엔 빌드 도구가 좀 과해 보이기도 해요. 그렇다면 프로젝트가 "어느 정도" 커지면 빌드 도구가 없으면 곤란해질까요?
[튜터의 가이드 및 해설]
기준을 세 가지로 떠올려보면 경계가 보여요. 파일 수, 외부 라이브러리, 함께 일하는 사람.
먼저 파일 수예요. 파일이 한두 개일 땐 손으로 컴파일해도 괜찮지만, 수십·수백 개가 되면 순서 맞춰 일일이 컴파일하는 건 사실상 불가능해요. 이때부터 빌드 도구가 컴파일을 자동으로 관리해줘야 해요.
다음은 외부 라이브러리예요. 자바 표준 기능만 쓸 땐(우리 프로젝트처럼) 받아올 게 없어 빌드 도구가 덜 아쉬워요. 하지만 외부 라이브러리를 하나라도 쓰기 시작하면, 그걸 받아오고 버전을 맞추는 일이 곧바로 번거로워져서 빌드 도구가 큰 도움이 돼요.
마지막은 사람이에요. 혼자 만들 땐 내 환경만 맞으면 되지만, 여러 명이 함께 만들면 "모두가 똑같은 버전·똑같은 방식" 으로 빌드해야 사고가 안 나요. 이 일관성을 보장해주는 게 빌드 도구의 큰 역할이고요.
정리하면, "파일이 많아지거나 / 외부 라이브러리를 쓰거나 / 여럿이 함께 만들기" 시작하는 순간이 빌드 도구가 꼭 필요해지는 경계예요. 작은 연습 코드엔 과할 수 있지만, 진짜 프로젝트는 거의 다 이 셋 중 하나에 걸리기 때문에 빌드 도구를 기본으로 쓰는 거예요.
🎯 면접관을 홀리는 핵심 멘트
"저는 빌드 도구의 필요성을 파일 수, 외부 라이브러리, 협업 인원 세 가지로 판단합니다. 파일이 많아지면 컴파일 관리가, 외부 라이브러리를 쓰면 의존성 관리가, 여럿이 함께 만들면 빌드 일관성이 필요해지는데, 빌드 도구가 이 셋을 모두 해결해줍니다. 작은 연습 코드엔 과할 수 있지만 실무 프로젝트는 거의 다 이 조건에 걸리기 때문에 빌드 도구가 기본이 된다고 생각합니다."
