Day 2 - Spring Boot 앱 · 컨테이너
파이프라인에 올릴 배포 단위(이미지) 만들기
목차
학습 목표
- 최소한의 Spring Boot 웹 앱을 구성한다
- 멀티 스테이지 Dockerfile로 JAR 이미지를 만든다
- Deployment / Service 매니페스트 초안을 이해한다
샘플 앱
Gradle 예시 (build.gradle 일부):
plugins {
id 'java'
id 'org.springframework.boot' version '3.2.x'
id 'io.spring.dependency-management' version '1.1.x'
}
dependencies {
implementation 'org.springframework.boot:spring-boot-starter-web'
implementation 'org.springframework.boot:spring-boot-starter-actuator'
testImplementation 'org.springframework.boot:spring-boot-starter-test'
}
컨트롤러:
@RestController
public class HelloController {
@GetMapping("/")
public Map<String, String> hello() {
return Map.of(
"service", "spring-demo",
"message", "hello from spring"
);
}
}
application.yml:
server:
port: 8080
management:
endpoints:
web:
exposure:
include: health,info
endpoint:
health:
probes:
enabled: true
헬스 체크 엔드포인트
| 용도 | 경로 (Actuator) |
|---|---|
| Liveness | /actuator/health/liveness |
| Readiness | /actuator/health/readiness |
| 일반 헬스 | /actuator/health |
EKS / Kubernetes probe에 그대로 연결합니다.
Dockerfile
멀티 스테이지 빌드 예시:
# build
FROM eclipse-temurin:17-jdk-alpine AS build
WORKDIR /workspace
COPY . .
RUN ./gradlew bootJar --no-daemon
# run
FROM eclipse-temurin:17-jre-alpine
WORKDIR /app
RUN addgroup -S app && adduser -S app -G app
USER app
COPY /workspace/build/libs/*.jar /app/app.jar
EXPOSE 8080
ENTRYPOINT ["java", "-jar", "/app/app.jar"]
Maven이면 mvn -B package -DskipTests + target/*.jar 로 동일 패턴입니다.
.dockerignore 권장:
.git
.idea
build
.gradle
*.md
로컬 실행
# 앱만
./gradlew bootRun
curl -s http://localhost:8080/
# 이미지
docker build -t spring-demo:local .
docker run --rm -p 8080:8080 spring-demo:local
curl -s http://localhost:8080/actuator/health
K8s 매니페스트 초안
GitOps 저장소에 넣을 최소 형태 (Day 4에서 Argo CD가 추적):
# deployment.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
name: spring-demo
labels:
app: spring-demo
spec:
replicas: 2
selector:
matchLabels:
app: spring-demo
template:
metadata:
labels:
app: spring-demo
spec:
containers:
- name: app
image: <ACCOUNT>.dkr.ecr.<REGION>.amazonaws.com/spring-demo:0.1.0
ports:
- containerPort: 8080
readinessProbe:
httpGet:
path: /actuator/health/readiness
port: 8080
initialDelaySeconds: 10
periodSeconds: 5
livenessProbe:
httpGet:
path: /actuator/health/liveness
port: 8080
initialDelaySeconds: 30
periodSeconds: 10
resources:
requests:
cpu: 100m
memory: 256Mi
limits:
cpu: "1"
memory: 512Mi
---
# service.yaml
apiVersion: v1
kind: Service
metadata:
name: spring-demo
spec:
selector:
app: spring-demo
ports:
- port: 80
targetPort: 8080
type: ClusterIP
이미지 태그(0.1.0)는 Day 3 CI가 커밋 SHA 등으로 갱신합니다.
실습 체크리스트
- Spring Boot 프로젝트 생성 ·
/· health 응답 확인 - 단위 테스트 1개 이상 통과
- Dockerfile 빌드 · 로컬 컨테이너 기동
- Deployment / Service YAML 초안 작성
- (선택) 로컬 kind/minikube에 수동 배포