개요
Kubernetes를 쓰다 보면 "설정값을 Pod에 어떻게 안전하게 전달하지?"라는 상황이 자주 생긴다.
이때 사용하는 대표 리소스가 ConfigMap과 Secret인데, 둘은 주입 방식(Env/Volume)이 거의 동일하지만 저장하는 데이터 성격과 보안 관점에서 중요한 차이가 있다.
1. Secret이란?
Secret은 비밀번호, 토큰, 인증서 같은 "민감한 값"을 Kubernetes 리소스로 저장하고 Pod에 주입하는 방식이다.
예를 들어 아래 같은 값들이 Secret으로 관리된다.
- DB 계정/비밀번호
- API Key / Access Token
- TLS 인증서 / 개인키
- Docker Registry 로그인 정보
즉, Secret의 역할은 간단히 말해:
"민감한 설정값을 클러스터에 저장해두고, 필요한 Pod에만 전달해서 사용하게 한다."
2. Secret vs ConfigMap, 같은 원리인가?
- Pod에 주입하는 방식은 거의 동일하다
- 환경변수(env)
- envFrom(여러 키를 한번에)
- 볼륨(volume) 마운트
하지만 차이가 있다.
(1) 용도 차이
- ConfigMap: 비민감 설정값(URL, 로그레벨, feature flag 등)
- Secret: 민감 정보 (비번, 토큰, 키, 인증서 등)
(2) data 저장 방식
- ConfigMap은 문자열 그대로 저장
- Secret은 data: 에 base64 인코딩된 값으로 저장하는 경우가 많다.
⚠️ 여기서 중요한 포인트:
→ base64는 "암호화"가 아니다. 단순 인코딩이라 복호화가 매우 쉽다.
따라서 Secret이 "자동으로 안전해지는 것"은 아니고, 운영 환경에서는 보안 설정이 함께 따라와야 한다.
(3) 보안 관점 차이
Secret을 제대로 쓰려면 아래를 함께 고려해야 한다.
- RBAC로 Secret 접근 최소화
- 불필요한 사용자/서비스계정에 secret get/list 권한 주지 않기
- 가능하면 etcd Encryption at rest 적용 (클러스터 설정)
- Pod에 필요한 Secret만 주입하기
3. Secret 종류 (자주 쓰는 타입)
- Opaque: 일반 Key-Value Secret (가장 흔함)
- kubernetes.io/tls: TLS 인증서/키 (tls.crt, tls.key)
- kubernetes.io/dockerconfigjson: Docker registry 인증 정보
4. 실습: Secret 생성 & Pod에 주입하기
실습은 아래 4단계로 진행한다.
1. Namespace 생성
2. Opaque Secret 생성
3. 환경변수로 주입
4. 볼륨으로 마운트
4.1 Namespace 생성
kubectl create ns secret-lab
kubectl config set-context --current --namespace=secret-lab
4.2 Secret 생성 (Opaque)
방법 A) YAML로 생성
먼저 base64 만들기(macOS):
echo -n 'hrlab' | base64
echo -n 'P@ssw0rd-123' | base64
그 결과를 data에 넣기:
apiVersion: v1
kind: Secret
metadata:
name: app-secret
namespace: secret-lab
type: Opaque
data:
db_user: aHJsYWI=
db_password: UEBzc3cwcmQtMTIz
방법 B) 명령어로 생성
리터럴 값으로 Secret을 생성한다.
kubectl create secret generic app-secret \
--from-literal=db_user=hrlab \
--from-literal=db_password='P@ssw0rd-123'
확인:
kubectl get secret
kubectl describe secret app-secret
- describe에서 실제 값이 안나오고 key 목록/크기만 출력된다.
학습용으로 실제 값을 확인해보면:
kubectl get secret app-secret -o jsonpath='{.data.db_user}' | base64 --decode; echo
kubectl get secret app-secret -o jsonpath='{.data.db_password}' | base64 --decode; echo
4.3 Pod에 Secret 주입: 환경변수 방식
secretKeyRef로 특정 key를 환경변수로 주입한다.
apiVersion: v1
kind: Pod
metadata:
name: env-secret-pod
spec:
containers:
- name: app
image: busybox:1.36
command: ["sh", "-c", "env | sort; sleep 3600"]
env:
- name: DB_USER
valueFrom:
secretKeyRef:
name: app-secret
key: db_user
- name: DB_PASSWORD
valueFrom:
secretKeyRef:
name: app-secret
key: db_password
적용:
kubectl apply -f pod-env-secret.yaml
kubectl get pod env-secret-pod -w
kubectl logs env-secret-pod | grep -E 'DB_USER|DB_PASSWORD'
✅ 로그에 DB_USER, DB_PASSWORD가 보이면 성공.
참고: 환경변수는 편하지만, 디버깅/덤프/로그 등으로 노출될 여지가 있어
보안이 특히 중요한 값은 볼륨 마운트(파일) 방식을 선호하기도 한다.
4.4 Pod에 Secret 주입: 볼륨(파일) 마운트 방식
Secret을 볼륨으로 마운트하면 /etc/secret 아래에 key 이름 그대로 파일이 생성된다.
apiVersion: v1
kind: Pod
metadata:
name: vol-secret-pod
spec:
containers:
- name: app
image: busybox:1.36
command: ["sh", "-c", "ls -l /etc/secret && sleep 3600"]
volumeMounts:
- name: secret-vol
mountPath: /etc/secret
readOnly: true
volumes:
- name: secret-vol
secret:
secretName: app-secret
적용 및 확인:
kubectl apply -f pod-vol-secret.yaml
kubectl get pod vol-secret-pod -w
kubectl exec -it vol-secret-pod -- sh
# inside container
ls -l /etc/secret
cat /etc/secret/db_user
cat /etc/secret/db_password
✅ 파일이 생성되고 값이 읽히면 성공.
'CKA' 카테고리의 다른 글
| [k8s] Deployment 정리(ReplicaSet, RollingUpdate, Rollback) (0) | 2026.02.23 |
|---|---|
| [k8s] 스케줄링 기본기: nodeSelector / nodeAffinity / podAntiAffinity로 Pod 배치 제어하기 (실습 포함) (0) | 2026.02.22 |
| [k8s] ConfigMap 정리(Env/Volume 주입, 변경 반영, 실습 포인트) (0) | 2026.02.17 |
| [k8s] kubectl 자동완성(Tab completion) 설정하기 : zsh에서 kubectl completion 켜는 방법 (0) | 2026.02.16 |
| [k8s] namespace 구분 (0) | 2026.02.15 |