
Java ํ๋ก์ ํธ๋ฅผ ์ค์ ํ ๋ ํ๋ก์ ํธ ์ฐํด๋ฆญํ๋ฉด Build Path๊ฐ ๋์จ๋ค. ์ฌ๊ธฐ์ ์ฐ๋ฆฌ๊ฐ Oracle JDBC ๋๋ผ์ด๋ฒ(ojdbc8.jar) ๊ฐ์ ์ธ๋ถ ๋ผ์ด๋ธ๋ฌ๋ฆฌ๋ฅผ ๋ฑ๋กํ ์ ์๋ค. ๋ MySQL Connection(mysql-connector-java.jar)์ด๋ผ๋ ์ง Getter์ Setter์ ์๋์์ฑํ๋ Lombok(lombok.jar) ๋ผ์ด๋ธ๋ฌ๋ฆฌ๋ฅผ ๋ฑ๋ก ํด ๋ณธ ์ ์ด ์์ ๊ฒ์ด๋ค.
ํ์๋ ํญ์ ์ด ๋ผ์ด๋ธ๋ฌ๋ฆฌ๋ค์ ์ถ๊ฐํ ๋ Classpath, Module Path ์ค ์ด๋์ ์ถ๊ฐํด์ผ ํ๋์ง ํท๊ฐ๋ ธ๊ธฐ ๋๋ฌธ์ ์ด ๊ธ์ ์์ฑํ๋ค. Buildpath๋ ์๋ฐ์์ ์ค์ํ ๊ฐ๋
์ด๋ฉฐ, ์ด๋ค ๊ฒ์ ๋ฑ๋กํด์ผ ํ๋์ง๋ ํ๋ก์ ํธ ํ๊ฒฝ๊ณผ ์ฌ์ฉ ๊ธฐ์ ์ ๋ฐ๋ผ ๋ฌ๋ผ์ง๋ค.
์ด๋ก ์ ์ธ ์ค๋ช
์ ๊ฑด๋ ๋ฐ๊ณ ์ธ์ ModulePath vs Classpath๋ฅผ ์ฌ์ฉํ๋์ง๋ง ์๊ณ ์ถ์ ์ฌ๋์ 6.์ธ์ ModulePath vs Classpath๋ฅผ ์ฌ์ฉํ ๊น? ๋ก ๋ฐ๋ก ์ด๋ํ๊ธฐ ๋ฐ๋๋ค.
1. Classpath์ ModulePath์ ๊ฐ๋
- Classpath: ์ฌ์ฉ์ ์ ์ ํด๋์ค(Class) ๋๋ ํจํค์ง(Package)์ ์์น (Java8 ๊น์ง ๊ธฐ๋ณธ ๋ฐฉ์)
- ModulePath: ์ฌ์ฉ์ ์ ์ ๋ชจ๋(Module)์ด ์์นํ๋ ๊ณณ
- ๋ชจ๋ํจ์ค๋ ํ ๋ง๋๋ก ๋ชจ๋ ๊ฐ๋ ์ ๋์ ํ์ฌ ํจํค์ง๋ฅผ ๊ทธ๋ฃนํํ ์์น์ด๋ค. Java 9๋ถํฐ ๋์ ๋์๋ค.
- โก ํ ๋ง๋๋ก Java 8 ์ดํ์์๋ Classpath ์ฌ์ฉ, Java 9 ์ด์์์๋ ModulePath ์ฌ์ฉ ๊ถ์ฅ
- ModulePath๋ฅผ ์ฌ์ฉํ๋ฉด exports ํค์๋๋ก ์ํ๋ ํจํค์ง๋ง ๋ช ํํ๊ฒ ๊ณต๊ฐํ ์ ์๊ณ , ๋๋จธ์ง๋ ๊ฐ์ถ ์ ์๋ค.
- ์ฆ, **์บก์ํ(Encapsulation)**๊ฐ ๊ฐ๋ฅํด์ง๊ณ , ๋ถํ์ํ ์ฝ๋ ์์กด์ฑ์ ๋ง์ ์ ์๋ค. ํ์ง๋ง ๊ฐ์ธ์ ์ผ๋ก ์ฐ์ตํ๋๊ฑฐ๋ฉด classpath๋ฅผ ์ฌ์ฉํ๋ ๊ฒ์ด ์ข๋ค. ๋ผ์ด๋ธ๋ฌ๋ฆฌ๋ฅผ ModulePath์ ์ถ๊ฐํ๋ฉด, module-info.java์์ requires oracle.jdbc ๊ฐ์ ์์ผ๋ก ์์กด์ฑ์ ์ง์ ์ค์ ํด์ฃผ์ด์ผ ํ๋ค. ์๋ฐ์ ์บก์ํ ์์น๋๋ฌธ์ ๊ทธ๋ ๋ค.
๊ทธ๋ฆผ์ ๋ณด๋ฉด์ ์ค๋ช ์ ํ์๋ฉด, ModulePath๋ ํจํค์ง๊ฐ ํ๋์ ๋ชจ๋๋ง ์ก์ธ์ค๊ฐ ๊ฐ๋ฅํ๊ณ , ์ฌ๋ฌ ํจํค์ง๋ฅผ ์ข ์์ํฌ ์ ์๋ค. ์์น์ ์ธ ๊ฐ๋ ์ด๋ผ๊ณ ์๊ฐํ๋ฉด ๋๋ค. JRE๋ ๋ฌด์กฐ๊ฑด Module์ ์์นํ๋ค. ๋ง์น ๋ฉ์๋๋ฅผ ํธ์ถํ๋๊ฒ ์ฒ๋ผ ๋ชจ๋์ ๋ง๋ค์ด ํธ์ถํ์ฌ ์ฌ์ฉํ๋ค. (interface๋ฅผ ํตํด ์ ๊ทผํ๋๊ฒ๊ณผ ์ ์ฌํ๋ค.)

๐ ๋ชจ๋(Module)
module ์ package๋ค์ ๋ชจ์์ด๋ฉฐ packages์ top์ ์ค์น๋๋ค.
์ฆ, module์ ์ต์์ ํจํค์ง๋ผ๊ณ ์๊ฐํ๋ฉด ๋๋ค. (ํจํค์ง๋ค์ ์์ ๊ฐ๋
)
module-info.java ํ์ผ์ ํฌํจํ๊ธฐ ๋๋ฌธ์ ์ ๊ทผ์ ์ด(์บก์ํ) ๊ฐ๋ฅ ํ๋ค.
์ด๊ฒ ๋ฌด์จ ๋ง์ด๋๋ฉด ๋ชจ๋์ ๋ด๋ถ๊ฐ ์จ๊ฒจ์ ธ ์๋ค. ๊ณต๊ฐ ์ค์ ํ์ง ์๋ ํ,
๋ํ ๋ชจ๋์ ๊ณ์ฝ๊ด๊ณ๋ฅผ ๊ฐ์ง๋ค. (์ฝ๋๊ฐ ์์๋๋ก ์๋ํ ๊ฒ์ด๋ผ๋ ๋ณด์ฆ์ด ์๋ค) ์ด๊ฑด ์๋์์ ์์ธํ ์ดํด๋ณด๊ฒ ๋ค.
2. ๋ชจ๋(Module)์ ๊ณ์ฝ๊ด๊ณ
๋ชจ๋์ ๊ณ์ฝ๊ด๊ณ๋ผ๋ ๋ง์ด ์ถ์์ ์ด๊ณ ์ ๋งคํด์ ๋ฐ๋ก ์กฐ์ฌํด ๋ณด์๋ค.
๋ชจ๋ ์์คํ
์์๋ ๋ชจ๋์ด ์ ๊ณตํ๋ ๊ธฐ๋ฅ๊ณผ ๊ทธ๊ฒ์ ์ฌ์ฉํ๋ ๋ค๋ฅธ ๋ชจ๋ ๊ฐ์ ๊ด๊ณ๊ฐ ๋ช
ํํ๊ฒ ์ ์๋๋ค. ์ฆ, ๋ชจ๋์ ๊ฐ๋ฐ์๊ฐ ๊ณต๊ฐํ๋๋ก ๊ฒฐ์ ํ ํจํค์ง๋ง ์ธ๋ถ์์ ์ฌ์ฉํ ์ ์๋๋ก ๋ณด์ฅํ๋ฉฐ, ์ด๋ฅผ ํตํด ์ฝ๋๊ฐ ์์๋๋ก ์๋ํ ์ ์๋๋ก ํ๋ค. ๋ฐ๋ฉด, ํด๋์คํจ์ค์์๋ ๋ชจ๋ ํจํค์ง๊ฐ ๊ณต๊ฐ๋๋ฏ๋ก ์๋ํ์ง ์์ ์ฝ๋ ์ ๊ทผ์ด ๊ฐ๋ฅํ ์ ์๋ค. ์ดํด๋ฅผ ๋๊ธฐ ์ํด ์๋ ์์๋ฅผ ์ดํด๋ณด์.
2-1. Modulepath ๋ฐฉ์
๋ชจ๋์ด ์ ๊ณตํ๋ ํจํค์ง (module-info.java)
module mymodule {
exports com.example.utils; // ์ด ํจํค์ง๋ง ์ธ๋ถ์ ๊ณต๊ฐ
}
com.example.utilsํจํค์ง๋ ๊ณต๊ฐ(export) ๋๋ฏ๋ก ๋ค๋ฅธ ๋ชจ๋์ด ์ฌ์ฉํ ์ ์์
ํ์ง๋ง, ๋ค๋ฅธ ํจํค์ง๋ ๊ฐ์ถฐ์ ธ ์์ด์ ์์์น ๋ชปํ ์ฝ๋ ๋ณ๊ฒฝ์ด ์ํฅ์ ์ฃผ์ง ์์
2-2. Classpath ๋ฐฉ์ (Java8 ์ดํ) ๋ฌธ์ ์
ํจํค์ง๋ฅผ ๊ฐ์ ธ๋ค ์ฐ๋ฉด ๋ณด์ฆ(guarantee)ํ ์ ์๋ ์ด์ ์ ๋ํด์ ์ค๋ช ํ์๋ฉด ์ผ๋ฐ์ ์ธ Classpath ๋ฐฉ์(Java 8 ์ดํ)์์๋ ํจํค์ง๋ฅผ ์ง์ ๊ฐ์ ธ๋ค ์จ์ผ ํ๋ค. ์ด ๊ฒฝ์ฐ, ํด๋น ํจํค์ง์ ๊ฐ๋ฐ์๊ฐ ๋ด๋ถ ์ฝ๋๋ฅผ ์์ ํ ๊ฐ๋ฅ์ฑ์ด ์๋ค.
import com.example.utils.StringUtils; // ๋ค๋ฅธ ๊ฐ๋ฐ์๊ฐ ๋ง๋ ์ ํธ๋ฆฌํฐ ํด๋์ค
public class Main {
public static void main(String[] args) {
System.out.println(StringUtils.capitalize("hello"));
}
}
๐จ ์ฌ๊ธฐ์ ๋ง์ฝ์ StringUtils์ ๋ด๋ถ ์ฝ๋๊ฐ ๋ณ๊ฒฝ๋๊ฑฐ๋ ์ญ์ ๋๋ฉด? ํจํค์ง๋ฅผ ๊ฐ์ ธ๋ค ์ฐ๋ ์ฝ๋๊ฐ ๊นจ์ง ์ ์๋ค. ์ฆ, ๋ณด์ฆ(guarantee)ํ ์ ์๋ค.
โ ๊ฒฐ๋ก : ๋ชจ๋ ์์คํ
์ ํน์ ํจํค์ง๋ง ๋
ธ์ถ์ํค๊ณ , ๋ด๋ถ ๊ตฌ์กฐ๋ ๊ฐ์ถฐ์ ์ฝ๋๊ฐ ์๋์น ์๊ฒ ๊นจ์ง๋ ๊ฒ์ ๋ฐฉ์งํ๋ค.
๋ฐ๋ฉด, ํจํค์ง๋ฅผ ์ง์ ๊ฐ์ ธ๋ค ์ฐ๋ฉด, ํจํค์ง ๋ด๋ถ ์ฝ๋๊ฐ ๋ฐ๋ ๊ฒฝ์ฐ ์์กดํ๋ ์ฝ๋๊ฐ ์ํฅ์ ๋ฐ์ ์ ์์ด ๋ณด์ฅ(guarantee)ํ ์ ์๋ค๋ ๊ฒ์ด๋ค.
์ฌ๊ธฐ์ ์์ธํ ๋ค์ด๊ฐ๋ฉด ๋ชจ๋์๋ Unnamed Module ๊ณผ Named Module์ด ์๋ค.
- Unnamed Module: Classpath์ ์ฝ๋๋ค์ ๋ชจ๋ unnamed module์ ์ํ๋ค.
- Named Module: ModulePath์ ์ฝ๋๋ค์ ๊ฐ์ ์ด๋ฆ์ ๊ฐ์ง๋ค.
3. Classpath
๐ Classpath (ํด๋์คํจ์ค)
- ๋ชจ๋ ํด๋์ค๋ "Unnamed Module"์ ์ํจ
- ํด๋์ค ๊ฐ ์์กด์ฑ์ด ๋ช ํํ์ง ์์ (์ถฉ๋ ๊ฐ๋ฅ์ฑ ๋์)
- ๋ชจ๋ ํจํค์ง๋ ๊ธฐ๋ณธ์ ์ผ๋ก ๊ณต๊ฐ(public)
- ์คํํ ๋ -cp ์ต์ ์ผ๋ก ์ค์
java -cp myapp.jar com.example.Main
4. Modulepath
- ๊ฐ ๋ชจ๋์ ๊ณ ์ ํ ์ด๋ฆ์ ๊ฐ์ง
- module-info.java๋ฅผ ํตํด ์์กด์ฑ์ ๋ช ํํ๊ฒ ์ ์ธ
- exports ํค์๋๋ฅผ ์ฌ์ฉํ์ฌ ๊ณต๊ฐํ ํจํค์ง๋ฅผ ์ ํํ ์ ์์
- ์คํํ ๋ --module-path ์ต์ ์ ์ฌ์ฉ
java --module-path mods -m mymodule/com.example.Main
module mymodule {
exports com.example.utils; // ์ธ๋ถ์์ ์ ๊ทผ ๊ฐ๋ฅ
requires anothermodule; // anothermodule์ด ํ์ํจ
}
5. ๋ชจ๋ ์์คํ ์ด ์ ๊ณตํ๋ ๊ธฐ๋ฅ & ์ฉ์ด ์ ๋ฆฌ ์ค๋ช
์ด๊ฑด ์ฝ๋ฉ์ ์ข ๋ฐฐ์ด ์ฌ๋์ด๋ผ๋ฉด ์๋ฐ๋ ์ ๋ณด์ฒ๋ฆฌ๊ธฐ์ฌ์์ ์์ฃผ ๋์ค๋ ๊ฐ๋
์ด๊ธฐ ๋๋ฌธ์ ์๊ณ ์๊ฒ ์ง๋ง
๋ชจ๋ฅด์๋ ๋ถ๋ค์ ์ํด ๊ฐ๋
์ค๋ช
์ ํ๋๋ก ํ๊ฒ ๋ค.
5-1. ์บก์ํ(Encapsulation)
์์์ ์ค๋ช
ํ์ง๋ง ์บก์ํ๋ฅผ ํ ๋ง๋๋ก ์์ฝํ๋ฉด exports ํค์๋๋ก ์ธ๋ถ์์ ์ ๊ทผ ๊ฐ๋ฅํ ํจํค์ง๋ฅผ ์ ํํ ์ ์๋ค๋ ๊ฐ๋
์ด๋ค.
Classpath์์๋ ๋ชจ๋ ํจํค์ง๊ฐ ๊ณต๊ฐ๋์์ง๋ง, ModulePath์์๋ ํจํค์ง์ ๊ณต๊ฐ/๋น๊ณต๊ฐ๋ฅผ ๋ช
ํํ๊ฒ ์ค์ ํ ์ ์๋ค๊ณ ํ๋ค.
Classpath(Java 8 ์ดํ)์์๋ ๋ชจ๋ ํจํค์ง๊ฐ ์๋์ผ๋ก ๊ณต๊ฐ๋๋ค. ๊ทธ๋ผ ๋ค๋ฅธ ์ฝ๋์์ ๋ง์๋๋ก import ๊ฐ๋ฅํ๊ฒ ์ง?
์ํ๋ ํจํค์ง๋ง ์ธ๋ถ์ ๊ณต๊ฐํ ๋ฐฉ๋ฒ์ด ์๊ณ ๋ด๋ถ ๊ตฌํ์ ๋ณดํธํ ์ ์๊ณ , ์๋์น ์์ ์ ๊ทผ๋ ๊ฐ๋ฅํ๋ค๋ ๊ฒ์ด๋ค.
๋ฐ๋ฉด ModulePath(Java 9 ์ด์, ๋ชจ๋ ์์คํ
)์์๋ exports ํค์๋๋ฅผ ์ฌ์ฉํ์ฌ ํน์ ํจํค์ง๋ง ๋ช
ํํ๊ฒ ๊ณต๊ฐ ๊ฐ๋ฅํ๋ค.
๋๋จธ์ง ํจํค์ง๋ ๊ธฐ๋ณธ์ ์ผ๋ก ๋น๊ณต๊ฐ(๋ค๋ฅธ ๋ชจ๋์์ import ๋ถ๊ฐ)์ด๋ค. ๋ฐ๋ผ์ ๋ด๋ถ ์ฝ๋ ๋ณดํธ๊ฐ ๊ฐ๋ฅํ๊ณ , ์๋๋ ๋ฐฉ์์ผ๋ก๋ง ์ ๊ทผ์ด ํ์ฉ๋๋ค.
๋ชจ๋ ์ ์ (module-info.java)
module mymodule {
exports com.example.utils; // โ
์ธ๋ถ์์ ์ฌ์ฉ ๊ฐ๋ฅ
}
ํจํค์ง ๊ตฌ์กฐ
mymodule/
โโโ com/example/utils/StringUtils.java โ
๊ณต๊ฐ๋จ
โโโ com/example/internal/SecretHelper.java โ ๋น๊ณต๊ฐ (์ธ๋ถ์์ import ๋ถ๊ฐ)
โโโ module-info.java
์ธ๋ถ ๋ชจ๋์์ ์ฌ์ฉ ๊ฐ๋ฅ
import com.example.utils.StringUtils; // โ
๊ฐ๋ฅ
import com.example.internal.SecretHelper; // โ ์ค๋ฅ! (๋น๊ณต๊ฐ)
5-2. ๊ณ์ฝ ๊ด๊ณ(Contract)
module-info.java์์ requires๋ก ๋ชจ๋ ๊ฐ ์์กด์ฑ์ ๋ช
ํํ๊ฒ ์ ์ธํ๋ค. ์ด ๋ง์ ํ์ด์ ์ค๋ช
ํ์๋ฉด ์ด๋ค ๋ชจ๋์ด ๋ค๋ฅธ ๋ชจ๋์ ํ์๋ก ํ๋์ง ์ ์ธํ๋ ์ญํ ์ ํ๋ค. Classpath์์๋ ์์กด์ฑ์ด ์๋์ผ๋ก ์ธ์๋์ง ์์ง๋ง, ModulePath์์๋ ๋ช
ํํ ์ ์ธ์ด ํ์ ํ๋ค.
๋ ๊ฐ์ ๋ชจ๋ (app๊ณผ utils)์ด ์๋ค๊ณ ๊ฐ์ ํด๋ณด์.
์ฌ๊ธฐ์ app ๋ชจ๋์ด utils ๋ชจ๋์ ์ฌ์ฉํ๋ ค๋ฉด ์์กด์ฑ์ ๋ช
ํํ๊ฒ ์ ์ธํด์ผ ํ๋ค.
๐ ํ๋ก์ ํธ ๊ตฌ์กฐ
myproject/
โโโ app/
โ โโโ module-info.java
โ โโโ com/example/app/Main.java
โโโ utils/
โ โโโ module-info.java
โ โโโ com/example/utils/StringUtils.java
utils ๋ชจ๋์ ์ ํธ๋ฆฌํฐ ๊ธฐ๋ฅ์ ์ ๊ณตํ๋ ๋ชจ๋์ ์งํฉ์ฒด์ด๋ค. app ๋ชจ๋์ ๋ฉ์ธ ์ ํ๋ฆฌ์ผ์ด์
๋ชจ๋์ด๋ค.
requires ํค์๋๋ฅผ ์ฐ๋ฉด ์์กด์ฑ์ ๋ช
ํํ๊ฒ ๊ด๋ฆฌํ ์ ์๋ค. ์๋ฅผ ๋ค์ด app ๋ชจ๋์ด utils ๋ชจ๋์ ํ์๋ก ํ๋ค๊ณ ์ ์ธํ๋ฉด, utils ๋ชจ๋์ด ์์ผ๋ฉด app ๋ชจ๋์ด ์์ ๋น๋๊ฐ ์ ๋๋๋ก ๋ง์ ์ ์๋ค. ๋๋ถ์ ๋ถํ์ํ ๋ชจ๋ ์ฐธ์กฐ๋ฅผ ๋ฐฉ์งํ ์ ์๊ณ , ํ์ํ ๊ฒ๋ง ๋ฑ๋ฑ ๊ฐ์ ธ๋ค ์ธ ์ ์๋ค.
๋ํ requires๋ ์บก์ํ๋ ๋ณด์ ์ธก๋ฉด์์๋ ๋์์ด ๋๋ค. utils ๋ชจ๋์์ exports๋ฅผ ์จ์ ํน์ ํจํค์ง๋ง ๊ณต๊ฐํ ์ ์๋๋ฐ, ์ด๋ ๊ฒ ํ๋ฉด app ๋ชจ๋์ utils์์ ํ์ฉ๋ ํจํค์ง๋ง ์ ๊ทผํ ์ ์๋ค. ๋๋ถ์ ๋ชจ๋ ๋ด๋ถ ์ฝ๋๊ฐ ๋ณดํธ๋๊ณ , ์ธ๋ถ์์๋ ๊ผญ ํ์ํ ๊ธฐ๋ฅ๋ง ์ฌ์ฉํ ์ ์๊ฒ ๋๋ ๊ฒ์ด๋ค.
๊ทธ๋ฆฌ๊ณ ์ ์ง๋ณด์ํ ๋๋ requires ๋์ ๋ง์ด ๋ณธ๋ค. ํ์ํ ๋ชจ๋์ ๋ช
ํํ๊ฒ ์ ๋ฆฌํด ๋๋ฉด ์ฝ๋๊ฐ ์ด๋์ ์๋์ง ์ฝ๊ฒ ์ถ์ ํ ์ ์๊ณ , module-info.java ํ์ผ๋ง ๋ณด๋ฉด ์ด๋ค ๋ชจ๋์ด ์ด๋ค ์์กด์ฑ์ ๊ฐ์ง๊ณ ์๋์ง ํ๋์ ์ ์ ์๋ค. ๋๋ถ์ ์ฝ๋ ๊ด๋ฆฌ๊ฐ ํจ์ฌ ์ฒด๊ณ์ ์ผ๋ก ๊ฐ๋ฅํด์ง๋ ๊ฒ์ด๋ค.
utils/module-info.java
module utils {
exports com.example.utils; // โ
`utils` ๋ชจ๋์์ `com.example.utils` ํจํค์ง๋ฅผ ๊ณต๊ฐ
}
utils/com/example/utils/StringUtils.java
package com.example.utils;
public class StringUtils {
public static String toUpper(String input) {
return input.toUpperCase();
}
}
app/module-info.java
module app {
requires utils; // โ
`app` ๋ชจ๋์ด `utils` ๋ชจ๋์ ํ์๋ก ํจ (์์กด์ฑ ์ ์ธ)
}
app/com/example/app/Main.java
package com.example.app;
import com.example.utils.StringUtils; // โ
utils ๋ชจ๋์์ ์ ๊ณตํ๋ ํด๋์ค ์ฌ์ฉ
public class Main {
public static void main(String[] args) {
String message = "hello, world!";
System.out.println(StringUtils.toUpper(message)); // "HELLO, WORLD!" ์ถ๋ ฅ
}
}
6. ์ธ์ ModulePath vs Classpath๋ฅผ ์ฌ์ฉํ ๊น?
์ผ๋จ Java 8 ์ดํ์์๋ Classpath๋ฅผ ์ฌ์ฉํ๋ค. JAR ํ์ผ์ Add External JARs๋ก ์ถ๊ฐํ๋ ๊ฒ์ด ๊ทธ ์์์ด๋ค.
๊ทธ๋ฆฌ๊ณ Java 9 ์ด์ (๋ชจ๋ ์์คํ
์ฌ์ฉ ์)์ ๋ผ์ด๋ธ๋ฌ๋ฆฌ๋ฆ ModulePath์ ์ถ๊ฐํ๋ค. ( module-info.java์์ requires ์ค์ ํ์)
์๋ฅผ ๋ค๋ฉด
ojdbc8.jar์ Classpath์ ์ถ๊ฐํ๋ฉด ๋ชจ๋ ํจํค์ง๋ฅผ ์์ ๋กญ๊ฒ ์ฐธ์กฐํ ์ ์๋ค.
ํ์ง๋ง, ModulePath์ ์ถ๊ฐํ๋ฉด ์๋์ฒ๋ผ module-info.java์์ requires๋ฅผ ์ค์ ํด์ผ ํ๋ค.
module mymodule {
requires java.sql; // JDBC ์ฌ์ฉ
requires oracle.jdbc; // Oracle JDBC ์ฌ์ฉ
}
์ด๊ฑด ์๋์ผ๋ก ์ค์ ๋์ง ์๋๋ค. ojdbc8.jar ๊ฐ์ ๋ผ์ด๋ธ๋ฌ๋ฆฌ๋ฅผ ModulePath์ ์ถ๊ฐํ๋ฉด, module-info.java์์ ์ง์ requires๋ฅผ ์ ์ธํด์ค์ผ ํ๋ค.
์? ์ด์ ๋ ์๋ฐ ๋ชจ๋ ์์คํ
์ด ๊ฐ์ ํ๋ ์บก์ํ ์์น ๋๋ฌธ์ด์ผ. Classpath์์๋ ๋ชจ๋ ํจํค์ง๋ฅผ ์์ ๋กญ๊ฒ ์ฐธ์กฐํ ์ ์์์ง๋ง, ModulePath์์๋ ๋ชจ๋๋ค์ด ๋ช
์์ ์ผ๋ก ๊ณต๊ฐ(exports)๋ ํจํค์ง๋ง ์ ๊ทผํ ์ ์๊ธฐ ๋๋ฌธ์ ๊ทธ๋์ ojdbc8.jar์ ModulePath์ ์ถ๊ฐํ๋ฉด, module-info.java์์ requires oracle.jdbc ๊ฐ์ ์์ผ๋ก ์์กด์ฑ์ ๋ช
ํํ๊ฒ ์ง์ ์ค์ ํ๋ค.
๋ง์ฝ module-info.java๋ฅผ ์ถ๊ฐํ๊ธฐ ๊ท์ฐฎ๊ฑฐ๋ ๊ธฐ์กด์ฒ๋ผ ์์ ๋กญ๊ฒ ์ฐธ์กฐํ๊ณ ์ถ๋ค๋ฉด, ojdbc8.jar์ Classpath์ ์ถ๊ฐํ๋ ๋ฐฉ๋ฒ๋ ๊ฐ๋ฅํ๋ค. ModulePath๋ฅผ ์ฌ์ฉํ๋ ค๋ฉด ์๋์ผ๋ก ์ค์ ํ๋ ๊ฒ ํ์์ด๊ธฐ ๋๋ฌธ์ ๊ทธ๋ฅ Classpath๋ฅผ ์ฐ์.
์ฐธ๊ณ ์๋ฃ & ํฌ์คํ ์ ๋์์ ์ฃผ์ ๋ถ๋ค
1. https://velog.io/@c4fiber/eclipse-modulepath-vs-classpath
2. https://whitekeyboard.tistory.com/849
'ํ๋ก๊ทธ๋๋ฐ์ธ์ด > Java' ์นดํ ๊ณ ๋ฆฌ์ ๋ค๋ฅธ ๊ธ

Java ํ๋ก์ ํธ๋ฅผ ์ค์ ํ ๋ ํ๋ก์ ํธ ์ฐํด๋ฆญํ๋ฉด Build Path๊ฐ ๋์จ๋ค. ์ฌ๊ธฐ์ ์ฐ๋ฆฌ๊ฐ Oracle JDBC ๋๋ผ์ด๋ฒ(ojdbc8.jar) ๊ฐ์ ์ธ๋ถ ๋ผ์ด๋ธ๋ฌ๋ฆฌ๋ฅผ ๋ฑ๋กํ ์ ์๋ค. ๋ MySQL Connection(mysql-connector-java.jar)์ด๋ผ๋ ์ง Getter์ Setter์ ์๋์์ฑํ๋ Lombok(lombok.jar) ๋ผ์ด๋ธ๋ฌ๋ฆฌ๋ฅผ ๋ฑ๋ก ํด ๋ณธ ์ ์ด ์์ ๊ฒ์ด๋ค.
ํ์๋ ํญ์ ์ด ๋ผ์ด๋ธ๋ฌ๋ฆฌ๋ค์ ์ถ๊ฐํ ๋ Classpath, Module Path ์ค ์ด๋์ ์ถ๊ฐํด์ผ ํ๋์ง ํท๊ฐ๋ ธ๊ธฐ ๋๋ฌธ์ ์ด ๊ธ์ ์์ฑํ๋ค. Buildpath๋ ์๋ฐ์์ ์ค์ํ ๊ฐ๋
์ด๋ฉฐ, ์ด๋ค ๊ฒ์ ๋ฑ๋กํด์ผ ํ๋์ง๋ ํ๋ก์ ํธ ํ๊ฒฝ๊ณผ ์ฌ์ฉ ๊ธฐ์ ์ ๋ฐ๋ผ ๋ฌ๋ผ์ง๋ค.
์ด๋ก ์ ์ธ ์ค๋ช
์ ๊ฑด๋ ๋ฐ๊ณ ์ธ์ ModulePath vs Classpath๋ฅผ ์ฌ์ฉํ๋์ง๋ง ์๊ณ ์ถ์ ์ฌ๋์ 6.์ธ์ ModulePath vs Classpath๋ฅผ ์ฌ์ฉํ ๊น? ๋ก ๋ฐ๋ก ์ด๋ํ๊ธฐ ๋ฐ๋๋ค.
1. Classpath์ ModulePath์ ๊ฐ๋
- Classpath: ์ฌ์ฉ์ ์ ์ ํด๋์ค(Class) ๋๋ ํจํค์ง(Package)์ ์์น (Java8 ๊น์ง ๊ธฐ๋ณธ ๋ฐฉ์)
- ModulePath: ์ฌ์ฉ์ ์ ์ ๋ชจ๋(Module)์ด ์์นํ๋ ๊ณณ
- ๋ชจ๋ํจ์ค๋ ํ ๋ง๋๋ก ๋ชจ๋ ๊ฐ๋ ์ ๋์ ํ์ฌ ํจํค์ง๋ฅผ ๊ทธ๋ฃนํํ ์์น์ด๋ค. Java 9๋ถํฐ ๋์ ๋์๋ค.
- โก ํ ๋ง๋๋ก Java 8 ์ดํ์์๋ Classpath ์ฌ์ฉ, Java 9 ์ด์์์๋ ModulePath ์ฌ์ฉ ๊ถ์ฅ
- ModulePath๋ฅผ ์ฌ์ฉํ๋ฉด exports ํค์๋๋ก ์ํ๋ ํจํค์ง๋ง ๋ช ํํ๊ฒ ๊ณต๊ฐํ ์ ์๊ณ , ๋๋จธ์ง๋ ๊ฐ์ถ ์ ์๋ค.
- ์ฆ, **์บก์ํ(Encapsulation)**๊ฐ ๊ฐ๋ฅํด์ง๊ณ , ๋ถํ์ํ ์ฝ๋ ์์กด์ฑ์ ๋ง์ ์ ์๋ค. ํ์ง๋ง ๊ฐ์ธ์ ์ผ๋ก ์ฐ์ตํ๋๊ฑฐ๋ฉด classpath๋ฅผ ์ฌ์ฉํ๋ ๊ฒ์ด ์ข๋ค. ๋ผ์ด๋ธ๋ฌ๋ฆฌ๋ฅผ ModulePath์ ์ถ๊ฐํ๋ฉด, module-info.java์์ requires oracle.jdbc ๊ฐ์ ์์ผ๋ก ์์กด์ฑ์ ์ง์ ์ค์ ํด์ฃผ์ด์ผ ํ๋ค. ์๋ฐ์ ์บก์ํ ์์น๋๋ฌธ์ ๊ทธ๋ ๋ค.
๊ทธ๋ฆผ์ ๋ณด๋ฉด์ ์ค๋ช ์ ํ์๋ฉด, ModulePath๋ ํจํค์ง๊ฐ ํ๋์ ๋ชจ๋๋ง ์ก์ธ์ค๊ฐ ๊ฐ๋ฅํ๊ณ , ์ฌ๋ฌ ํจํค์ง๋ฅผ ์ข ์์ํฌ ์ ์๋ค. ์์น์ ์ธ ๊ฐ๋ ์ด๋ผ๊ณ ์๊ฐํ๋ฉด ๋๋ค. JRE๋ ๋ฌด์กฐ๊ฑด Module์ ์์นํ๋ค. ๋ง์น ๋ฉ์๋๋ฅผ ํธ์ถํ๋๊ฒ ์ฒ๋ผ ๋ชจ๋์ ๋ง๋ค์ด ํธ์ถํ์ฌ ์ฌ์ฉํ๋ค. (interface๋ฅผ ํตํด ์ ๊ทผํ๋๊ฒ๊ณผ ์ ์ฌํ๋ค.)

๐ ๋ชจ๋(Module)
module ์ package๋ค์ ๋ชจ์์ด๋ฉฐ packages์ top์ ์ค์น๋๋ค.
์ฆ, module์ ์ต์์ ํจํค์ง๋ผ๊ณ ์๊ฐํ๋ฉด ๋๋ค. (ํจํค์ง๋ค์ ์์ ๊ฐ๋
)
module-info.java ํ์ผ์ ํฌํจํ๊ธฐ ๋๋ฌธ์ ์ ๊ทผ์ ์ด(์บก์ํ) ๊ฐ๋ฅ ํ๋ค.
์ด๊ฒ ๋ฌด์จ ๋ง์ด๋๋ฉด ๋ชจ๋์ ๋ด๋ถ๊ฐ ์จ๊ฒจ์ ธ ์๋ค. ๊ณต๊ฐ ์ค์ ํ์ง ์๋ ํ,
๋ํ ๋ชจ๋์ ๊ณ์ฝ๊ด๊ณ๋ฅผ ๊ฐ์ง๋ค. (์ฝ๋๊ฐ ์์๋๋ก ์๋ํ ๊ฒ์ด๋ผ๋ ๋ณด์ฆ์ด ์๋ค) ์ด๊ฑด ์๋์์ ์์ธํ ์ดํด๋ณด๊ฒ ๋ค.
2. ๋ชจ๋(Module)์ ๊ณ์ฝ๊ด๊ณ
๋ชจ๋์ ๊ณ์ฝ๊ด๊ณ๋ผ๋ ๋ง์ด ์ถ์์ ์ด๊ณ ์ ๋งคํด์ ๋ฐ๋ก ์กฐ์ฌํด ๋ณด์๋ค.
๋ชจ๋ ์์คํ
์์๋ ๋ชจ๋์ด ์ ๊ณตํ๋ ๊ธฐ๋ฅ๊ณผ ๊ทธ๊ฒ์ ์ฌ์ฉํ๋ ๋ค๋ฅธ ๋ชจ๋ ๊ฐ์ ๊ด๊ณ๊ฐ ๋ช
ํํ๊ฒ ์ ์๋๋ค. ์ฆ, ๋ชจ๋์ ๊ฐ๋ฐ์๊ฐ ๊ณต๊ฐํ๋๋ก ๊ฒฐ์ ํ ํจํค์ง๋ง ์ธ๋ถ์์ ์ฌ์ฉํ ์ ์๋๋ก ๋ณด์ฅํ๋ฉฐ, ์ด๋ฅผ ํตํด ์ฝ๋๊ฐ ์์๋๋ก ์๋ํ ์ ์๋๋ก ํ๋ค. ๋ฐ๋ฉด, ํด๋์คํจ์ค์์๋ ๋ชจ๋ ํจํค์ง๊ฐ ๊ณต๊ฐ๋๋ฏ๋ก ์๋ํ์ง ์์ ์ฝ๋ ์ ๊ทผ์ด ๊ฐ๋ฅํ ์ ์๋ค. ์ดํด๋ฅผ ๋๊ธฐ ์ํด ์๋ ์์๋ฅผ ์ดํด๋ณด์.
2-1. Modulepath ๋ฐฉ์
๋ชจ๋์ด ์ ๊ณตํ๋ ํจํค์ง (module-info.java)
module mymodule { exports com.example.utils; // ์ด ํจํค์ง๋ง ์ธ๋ถ์ ๊ณต๊ฐ }
com.example.utilsํจํค์ง๋ ๊ณต๊ฐ(export) ๋๋ฏ๋ก ๋ค๋ฅธ ๋ชจ๋์ด ์ฌ์ฉํ ์ ์์
ํ์ง๋ง, ๋ค๋ฅธ ํจํค์ง๋ ๊ฐ์ถฐ์ ธ ์์ด์ ์์์น ๋ชปํ ์ฝ๋ ๋ณ๊ฒฝ์ด ์ํฅ์ ์ฃผ์ง ์์
2-2. Classpath ๋ฐฉ์ (Java8 ์ดํ) ๋ฌธ์ ์
ํจํค์ง๋ฅผ ๊ฐ์ ธ๋ค ์ฐ๋ฉด ๋ณด์ฆ(guarantee)ํ ์ ์๋ ์ด์ ์ ๋ํด์ ์ค๋ช ํ์๋ฉด ์ผ๋ฐ์ ์ธ Classpath ๋ฐฉ์(Java 8 ์ดํ)์์๋ ํจํค์ง๋ฅผ ์ง์ ๊ฐ์ ธ๋ค ์จ์ผ ํ๋ค. ์ด ๊ฒฝ์ฐ, ํด๋น ํจํค์ง์ ๊ฐ๋ฐ์๊ฐ ๋ด๋ถ ์ฝ๋๋ฅผ ์์ ํ ๊ฐ๋ฅ์ฑ์ด ์๋ค.
import com.example.utils.StringUtils; // ๋ค๋ฅธ ๊ฐ๋ฐ์๊ฐ ๋ง๋ ์ ํธ๋ฆฌํฐ ํด๋์ค public class Main { public static void main(String[] args) { System.out.println(StringUtils.capitalize("hello")); } }
๐จ ์ฌ๊ธฐ์ ๋ง์ฝ์ StringUtils์ ๋ด๋ถ ์ฝ๋๊ฐ ๋ณ๊ฒฝ๋๊ฑฐ๋ ์ญ์ ๋๋ฉด? ํจํค์ง๋ฅผ ๊ฐ์ ธ๋ค ์ฐ๋ ์ฝ๋๊ฐ ๊นจ์ง ์ ์๋ค. ์ฆ, ๋ณด์ฆ(guarantee)ํ ์ ์๋ค.
โ ๊ฒฐ๋ก : ๋ชจ๋ ์์คํ
์ ํน์ ํจํค์ง๋ง ๋
ธ์ถ์ํค๊ณ , ๋ด๋ถ ๊ตฌ์กฐ๋ ๊ฐ์ถฐ์ ์ฝ๋๊ฐ ์๋์น ์๊ฒ ๊นจ์ง๋ ๊ฒ์ ๋ฐฉ์งํ๋ค.
๋ฐ๋ฉด, ํจํค์ง๋ฅผ ์ง์ ๊ฐ์ ธ๋ค ์ฐ๋ฉด, ํจํค์ง ๋ด๋ถ ์ฝ๋๊ฐ ๋ฐ๋ ๊ฒฝ์ฐ ์์กดํ๋ ์ฝ๋๊ฐ ์ํฅ์ ๋ฐ์ ์ ์์ด ๋ณด์ฅ(guarantee)ํ ์ ์๋ค๋ ๊ฒ์ด๋ค.
์ฌ๊ธฐ์ ์์ธํ ๋ค์ด๊ฐ๋ฉด ๋ชจ๋์๋ Unnamed Module ๊ณผ Named Module์ด ์๋ค.
- Unnamed Module: Classpath์ ์ฝ๋๋ค์ ๋ชจ๋ unnamed module์ ์ํ๋ค.
- Named Module: ModulePath์ ์ฝ๋๋ค์ ๊ฐ์ ์ด๋ฆ์ ๊ฐ์ง๋ค.
3. Classpath
๐ Classpath (ํด๋์คํจ์ค)
- ๋ชจ๋ ํด๋์ค๋ "Unnamed Module"์ ์ํจ
- ํด๋์ค ๊ฐ ์์กด์ฑ์ด ๋ช ํํ์ง ์์ (์ถฉ๋ ๊ฐ๋ฅ์ฑ ๋์)
- ๋ชจ๋ ํจํค์ง๋ ๊ธฐ๋ณธ์ ์ผ๋ก ๊ณต๊ฐ(public)
- ์คํํ ๋ -cp ์ต์ ์ผ๋ก ์ค์
java -cp myapp.jar com.example.Main
4. Modulepath
- ๊ฐ ๋ชจ๋์ ๊ณ ์ ํ ์ด๋ฆ์ ๊ฐ์ง
- module-info.java๋ฅผ ํตํด ์์กด์ฑ์ ๋ช ํํ๊ฒ ์ ์ธ
- exports ํค์๋๋ฅผ ์ฌ์ฉํ์ฌ ๊ณต๊ฐํ ํจํค์ง๋ฅผ ์ ํํ ์ ์์
- ์คํํ ๋ --module-path ์ต์ ์ ์ฌ์ฉ
java --module-path mods -m mymodule/com.example.Main
module mymodule { exports com.example.utils; // ์ธ๋ถ์์ ์ ๊ทผ ๊ฐ๋ฅ requires anothermodule; // anothermodule์ด ํ์ํจ }
5. ๋ชจ๋ ์์คํ ์ด ์ ๊ณตํ๋ ๊ธฐ๋ฅ & ์ฉ์ด ์ ๋ฆฌ ์ค๋ช
์ด๊ฑด ์ฝ๋ฉ์ ์ข ๋ฐฐ์ด ์ฌ๋์ด๋ผ๋ฉด ์๋ฐ๋ ์ ๋ณด์ฒ๋ฆฌ๊ธฐ์ฌ์์ ์์ฃผ ๋์ค๋ ๊ฐ๋
์ด๊ธฐ ๋๋ฌธ์ ์๊ณ ์๊ฒ ์ง๋ง
๋ชจ๋ฅด์๋ ๋ถ๋ค์ ์ํด ๊ฐ๋
์ค๋ช
์ ํ๋๋ก ํ๊ฒ ๋ค.
5-1. ์บก์ํ(Encapsulation)
์์์ ์ค๋ช
ํ์ง๋ง ์บก์ํ๋ฅผ ํ ๋ง๋๋ก ์์ฝํ๋ฉด exports ํค์๋๋ก ์ธ๋ถ์์ ์ ๊ทผ ๊ฐ๋ฅํ ํจํค์ง๋ฅผ ์ ํํ ์ ์๋ค๋ ๊ฐ๋
์ด๋ค.
Classpath์์๋ ๋ชจ๋ ํจํค์ง๊ฐ ๊ณต๊ฐ๋์์ง๋ง, ModulePath์์๋ ํจํค์ง์ ๊ณต๊ฐ/๋น๊ณต๊ฐ๋ฅผ ๋ช
ํํ๊ฒ ์ค์ ํ ์ ์๋ค๊ณ ํ๋ค.
Classpath(Java 8 ์ดํ)์์๋ ๋ชจ๋ ํจํค์ง๊ฐ ์๋์ผ๋ก ๊ณต๊ฐ๋๋ค. ๊ทธ๋ผ ๋ค๋ฅธ ์ฝ๋์์ ๋ง์๋๋ก import ๊ฐ๋ฅํ๊ฒ ์ง?
์ํ๋ ํจํค์ง๋ง ์ธ๋ถ์ ๊ณต๊ฐํ ๋ฐฉ๋ฒ์ด ์๊ณ ๋ด๋ถ ๊ตฌํ์ ๋ณดํธํ ์ ์๊ณ , ์๋์น ์์ ์ ๊ทผ๋ ๊ฐ๋ฅํ๋ค๋ ๊ฒ์ด๋ค.
๋ฐ๋ฉด ModulePath(Java 9 ์ด์, ๋ชจ๋ ์์คํ
)์์๋ exports ํค์๋๋ฅผ ์ฌ์ฉํ์ฌ ํน์ ํจํค์ง๋ง ๋ช
ํํ๊ฒ ๊ณต๊ฐ ๊ฐ๋ฅํ๋ค.
๋๋จธ์ง ํจํค์ง๋ ๊ธฐ๋ณธ์ ์ผ๋ก ๋น๊ณต๊ฐ(๋ค๋ฅธ ๋ชจ๋์์ import ๋ถ๊ฐ)์ด๋ค. ๋ฐ๋ผ์ ๋ด๋ถ ์ฝ๋ ๋ณดํธ๊ฐ ๊ฐ๋ฅํ๊ณ , ์๋๋ ๋ฐฉ์์ผ๋ก๋ง ์ ๊ทผ์ด ํ์ฉ๋๋ค.
๋ชจ๋ ์ ์ (module-info.java)
module mymodule { exports com.example.utils; // โ
์ธ๋ถ์์ ์ฌ์ฉ ๊ฐ๋ฅ }
ํจํค์ง ๊ตฌ์กฐ
mymodule/ โโโ com/example/utils/StringUtils.java โ
๊ณต๊ฐ๋จ โโโ com/example/internal/SecretHelper.java โ ๋น๊ณต๊ฐ (์ธ๋ถ์์ import ๋ถ๊ฐ) โโโ module-info.java
์ธ๋ถ ๋ชจ๋์์ ์ฌ์ฉ ๊ฐ๋ฅ
import com.example.utils.StringUtils; // โ
๊ฐ๋ฅ import com.example.internal.SecretHelper; // โ ์ค๋ฅ! (๋น๊ณต๊ฐ)
5-2. ๊ณ์ฝ ๊ด๊ณ(Contract)
module-info.java์์ requires๋ก ๋ชจ๋ ๊ฐ ์์กด์ฑ์ ๋ช
ํํ๊ฒ ์ ์ธํ๋ค. ์ด ๋ง์ ํ์ด์ ์ค๋ช
ํ์๋ฉด ์ด๋ค ๋ชจ๋์ด ๋ค๋ฅธ ๋ชจ๋์ ํ์๋ก ํ๋์ง ์ ์ธํ๋ ์ญํ ์ ํ๋ค. Classpath์์๋ ์์กด์ฑ์ด ์๋์ผ๋ก ์ธ์๋์ง ์์ง๋ง, ModulePath์์๋ ๋ช
ํํ ์ ์ธ์ด ํ์ ํ๋ค.
๋ ๊ฐ์ ๋ชจ๋ (app๊ณผ utils)์ด ์๋ค๊ณ ๊ฐ์ ํด๋ณด์.
์ฌ๊ธฐ์ app ๋ชจ๋์ด utils ๋ชจ๋์ ์ฌ์ฉํ๋ ค๋ฉด ์์กด์ฑ์ ๋ช
ํํ๊ฒ ์ ์ธํด์ผ ํ๋ค.
๐ ํ๋ก์ ํธ ๊ตฌ์กฐ
myproject/ โโโ app/ โ โโโ module-info.java โ โโโ com/example/app/Main.java โโโ utils/ โ โโโ module-info.java โ โโโ com/example/utils/StringUtils.java
utils ๋ชจ๋์ ์ ํธ๋ฆฌํฐ ๊ธฐ๋ฅ์ ์ ๊ณตํ๋ ๋ชจ๋์ ์งํฉ์ฒด์ด๋ค. app ๋ชจ๋์ ๋ฉ์ธ ์ ํ๋ฆฌ์ผ์ด์
๋ชจ๋์ด๋ค.
requires ํค์๋๋ฅผ ์ฐ๋ฉด ์์กด์ฑ์ ๋ช
ํํ๊ฒ ๊ด๋ฆฌํ ์ ์๋ค. ์๋ฅผ ๋ค์ด app ๋ชจ๋์ด utils ๋ชจ๋์ ํ์๋ก ํ๋ค๊ณ ์ ์ธํ๋ฉด, utils ๋ชจ๋์ด ์์ผ๋ฉด app ๋ชจ๋์ด ์์ ๋น๋๊ฐ ์ ๋๋๋ก ๋ง์ ์ ์๋ค. ๋๋ถ์ ๋ถํ์ํ ๋ชจ๋ ์ฐธ์กฐ๋ฅผ ๋ฐฉ์งํ ์ ์๊ณ , ํ์ํ ๊ฒ๋ง ๋ฑ๋ฑ ๊ฐ์ ธ๋ค ์ธ ์ ์๋ค.
๋ํ requires๋ ์บก์ํ๋ ๋ณด์ ์ธก๋ฉด์์๋ ๋์์ด ๋๋ค. utils ๋ชจ๋์์ exports๋ฅผ ์จ์ ํน์ ํจํค์ง๋ง ๊ณต๊ฐํ ์ ์๋๋ฐ, ์ด๋ ๊ฒ ํ๋ฉด app ๋ชจ๋์ utils์์ ํ์ฉ๋ ํจํค์ง๋ง ์ ๊ทผํ ์ ์๋ค. ๋๋ถ์ ๋ชจ๋ ๋ด๋ถ ์ฝ๋๊ฐ ๋ณดํธ๋๊ณ , ์ธ๋ถ์์๋ ๊ผญ ํ์ํ ๊ธฐ๋ฅ๋ง ์ฌ์ฉํ ์ ์๊ฒ ๋๋ ๊ฒ์ด๋ค.
๊ทธ๋ฆฌ๊ณ ์ ์ง๋ณด์ํ ๋๋ requires ๋์ ๋ง์ด ๋ณธ๋ค. ํ์ํ ๋ชจ๋์ ๋ช
ํํ๊ฒ ์ ๋ฆฌํด ๋๋ฉด ์ฝ๋๊ฐ ์ด๋์ ์๋์ง ์ฝ๊ฒ ์ถ์ ํ ์ ์๊ณ , module-info.java ํ์ผ๋ง ๋ณด๋ฉด ์ด๋ค ๋ชจ๋์ด ์ด๋ค ์์กด์ฑ์ ๊ฐ์ง๊ณ ์๋์ง ํ๋์ ์ ์ ์๋ค. ๋๋ถ์ ์ฝ๋ ๊ด๋ฆฌ๊ฐ ํจ์ฌ ์ฒด๊ณ์ ์ผ๋ก ๊ฐ๋ฅํด์ง๋ ๊ฒ์ด๋ค.
utils/module-info.java
module utils { exports com.example.utils; // โ
`utils` ๋ชจ๋์์ `com.example.utils` ํจํค์ง๋ฅผ ๊ณต๊ฐ }
utils/com/example/utils/StringUtils.java
package com.example.utils; public class StringUtils { public static String toUpper(String input) { return input.toUpperCase(); } }
app/module-info.java
module app { requires utils; // โ
`app` ๋ชจ๋์ด `utils` ๋ชจ๋์ ํ์๋ก ํจ (์์กด์ฑ ์ ์ธ) }
app/com/example/app/Main.java
package com.example.app; import com.example.utils.StringUtils; // โ
utils ๋ชจ๋์์ ์ ๊ณตํ๋ ํด๋์ค ์ฌ์ฉ public class Main { public static void main(String[] args) { String message = "hello, world!"; System.out.println(StringUtils.toUpper(message)); // "HELLO, WORLD!" ์ถ๋ ฅ } }
6. ์ธ์ ModulePath vs Classpath๋ฅผ ์ฌ์ฉํ ๊น?
์ผ๋จ Java 8 ์ดํ์์๋ Classpath๋ฅผ ์ฌ์ฉํ๋ค. JAR ํ์ผ์ Add External JARs๋ก ์ถ๊ฐํ๋ ๊ฒ์ด ๊ทธ ์์์ด๋ค.
๊ทธ๋ฆฌ๊ณ Java 9 ์ด์ (๋ชจ๋ ์์คํ
์ฌ์ฉ ์)์ ๋ผ์ด๋ธ๋ฌ๋ฆฌ๋ฆ ModulePath์ ์ถ๊ฐํ๋ค. ( module-info.java์์ requires ์ค์ ํ์)
์๋ฅผ ๋ค๋ฉด
ojdbc8.jar์ Classpath์ ์ถ๊ฐํ๋ฉด ๋ชจ๋ ํจํค์ง๋ฅผ ์์ ๋กญ๊ฒ ์ฐธ์กฐํ ์ ์๋ค.
ํ์ง๋ง, ModulePath์ ์ถ๊ฐํ๋ฉด ์๋์ฒ๋ผ module-info.java์์ requires๋ฅผ ์ค์ ํด์ผ ํ๋ค.
module mymodule { requires java.sql; // JDBC ์ฌ์ฉ requires oracle.jdbc; // Oracle JDBC ์ฌ์ฉ }
์ด๊ฑด ์๋์ผ๋ก ์ค์ ๋์ง ์๋๋ค. ojdbc8.jar ๊ฐ์ ๋ผ์ด๋ธ๋ฌ๋ฆฌ๋ฅผ ModulePath์ ์ถ๊ฐํ๋ฉด, module-info.java์์ ์ง์ requires๋ฅผ ์ ์ธํด์ค์ผ ํ๋ค.
์? ์ด์ ๋ ์๋ฐ ๋ชจ๋ ์์คํ
์ด ๊ฐ์ ํ๋ ์บก์ํ ์์น ๋๋ฌธ์ด์ผ. Classpath์์๋ ๋ชจ๋ ํจํค์ง๋ฅผ ์์ ๋กญ๊ฒ ์ฐธ์กฐํ ์ ์์์ง๋ง, ModulePath์์๋ ๋ชจ๋๋ค์ด ๋ช
์์ ์ผ๋ก ๊ณต๊ฐ(exports)๋ ํจํค์ง๋ง ์ ๊ทผํ ์ ์๊ธฐ ๋๋ฌธ์ ๊ทธ๋์ ojdbc8.jar์ ModulePath์ ์ถ๊ฐํ๋ฉด, module-info.java์์ requires oracle.jdbc ๊ฐ์ ์์ผ๋ก ์์กด์ฑ์ ๋ช
ํํ๊ฒ ์ง์ ์ค์ ํ๋ค.
๋ง์ฝ module-info.java๋ฅผ ์ถ๊ฐํ๊ธฐ ๊ท์ฐฎ๊ฑฐ๋ ๊ธฐ์กด์ฒ๋ผ ์์ ๋กญ๊ฒ ์ฐธ์กฐํ๊ณ ์ถ๋ค๋ฉด, ojdbc8.jar์ Classpath์ ์ถ๊ฐํ๋ ๋ฐฉ๋ฒ๋ ๊ฐ๋ฅํ๋ค. ModulePath๋ฅผ ์ฌ์ฉํ๋ ค๋ฉด ์๋์ผ๋ก ์ค์ ํ๋ ๊ฒ ํ์์ด๊ธฐ ๋๋ฌธ์ ๊ทธ๋ฅ Classpath๋ฅผ ์ฐ์.
์ฐธ๊ณ ์๋ฃ & ํฌ์คํ ์ ๋์์ ์ฃผ์ ๋ถ๋ค
1. https://velog.io/@c4fiber/eclipse-modulepath-vs-classpath
2. https://whitekeyboard.tistory.com/849