◇ PART · BOOT

SpringBoot 개요

설정의 무게를 내려놓고 다시 만나는 Spring

학습 목표

  • Spring Legacy 의 설정 파일이 왜 그렇게 많았는지 자기 말로 설명할 수 있다
  • SpringBoot 가 그 부담을 어떻게 줄이는지 큰 그림으로 안다
  • @SpringBootApplication 한 줄과 Starter 의존성 의 역할을 안다
  • SpringBoot 가 대신 해주지 않는 것 도 함께 안다

⚠️ 이전 과정의 끝에서

v∞ 까지 가본 사람만 아는 피로

Hello Servlet (v0) 부터 REST API 게시판 (v∞) 까지 — 우리는 끝까지 갔습니다.

그런데 새 프로젝트를 시작하려고 하면 — 그 모든 설정을 처음부터 다시 써야 합니다. web.xml, servlet-context.xml, root-context.xml, pom.xml, ViewResolver, 인코딩 필터…

코드 한 줄도 짜기 전에 30분이 사라집니다.

⚠️ 이상한 일

매 프로젝트마다 7번씩 똑같은 설정
프로젝트 A : web.xml + servlet-context.xml + root-context.xml + pom.xml ... 프로젝트 B : web.xml + servlet-context.xml + root-context.xml + pom.xml ... 프로젝트 C : web.xml + servlet-context.xml + root-context.xml + pom.xml ... ↑ 99% 같은 내용을 매번 다시 작성

사실상 복사-붙여넣기의 연속. 그런데 한 줄만 어긋나도 톰캣이 안 뜹니다.

⚠️ XML 설정 지옥 — 의존 그래프

┌─────────────┐ 참조 ┌──────────────────────┐ │ web.xml │ ─────→ │ servlet-context.xml │ └─────────────┘ └──────────────────────┘ │ 등록 │ 의존 ↓ ↓ ┌──────────────────┐ ┌────────────────────┐ │ encoding-filter │ │ root-context.xml │ └──────────────────┘ └────────────────────┘ │ DataSource / TX ↓ ┌──────────────────┐ │ pom.xml (50줄) │ └──────────────────┘ │ ┌───────┴────────┐ ↓ ↓ log4j.xml view-resolver

파일 7개가 서로를 참조 합니다. 한 줄만 어긋나도 톰캣이 안 뜨고, 어느 파일이 원인인지 학생은 알 길이 없습니다.

⚠️ web.xml 한 파일조차 이 정도


<servlet>
  <servlet-name>appServlet</servlet-name>
  <servlet-class>...DispatcherServlet</servlet-class>
  <init-param>
    <param-name>contextConfigLocation</param-name>
    <param-value>servlet-context.xml</param-value>
  </init-param>
</servlet>
<servlet-mapping>
  <url-pattern>/</url-pattern>
</servlet-mapping>
        

web.xml 의 일부. 합치면 100줄을 넘습니다.

⚠️ 버전을 직접 적던 시절

Legacy 시절의 pom.xml — 의존성마다 버전 번호를 일일이 손으로 적었습니다.


<dependency>
  <groupId>org.springframework</groupId>
  <artifactId>spring-webmvc</artifactId>
  <version>5.3.20</version>
</dependency>
<dependency>
  <groupId>org.springframework</groupId>
  <artifactId>spring-jdbc</artifactId>
  <version>5.2.8</version>  <!-- ← 한 줄 어긋남 -->
</dependency>
<dependency>
  <groupId>org.mybatis</groupId>
  <artifactId>mybatis-spring</artifactId>
  <version>2.0.6</version>
</dependency>
        

⚠️ 검색의 시작

버전 한 자릿수 차이로 빌드 실패

spring-jdbc 의 5.2.8 — 한 줄 어긋났을 뿐인데 톰캣이 안 뜹니다. 콘솔의 빨간 스택트레이스 앞에서 학생은 어디부터 봐야 할지 모릅니다.

검색해보면 「Spring 5.3 에는 mybatis-spring 2.1 이상이 필요합니다」 같은 답을 한참 뒤에야 발견. 코드 한 줄 짜기 전에 또 30분.

🛠️ SpringBoot — 등장 배경

"매번 같은 설정을 다시 쓰지 맙시다"

Spring 팀이 같은 고민을 했습니다. 99% 같은 설정이라면 — 기본값을 프레임워크가 미리 들고 있으면 되지 않을까?

사용자는 다른 1% 만 적으면 됩니다. 이게 SpringBoot 의 핵심 철학입니다.

베이스 키트 비유

이미 조립된 베이스 키트 위에서 출발하는 셈. Spring 자체가 사라진 게 아니라, 설정만 미리 깔아둔 Spring 입니다.

🛠️ Auto-Configuration — 자동 설정

@SpringBootApplication 한 줄

이 어노테이션 하나가 "클래스패스에 뭐가 있는지 보고, 알아서 필요한 빈을 등록" 합니다.

[classpath 스캔] → [@Conditional 판정] → [빈 자동 등록] spring-webmvc 발견 → @ConditionalOnClass → DispatcherServlet ✓ tomcat-embed 발견 → @ConditionalOnClass → TomcatWebServer ✓ jackson 발견 → @ConditionalOnClass → JsonConverter ✓ mybatis-boot 발견 → @ConditionalOnBean(DS) → SqlSessionFactory✓

Legacy 에서 우리가 손으로 적던 XML — 그걸 SpringBoot 가 대신 적어줍니다.

📊 Auto-Configuration 흐름 — 한 그림

🛠️ Starter — 묶음 의존성

spring-boot-starter-web 한 줄

웹 애플리케이션에 필요한 의존성을 이미 검증된 버전으로 묶어둔 세트.

spring-boot-starter-web 한 줄 ├── spring-webmvc (호환 버전) ├── spring-web (호환 버전) ├── tomcat-embed-core ├── jackson-databind (JSON 변환) └── ...

버전 번호를 우리가 안 적습니다. SpringBoot 버전 하나 가 모든 하위 의존성의 호환 버전을 결정합니다.

📊 Starter 한 줄이 풀어내는 트리

🛠️ 임베디드 톰캣

main() 메서드로 바로 실행

Legacy 에서는 톰캣을 따로 설치 → war 를 톰캣에 배포 했습니다. SpringBoot 는 톰캣을 jar 안에 품고 있어서 — java -jar app.jar 한 줄로 실행됩니다.

[Legacy — 외부 톰캣] [Boot — 내장 톰캣] ┌──────────────────┐ ┌──────────────────┐ │ Tomcat 설치 │ │ app.jar │ │ (별도 프로세스) │ │ ┌────────────┐ │ │ ┌────────────┐ │ │ │ Tomcat │ │ │ │ webapps/ │ │ ← war 배포 → │ │ (내장) │ │ │ │ app.war │ │ │ ├────────────┤ │ │ └────────────┘ │ │ │ 내 코드 │ │ └──────────────────┘ │ └────────────┘ │ ↑ └──────────────────┘ 톰캣 켜고, war 옮기고, 재시작 ↑ java -jar app.jar (끝)

IDE 에서도 마찬가지. 「Run on Server」 가 아니라 그냥 main() 실행.

💻 Hello World — Application.java


package com.example.demo;

import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;

@SpringBootApplication
public class DemoApplication {
    public static void main(String[] args) {
        SpringApplication.run(DemoApplication.class, args);
    }
}
        

10줄짜리 파일 이 — Legacy 의 web.xml + servlet-context.xml + root-context.xml + 톰캣 설정을 전부 대체합니다.

💻 Controller 는 그대로


@Controller
public class HelloController {
    @GetMapping("/hello")
    public String hello(Model model) {
        model.addAttribute("msg", "안녕, SpringBoot!");
        return "hello";
    }
}
        

Controller 코드는 Legacy 와 100% 같습니다. @Controller, @GetMapping, Model — 우리가 v0 ~ v∞ 동안 익힌 모든 것이 그대로 살아있습니다.

바뀐 건 설정의 무게, 코어 사용법은 그대로.

💻 pom.xml — Legacy 쪽

Legacy — 약 50줄, 버전 직접 지정

<dependency>
  <groupId>org.springframework</groupId>
  <artifactId>spring-webmvc</artifactId>
  <version>5.3.20</version>
</dependency>
<dependency>
  <groupId>jstl</groupId>
  <artifactId>jstl</artifactId>
  <version>1.2</version>
</dependency>
<!-- ... 12개 더 ... -->
          

버전을 손으로 적고 충돌은 직접 해결. 의존성 12개 → 1개로 — 다음 슬라이드에서 Boot 가 같은 자리를 어떻게 적는지 봅니다.

💻 pom.xml — Boot 쪽

Boot — 약 5줄, 버전 자동

<dependency>
  <groupId>org.springframework.boot</groupId>
  <artifactId>spring-boot-starter-web</artifactId>
</dependency>
          

버전 번호가 사라졌습니다. SpringBoot 버전 하나 가 spring-webmvc · jstl · jackson · 톰캣까지 호환 버전을 전부 보증합니다.

의존성 12개 → 1개로 압축. 같은 화면이 같은 코드로 뜨는데, pom.xml 만 가벼워졌습니다.

💻 application.properties — 7개 XML 이 1개로


server.port=8080
spring.datasource.url=jdbc:mysql://localhost:3306/myapp
spring.datasource.username=root
spring.datasource.password=secret
spring.mvc.view.prefix=/WEB-INF/views/
spring.mvc.view.suffix=.jsp
mybatis.mapper-locations=classpath:mappers/*.xml
        

키 = 값 형식의 평범한 텍스트. XML 의 중첩 태그가 사라지고, Legacy 의 root-context.xml + ViewResolver + SqlSessionFactory 가 이 한 파일로 압축됩니다.

🔄 Before / After — 한 화면

항목 ⚠️ Spring Legacy ✓ SpringBoot
web.xml ~ 100 줄 직접 작성 0 줄 (자동)
Spring 설정 servlet-context.xml + root-context.xml ~ 100 줄 application.properties 1 파일
pom.xml ~ 50 줄 (버전 직접 지정) ~ 5 줄 (버전 자동)
WAS 톰캣 별도 설치 + war 배포 임베디드 톰캣 (jar 안)
실행 Eclipse Server 등록 → Add → Start java -jar app.jar
버전 충돌 직접 해결 (검색·시행착오) SpringBoot 버전이 보증
코드 (Controller) ↔ 동일 — @Controller, @GetMapping, Model 그대로

🔄 실행 방법 비교

[Legacy 실행] ① 톰캣 다운로드 / 설치 ② Eclipse 에서 Server 등록 ③ 프로젝트를 Server 에 Add ④ Server Start ⑤ http://localhost:8080/myapp/hello [Boot 실행] ① main() 우클릭 → Run ② http://localhost:8080/hello

학생이 첫날 만나는 "환경 세팅의 벽" 자체가 사라집니다.

📋 SpringBoot 가 안 풀어주는 것

착각하기 쉬운 부분

SpringBoot 는 설정의 무게 만 줄여줍니다. 다음 것들은 여전히 우리 책임입니다:

  • 비즈니스 로직 — 게시판 권한 체크, 결제 처리, 검증 규칙
  • DB 스키마 설계 — 어떤 테이블, 어떤 인덱스
  • SQL — MyBatis 쿼리는 직접 작성
  • 화면 흐름 — Controller → Service → Mapper 4 박스 사고는 그대로

이전 과정에서 익힌 「데이터 흐름」 사고는 100% 그대로 살아있습니다. 오히려 더 잘 보입니다.

📊 한 그림 정리

이번 차시의 데이터 흐름

설정 7개 파일
@SpringBootApplication 1줄 + application.properties
Controller → Service → Mapper → DB
파란 칸 — Legacy 의 설정 7개 파일 이 SpringBoot 의 자동 설정 1개 로 대체. 그 아래의 4 박스 흐름은 그대로 유지.

정리

오늘 들고 가는 3가지

  • SpringBoot = 설정이 미리 깔린 Spring. 코어는 그대로, 무게만 덜어냄
  • @SpringBootApplication + Starter 두 단어가 핵심. 자동 설정 + 묶음 의존성
  • 비즈니스 로직은 여전히 우리 책임 — 이전 과정의 흐름 사고가 그대로 살아있음

다음 차시: SpringBoot 프로젝트 첫 실행 — Spring Initializr 로 5분 안에 Hello.