Java/JVM
[JVM 밑바닥까지 파헤치기] 7-3. 클래스 로딩 매커니즘: 자바 모듈 시스템
noahkim_
2024. 12. 23. 19:34
저우즈밍 님의 "JVM 밑바닥까지 파헤치기" 책을 정리한 포스팅 입니다
1. JPMS
- Java 9에서 도입된 모듈 시스템
- ⚠️ 기존의 Java는 JAR 단위의 클래스패스 기반 구조는 의존성/캡슐화가 느슨하였음
- ✅ 모듈 단위의 캡슐화, 격리, 의존성 명시 시스템이 도입됨
- ➡️ 실행 시점에 의존성/가시성을 검증한 후 실행함
클래스패스 문제점) 순환 참조
더보기
- 순환 참조를 감지/차단하지 못함
- ⚠️ 프로젝트가 커질수록 스파게티 의존성이 되기 쉬움
- ❌ 초기화 순서 문제 (ClassCircularityError)
- ❌ 결합도 높아짐
클래스패스 문제점) 런타임 오류
더보기
- 컴파일 타임에 존재했던 의존성이, 런타임 배포시에 빠지면 런타임 에러가 터짐
- ❌ ClassNotFoundException / NoClassDefFoundError (클래스 없음)
- ❌ NoSuchMethodError / NoSuchFieldError (클래스 버전 다름)
module-info.java
- 모듈의 경계와 의존성을 정의하는 선언 파일 (메타데이터 역할)
- ✅ 디렉토리에 .module-info.java가 포함되어 있으면 모듈로 간주됨
| 키워드 | 설명 |
| requires |
다른 모듈을 참조함
|
| exports |
모듈 내부 패키지를 외부에 공개
|
| uses |
서비스 인터페이스 사용 명시 (e.g. ServiceLoader)
|
| provides |
uses 대상 인터페이스의 구현체 제공 명시
|
| open |
리플렉션 허용용 → 특정 패키지를 리플렉션 API에 공개
|
코드) module-info.java
더보기
module com.example.app {
requires java.sql;
requires com.example.lib;
exports com.example.api;
uses com.example.spi.PaymentService;
provides com.example.spi.PaymentService
with com.example.impl.PaymentServiceImpl;
}
모듈 경로 (--module-path)
- 모듈들이 위치하는 디렉토리
- ✅ 기존 클래스패스와 병행 사용 가능
코드) --module-path
더보기
java --module-path mods --class-path libs ...
2. 모듈화 시대의 클래스 로더
- Java 9부터 디렉토리 통합 (JAVA_HOME/jre 삭제 → lib/module 통합)
- 확장 디렉토리 삭제 (lib/ext 삭제)
BuiltinClassLoader
- Java 9 이후 기본 클래스 로더
- ✅ 기존의 URLClassLoader을 대체함
- ✅ 모듈 의존성 및 가시성을 고려하여 로드 (모듈 그래프 기반)