์๋
ํ์ธ์. Dooray ์์ ์ธ์ฆ ์๋ฒ๋ฅผ ๊ฐ๋ฐํ๊ณ ์๋ ๊น๋ณ๋ถ์
๋๋ค.
Dooray ์ธ์ฆ์๋ฒ๊ฐ ์ฌ์ฉํ๋ Spring Boot ํ๋ ์ ์ํฌ ๋ฒ์ ์ ์
๊ทธ๋ ์ด๋ ํ๋ฉด์ ๊ฒช์ ๋ช๊ฐ์ง ๋ด์ฉ๋ค์ ๊ณต์ ํ๋ ค๊ณ ํฉ๋๋ค.
2022๋
11์์ ๊ธฐ์กด์ Spring framework 5 ์ Spring Boot 2.X ๋ฒ์ ์ ๋์ฒดํ๋ Spring framework 6์ Spring Boot 3 ๊ฐ ๋ฆด๋ฆฌ์ฆ ๋์์ต๋๋ค.
์๋ก์ด ์คํ๋ง ๋ถํธ 3.0์ ์๋ก ์
๊ทธ๋ ์ด๋๋ ์๋ง์ ๋ผ์ด๋ธ๋ฌ๋ฆฌ๋ค์ ํฌํจํ๊ณ ์์ง๋ง, ๋ค์๊ณผ ๊ฐ์ ํฐ ํน์ง์ด ์์ต๋๋ค.
- Java17๊ณผ Java19 ์ง์
- GraalVM ์ง์
- Spring framework 6.0 ๊ธฐ๋ฐ
์๋ก์ด ์คํ๋ง ๋ถํธ 3.0 ๋ Java17 ์ ๊ธฐ๋ฐ์ผ๋ก ์์ฑ๋ ์๋ก์ด ํ๋ ์ ์ํฌ์ ๋๋ค.
๋ง์ฝ ์ฌ๋ฌ๋ถ๋ค์ด ์์ง๋ Java8 ์ ์ฌ์ฉํ๊ณ ์๋ค๋ฉด, ์คํ๋ง ๋ถํธ 3.0์ ์ฌ์ฉํ ์ ์์ต๋๋ค.
๊ทธ๋์ ์คํ๋ง์์๋ ์ผ์ ๊ธฐ๊ฐ๋์ Spring Boot 2.7๊ณผ 3.0์ ๊ณ์ ์ ์ง ๋ณด์ํ ๊ณํ์ด๋ผ๊ณ ํฉ๋๋ค.
๋ค์ ๊ทธ๋ฆผ์ ๋ณด๋ฉด ๋ณด์ ์ ๋ฐ์ดํธ๋ ๋ฒ๊ทธ ์์ ์ 2023๋ ๋ง๊น์ง ์ง์ํ๋ค๊ณ ํ๋ ๊ฐ๋ฅํ๋ฉด ๋น ๋ฅธ ์๊ฐ์ ์ ๊ทธ๋ ์ด๋ ํ๋ ๊ฒ์ด ์ข๊ฒ ์ต๋๋ค.

์ด๋ฒ ์คํ๋ง ๋ถํธ 3.0 ์๋ ์ด๋ฐ ํน์ง๋ค ์ธ์๋ Jakarta EE ๋ฅผ ์ง์ํ๋ค๋ ํฐ ๋ณ๊ณก์ ์ด ์๊ฒผ์ต๋๋ค.
๊ธฐ์กด์ ์ฐ๋ฆฌ๋ JavaEE ๋ฅผ ์ฌ์ฉํ๊ณ ์์์ต๋๋ค.
์ฌ์ฉ์์ ์์ฒญ์ ์ฒ๋ฆฌํ๊ณ ์ ์ ํ ์๋ต์ ์ ๋ฌํ๋ HttpServletRequest ์ HttpServletResponse ๊ฐ ๋ํ์ ์ธ ํด๋์ค์ ๋๋ค. ์ด๋ค ํด๋์ค๋ค์ javax.servlet.http ํจํค์ง์ ํฌํจ๋์ด ์์ต๋๋ค.
ํ์ง๋ง Spring Boot 3.0 ์์๋ JavaEE ๊ฐ ์๋ Jakarta EE ๋ฅผ ์ฌ์ฉํด์ผ ํ๋ฏ๋ก jakarta.servlet.http.HttpServletRequest, jakarta.servlet.http.HttpServletResponse ๋ฅผ ์์ค ์ฝ๋์ import ํด์ผ ํฉ๋๋ค.
๊ทธ๋ฌ๋ฏ๋ก ๊ธฐ์กด์ Spring Boot 2.X ๋ฅผ 3.0 ์ผ๋ก ์
๊ทธ๋ ์ด๋ ํ๋ ค๋ฉด ์๋ง์ ์ฝ๋๋ฅผ ์์ ํด์ผ ํฉ๋๋ค.
Jakarta EE
2017๋ ํ๋ฐ๊ธฐ ์ค๋ผํด์ JavaEE ํ๋ก์ ํธ๋ฅผ ๋น์๋ฆฌ ๊ธฐ๊ด์ธ ์ดํด๋ฆฝ์ค ์ฌ๋จ์ผ๋ก ์ด๊ดํ๋ ๋ด์ฉ์ ๋ฐํํฉ๋๋ค.
์ด๋ ์ฌ์ค์ JavaEE ์ ๊ธฐ์ ์ฃผ๋๊ถ์ด ์ค๋ผํด์์ ์ดํด๋ฆฝ์ค ์ฌ๋จ์ผ๋ก ๋์ด๊ฐ ์ฌ๊ฑด์
๋๋ค.
ํ์ง๋ง JavaEE ์ํ๊ถ์ ์ค๋ผํด์ด ๊ฐ๊ณ ์์ด์ ์ดํด๋ฆฝ์ค ์ฌ๋จ์์๋ JavaEE ํจํค์ง ์ด๋ฆ์ธ javax.* ๋ฅผ ์ฌ์ฉํ ์ ์์ต๋๋ค.
์ดํด๋ฆฝ์ค ์ฌ๋จ์ Jakarta EE ๋ผ๊ณ ํ๊ณ ํจํค์ง๋ jakarta.* ๋ก ๋ช
๋ช
ํฉ๋๋ค.
๋ค์๊ณผ ๊ฐ์ JavaEE ์ด๋ฆ๋ค์ด JakartaEE ์ด๋ฆ์ผ๋ก ์๋กญ๊ฒ ๋ณ๊ฒฝ๋์๊ณ , ํจํค์ง ์ด๋ฆ๋ก ๋ณ๊ฒฝ๋์์ต๋๋ค.
- Java Servlet(javax.servlet) -> Jakarta Servlet(jakarta.servlet)
- Java Message Servie (javax.jms) -> Jakarta Messaging (jakart.jms)
- JPA:Java Persistence API (javax.persistence) -> Jakarta Persistence(jakarta.persistence)
- JTA:Java Transaction API (javax.transaction) -> Jakarta Transaction(jakarta.transaction)
- Java Mail (javax.mail) -> Jakarta Mail (jakarta.mail)
Spring Boot 2.7.X ์์ 3.0.1 ์ผ๋ก ์ ๊ทธ๋ ์ด๋
๊ฐ์ฅ ๋จผ์ ํ ์ผ์ ํ๋ก์ ํธ์ JDK ๋ฒ์ ์ ์ฌ๋ฆฌ๋ ์ผ์ ๋๋ค. ๊ธฐ์กด์ Java17 ์ด์์ ์ฌ์ฉํ๊ณ ์์๋ค๋ฉด, ์์ ํ ์ผ์ด ์์ต๋๋ค.
๋๋ฒ์งธ๋ pom.xml ์ ์ด์ด์ Spring Boot ์ ๋ฒ์ ์ ์ฌ๋ฆฌ๋ ์ผ์ ๋๋ค
<parent/> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-parent</artifactId> <version>3.0.1</version> </parent> ... <properties> <java.version>17</java.version> </properties>
์คํ๋ง ํ๋ ์์ํฌ ๋ฒ์ ์ ์ฌ๋ฆฌ๋ฉด JavaEE ๊ฐ Jakarta EE ๋ก ๋ณ๊ฒฝ๋์ด ํจํค์ง์ ํด๋์ค ์ฌ์ฉ๋ฒ์ ๋ ๋ณํ๊ฐ ๋ฐ์ํฉ๋๋ค.
์คํ๋ง ํ๋ ์์ํฌ์ ๋ฒ์ ์ด 6.0 ์ผ๋ก ์ฌ๋ผ๊ฐ๋ฉด์, ํ๋ ์ ์ํฌ์์ ์ ๊ณตํ๋ ํด๋์ค์ ์ฌ์ฉ ๋ฐฉ๋ฒ ๋ํ ๋ณ๊ฒฝ์ด ์์ต๋๋ค. ๋ง์ฝ ํ๋ฒ์ ํจํค์ง ๊ฒฝ๋ก๋ฅผ ๋ฐ๊พธ๋ ค๊ณ IDE ๊ฐ ์ ๊ณตํ๋ replace ๊ธฐ๋ฅ์ ์ฌ์ฉํ๋ฉด ๊ณค๋ํฉ๋๋ค.
‘import javax.’ ๋ฌธ์์ด์ ์ฐพ์์ ‘import jakarta.’ ๋ก ๋ณ๊ฒฝํ์ง ๋ง์ธ์.
“javax.sql.DataSource”๋ “javax.crypto.SecretKey” ๊ฐ์ ํด๋์ค๋ JDK ์ ํฌํจ๋์ด์๋ ๊ฒ๋ค์ด๋ฉฐ ์ด๋ค์ ๋ฐ๋์ง ์์์ผ๋๊น์.
๋ํ์ ์ธ ๋ช๊ฐ์ง ํด๋์ค๋ค์ ๋์ดํ๋ฉด ๋ค์๊ณผ ๊ฐ์ต๋๋ค.
import javax.annotation.PostConstruct; -> import jakarta.annotation.PostConstruct; import javax.persistence.EntityManager; -> import jakarta.persistence.EntityManager; import javax.persistence.Column; -> import jakarta.persistence.Column; import javax.persistence.Convert; -> import jakarta.persistence.Convert; import javax.persistence.Entity; -> import jakarta.persistence.Entity; import javax.servlet.http.HttpServletRequest; -> import jakarta.servlet.http.HttpServletRequest;
์๋ง๋ ์๋ง์ ํด๋์ค๋ค์ ๋ค์ import ํด์ผ ํฉ๋๋ค.
๋ง์ฝ ๋ค์๊ณผ ๊ฐ์ ํด๋์ค๋ฅผ ์ฌ์ฉํ๊ณ ์๋ค๋ฉด, ์คํ๋ง ํ๋ ์์ํฌ 6.0 ์์ ์ ๊ณตํ๋ ํด๋์ค๋ค๋ก ๋ณ๊ฒฝํด์ผ ํฉ๋๋ค.
๋ค์ ํด๋์ค๋ค์ ๋จ์ํ ํจํค์ง ์ด๋ฆ์ spring5 -> spring6 ๋ก ๋ณ๊ฒฝํ๋ฉด ๊ธฐ๋ฅ์ ๊ทธ๋๋ก ์ฌ์ฉํ ์ ์์ต๋๋ค.
import org.thymeleaf.spring5.SpringTemplateEngine; import org.thymeleaf.spring5.templateresolver.SpringResourceTemplateResolver; import org.thymeleaf.spring5.view.ThymeleafViewResolver;
์ธ๋ถ ๋ผ์ด๋ธ๋ฌ๋ฆฌ์ ์์กดํ๋ ๊ฒฝ์ฐ์๋ JakartaEE ์ ๋ง๊ฒ ๋ณ๊ฒฝ๋ ๋ผ์ด๋ธ๋ฌ๋ฆฌ๋ฅผ ์ฌ์ฉํด์ผ ํฉ๋๋ค.
XML ์ ์ฒ๋ฆฌํ๋ Jaxb ๋ JavaMail ์ด ๋ํ์ ์
๋๋ค.
๋ค์์ pom.xml ์์ ์ด๋ฉฐ, ๋ณ๊ฒฝ ์ /ํ์ ๋น๊ตํ์ต๋๋ค.
// Before Spring Boot 3.0 <dependency> <groupId>javax.xml.bind</groupId> <artifactId>jaxb-api</artifactId> <version>2.3.1</version> </dependency> <dependency> <groupId>javax.mail</groupId> <artifactId>mail</artifactId> <version>1.4.7</version> </dependency>
// After Spring Boot 3.0 <dependency> <groupId>jakarta.xml.bind</groupId> <artifactId>jakarta.xml.bind-api</artifactId> <version>4.0.0</version> </dependency> <dependency> <groupId>jakarta.mail</groupId> <artifactId>jakarta.mail-api</artifactId> <version>2.1.0</version> </dependency>
๋ง์ฝ ํ๋ก์ ํธ๊ฐ ์ฌ๋ด์์ ๋ง๋ ๋ผ์ด๋ธ๋ฌ๋ฆฌ(In-House Library)์ ์์กดํ๋์ง ํ์ธํ ํ์๊ฐ ์์ต๋๋ค.
๋ง์ฝ ์ด ๋ผ์ด๋ธ๋ฌ๋ฆฌ๊ฐ Spring Framework 6.0 ์์ ์ง์ํ์ง ์๋ ํด๋์ค ํน์ JavaEE ํด๋์ค๋ฅผ ์ฌ์ฉํ๋ ๊ฒฝ์ฐ, ์ ์ ํ ํด๋์ค๋ฅผ ์ฐพ์ ์ ์์ด์ ์คํ๋์ง ์์ต๋๋ค.
Query DSL ์ค์
์ ํ๋ฆฌ์ผ์ด์ ์ด Query DSL ์ ์ฌ์ฉํ๋ ๊ฒฝ์ฐ, ๋ ๋ง์ ์ฃผ์๊ฐ ํ์ํฉ๋๋ค.
์ด ๊ธ์ ์ฐ๋ ์์ ์์(2023/01/07) QueryDSL ์ต์ ๋ฒ์ ์ 5.0.0 ์
๋๋ค.
๊ธฐ์กด ์ ํ๋ฆฌ์ผ์ด์
์ด QueryDSL 5.0.0 ์ ์ฌ์ฉํ๊ณ ์๋๋ผ๋, JakartaEE ๋ฅผ ์ง์ํ๋๋ก ์ค์ ์ ๋ณ๊ฒฝํด์ค์ผ ํฉ๋๋ค.
๋ค์์ pom.xml ์ ํ์ธํด๋ด ์๋ค. classifier ์์ฑ์ ์ฌ์ฉํ์ฌ jakarta ๋ฅผ ์ค์ ํ๊ฒ์ ํ์ธํ ์ ์์ต๋๋ค.
// FROM <dependency> <groupId>com.querydsl</groupId> <artifactId>querydsl-apt</artifactId> <version>5.0.0</version> <scope>provided</scope> </dependency> <dependency> <groupId>com.querydsl</groupId> <artifactId>querydsl-jpa</artifactId> <version>5.0.0</version> </dependency> ------------------------------------------------------------- // TO <dependency> <groupId>com.querydsl</groupId> <artifactId>querydsl-apt</artifactId> <version>5.0.0</version> <classifier>jakarta</classifier> <scope>provided</scope> </dependency> <dependency> <groupId>com.querydsl</groupId> <artifactId>querydsl-jpa</artifactId> <version>5.0.0</version> <classifier>jakarta</classifier> </dependency>
QueryDSL ์ apt-maven-plugin ์ ์ฌ์ฉํ์ฌ ์ปดํ์ผ ๊ณผ์ ์์ Q-Type ํด๋์ค๋ฅผ ์์ฑํฉ๋๋ค.
ํ์ง๋ง querydsl-apt jakarta ๋ฒ์ ์์๋ apt-maven-plugin ์ด ํ์ ์์ต๋๋ค.
๋ง์ฝ pom.xml ์ apt-maven-plugin ์ค์ ์ด ์๋ค๋ฉด ๋ค์๊ณผ ๊ฐ์ด ์๋ฌ๊ฐ ๋ฐ์ํ ์ ์์ต๋๋ค.
[INFO] --- maven-compiler-plugin:3.10.1:compile (default-compile) @
[INFO] Changes detected - recompiling the module!
[INFO] Compiling 216 source files to ...
Attempt to recreate a file for type com.dooray.idp.domain.QMember
Attempt to recreate a file for type com.dooray.idp.domain.QTenant
...
[INFO] -------------------------------------------------------------
[ERROR] COMPILATION ERROR :
[INFO] -------------------------------------------------------------
[ERROR] Attempt to recreate a file for type com.dooray.idp.domain.QMember
[ERROR] Attempt to recreate a file for type com.dooray.idp.domain.QTenant
...
[INFO] 2 errors
์ด๋ ์ฌ๋ฌ๋ถ์ด ์ค์ ํ apt-maven-plugin ์ ์ ๊ฑฐํ๋ฉด ๋ฉ๋๋ค.
querydsl-apt jakarta ๋ฒ์ ์์๋ javax.annotation.processing.Processor ๋ฅผ ์๋น์ค๋ก ์ ๊ณตํ๊ณ ์๊ณ , ์๋ฐ ์ปดํ์ผ๋ฌ๊ฐ ์ด๋ฅผ ์ฌ์ฉํ์ฌ Q-class ๋ฅผ target/generated-sources/annotation ์ ์์ฑํฉ๋๋ค.
๊ทธ๋ฌ๋ฏ๋ก ์ฌ๋ฌ๋ถ๋ค์ apt-maven-plugin ์ด ์ด์ค ๋์ํด์ ์๋ฌ๊ฐ ๋ฐ์ํ๋ ๊ฒ์ ๋๋ค.

์ด์ ๊ด๋ จ๋ ์์ธํ ๋ด์ฉ์ ๋ค์ ๋งํฌ๋ก ์ฐธ๊ณ ํ์ธ์