스프링 부트가 뭐지?
의존관리 잘 해주고, 내장 서버 끼워주는.. 그런거 아냐?
대충은 알고 있지만 구체적으로 생각해 본적은 없어 포스팅으로 정리하고자 한다.
스프링
스프링 프레임워크는 2002년에 Rod Johnson이 발표한 "Expert One-on-One J2EE Design and Development"이라는 책에서 출발하였다. 이 책에서 그는 자바 엔터프라이즈 플랫폼의 복잡성에 대한 비판을 제기하고, 이를 해결하기 위한 기초적인 구조를 제안했다. 그 결과로 탄생한 것이 바로 스프링 프레임워크이며, 2003년에 첫 버전이 공개되었다.
스프링 프레임워크는 다음과 같은 이유로 개발자들에게 큰 인기를 얻게 되었다.
의존성 주입 (Dependency Injection) 스프링은 의존성 주입을 통해 객체 간의 결합도를 줄이고, 코드의 재사용성과 테스트 용이성을 향상시켰다. 이에 반해, EJB에서는 의존성이 높고, 테스트와 재사용이 어려웠다.
AOP (Aspect Oriented Programming) 스프링은 AOP를 통해 횡단 관심사를 분리하여 코드의 모듈화를 증가시키고, 관련된 부분을 재사용하게 한다. EJB는 이러한 기능을 제공하지 않았다.
포괄적인 데이터 액세스 프레임워크: 스프링은 다양한 데이터 액세스 기술을 지원하며, 이에 따른 예외 처리를 단순화였다. 반면에 EJB는 복잡한 데이터 액세스와 트랜잭션 관리를 요구했다.
MVC 웹 프레임워크: 간편한 웹 애플리케이션 개발을 가능하게 하며, 다른 웹 프레임워크와의 쉬운 통합을 지원한다.
경량 컨테이너: 스프링은 EJB와 달리 경량 컨테이너를 사용하여 구동되며, 특정 환경에 구속받지 않는다. 이로 인해 스프링은 더 빠른 시작 시간과 더 적은 메모리 소비를 제공한다.
이러한 특징들 덕분에 스프링은 복잡한 엔터프라이즈 수준의 자바 애플리케이션 개발을 단순화하고 효율화하는 데 큰 도움이 되었다. 스프링은 모듈화가 잘 되어 있어 개발자가 필요한 기능만 선택하여 사용할 수 있으며, 유연성과 확장성이 뛰어나 다양한 프로젝트에 적용하기 쉬웠다. 이러한 이유로 EJB에 지쳐있던 개발자들이 환호하게 만들었다.
그러나 여전히..
봄이 왔음에도 여전히 춥다는 사람들이 많았다. 이유는 다음과 같다.
@Configuration
@EnableWebMvc
@ComponentScan(basePackages = "com.example.project")
public class WebConfig implements WebMvcConfigurer {
@Autowired
private ApplicationContext applicationContext;
@Override
public void configureViewResolvers(ViewResolverRegistry registry) {
ThymeleafViewResolver resolver = new ThymeleafViewResolver();
resolver.setTemplateEngine(templateEngine());
registry.viewResolver(resolver);
}
@Bean
public SpringTemplateEngine templateEngine() {
SpringTemplateEngine templateEngine = new SpringTemplateEngine();
templateEngine.setTemplateResolver(templateResolver());
return templateEngine;
}
@Bean
public ITemplateResolver templateResolver() {
SpringResourceTemplateResolver templateResolver = new SpringResourceTemplateResolver();
templateResolver.setApplicationContext(applicationContext);
templateResolver.setPrefix("/WEB-INF/views/");
templateResolver.setSuffix(".html");
return templateResolver;
}
}
순수 스프링을 사용해 viewResolver 빈을 등록하는 예시코드이다.
suffix와 prefix를 세팅하여 templateResolver 빈을 등록하고, templateResolver빈을 주입받아 templateEngine빈을 등록한다. 그리고 templateEngine을 주입받아 ViewResolver 빈을 등록한다.
위 코드만 보면 저 정도는 별거 아니다 싶지만
WebConfig 뿐 아니라 DataSource 설정, 등록한 의존의 버전관리 등 필요한 모든 설정에 대해 개발자들은 손수 설정해야 한다. 필자 역시 Spring boot를 배우기 이전 순수 Spring의 설정에 뚜들겨 맞고 몇 번 나가떨어진 기억이 있다.
스프링 부트의 등장
스프링 설정의 복잡성을 보완하기 위해 스프링 부트가 등장했다.
Spring Boot는 Spring 기반의 애플리케이션을 쉽게 만들 수 있게 도와주는 프레임워크이다. 주요 개념은 다음과 같다.
자동 구성(Auto Configuration) Spring Boot는 classpath 설정, 다른 빈들, 다양한 설정들에 따라 자동으로 Spring 설정을 해준다.
내장 서버 Spring Boot는 내장 Tomcat, Jetty, Undertow 등의 서버를 가지고 있어 따로 서버를 구축하지 않아도 된다.
스프링 부트 스타터(Spring Boot Starters) 의존성 그룹을 모아둔 것으로, 버전도 자동으로 관리된다. 이를 통해 빠르게 개발 환경을 설정할 수 있다.
위에서 예시로 보여진 뷰 리졸버를 빈으로 등록하는 과정도 스프링 부트에서는 타임리프 의존을 추가하는 것만으로 생략할 수 있다. 뿐만 아니라 스프링은 의존을 추가하는 것만으로도 관련된 의존을 알아서 받아오고 버전관리까지 해주며 내장 서버까지 포함해 바로 실행가능한 패키지를 빌드하여 제공한다.
어플리케이션에서 자주 사용되는 설정을 자동으로 제공해주며 일종의 스프링 어플리케이션의 템플릿 역할을 하는 것이다.
이를 통해 개발자는 설정에 쏟는 시간을 아끼고 순수 개발에 집중할 수 있게 되었다.
무조건 부트?
스프링 부트에 단점이 있을까 싶지만, 굳이 생각해보자면 다음과 같은 단점을 생각해볼 수 있을 것 같다.
과도한 자동화: Spring Boot는 많은 설정들을 자동화하므로, 때로는 원하는대로 동작하지 않을 때 어떤 설정이 문제인지 파악하기 어려울 수 있다. 이로 인해 디버깅이 복잡해질 수 있다.
불필요한 의존성: Spring Boot의 Starter 의존성은 많은 라이브러리를 포함하고 있다. 이는 개발을 편하게 하지만 불필요한 라이브러리가 포함될 가능성이 있으며, 이는 애플리케이션의 패키지 크기를 늘리고 때로는 의존성 충돌을 일으킬 수 있다.
그러나 위와 같은 문제는 스프링 부트에 대한 이해가 있다면 해결 가능한 문제이다.
또한, 설정이 너무 복잡한 어플리케이션의 경우 순수 스프링을 통해 설정을 직접 구성할 수 있겠으나 이 역시 스프링 부트를 통해서 웬만한 경우에 대한 설정이 가능하기 때문에, 부트를 두고 순수 스프링을 사용할 일이 있을까 싶다.