endermaru/22-5-team1-server 이미지를 deployment로 사용# latest 태그가 붙은 이미지를 기본으로 사용
$ kubectl create deployment spring --image=endermaru/22-5-team1-server
$ kubectl expose deployment spring --type=LoadBalancer --port=8080
$ minikube service spring
# 접속 후 정상 작동!(외부 포트는 랜덤)
http://127.0.0.1:2150/swagger-ui
$ kubectl get pods
NAME READY STATUS RESTARTS AGE
spring-6b68c5cbb6-sqv29 1/1 Running 0 2m34s
# Spring 앱 시작 시 프로필 등 환경변수 설정 안 됨(local, prod 등)
$ kubectl logs spring-6b68c5cbb6-sqv29
...
2025-04-22T15:21:08.278+09:00 INFO 1 --- [team1server] [ main] c.waffletoy.team1server.ApplicationKt : No active profile set, falling back to 1 default profile: "default"
...
docker compose, env 등을 활용한 환경변수 사용 불가능(spring.profiles.active...)
→ deployment를 생성한 뒤 새로운 pod에 환경변수를 지정하여 생성 가능
→ 그럼에도 환경변수값을 일일이 넣어준 pod을 별도 생성 필요
docker compose에 선언한 redis 컨테이너도 별도로 생성, 연결 필요
# deployment 없이 spring이라는 이름, app=spring2 라벨을 가진 pod을 생성
# spring.profiles.active 속성을 환경변수로 지정(underscore)
$ kubectl run spring \
--image=endermaru/22-5-team1-server \
--env=SPRING_PROFILES_ACTIVE=local \
--port=8080 \
--labels="app=spring2" # 라벨 지정으로 기존 pod과 구분 가능하게
# pod 이름과 라벨 확인
$ kubectl get pods --show-labels
NAME READY STATUS RESTARTS AGE LABELS
spring 1/1 Running 0 72s app=spring2
spring-6b68c5cbb6-sqv29 1/1 Running 0 20m app=spring,pod-template-hash=6b68c5cbb6
# 서비스 생성(미리 생성된 spring 서비스와 이름 구분, 필요시 --selector로 특정 pod 지정 가능)
$ kubectl expose pod spring --type=LoadBalancer --port=8080 --name=spring2
$ kubectl get svc
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
kubernetes ClusterIP 10.96.0.1 <none> 443/TCP 4d19h
spring LoadBalancer 10.111.25.65 <pending> 8080:30687/TCP 23m
spring2 LoadBalancer 10.98.10.200 <pending> 8080:31232/TCP 11s
# 접속해서 작동하는지 확인
$ minikube service spring2
# 해당 pod의 로그 확인
$ kubectl logs spring
...
2025-06-24T15:34:57.630+09:00 INFO 1 --- [internhasha] [ main] c.w.internhasha.ApplicationKt : The following 1 profile is active: "local"
....
# 서비스에 연결된 pod 엔드포인트 확인
$ kubectl get endpoints spring
NAME ENDPOINTS AGE
spring 10.244.0.15:8080 28m # 기존 서비스
$ kubectl get endpoints spring2
NAME ENDPOINTS AGE
spring2 10.244.0.17:8080 5m42s # 새로 만든 서비스
# pod의 IP(엔드포인트) 확인
$ kubectl get pods -o wide
NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES
spring 1/1 Running 0 11m 10.244.0.17 minikube <none> <none>
spring-6b68c5cbb6-sqv29 1/1 Running 0 31m 10.244.0.15 minikube <none> <none>
Cluster IP vs. Endpoint by GPT
엔드포인트:
- 서비스가 실제로 트래픽을 보낼 Pod들의 네트워크 주소(IP) 목록
- Pod가 재시작되면 변경될 수 있음
- 서비스의 selector를 기반으로 자동으로 엔드포인트를 생성/업데이트
- 서비스의 selector와 일치하는 라벨을 가진 Pod들을 찾음
- 해당 Pod들의 IP와 포트를 엔드포인트에 등록
- Pod가 추가/삭제되면 엔드포인트도 자동으로 업데이트
Cluster IP:
- 서비스의 가상 IP 주소
- kube-proxy에 의해 관리되는 Virtual IP
- 다른 Pod이 ClusterIP로 요청을 보내면, kube-proxy가 해당 요청을 Endpoint에 등록된 실제 Pod IP로 직접 전달
kubectl 명령어를 사용이 제한되는 환경에서는 사용 불가능⇒ 배포 환경이나 복잡한 환경에서는 더 관리하기 용이한 선언적 방식을 채택할 필요성이 있음